<div><span class="gmail_quote">On 12/26/07, <b class="gmail_sendername">Cristian Baboi</b> &lt;<a onclick="return top.js.OpenExtLink(window,event,this)" href="mailto:cristian.baboi@gmail.com" target="_blank">cristian.baboi@gmail.com
</a>&gt; wrote:</span> 
<blockquote class="gmail_quote" style="PADDING-LEFT: 1ex; MARGIN: 0px 0px 0px 0.8ex; BORDER-LEFT: #ccc 1px solid">The reason I want to build functions of type String -&gt; (a -&gt; b) is because<br>I want to see how far I can get with &quot;functions are first class citizens&quot; 
<br>in Haskell. I thought that if I read the function from an external source,<br>there is no way the compiler could know what I&#39;ll read. I want to see if I<br>can build a Haskell function at runtime, not a data structure that I can 
<br>interpret.</blockquote>
<div>&nbsp;</div>
<div>Those two questions are intimately related, though.&nbsp;&nbsp;Consider the following simple program:</div>
<div>&nbsp;</div>
<div>&gt; {-# LANGUAGE GADTs #-}</div>
<div>&gt; module Compile where</div>
<div>&gt;</div>
<div>&gt; data Term a where</div>
<div>&gt; &nbsp;&nbsp;&nbsp;&nbsp;App :: Term (a -&gt; b) -&gt; Term a -&gt; Term b</div>
<div>&gt; &nbsp;&nbsp;&nbsp; Prim :: a -&gt; Term a</div>
<div>&nbsp;</div>
<div>Implementation of lambda-abstractions is left as an exercise for the reader.</div>
<div>&nbsp;</div>
<div>&gt; compile :: Term a -&gt; a</div>
<div>
<div>&gt; compile (Prim x)&nbsp;= x</div>&gt; compile (App x y) = compile x $ compile y</div>
<div>&nbsp;</div>
<div>
<div>While &quot;compile&quot; looks like an interpreter (and it is), there is no reason why &quot;a&quot; has to be a concrete data type; it could be a function type, as demonstrated here:</div>
<div>&nbsp;</div></div>
<div>&gt; uncompiled_func :: Term (Int -&gt; Int)</div>
<div>&gt; uncompiled_func = App (Prim (+)) (Prim 1)</div>
<div>&gt;</div>
<div>&gt; compiled_func :: Int -&gt; Int</div>
<div>&gt; compiled_func = compile uncompiled_func</div>
<div>&nbsp;</div>
<div>The first time you evaluate &quot;compiled_func&quot;, you&#39;ll run the &quot;compiler&quot; which will create a function for you.&nbsp;&nbsp;Consider the lazy evaluation order&nbsp;of this program:</div>
<div>&nbsp;</div>
<div>&gt; result :: Int</div>
<div>&gt; result = compiled_func 3&nbsp;+ compiled_func 4</div>
<div>&nbsp;</div>
<div>I&#39;ll use &quot;let&quot; to represent sharing and &quot;plus#&quot; to represent the primitive operation of adding two numbers which (+) is defined in terms of.</div>
<div>That is, (+) = \x y -&gt; plus# x y</div>
<div>&nbsp;</div>
<div>result</div>
<div>=&gt; compiled_func 3 + compiled_func 4</div>
<div>=&gt; (\x y -&gt; plus# x y) (compiled_func 3) (compiled_func 4)</div>
<div>=&gt; plus# (compiled_func 3) (compiled_func 4)</div>
<div>=&gt; let compiled_func = compile uncompiled_func in plus# (compiled_func 3) (compiled_func 4)</div>
<div>&nbsp; (evaluating compiled_func)</div>
<div>&nbsp; compile (App (Prim (+)) (Prim 1))</div>
<div>&nbsp; =&gt; compile (Prim (+))&nbsp;(compile (Prim 1))</div>
<div>&nbsp; =&gt; (+) (compile (Prim 1))</div>
<div>&nbsp; =&gt; (\x y -&gt; plus# x y) (compile (Prim 1))</div>
<div>&nbsp; =&gt; (\y -&gt; plus# (compile (Prim 1)) y)</div>
<div>&nbsp; which is WHNF</div>
<div>=&gt; let compiled_func = (\y -&gt; plus# (compile (Prim 1)) y) in plus# (compiled_func 3) (compiled_func 4)</div>
<div>=&gt; let inner = (compile (Prim 1)); compiled_func =&nbsp;\y -&gt; plus# inner y&nbsp;in&nbsp;plus# (compiled_func 3) (compiled_func 4)</div>
<div>
<div>=&gt; let inner = (compile (Prim 1)) in&nbsp;plus# (plus# inner 3) ((\y -&gt; plus# inner y) 4)</div>=&gt; let inner = 1 in plus# (plus# inner 3) ((\y -&gt; plus# inner y) 4)</div>
<div>=&gt;&nbsp;plus# 4&nbsp;((\y -&gt; plus# 1 y) 4)</div>
<div>=&gt; plus# 4 (plus# 1 4)</div>
<div>=&gt; plus# 4 5</div>
<div>=&gt; 9</div>
<div>&nbsp;</div>
<div>Note that &quot;compile&quot; only gets run once on each subexpression; the end result is that you end up with a regular Haskell function which does no interpretation at all!</div>
<div>&nbsp;</div>
<div>All that remains is creation of something of type &quot;Term a&quot; from an untyped representation.&nbsp; Oleg&#39;s done the work here and you can see a full implementation in this message:</div><a href="http://www.haskell.org/pipermail/haskell-cafe/2007-October/032591.html">
http://www.haskell.org/pipermail/haskell-cafe/2007-October/032591.html</a>
<div>&nbsp;</div>
<div>&nbsp; -- ryan</div></div>