<?xml version="1.0" encoding="utf-8"?><feed xmlns="http://www.w3.org/2005/Atom" xml:lang="en"><generator uri="https://jekyllrb.com/" version="4.4.1">Jekyll</generator><link href="https://andrevidela.com/feed.xml" rel="self" type="application/atom+xml"/><link href="https://andrevidela.com/" rel="alternate" type="text/html" hreflang="en"/><updated>2026-07-29T14:41:57+00:00</updated><id>https://andrevidela.com/feed.xml</id><title type="html">André Videla</title><subtitle>Welcome to my personal website, where you will find everything that I do, that I&apos;ve done, and that I&apos;m working on. </subtitle><entry><title type="html">Cafes Across the World</title><link href="https://andrevidela.com/blog/2025/cafes-across-the-world/" rel="alternate" type="text/html" title="Cafes Across the World"/><published>2025-10-31T04:14:00+00:00</published><updated>2025-10-31T04:14:00+00:00</updated><id>https://andrevidela.com/blog/2025/cafes-across-the-world</id><content type="html" xml:base="https://andrevidela.com/blog/2025/cafes-across-the-world/"><![CDATA[<p>Here is a list of places I’ve frequented and thought were noteworthy if you like sitting down and reading a book, writing, or working on a laptop while having access to good coffee or snacks.</p> <h2 id="japan">Japan</h2> <h3 id="tokyo-keilo-cafe"><a href="https://maps.app.goo.gl/bod9TDTnLmTYY3U58">Tokyo: KEILO Cafe</a></h3> <p>On day in Tokyo, I had a meeting in Akihabara at 2pm. I was looking for somewhere to sit that’s not another large chain with shitty coffee. I found this place at random and sat hoping it wouldn’t be too crowded, otherwise it’s quite rude to hoard the space for yourself when there are other customers attempting to use the space.</p> <p>Thankfully, while there was a lot of activity, the seating spots never completely filled up and there was another person working on their laptop. The coffee is absolutely incredible and their specials are really good.</p> <h3 id="kyoto-cafe-mole"><a href="https://maps.app.goo.gl/kLvHky3BNWobkgwr8">Kyoto: Cafe Mole</a></h3> <p>This one is unique. Very dark ambiance, very chill staff, the owner has incredible taste in music and will rotate the vinyl player as the day goes. Like lots of small establishment of this kind, they also serve food. The coffee is quite good too, they grind it in front of you and make it meticulously. Depending on the time of day it’s quiet or quite lively. Unfortunately it gets quite busy around 2pm but if you go close to closing time the vibes are immaculate.</p> <h3 id="hiroshima-shake-hands-coworking"><a href="https://maps.app.goo.gl/8xQh2527kwSRkUs6A">Hiroshima: Shake Hands Coworking</a></h3> <p>Alright this one isn’t a cafe, but it’s where I spent most of the time that I would usually spend in a cafe: reading and working.</p> <p>Shake hands is a very friendly coworking space, it’s quiet but there is a small common area and if you look western, people will be intrigued by your work and come talk to you. The butter toast is an incredible deal and I’ve had it many times. The space isn’t very large but very well located and ideal to get work done. i’ve never had to reserve or book in advance and they give you free drinks. there is a small flat entrance fee, it’s a coworking space afterall, but it’s definitely worth it.</p> <h2 id="switzerland">Switzerland</h2> <h3 id="lausanne-arteastry"><a href="https://www.arteastry.ch">Lausanne: Arteastry</a></h3> <p>This is new and I’ve only been there twice for maybe 30m. Sitting in a cafe with a laptop isn’t really something that’s socially acceptable in switzerland and so there isn’t much affordances made for this use. However, in general, if you go later in the day when it’s about 1h before it closes, nobody will complain and you might get the chance to talk with the owners. This café has actually incredible blends, mixes and teas. I’ve tried their hojicha and their coffee both were incredible, especially given that good asian tea is not easy to come-by in europe. The owners actually run a gallery at the back and they have opening times for expos and also sell pieces. 100% worth visiting for the high-quality drinks and the wonderful art.</p> <h3 id="neuchatel-la-crêperie-bretonne"><a href="https://maps.app.goo.gl/UKuaHpEyr5AAgxev8">Neuchatel: La crêperie Bretonne</a></h3> <p>For a reason that escapes me, Neuchatel has a lot of crêperies. They’re all delicious. This one in particular strike a perfect balance of:</p> <ul> <li>tasty food</li> <li>cheap</li> <li>amazing home-made ice tea</li> <li>centrally located</li> <li>quiet during the day</li> </ul> <p>Again, sitting at a cafe to do work isn’t a thing in switzerland, but if it’s quiet and you’re not bothering anyone it’s okay. I’ve spent many days reading a book or reviewing drafts at this establishment. The outdoor seating is very welcome in summer.</p> <h3 id="geneva">Geneva</h3> <p>I hate geneva.</p> <p>Just kidding, the <a href="https://maps.app.goo.gl/vz4CfHPTxT8cyT3Z9">Payot library</a> in the center has a very good coffee place where you can sit and you often find students and freelancers doing work. as a bonus you can walk around a browse interesting books.</p> <h2 id="usa">USA</h2> <h3 id="new-york">New york</h3> <p>I hate new york.</p> <p>This time I mean it.</p> <h3 id="san-diego-cafe-de-lopéra"><a href="https://maps.app.goo.gl/PFGFidmgNTusga749">San Diego: Cafe de l’opéra</a></h3> <p>Thinking about it, most of this place is average. But given the fact that it serves the best croissants I’ve had on the continent is made me come back over and over again.</p> <p>The establishment is quite small and the sandwiches and sweets, while tasty, don’t deserve any special mention. Except for the croissants, oh my goodness. The place gets a bit noisy, but what cafe in america doesn’t? The interior looks nice, the location is good, close to the convention center, the metro and some nice other restaurants.</p> <h2 id="united-kingdon">United Kingdon</h2> <h2 id="london-calico-cafe"><a href="https://maps.app.goo.gl/DQ847rj7q6fRKzwU8">London: Calico Cafe</a></h2> <p>Another case of “I was walking around and was looking for somewhere to work” that paned out incredibly well. Calico cafe has a wonderful interior, and probably the best coffee in this entire list, with an extensive list of pourovers and wide variety of beans. The owner is very meticulous and runs a very competent staff. If you’re lucky, and sit at the bar, you might witness them experimenting with coffee formulas, temperatures, timings, mineral content, and might get served the extras.</p> <h2 id="glasgow-hinba-bakery--coffee"><a href="https://maps.app.goo.gl/ucxp8j381sSpQjqTA">Glasgow: Hinba bakery + Coffee</a></h2> <p>With 4 branches (one of them is the bakery) across the city and the best baked goods of all, Hinba is a clear stand out in the coffee scene in glasgow. Very convently located, each location has its own character and benefits, making it the experience varied, yet the quality is consistent.</p> <h2 id="edinburgh-cafe-nomad"><a href="https://maps.app.goo.gl/QMHuMUnDRhhuvkxH8">Edinburgh: Cafe Nomad</a></h2> <p>I’ve never actualy had the time to sift through and find “the best” cafe in edinburgh, but Cafe Nomad hit the appropriate niche for me that it’s seen a lot of my business in edinburgh: It’s the best coffee shop that’s walking distance from the Haymarket train station. I’d say most of their options are average, but the vegan food is quite good and the cinamon bun is great. The location and ambiance really win here, it’s cosy, warm and practical to wait between train transfers.</p>]]></content><author><name></name></author><category term="coffee"/><summary type="html"><![CDATA[Cafés and places I like spending time in.]]></summary></entry><entry><title type="html">Binding Application in Idris</title><link href="https://andrevidela.com/blog/2025/binding-application/" rel="alternate" type="text/html" title="Binding Application in Idris"/><published>2025-07-10T20:00:00+00:00</published><updated>2025-07-10T20:00:00+00:00</updated><id>https://andrevidela.com/blog/2025/binding-application</id><content type="html" xml:base="https://andrevidela.com/blog/2025/binding-application/"><![CDATA[<p>I’ve recently implemented <em>binding</em> application as a language feature in Idris. This feature allows writing types such as Dependent pairs in a more ergonomic way without relying on special compiler magic. Or rather, the compiler magic is made available to everyone. This post is a collection of uses for this feature.</p> <p>This feature is not publicly available yet, but I intend to make it available in the near future.</p> <h2 id="what-is-it">What is it?</h2> <p>Binding syntax and binding-application is an idea I had a couple of years ago and presented at <a href="https://popl24.sigplan.org/details/wits-2024-papers/1/Binding-Syntax-for-Dependently-Typed-Programs">WITS 2024</a>. It’s a syntactic feature piggybacking on the function-space of a dependent programming language that offers some customisation to the notion of <em>binding</em>. The main use case is to facilitate writing types such as \(\Pi\) or \(\Sigma\) where the second argument is a function dependent on the type given in the first argument. In Idris, one can mark such functions as <code class="language-plaintext highlighter-rouge">typebind</code> because they are meant to bind a type argument, and any such function written <code class="language-plaintext highlighter-rouge">f (x : t) | g x</code> desugars to <code class="language-plaintext highlighter-rouge">f t (\x : t =&gt; g x)</code> This pattern can be generalised to any function with a trailing lambda where the second argument does not necessarily depend on the first. This syntax looks like this <code class="language-plaintext highlighter-rouge">f (x &lt;- e) | g x</code> and desugars to <code class="language-plaintext highlighter-rouge">f e (\x : ? =&gt; g x)</code>, those functions are <code class="language-plaintext highlighter-rouge">autobind</code> since the type is automatically inferred.</p> <p>Let’s move onto the use cases.</p> <h3 id="sigma">Sigma</h3> <p>Dependent pairs, or sigma-types, are ubiquitous in programming with dependent types. If you define your own sigma-type, you have to use a lambda to describe the type of the second projection.</p> <div class="language-idris highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="n">record</span> <span class="kt">Sigma</span> <span class="p">(</span><span class="n">a</span> <span class="o">:</span> <span class="kt">Type</span><span class="p">)</span> <span class="p">(</span><span class="n">b</span> <span class="o">:</span> <span class="n">a</span> <span class="o">-&gt;</span> <span class="kt">Type</span><span class="p">)</span> <span class="kr">where</span>
  <span class="n">constructor</span> <span class="p">(</span><span class="o">&amp;&amp;</span><span class="p">)</span>
  <span class="n">first</span> <span class="o">:</span> <span class="n">a</span>
  <span class="n">second</span> <span class="o">:</span> <span class="n">b</span> <span class="n">first</span>

<span class="nf">RichList :</span> <span class="kt">Type </span><span class="o">-&gt;</span> <span class="kt">Type
RichList</span> <span class="n">a</span> <span class="o">=</span> <span class="kt">Sigma</span> <span class="kt">Nat </span><span class="p">(</span><span class="nf">\</span><span class="n">n</span> <span class="o">=&gt;</span> <span class="kt">Vect</span> <span class="n">n</span> <span class="n">a</span><span class="p">)</span> <span class="c1">-- lambda here</span>
</code></pre></div></div> <p>By marking the type as binding, we can use a much more natural syntactic form.</p> <div class="language-idris highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="n">typebind</span>
<span class="n">record</span> <span class="kt">Sigma</span> <span class="p">(</span><span class="n">a</span> <span class="o">:</span> <span class="kt">Type</span><span class="p">)</span> <span class="p">(</span><span class="n">b</span> <span class="o">:</span> <span class="n">a</span> <span class="o">-&gt;</span> <span class="kt">Type</span><span class="p">)</span> <span class="kr">where</span>
  <span class="n">constructor</span> <span class="p">(</span><span class="o">&amp;&amp;</span><span class="p">)</span>
  <span class="n">first</span> <span class="o">:</span> <span class="n">a</span>
  <span class="n">second</span> <span class="o">:</span> <span class="n">b</span> <span class="n">first</span>

<span class="nf">RichList :</span> <span class="kt">Type </span><span class="o">-&gt;</span> <span class="kt">Type
RichList</span> <span class="n">a</span> <span class="o">=</span> <span class="kt">Sigma</span> <span class="p">(</span><span class="n">n</span> <span class="o">:</span> <span class="kt">Nat</span><span class="p">)</span> <span class="o">|</span> <span class="kt">Vect</span> <span class="n">n</span> <span class="n">a</span>
</code></pre></div></div> <h3 id="exists">Exists</h3> <p>The Idris <code class="language-plaintext highlighter-rouge">base</code> library has a type called <code class="language-plaintext highlighter-rouge">Exists : (a : Type) -&gt; (b : a -&gt; Type) -&gt; Type</code> which is exactly the same as the dependent pair, except that its first argument is erased. Marking the type as <code class="language-plaintext highlighter-rouge">typebind</code> allows writing <code class="language-plaintext highlighter-rouge">Exists (a : Type) | p a</code>, that syntax enables the natural mathematical reading “There exists a type <code class="language-plaintext highlighter-rouge">a</code> <em>such that</em> <code class="language-plaintext highlighter-rouge">p</code> of <code class="language-plaintext highlighter-rouge">a</code> holds”.</p> <div class="language-idris highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="n">typebind</span>
<span class="n">record</span> <span class="kt">Exists </span><span class="p">(</span><span class="n">a</span> <span class="o">:</span> <span class="kt">Type</span><span class="p">)</span> <span class="p">(</span><span class="n">b</span> <span class="o">:</span> <span class="n">a</span> <span class="o">-&gt;</span> <span class="kt">Type</span><span class="p">)</span> <span class="kr">where</span>
  <span class="n">constructor</span> <span class="p">(</span><span class="o">-!</span><span class="p">)</span>
  <span class="mf">0</span> <span class="n">index</span> <span class="o">:</span> <span class="n">a</span>
  <span class="n">pred</span> <span class="o">:</span> <span class="n">b</span> <span class="n">index</span>
</code></pre></div></div> <h3 id="subset">Subset</h3> <p>A similar type exists in base except that the predicate is erased. This type represents values which are constrained by a predicate, but we don’t need to carry the predicate at runtime.</p> <div class="language-idris highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="n">typebind</span>
<span class="n">record</span> <span class="kt">Subset</span> <span class="p">(</span><span class="n">a</span> <span class="o">:</span> <span class="kt">Type</span><span class="p">)</span> <span class="p">(</span><span class="n">pred</span> <span class="o">:</span> <span class="n">a</span> <span class="o">-&gt;</span> <span class="kt">Type</span><span class="p">)</span> <span class="kr">where</span>
  <span class="n">constructor</span> <span class="p">(</span><span class="o">!-</span><span class="p">)</span>
  <span class="n">value</span> <span class="o">:</span> <span class="n">a</span>
  <span class="mf">0</span> <span class="n">constraint</span> <span class="o">:</span> <span class="nb">pred </span><span class="n">value</span>
</code></pre></div></div> <p>Such a type can be written <code class="language-plaintext highlighter-rouge">Subset (x : Nat) | LTE x 9</code> and can be read “a value <code class="language-plaintext highlighter-rouge">x</code> of type <code class="language-plaintext highlighter-rouge">Nat</code> <em>such that</em> <code class="language-plaintext highlighter-rouge">x</code> is smaller or equal to <code class="language-plaintext highlighter-rouge">9</code>”</p> <h3 id="ornaments">Ornaments</h3> <p>Ornaments are type-descriptors, they contain all the necessary to build types within a dependently-typed programming language. Here is the most basic definitions:</p> <div class="language-idris highlighter-rouge"><div class="highlight"><pre class="highlight"><code>  <span class="kr">data</span> <span class="kt">Orn</span> <span class="o">:</span> <span class="p">(</span><span class="n">j</span> <span class="o">:</span> <span class="kt">Type</span><span class="p">)</span> <span class="o">-&gt;</span> <span class="p">(</span><span class="n">j</span> <span class="o">-&gt;</span> <span class="n">i</span><span class="p">)</span> <span class="o">-&gt;</span> <span class="kt">Desc</span> <span class="n">i</span> <span class="o">-&gt;</span> <span class="kt">Type </span><span class="kr">where</span>

    <span class="kt">Say</span> <span class="o">:</span> <span class="kt">Inverse</span> <span class="n">e</span> <span class="n">i</span> <span class="o">-&gt;</span> <span class="kt">Orn</span> <span class="n">j</span> <span class="n">e</span> <span class="p">(</span><span class="kt">Say</span> <span class="n">i</span><span class="p">)</span>

    <span class="kt">Ask</span> <span class="o">:</span> <span class="kt">Inverse</span> <span class="n">e</span> <span class="n">i</span> <span class="o">-&gt;</span> <span class="kt">Orn</span> <span class="n">j</span> <span class="n">e</span> <span class="n">d</span> <span class="o">-&gt;</span> <span class="kt">Orn</span> <span class="n">j</span> <span class="n">e</span> <span class="p">(</span><span class="kt">Ask</span> <span class="n">i</span> <span class="n">d</span><span class="p">)</span>

    <span class="kt">Sig</span> <span class="o">:</span> <span class="p">(</span><span class="n">s</span> <span class="o">:</span> <span class="kt">Type</span><span class="p">)</span> <span class="o">-&gt;</span> <span class="p">{</span><span class="n">d</span> <span class="o">:</span> <span class="n">s</span> <span class="o">-&gt;</span> <span class="kt">Desc</span> <span class="n">i</span><span class="p">}</span> <span class="o">-&gt;</span> <span class="p">((</span><span class="n">sv</span> <span class="o">:</span> <span class="n">s</span><span class="p">)</span> <span class="o">-&gt;</span> <span class="kt">Orn</span> <span class="n">j</span> <span class="n">e</span> <span class="p">(</span><span class="n">d</span> <span class="n">sv</span><span class="p">))</span> <span class="o">-&gt;</span> <span class="kt">Orn</span> <span class="n">j</span> <span class="n">e</span> <span class="p">(</span><span class="kt">Sig</span> <span class="n">s</span> <span class="n">d</span><span class="p">)</span>

    <span class="kt">Del</span> <span class="o">:</span> <span class="p">(</span><span class="n">s</span> <span class="o">:</span> <span class="kt">Type</span><span class="p">)</span> <span class="o">-&gt;</span> <span class="p">(</span><span class="n">s</span> <span class="o">-&gt;</span> <span class="kt">Orn</span> <span class="n">j</span> <span class="n">e</span> <span class="n">d</span><span class="p">)</span> <span class="o">-&gt;</span> <span class="kt">Orn</span> <span class="n">j</span> <span class="n">e</span> <span class="n">d</span>
</code></pre></div></div> <p>We notice that both <code class="language-plaintext highlighter-rouge">Sig</code> and <code class="language-plaintext highlighter-rouge">Del</code> have the perfect shape for making use of binding application. Therefore, we can rename them and mark them as binding:</p> <div class="language-haskell highlighter-rouge"><div class="highlight"><pre class="highlight"><code>  <span class="kr">data</span> <span class="kt">Orn</span> <span class="o">:</span> <span class="p">(</span><span class="n">j</span> <span class="o">:</span> <span class="kt">Type</span><span class="p">)</span> <span class="o">-&gt;</span> <span class="p">(</span><span class="n">j</span> <span class="o">-&gt;</span> <span class="n">i</span><span class="p">)</span> <span class="o">-&gt;</span> <span class="kt">Desc</span> <span class="n">i</span> <span class="o">-&gt;</span> <span class="kt">Type</span> <span class="kr">where</span>

    <span class="kt">Say</span> <span class="o">:</span> <span class="kt">Inverse</span> <span class="n">e</span> <span class="n">i</span> <span class="o">-&gt;</span> <span class="kt">Orn</span> <span class="n">j</span> <span class="n">e</span> <span class="p">(</span><span class="kt">Say</span> <span class="n">i</span><span class="p">)</span>

	<span class="kt">Ask</span> <span class="o">:</span> <span class="kt">Inverse</span> <span class="n">e</span> <span class="n">i</span> <span class="o">-&gt;</span> <span class="kt">Orn</span> <span class="n">j</span> <span class="n">e</span> <span class="n">d</span> <span class="o">-&gt;</span> <span class="kt">Orn</span> <span class="n">j</span> <span class="n">e</span> <span class="p">(</span><span class="kt">Ask</span> <span class="n">i</span> <span class="n">d</span><span class="p">)</span>

    <span class="n">typebind</span>
    <span class="err">Σ</span> <span class="o">:</span> <span class="p">(</span><span class="n">s</span> <span class="o">:</span> <span class="kt">Type</span><span class="p">)</span> <span class="o">-&gt;</span> <span class="p">{</span><span class="n">d</span> <span class="o">:</span> <span class="n">s</span> <span class="o">-&gt;</span> <span class="kt">Desc</span> <span class="n">i</span><span class="p">}</span> <span class="o">-&gt;</span> <span class="p">((</span><span class="n">sv</span> <span class="o">:</span> <span class="n">s</span><span class="p">)</span> <span class="o">-&gt;</span> <span class="kt">Orn</span> <span class="n">j</span> <span class="n">e</span> <span class="p">(</span><span class="n">d</span> <span class="n">sv</span><span class="p">))</span> <span class="o">-&gt;</span> <span class="kt">Orn</span> <span class="n">j</span> <span class="n">e</span> <span class="p">(</span><span class="kt">Sig</span> <span class="n">s</span> <span class="n">d</span><span class="p">)</span>

    <span class="n">typebind</span>
    <span class="err">Δ</span>  <span class="o">:</span> <span class="p">(</span><span class="n">s</span> <span class="o">:</span> <span class="kt">Type</span><span class="p">)</span> <span class="o">-&gt;</span> <span class="p">(</span><span class="n">s</span> <span class="o">-&gt;</span> <span class="kt">Orn</span> <span class="n">j</span> <span class="n">e</span> <span class="n">d</span><span class="p">)</span> <span class="o">-&gt;</span> <span class="kt">Orn</span> <span class="n">j</span> <span class="n">e</span> <span class="n">d</span>
</code></pre></div></div> <p>Every time we want to use <code class="language-plaintext highlighter-rouge">Σ</code> or <code class="language-plaintext highlighter-rouge">Δ</code>, we can use binding syntax, for example, the ornament decorating the <code class="language-plaintext highlighter-rouge">Nat</code> description into <code class="language-plaintext highlighter-rouge">Fin n</code> makes use of <code class="language-plaintext highlighter-rouge">Δ</code>:</p> <div class="language-idris highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="nf">NatD :</span> <span class="kt">Desc</span> <span class="nb">()</span>
<span class="kt">NatD</span> <span class="o">=</span> <span class="kt">Sig</span> <span class="p">(</span><span class="o">#</span><span class="p">[</span><span class="s">"Z"</span><span class="p">,</span> <span class="s">"S"</span><span class="p">])</span> <span class="o">$</span> <span class="nf">\</span><span class="kr">case</span>
    <span class="s">"Z"</span> <span class="o">=&gt;</span> <span class="kt">Say</span> <span class="nb">()</span>
    <span class="s">"S"</span> <span class="o">=&gt;</span> <span class="kt">Ask</span> <span class="nb">()</span> <span class="p">(</span><span class="kt">Say</span> <span class="nb">()</span><span class="p">)</span>

<span class="nf">FinO :</span> <span class="kt">Orn</span> <span class="kt">NatT</span> <span class="p">(</span><span class="nb">const ()</span><span class="p">)</span> <span class="kt">NatD</span>
<span class="kt">FinO</span> <span class="o">=</span> <span class="kt">Sig</span> <span class="p">(</span><span class="o">#</span><span class="p">[</span><span class="s">"Z"</span><span class="p">,</span> <span class="s">"S"</span><span class="p">])</span> <span class="o">$</span> <span class="nf">\</span><span class="kr">case</span>
    <span class="s">"Z"</span> <span class="o">=&gt;</span> <span class="err">Δ</span> <span class="p">(</span><span class="n">xn</span> <span class="o">:</span> <span class="kt">NatT</span><span class="p">)</span> <span class="o">|</span> <span class="kt">Say</span> <span class="p">(</span><span class="kt">Ok</span> <span class="p">(</span><span class="kt">S</span> <span class="n">xn</span><span class="p">))</span>
    <span class="s">"S"</span> <span class="o">=&gt;</span> <span class="err">Δ</span> <span class="p">(</span><span class="n">xn</span> <span class="o">:</span> <span class="kt">NatT</span><span class="p">)</span> <span class="o">|</span> <span class="kt">Ask</span> <span class="p">(</span><span class="kt">Ok</span> <span class="n">xn</span><span class="p">)</span> <span class="p">(</span><span class="kt">Say</span> <span class="p">(</span><span class="kt">Ok</span> <span class="p">(</span><span class="kt">S</span> <span class="n">xn</span><span class="p">)))</span>
</code></pre></div></div> <h3 id="forall">ForAll</h3> <p>Another type in <a href="https://www.idris-lang.org/docs/idris2/current/base_docs/docs/Data.List.Quantifiers.html#Data.List.Quantifiers.All.All"><code class="language-plaintext highlighter-rouge">base</code></a> is the predicate transformer <code class="language-plaintext highlighter-rouge">All : (p : a -&gt; Type) -&gt; (xs : List a) -&gt; Type</code>. It takes a predicate <code class="language-plaintext highlighter-rouge">p</code> and ensures it holds for every element of the list <code class="language-plaintext highlighter-rouge">xs</code>. There are some cases where writing the predicate is a bit awkward because it cannot be written point-free and requires a lambda. For this, one can use a binding alias:</p> <div class="language-idris highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="n">autobind</span>
<span class="nf">ForAll :</span> <span class="kt">List </span><span class="n">a</span> <span class="o">-&gt;</span> <span class="p">(</span><span class="n">a</span> <span class="o">-&gt;</span> <span class="kt">Type</span><span class="p">)</span> <span class="o">-&gt;</span> <span class="kt">Type
ForAll</span> <span class="n">xs</span> <span class="n">p</span> <span class="o">=</span> <span class="kt">All</span> <span class="n">p</span> <span class="n">xs</span>
</code></pre></div></div> <p>Because the first argument is not a type, we use <code class="language-plaintext highlighter-rouge">autobind</code> instead of <code class="language-plaintext highlighter-rouge">typebind</code>. The syntax also makes clear that we are “iterating” over the list rather than using the list itself as the argument to the predicate.</p> <p>This enables the syntax:</p> <div class="language-idris highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="kt">ForAll</span> <span class="p">(</span><span class="n">x</span> <span class="o">&lt;-</span> <span class="n">xs</span><span class="p">)</span> <span class="o">|</span> <span class="kc">LTE</span> <span class="n">x</span> <span class="mf">9</span>
</code></pre></div></div> <p>Which reads “for all <code class="language-plaintext highlighter-rouge">x</code> in <code class="language-plaintext highlighter-rouge">xs</code> the predicate <code class="language-plaintext highlighter-rouge">LTE x 9</code> holds”</p> <p>Without the binding syntax, we would have to write the following, which doesn’t read as nicely:</p> <div class="language-idris highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="kt">All</span> <span class="p">(</span><span class="nf">\</span><span class="n">x</span> <span class="o">=&gt;</span> <span class="kc">LTE</span> <span class="n">x</span> <span class="mf">9</span><span class="p">)</span> <span class="n">xs</span>
</code></pre></div></div> <h3 id="forsome">ForSome</h3> <p>In addition to <code class="language-plaintext highlighter-rouge">All</code> there is <a href="https://www.idris-lang.org/docs/idris2/current/base_docs/docs/Data.List.Quantifiers.html#Data.List.Quantifiers.Any.Any"><code class="language-plaintext highlighter-rouge">Any</code></a> a predicate transformer that holds exactly one proof that an element in the list satisfies the predicate. The alias can be written in the same way:</p> <div class="language-idris highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="n">autobind</span>
<span class="nf">ForSome :</span> <span class="kt">List </span><span class="n">a</span> <span class="o">-&gt;</span> <span class="p">(</span><span class="n">a</span> <span class="o">-&gt;</span> <span class="kt">Type</span><span class="p">)</span> <span class="o">-&gt;</span> <span class="kt">Type
ForSome</span> <span class="n">xs</span> <span class="n">p</span> <span class="o">=</span> <span class="kt">Any</span> <span class="n">p</span> <span class="n">xs</span>
</code></pre></div></div> <p>And similarly we can write</p> <div class="language-idris highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="kt">ForSome</span> <span class="p">(</span><span class="n">x</span> <span class="o">&lt;-</span> <span class="n">xs</span><span class="p">)</span> <span class="o">|</span> <span class="kc">LTE</span> <span class="n">x</span> <span class="mf">9</span>
</code></pre></div></div> <p>With the benefit that it reads nicely as “For some <code class="language-plaintext highlighter-rouge">x</code> in <code class="language-plaintext highlighter-rouge">xs</code>, the predicate <code class="language-plaintext highlighter-rouge">LTE x 9</code> holds”</p> <h3 id="for-loops">For-Loops</h3> <p>The most exciting application for me is the fact that we can have idiomatic-looking for-loops in the language.</p> <p>A for-loop in its C interpretation is a loop defined by three components: An initial state, a break condition, and a state update. This is a very low-level representation of loops, so much so that subsequent languages have abstracted over the notion of loops by relying on <em>iterators</em>. While the details differ from language to language, the general idea remains: An iterator allows iterating over each element once using <code class="language-plaintext highlighter-rouge">for</code>. Here are a few examples where the iterator is <code class="language-plaintext highlighter-rouge">xs</code>:</p> <div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>// python
for x in xs:
  body

//scala
for (x &lt;- xs) body

// zig
for (xs) |x| {
  body
}

// java
for (x : xs) {
  body
}

//rust
for x in xs {
  body
}
</code></pre></div></div> <p>Back to Idris, it has a function <code class="language-plaintext highlighter-rouge">traverse</code> with the type <code class="language-plaintext highlighter-rouge">traverse : Traversable t =&gt; Applicative f =&gt; (a -&gt; f b) -&gt; t a -&gt; f (t b)</code>, this type captures the notion that for every “ iterator” <code class="language-plaintext highlighter-rouge">t</code>, we can perform a side-effect <code class="language-plaintext highlighter-rouge">f</code> and return a new list. With binding application we can define <code class="language-plaintext highlighter-rouge">for</code> in Idris as an alias for <code class="language-plaintext highlighter-rouge">traverse</code>.</p> <div class="language-haskell highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="n">autobind</span>
<span class="n">for</span> <span class="o">:</span> <span class="kt">Applicative</span> <span class="n">f</span> <span class="o">=&gt;</span> <span class="kt">Traversable</span> <span class="n">t</span> <span class="o">=&gt;</span> <span class="n">t</span> <span class="n">a</span> <span class="o">-&gt;</span> <span class="p">(</span><span class="n">a</span> <span class="o">-&gt;</span> <span class="n">f</span> <span class="n">b</span><span class="p">)</span> <span class="o">-&gt;</span> <span class="n">f</span> <span class="p">(</span><span class="n">t</span> <span class="n">b</span><span class="p">)</span>
<span class="n">for</span> <span class="o">=</span> <span class="n">flip</span> <span class="n">traverse</span>
</code></pre></div></div> <p>It enables the following syntax:</p> <div class="language-idris highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="nf">xs :</span> <span class="kt">List String</span>
<span class="n">xs</span> <span class="o">=</span> <span class="p">[</span><span class="s">"hello"</span><span class="p">,</span>  <span class="s">"world"</span><span class="p">,</span> <span class="s">"!"</span><span class="p">]</span>

<span class="nf">main :</span> <span class="kt">IO </span><span class="nb">()</span>
<span class="n">main</span> <span class="o">=</span> <span class="n">ignore</span> <span class="o">$</span> <span class="n">for</span> <span class="p">(</span><span class="n">x</span> <span class="o">&lt;-</span> <span class="n">xs</span><span class="p">)</span> <span class="o">|</span>
  <span class="nb">putStrLn </span><span class="n">x</span>
</code></pre></div></div> <p>Which mimics the syntax used in other programming languages to iterate on a list. <code class="language-plaintext highlighter-rouge">ignore</code> discards the result of the iteration.</p>]]></content><author><name></name></author><category term="Dependent-types,"/><category term="idris,"/><category term="programming"/><summary type="html"><![CDATA[The new binding application in Idris helps write programs with dependent pairs and other structures with lambda as the trailing argument. This post is a small collection of uses I have for it.]]></summary></entry><entry><title type="html">Programing Pipelines Using Dependent Types</title><link href="https://andrevidela.com/blog/2025/program-pipelines.idr/" rel="alternate" type="text/html" title="Programing Pipelines Using Dependent Types"/><published>2025-01-11T14:57:00+00:00</published><updated>2025-01-11T14:57:00+00:00</updated><id>https://andrevidela.com/blog/2025/program-pipelines.idr</id><content type="html" xml:base="https://andrevidela.com/blog/2025/program-pipelines.idr/"><![CDATA[ <p>Sometimes, writing a large program is conceptually as simple as translating from a big unstructured input into a more and more structured output. A good example is a single-pass compiler:</p> <ul> <li>First we perform lexical analysis on a big string, this gives us a list of tokens.</li> <li>Then we parse the tokens into a tree.</li> <li>Then we do some semantic analysis on the tree, usually this involves some typechecking and error reporting</li> <li>Once we know what the program is, we generate code for it.</li> </ul> <h2 id="introducing-the-pipeline">Introducing the pipeline</h2> <figure> <picture> <source class="responsive-img-srcset" srcset="/assets/img/pipeline_illust_mid-480.webp 480w,/assets/img/pipeline_illust_mid-800.webp 800w,/assets/img/pipeline_illust_mid-1400.webp 1400w," sizes="95vw" type="image/webp"/> <img src="/assets/img/pipeline_illust_mid.png" class="img-fluid rounded z-depth-1" width="100%" height="auto" data-zoomable="" loading="lazy" onerror="this.onerror=null; $('.responsive-img-srcset').remove();"/> </picture> </figure> <div class="caption"> An illustration of a pipeline with 4 layers and 3 stages. </div> <p>This structure is purely linear, and functional programmers will be delighted to point out that you can implement an entire compiler pipeline using nothing but function composition:</p> <div class="language-haskell highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="n">codegen</span> <span class="o">::</span> <span class="kt">Sema</span> <span class="o">-&gt;</span> <span class="kt">String</span>
<span class="n">typecheck</span> <span class="o">::</span> <span class="kt">Tree</span> <span class="o">-&gt;</span> <span class="kt">Sema</span>
<span class="n">parsing</span> <span class="o">::</span> <span class="p">[</span><span class="kt">Token</span><span class="p">]</span> <span class="o">-&gt;</span> <span class="kt">Tree</span>
<span class="n">lexing</span> <span class="o">::</span> <span class="kt">String</span> <span class="o">-&gt;</span> <span class="p">[</span><span class="kt">Token</span><span class="p">]</span>

<span class="n">compiler</span> <span class="o">::</span> <span class="kt">String</span> <span class="o">-&gt;</span> <span class="kt">String</span>
<span class="n">compiler</span> <span class="o">=</span> <span class="n">codegen</span> <span class="o">.</span> <span class="n">typecheck</span> <span class="o">.</span> <span class="n">parsing</span> <span class="o">.</span> <span class="n">lexing</span>
</code></pre></div></div> <p>Of course this is pure fantasy, there is no error reporting, no way to debug it, and no command line tool. But the core idea is compelling: what if there was a way to implement a compiler as a single pipeline of operation that clearly describes what each step achieves? For this, we’re going to define <em>pipelined programs</em> using Idris, because it uses dependent types, and it is reasonably fast and production ready. We define a <em>pipeline</em> as a list of <em>Types</em>, each type represents an intermediate layer.</p> <div class="language-idris highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="nf">Pipeline :</span> <span class="kt">Nat </span><span class="o">-&gt;</span> <span class="kt">Type
Pipeline</span> <span class="n">length</span> <span class="o">=</span> <span class="kt">Vect</span> <span class="nb">length </span><span class="kt">Type
</span>
<span class="nf">CompilerPipeline :</span> <span class="kt">Pipeline</span> <span class="o">?</span>
<span class="kt">CompilerPipeline</span> <span class="o">=</span>
  <span class="p">[</span> <span class="kt">String</span>
  <span class="p">,</span> <span class="kt">List Token</span>
  <span class="p">,</span> <span class="kt">Tree</span>
  <span class="p">,</span> <span class="kt">Sema</span>
  <span class="p">,</span> <span class="kt">String</span>
  <span class="p">]</span>
</code></pre></div></div> <p>With it, we define a <em>compiler pipeline</em> as the list of types <code class="language-plaintext highlighter-rouge">String</code>, <code class="language-plaintext highlighter-rouge">List Token</code>, <code class="language-plaintext highlighter-rouge">Tree</code>, <code class="language-plaintext highlighter-rouge">Sema</code>, and <code class="language-plaintext highlighter-rouge">String</code>, representing all the stages of our compiler.</p> <p>The pipeline is indexed by it length, to ensure that our pipeline is valid this length needs to be at least 2, since we need a type from which we start, and a type to which we arrive. Using this fact we can define the <em>implementation</em> for a pipeline.</p> <div class="language-idris highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="c1">-- Well formed pipelines have at least 2 elements, the start and the end type</span>
<span class="nf">Impl :</span> <span class="kt">Pipeline</span> <span class="p">(</span><span class="mf">2</span> <span class="o">+</span> <span class="n">n</span><span class="p">)</span> <span class="o">-&gt;</span> <span class="kt">Type
Impl</span> <span class="p">(</span><span class="n">x</span> <span class="o">::</span> <span class="n">y</span> <span class="o">::</span> <span class="kt">[]</span><span class="p">)</span> <span class="o">=</span> <span class="n">x</span> <span class="o">-&gt;</span> <span class="n">y</span>
<span class="kt">Impl</span> <span class="p">(</span><span class="n">x</span> <span class="o">::</span> <span class="n">y</span> <span class="o">::</span> <span class="n">z</span> <span class="o">::</span> <span class="n">xs</span><span class="p">)</span> <span class="o">=</span> <span class="kt">Pair</span> <span class="p">(</span><span class="n">x</span> <span class="o">-&gt;</span> <span class="n">y</span><span class="p">)</span> <span class="p">(</span><span class="kt">Impl</span> <span class="p">(</span><span class="n">y</span> <span class="o">::</span> <span class="n">z</span> <span class="o">::</span> <span class="n">xs</span><span class="p">))</span>
</code></pre></div></div> <p>We can test our implementation by asking in the REPL what is a valid implementation of out compiler pipeline.</p> <div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>&gt; Impl CompilerPipeline
&lt; (String -&gt; List Token, (List Token -&gt; Tree, (Tree -&gt; Sema, Sema -&gt; String)))
</code></pre></div></div> <p>This is a 4-tuple of functions <code class="language-plaintext highlighter-rouge">String -&gt; List Token</code>, <code class="language-plaintext highlighter-rouge">List Token -&gt; Tree</code>, <code class="language-plaintext highlighter-rouge">Tree -&gt; Sema</code> and <code class="language-plaintext highlighter-rouge">Sema -&gt; String</code>, exactly what we wanted, each of those function represents a stage in our compiler.</p> <p>Now that <code class="language-plaintext highlighter-rouge">Impl</code> correctly gives us the type of an appropriate implementation for a pipeline, we still need to <em>run</em> the pipeline. Running the pipeline should amount to using function composition on each of the functions. Unfortunately it’s not that easy because each intermediate step uses a different type and we can’t just blindly apply a function without knowing its type.</p> <p>Like before, to run a <code class="language-plaintext highlighter-rouge">Pipeline</code>, it needs at least two elements. Running a pipeline should result in a simple function from the first layer of the pipeline to the last one. To write this we use the function <code class="language-plaintext highlighter-rouge">head</code> and <code class="language-plaintext highlighter-rouge">last</code> from <code class="language-plaintext highlighter-rouge">Data.Vect</code> those functions do exactly what you expect from their name but here we call them to define the type of the function that will result from running the pipeline.</p> <div class="language-idris highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="c1">-- When we run the pipeline `p` we expect to get out a function `head p -&gt; last `p`,</span>
<span class="c1">-- that is, the first stage of the pipeline as the argument of the function and the</span>
<span class="c1">-- last stage as the result of it.</span>
<span class="nf">Run :</span> <span class="p">(</span><span class="n">p</span> <span class="o">:</span> <span class="kt">Pipeline</span> <span class="p">(</span><span class="mf">2</span> <span class="o">+</span> <span class="n">n</span><span class="p">))</span> <span class="o">-&gt;</span> <span class="kt">Impl</span> <span class="n">p</span> <span class="o">-&gt;</span> <span class="nb">head </span><span class="n">p</span> <span class="o">-&gt;</span> <span class="nb">last </span><span class="n">p</span>
<span class="c1">-- In the base case, the pipeline contains only one stage x -&gt; y so we return it</span>
<span class="kt">Run</span> <span class="p">[</span><span class="n">x</span><span class="p">,</span> <span class="n">y</span><span class="p">]</span> <span class="n">f</span> <span class="o">=</span> <span class="n">f</span>
<span class="c1">-- In the inductive case, we compose `f` with the rest of the pipeline</span>
<span class="kt">Run</span> <span class="p">(</span><span class="n">s</span> <span class="o">::</span> <span class="n">t</span> <span class="o">::</span> <span class="n">x</span> <span class="o">::</span> <span class="n">xs</span><span class="p">)</span> <span class="p">(</span><span class="n">f</span><span class="p">,</span> <span class="n">cont</span><span class="p">)</span> <span class="o">=</span> <span class="kt">Run</span> <span class="p">(</span><span class="n">t</span> <span class="o">::</span> <span class="n">x</span> <span class="o">::</span> <span class="n">xs</span><span class="p">)</span> <span class="n">cont</span> <span class="o">.</span> <span class="n">f</span>
</code></pre></div></div> <p>The base case runs the single stage we have with the argument we’re given. The inductive case runs the remainder of the pipeline after running the current stage represented by the function <code class="language-plaintext highlighter-rouge">f</code>.</p> <p>We can test this idea by assuming we have functions <code class="language-plaintext highlighter-rouge">lex</code>, <code class="language-plaintext highlighter-rouge">parse</code>, <code class="language-plaintext highlighter-rouge">typecheck</code> and <code class="language-plaintext highlighter-rouge">codegen</code> like in the haskell example and see what happens:</p> <div class="language-idris highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="nf">lex :</span> <span class="kt">String</span> <span class="o">-&gt;</span> <span class="kt">List Token</span>
<span class="nf">parse :</span> <span class="kt">List Token</span> <span class="o">-&gt;</span> <span class="kt">Tree</span>
<span class="nf">typecheck :</span> <span class="kt">Tree</span> <span class="o">-&gt;</span> <span class="kt">Sema</span>
<span class="nf">codegen :</span> <span class="kt">Sema</span> <span class="o">-&gt;</span> <span class="kt">String</span>

<span class="nf">runCompiler :</span> <span class="kt">String</span> <span class="o">-&gt;</span> <span class="kt">String</span>
<span class="n">runCompiler</span> <span class="o">=</span> <span class="kt">Run</span> <span class="kt">CompilerPipeline</span> <span class="p">(</span><span class="n">lex</span><span class="p">,</span> <span class="n">parse</span><span class="p">,</span> <span class="n">typecheck</span><span class="p">,</span> <span class="n">codegen</span><span class="p">)</span>
</code></pre></div></div> <p>And it typechecks! We cannot run this code because we don’t have an implementation for <code class="language-plaintext highlighter-rouge">lex</code>, <code class="language-plaintext highlighter-rouge">parse</code>, etc, but we’ve at least reached our goal: to build a datastructure that help us keep track of what are the stages in our pipeline.</p> <h2 id="handling-effects">Handling effects</h2> <p>This is quite cool, but it’s not the end. Remember that compiler need to perform a lot of side effects, returning errors, sometimes print out intermediate trees for debugging, how does the pipeline help for that?</p> <p>Well the great benefit from the pipeline is that we’ve separated the information about the stages from the information about the runtime implementation of the stages. This information is created by <code class="language-plaintext highlighter-rouge">Impl</code> which creates the type of an implementation given a pipeline, but this current version only places the types end-to-end without changes. What if we add an extra <code class="language-plaintext highlighter-rouge">Monad</code> around the types such that instead of functions <code class="language-plaintext highlighter-rouge">a -&gt; b</code>, each stage is now an effectful function <code class="language-plaintext highlighter-rouge">a -&gt; m b</code>.</p> <p>First we define <code class="language-plaintext highlighter-rouge">m : Type -&gt; Type</code>, our monad, we use a parameter block because we will use it for running our programs too.</p> <div class="language-idris highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="n">parameters</span> <span class="p">{</span><span class="mf">0</span> <span class="n">m</span> <span class="o">:</span> <span class="kt">Type </span><span class="o">-&gt;</span> <span class="kt">Type</span><span class="p">}</span>
</code></pre></div></div> <p>Then, in the implementation, we use the same type signature, but in the base-case, instead of returning <code class="language-plaintext highlighter-rouge">x -&gt; y</code>, we return <code class="language-plaintext highlighter-rouge">x -&gt; m y</code>. And similarly with the inductive case.</p> <div class="language-idris highlighter-rouge"><div class="highlight"><pre class="highlight"><code>  <span class="mf">0</span>
  <span class="kt">ImplM</span> <span class="o">:</span> <span class="kt">Pipeline</span> <span class="p">(</span><span class="mf">2</span> <span class="o">+</span> <span class="n">n</span><span class="p">)</span> <span class="o">-&gt;</span> <span class="kt">Type
</span>  <span class="kt">ImplM</span> <span class="p">[</span><span class="n">x</span><span class="p">,</span> <span class="n">y</span><span class="p">]</span> <span class="o">=</span> <span class="n">x</span> <span class="o">-&gt;</span> <span class="n">m</span> <span class="n">y</span>
  <span class="kt">ImplM</span> <span class="p">(</span><span class="n">x</span> <span class="o">::</span> <span class="n">y</span> <span class="o">::</span> <span class="n">z</span> <span class="o">::</span> <span class="n">xs</span><span class="p">)</span> <span class="o">=</span> <span class="kt">Pair</span> <span class="p">(</span><span class="n">x</span> <span class="o">-&gt;</span> <span class="n">m</span> <span class="n">y</span><span class="p">)</span> <span class="p">(</span><span class="kt">ImplM</span> <span class="p">(</span><span class="n">y</span> <span class="o">::</span> <span class="n">z</span> <span class="o">::</span> <span class="n">xs</span><span class="p">))</span>
</code></pre></div></div> <p>Like before, we now test <code class="language-plaintext highlighter-rouge">ImplM</code> in the repl with a monad <code class="language-plaintext highlighter-rouge">Maybe</code> and we get:</p> <div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>&gt; ImplM {m = Maybe} CompilerPipeline
&lt; (String -&gt; Maybe (List Token), (List Token -&gt; Maybe Tree, (Tree -&gt; Maybe Sema, Sema -&gt; Maybe String)))
</code></pre></div></div> <p>Now every stage runs in a <code class="language-plaintext highlighter-rouge">Maybe</code> monad, and we could replace this monad by anything else and obtain all sorts of effects. It remains to run a pipeline with effects using our effectful implementation. We implement a function just like <code class="language-plaintext highlighter-rouge">Run</code> but we make use of <em>kleisli</em> composition instead of function composition.</p> <div class="language-idris highlighter-rouge"><div class="highlight"><pre class="highlight"><code>  <span class="kt">RunM</span> <span class="o">:</span> <span class="p">(</span><span class="n">mon</span> <span class="o">:</span> <span class="nc">Monad </span><span class="n">m</span><span class="p">)</span> <span class="o">=&gt;</span> <span class="p">(</span><span class="n">p</span> <span class="o">:</span> <span class="kt">Pipeline</span> <span class="p">(</span><span class="mf">2</span> <span class="o">+</span> <span class="n">n</span><span class="p">))</span> <span class="o">-&gt;</span> <span class="kt">ImplM</span> <span class="n">p</span> <span class="o">-&gt;</span> <span class="kt">Vect</span><span class="o">.</span><span class="nb">head </span><span class="n">p</span> <span class="o">-&gt;</span> <span class="n">m</span> <span class="p">(</span><span class="kt">Vect</span><span class="o">.</span><span class="nb">last </span><span class="n">p</span><span class="p">)</span>
  <span class="kt">RunM</span> <span class="p">[</span><span class="n">x</span><span class="p">,</span> <span class="n">y</span><span class="p">]</span>  <span class="n">f</span> <span class="o">=</span> <span class="n">f</span>
  <span class="kt">RunM</span> <span class="p">(</span><span class="n">x</span> <span class="o">::</span> <span class="n">y</span> <span class="o">::</span> <span class="n">z</span> <span class="o">::</span> <span class="n">xs</span><span class="p">)</span> <span class="p">(</span><span class="n">f</span><span class="p">,</span> <span class="n">c</span><span class="p">)</span> <span class="o">=</span> <span class="n">f</span> <span class="o">&gt;=&gt;</span> <span class="kt">RunM</span> <span class="p">(</span><span class="n">y</span> <span class="o">::</span> <span class="n">z</span> <span class="o">::</span> <span class="n">xs</span><span class="p">)</span> <span class="n">c</span>
</code></pre></div></div> <p>To run the compiler, each stage needs to perform an effect, here we’re using <code class="language-plaintext highlighter-rouge">Either String</code> to represent errors:</p> <div class="language-idris highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="kr">namespace</span> <span class="kt">EffectfulCompiler</span>
  <span class="n">lex</span> <span class="o">:</span> <span class="kt">String</span> <span class="o">-&gt;</span> <span class="kt">Either String</span> <span class="p">(</span><span class="kt">List Token</span><span class="p">)</span>
  <span class="n">parse</span> <span class="o">:</span> <span class="kt">List Token</span> <span class="o">-&gt;</span> <span class="kt">Either String</span> <span class="kt">Tree</span>
  <span class="n">typecheck</span> <span class="o">:</span> <span class="kt">Tree</span> <span class="o">-&gt;</span> <span class="kt">Either String</span> <span class="kt">Sema</span>
  <span class="n">codegen</span> <span class="o">:</span> <span class="kt">Sema</span> <span class="o">-&gt;</span> <span class="kt">Either String</span> <span class="kt">String</span>

  <span class="n">runCompiler</span> <span class="o">:</span> <span class="kt">String</span> <span class="o">-&gt;</span> <span class="kt">Either String</span> <span class="kt">String</span>
  <span class="n">runCompiler</span> <span class="o">=</span> <span class="kt">RunM</span> <span class="kt">CompilerPipeline</span> <span class="p">(</span><span class="n">lex</span><span class="p">,</span> <span class="n">parse</span><span class="p">,</span> <span class="n">typecheck</span><span class="p">,</span> <span class="n">codegen</span><span class="p">)</span>
</code></pre></div></div> <p>Crucially, we’ve not changed the pipeline at all! We’ve only changed how to interpret it as a runtime program.</p> <h2 id="debugging-programs">Debugging programs</h2> <p>Finally, using the same datastructure we can run our pipeline in <em>debug mode</em>. This mode will print in the terminal all the intermediate steps so that you can see what is happening at each stage. For this to work, we need to make sure that, for all layers in the pipeline, we have a way to <em>print</em> the result of the computation, we achieve this with the <code class="language-plaintext highlighter-rouge">All : (ty -&gt; Type) -&gt; Vect n ty -&gt; Type</code> type which takes a list of elements and a predicate over that list, and describes a list of proofs that ensure the predicate hold for every value of <code class="language-plaintext highlighter-rouge">ty</code> given. In our case, the predicate given is the <code class="language-plaintext highlighter-rouge">Show</code> interface, and so for each type there must exist a <code class="language-plaintext highlighter-rouge">Show</code> instance.</p> <p>The rest of the function is the same as before, except we compose each <code class="language-plaintext highlighter-rouge">f</code> with <code class="language-plaintext highlighter-rouge">pure . traceValBy show</code> to print the value we just computed.</p> <div class="language-idris highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="nf">RunTraceM :</span> <span class="nc">Monad </span><span class="n">m</span> <span class="o">=&gt;</span> <span class="p">(</span><span class="n">p</span> <span class="o">:</span> <span class="kt">Pipeline</span> <span class="p">(</span><span class="mf">2</span> <span class="o">+</span> <span class="n">n</span><span class="p">))</span> <span class="o">-&gt;</span> <span class="p">(</span><span class="n">print</span> <span class="o">:</span> <span class="kt">All</span> <span class="kt">Show</span> <span class="n">p</span><span class="p">)</span> <span class="o">=&gt;</span> <span class="kt">ImplM</span> <span class="p">{</span><span class="n">m</span><span class="p">}</span> <span class="n">p</span> <span class="o">-&gt;</span> <span class="kt">Vect</span><span class="o">.</span><span class="nb">head </span><span class="n">p</span> <span class="o">-&gt;</span> <span class="n">m</span> <span class="p">(</span><span class="kt">Vect</span><span class="o">.</span><span class="nb">last </span><span class="n">p</span><span class="p">)</span>
<span class="kt">RunTraceM</span> <span class="p">[</span><span class="n">x</span><span class="p">,</span> <span class="n">y</span><span class="p">]</span> <span class="p">{</span><span class="n">print</span> <span class="o">=</span> <span class="p">[</span><span class="n">p1</span><span class="p">,</span> <span class="n">p2</span><span class="p">]}</span> <span class="n">f</span> <span class="o">=</span> <span class="n">f</span> <span class="o">&gt;=&gt;</span> <span class="n">pure</span> <span class="o">.</span> <span class="n">traceValBy</span> <span class="n">show</span>
<span class="kt">RunTraceM</span> <span class="p">(</span><span class="n">x</span> <span class="o">::</span> <span class="n">y</span> <span class="o">::</span> <span class="n">z</span> <span class="o">::</span> <span class="n">xs</span><span class="p">)</span> <span class="p">{</span><span class="n">print</span> <span class="o">=</span> <span class="n">p</span> <span class="o">::</span> <span class="n">q</span> <span class="o">::</span> <span class="n">ps</span><span class="p">}</span> <span class="p">(</span><span class="n">f</span><span class="p">,</span> <span class="n">c</span><span class="p">)</span> <span class="o">=</span>
  <span class="n">f</span> <span class="o">&gt;=&gt;</span> <span class="n">pure</span> <span class="o">.</span> <span class="n">traceValBy</span> <span class="nb">show </span><span class="o">&gt;=&gt;</span> <span class="kt">RunTraceM</span> <span class="p">(</span><span class="n">y</span> <span class="o">::</span> <span class="n">z</span> <span class="o">::</span> <span class="n">xs</span><span class="p">)</span> <span class="n">c</span>
</code></pre></div></div> <p>Calling our pipeline with <code class="language-plaintext highlighter-rouge">RunTraceM</code> will print out every intermediate value produced by the pipeline, It won’t print the first argument given to it but since we already have it, we can print it when we call the pipeline.</p> <h2 id="conclusion">Conclusion</h2> <p>There is much more to say about this but is already more than we can usually do without dependent types. We can take the pipeline and build multiple runtimes for it, and run it in multiple modes as well. I’ve not shown it here but we can also implement operations on the pipeline like concatenation, splicing, etc. Those operations should reflect what happens at runtime: Concatenating two pipeline should compose two programs that run them. This framework can be extended in many other ways but that will serve as a solid base for now, see you in the next one.</p> <p>The code is available as a library: <a href="https://gitlab.com/glaive-research/pipelines">https://gitlab.com/glaive-research/pipelines</a>.</p>]]></content><author><name></name></author><category term="dependent-types"/><category term="idris"/><category term="programming"/><category term="software-engineering"/><summary type="html"><![CDATA[Sometimes, writing a large program is conceptually as simple as translating from a big unstructured input into a more and more structured output. In this post, we present a data structure to talk about such programs and demonstrate its use and flexbility using a single-pass compiler as case-study.]]></summary></entry><entry><title type="html">Govan Active Travel</title><link href="https://andrevidela.com/blog/2024/govan-active-travel/" rel="alternate" type="text/html" title="Govan Active Travel"/><published>2024-11-29T04:14:00+00:00</published><updated>2024-11-29T04:14:00+00:00</updated><id>https://andrevidela.com/blog/2024/govan-active-travel</id><content type="html" xml:base="https://andrevidela.com/blog/2024/govan-active-travel/"><![CDATA[<p>This is a report building on the designs provided by the <a href="https://storymaps.arcgis.com/collections/c390337efca64158b725c0c99bf61f12">connecting greater govan project</a> to facilitate active travel through the Govan area and develop it economically and culturally.</p> <p>First I will present the governing idea that drives the feedback and then show 3 edited documents that detail in what way the street layout can be changed to achieve the goals presented. The final section makes a case against 2-way cycle lanes before concluding.</p> <h2 id="part-1--govan-cross-and-public-space">Part 1 : Govan Cross and Public Space</h2> <p>The first part of the feedback is to question the place of govan cross and the way it serves the community. As of today, Govan cross, and its main street govan road, serve as a carrier of through traffic, as well as a parking resource for non-residents.</p> <p>The goal of the following map is to transform the role of Govan Rd from a through-traffic road and parking spot, to a street that facilitates pedestrian access, wheelchair access, and cycling. With the aim to create more spaces for families, shops, and on-street activities like markets or events. All while allowing access to motor vehicles for people with mobility challenges, deliveries, and resident parking.</p> <p>This is achieved by creating a large pedestrian-only space at the core of Govan cross, allowing the streets to be decorated with trees, bushes and benches, and the extra space to be used for events, markets, and food stalls.</p> <ul> <li>Green is the pedestrian-only zone without motor vehicles</li> <li>Orange is the resident traffic access for motor vehicles</li> <li>Red is the through traffic for motor vehicles</li> </ul> <figure> <picture> <source class="responsive-img-srcset" srcset="/assets/img/govan-overview-480.webp 480w,/assets/img/govan-overview-800.webp 800w,/assets/img/govan-overview-1400.webp 1400w," sizes="95vw" type="image/webp"/> <img src="/assets/img/govan-overview.jpeg" class="img-fluid rounded z-depth-1" width="100%" height="auto" data-zoomable="" loading="lazy" onerror="this.onerror=null; $('.responsive-img-srcset').remove();"/> </picture> </figure> <p>This layout provides 4 opportunities for place-making, from east to west:</p> <h3 id="the-area-between-govan-subway-station-and-the-new-bridge">The Area Between Govan Subway Station and the New Bridge</h3> <p>The opening of the bridge towards Partick and the Riverside Museum is a great opportunity to revise the way visitors are expected to access it. As of today, once a visitor exits the subway station, they have to cross a busy road, often littered with parked cars, hindering visibility, to reach Water Row and cross the bridge. What is more, the space taken by the road prevents any future businesses from developing by capitalising on the additional foot traffic.</p> <p>Restricting access to vehicles between the station and water row greatly facilitates access to the bridge for people with mobility difficulties and creates an additional space for the community. Vehicle access to Water Row for residents, deliveries, and visitors is guaranteed by Burleigh St, which itself would become accessible via Golspie St.</p> <h3 id="the-area-in-front-of-the-pierce-institute">The Area in Front of the Pierce Institute</h3> <p>The Pierce Institute is an important community hub in Govan, but as of right now, it is only directly accessible by 4 parking spots in front of it. Pedestrian access is difficult due to the high speed at which vehicles traverse Govan Rd, and cycle access is non-existent. Pedestrianising the street ensures easy access from the subway station. It also creates a plaza where both the Pierce Institute and the William Pierce statue can stand on uninterrupted grounds. Finally, the place provides dignified access to the Old Govan Church, a building whose historical importance has been too long neglected.</p> <h3 id="the-area-in-front-of-the-lyceum">The Area in Front of the Lyceum</h3> <p>The Lyceum building is of great importance to the community, as the current plans to reclaim it can attest, and it is paramount that its surroundings reflect that. Today, the intersection in front of the lyceum building entirely yields to through traffic, ensuring that the perception of the lyceum building remains that of a curiosity on the side of the road rather than a place to be celebrated by the local community. Future plans should ensure that the area in front of the Lyceum building is a place for people. And is starts with creating that space for the people.</p> <h3 id="the-west-intersection-between-golspie-st-and-govan-rd">The West Intersection Between Golspie St and Govan Rd</h3> <p>Today, this intersection is a source of traffic delay, pedestrian confusion, and unsatisfactory road maintenance. It is clear that this intersection has failed to serve the local community. The proposal is to remove the intersection entirely, and employ the additional space for a plaza that would bring foot traffic to the surrounding businesses, and create a space for children and families to enjoy. The space could also host some food trucks to serve the workers of the area and markets for the residents on the weekend.</p> <h3 id="a-note-about-bus-access">A Note About Bus Access</h3> <p>This proposal removes 3 bus stops along Govan Rd. Those stops are currently served by the buses M23 and M26 from McGill. Instead of going through GovanRd, they will need to stop at the south of the subway station where the current x19 stop, and follow the same pattern of stops (Govan Interchange, Helen St, Govan Rd). This is, in fact, a good thing, since anyone going west, towards QUEH, currently, has to choose whether to bet on bus 23 to come in first and wait at the north bus stop on Govan Rd. Or bet on the x19 and wait at the south bus stop on Golspie St. By consolidating both bust stops, this coinflip goes away and everyone is guaranteed to board the fastest bus westward. Additionally, all buses now make use of the fast link, instead of getting stuck at traffic lights on Govan Rd. Finally, access to Govan Rd is not significantly hampered since the bus stops at the west and east remain relatively unchanged, the new bus stops would be at most 50m further. The Old Govan Church is the point of interest most affected by the removal since it loses the bus stop in front of it served by the 23 and 26. Thankfully, removing this bus stop only increases the walking time by 3m, to reach the stops currently served by the x19, it increases the foot traffic in front of the local businesses.</p> <h2 id="part-2-detailed-plans">Part 2: Detailed Plans</h2> <p>This section provides detailed changes to the proposed design in the form of edited plans. These changes explain how the above design goals can be achieved in practice. There are three plans tracing</p> <p>The plan to pedestrianise Govan creates multiple opportunities for people and businesses to use the space freely. It also fluidifies vehicle traffic by directing through traffic via Golspie St and removing traffic lights and sources of road conflict.</p> <figure> <picture> <source class="responsive-img-srcset" srcset="/assets/img/Govan-east-480.webp 480w,/assets/img/Govan-east-800.webp 800w,/assets/img/Govan-east-1400.webp 1400w," sizes="95vw" type="image/webp"/> <img src="/assets/img/Govan-east.jpeg" class="img-fluid rounded z-depth-1" width="100%" height="auto" data-zoomable="" loading="lazy" onerror="this.onerror=null; $('.responsive-img-srcset').remove();"/> </picture> </figure> <h4 id="east-access-to-govan-rd">East access to Govan Rd</h4> <p>The east access of Govan Cross is rendered difficult due to multiple streets joining at slightly off angles. Currently, most of the space is used by the intersection between Govan Rd and Golspie St. The roads are wide, the traffic lights often induce jamming and crossing the intersection as a pedestrian and a cyclist is challenging.</p> <p>The new design aims to safely bring cycle traffic from Govan Rd to Orkney St, while enabling pedestrians to cross safely at multiple junctions. Vechicle traffic is also improved by removing traffic lights, using the expansive space at the interesection to build a roundabout, and allowing residents to access Napier Road and Govan Road, using the layout shown above.</p> <h4 id="govan-rd-and-the-town-centre">Govan Rd and the Town Centre</h4> <p>With the pedestrianisation of most of the town center, access to businesses, points of interests (Old Govan Church, Riverside Museum), and community destinations (Pierce Institute) is made easier than ever. The additional room creates space for adults to gather and kids to play. The lack of private vehicles guarantees easy access for delivery vehicles, emergency vehicles, and people with mobility difficulties. Bike lanes are pushed to the side to leave room for pedestrians and do not require any grade separation.</p> <h3 id="govanrdfairfield--west-access-to-govan-cross">GovanRd/Fairfield &amp; West access to Govan cross</h3> <p>Govan connects to its historical roots as a ship building neighborhood, but the current street layout makes accessing this history difficult and unpleasant. The core of the proposed layout is to provide a new public space obtained by removing the intersection with Golspie St and diverting through traffic away from the centre.</p> <figure> <picture> <source class="responsive-img-srcset" srcset="/assets/img/Govan-west-480.webp 480w,/assets/img/Govan-west-800.webp 800w,/assets/img/Govan-west-1400.webp 1400w," sizes="95vw" type="image/webp"/> <img src="/assets/img/Govan-west.png" class="img-fluid rounded z-depth-1" width="100%" height="auto" data-zoomable="" loading="lazy" onerror="this.onerror=null; $('.responsive-img-srcset').remove();"/> </picture> </figure> <h4 id="govan-rd-west-intersection-with-golspie-st">Govan Rd West Intersection with Golspie St</h4> <p>This intersection, as of today, is unsatisfactory. The traffic signals create delays, the layout does not leave any room for cyclists or pedestrians, access to businesses is limited, and access to the fairfield museum is unpleasant by foot from the station due to the amount of noise and polluting traffic at the intersection.</p> <p>To address those shortcomings, the proposed design removes the intersection altogether, adds zebra crossings for bikes and pedestrians, and creates a new space for people to use and congregate. This space should boost access to local businesses by providing outdoor seating, space for play, and opportunities to develop new businesses like markets or food trucks. It also makes access to the Fairfield Heritage Museum by foot much more pleasant from the subway station and greatly increases access to businesses for pedestrians and cyclists. The added space can accommodate outdoor seating, food trucks or seasonal markets. The fastlink bus lane remains unaffected and the connection to Elder Park is seamless</p> <h4 id="elder-park-bike-lane">Elder park bike lane</h4> <p>The change is simple: move the lane to the south of the road so that cyclists can access the park without endangering themselves, or endangering pedestrians.</p> <h3 id="govan-rd-and-linthouse">Govan Rd and Linthouse</h3> <p>The final section of this feedback document concerns the Linthouse neighborhood and its connection to Govan Rd. The original design removes a much-needed bus lane, this proposal reinstates the bus land and explains how to make the south bike lane around Elder Park connect with the interchange.</p> <figure> <picture> <source class="responsive-img-srcset" srcset="/assets/img/linthouse-480.webp 480w,/assets/img/linthouse-800.webp 800w,/assets/img/linthouse-1400.webp 1400w," sizes="95vw" type="image/webp"/> <img src="/assets/img/linthouse.png" class="img-fluid rounded z-depth-1" width="100%" height="auto" data-zoomable="" loading="lazy" onerror="this.onerror=null; $('.responsive-img-srcset').remove();"/> </picture> </figure> <h4 id="north-west-of-elder-park">North West of Elder Park</h4> <p>The large intersection at the northwest of Elder Park is notoriously difficult to navigate by bike. The proposed change simply takes into account the fact that the bike lane is now at the southmost lane of the street. It keeps the current road design for vehicles with 1 bus lane and 2 car traffic lanes. It also reinstates the fast link bus lane west of the exchange while keeping the proposed bike lane.</p> <h4 id="towards-queh">Towards QUEH</h4> <p>Further west, the bike lane merges with the bus lane for the duration of the bridge and the next block. This is due to space constraints on this specific stretch of the street, keeping the bus lane is of utmost importance given its connection to QEUH. The bike layout around Burghead Pl and Peninver Dr remains the same, with added traffic calming in the form of parking space allocated on alternating sides of the road. The bus lane is extended all the way to the intersection of Govan Rd With Moss Rd, again to avoid delays incurred by private vehicles when reaching the hospital.</p> <h2 id="general-concern-about-2-way-bike-lanes">General concern about 2-way bike lanes</h2> <p>One of the issues with 2-way cycle lanes, is that access to the points of interest are guaranteed only from one side of the road. If a cyclist wishes to access a business, or a building, across their designated cycle lane they have three choices, all of which are bad:</p> <ul> <li>Cross the road through oncoming traffic on both sides</li> <li>Cycle until reaching a crossing, cross and join the car lane on the opposite direction</li> <li>Cycle until reaching a crossing, cross, and join the pedestrian pavement.</li> </ul> <p>Those three situations are illustrated in the image that follows:</p> <figure> <picture> <source class="responsive-img-srcset" srcset="/assets/img/2-way-cycle-lanes-480.webp 480w,/assets/img/2-way-cycle-lanes-800.webp 800w,/assets/img/2-way-cycle-lanes-1400.webp 1400w," sizes="95vw" type="image/webp"/> <img src="/assets/img/2-way-cycle-lanes.jpeg" class="img-fluid rounded z-depth-1" width="100%" height="auto" data-zoomable="" loading="lazy" onerror="this.onerror=null; $('.responsive-img-srcset').remove();"/> </picture> </figure> <p>In the first scenario, the cyclist will encounter 3 sources of conflict: Incoming cycle traffic, and two lanes of vehicle traffic. This is in the best-case scenario where there is no parking and only two car lanes. This outcome is the most direct and the most dangerous, failing to protect cyclists from motor vehicle traffic.</p> <p>In the second scenario, the cyclist does not encounter any conflicts but does not make use of the bike lane on the last stretch of the trip. While this is safer for the cyclist, it also questions the role of the bike lane as a tool to protect different modes of transit, since, in this case, the bike lane fails to protect the cyclist on their way to their destination.</p> <p>In the last scenario, the cyclist does not encounter any conflict either, however, it <em>creates</em> conflicts with pedestrian traffic that is now put in danger by the cyclist. Again this questions the role of the bike lane as a tool to protect multi-modal forms of transit. We built a bike lane to protect pedestrian from bikes, yet, they end up sharing the same space.</p> <p>In conclusion, 2-way cycle lanes excel when all the points of interest are gathered on the same side of the road. Whenever that is <em>not</em> the case, they fail at their role to protect the users of the street. The proposed plans keeps 2-way bike lanes along Elder Park and in the Linthouse area because all the points of interest are on the same side. But it would be nice to eliminate 2-way cycle lanes in other parts of the designs proposed by Jacobs.</p> <h2 id="conclusion">Conclusion</h2> <p>Thank you for your time and for your work. I am optimistic that the changes to come in Govan are for the better, and I hope that this piece of feedback can help the area reach its potential as a historically important part of Glasgow and as a centre for cultural activities.</p>]]></content><author><name></name></author><category term="pedestrian"/><category term="space"/><category term="place-making"/><category term="cycle"/><category term="lane"/><category term="bike"/><summary type="html"><![CDATA[A new proposal for Govan Active Travel strategy]]></summary></entry></feed>