TE
科技回声
首页24小时热榜最新最佳问答展示工作
GitHubTwitter
首页

科技回声

基于 Next.js 构建的科技新闻平台,提供全球科技新闻和讨论内容。

GitHubTwitter

首页

首页最新最佳问答展示工作

资源链接

HackerNews API原版 HackerNewsNext.js

© 2025 科技回声. 版权所有。

The Meta-Circular Evaluator (2016)

40 点作者 ptr大约 6 年前

2 条评论

triska大约 6 年前
That&#x27;s a very interesting topic and nice write-up, thank you for sharing!<p>For comparison, here is a small interpreter for a subset of Prolog, written in Prolog:<p><pre><code> mi([]). mi([G|Gs]) :- clause_(G, Body), mi(Body), mi(Gs). </code></pre> This states that: First, the empty conjunction (of goals) is true, and second, if there is at least one goal left, than the conjunction is true <i>if</i> there is a suitable clause whose body evaluates to true, and the same holds for all remaining goals.<p>For example, we can define append&#x2F;3 as follows in this representation:<p><pre><code> clause_(append([], Ys, Ys), []). clause_(append([X|Xs], Ys, [X|Zs]), [append(Xs,Ys,Zs)]). </code></pre> and then evaluate it with our interpreter:<p><pre><code> ?- mi([append([a,b,c], [d,e], Ls)]). Ls = [a, b, c, d, e]. </code></pre> Characteristically, it also works in other directions. For example:<p><pre><code> ?- mi([append([a,b,c], Rs, [a,b,c,d,e])]). Rs = [d, e]. </code></pre> and also:<p><pre><code> ?- mi([append(As, Bs, [x,y])]). As = [], Bs = [x, y] ; As = [x], Bs = [y] ; As = [x, y], Bs = [] ; false. </code></pre> Now the point: The clauses of the meta-interpreter itself can <i>also</i> be stated in this form, namely as:<p><pre><code> clause_(mi([]), []). clause_(mi([G|Gs]), [clause_(G,Body),mi(Body),mi(Gs)]). </code></pre> Now we only have to define what clause_&#x2F;2 means, which we can do with:<p><pre><code> clause_(clause_(G, Body), []) :- clause_(G, Body). </code></pre> And now we can use our meta-interpreter to evaluate its own code as it interprets a program, arbitrarily deeply layered:<p><pre><code> ?- mi([mi([mi([append([a,b,c],[d,e],Ls)])])]). Ls = [a, b, c, d, e]. </code></pre> Hence, Prolog admits a meta-circular evaluator in at most 5 lines of code. With a better representation for clauses (using list differences), you can reduce the interpreter to 4 lines of code and at the same time make it tail-recursive.
评论 #19294623 未加载
nickdrozd大约 6 年前
The post is based on SICP, and the author briefly discusses dynamic scoping after finding it in some other blog posts or something. In fact, the first edition of SICP contained a discussion of dynamic scoping. I don&#x27;t know why it was removed from the second edition, because it&#x27;s an interesting and important topic. Dynamic scoping also features in the SICP videos [1], which were produced around the time the first edition came out.<p>[1] <a href="https:&#x2F;&#x2F;www.youtube.com&#x2F;watch?v=t5EI5fXX8K0&amp;feature=youtu.be&amp;t=1098" rel="nofollow">https:&#x2F;&#x2F;www.youtube.com&#x2F;watch?v=t5EI5fXX8K0&amp;feature=youtu.be...</a>