4

SICP第4章では、構文解析を実行から分離することによってメタサーキュラーエバリュエーターが変更され、evalプロシージャは次のようになります。

(define (eval exp env)
    ((analyze exp) env))

そして本はanalyze、実行プロシージャが何度も呼び出されるかもしれない間、これは式で一度呼び出されるので、これは仕事を節約するだろうと言っています。

私の質問は、この最適化はどのように機能するのかということです。再帰的なプロシージャ呼び出しでは機能しますが、他の場合はどうでしょうか。エバリュエーターは式を次々に評価し、eval同じ形式であっても各式で呼び出されます。

4

3 に答える 3

4

いくつかのことを確認する必要があります:(a)関数は各式を1回だけウォークオーバーします、(b)構文をスキャンするanalyzeコードは外部にありません、(c)返される関数はそれ自体を呼び出さないため、その関数を実行してもリードしません構文をさらにスキャンする場合、(d)これは、関数を2回呼び出すと、その構文が2回スキャンされることを意味する通常の評価関数とはすべて異なります。analyzeanalyze

ところで、はるかに良い名前analyzecompile-入力言語(sexprs)をターゲット言語(ここではマシンコードとして機能する関数)に実際に変換します。

于 2012-02-06T06:59:57.817 に答える
1

コンパイラとインタプリタの違いは次のとおりです。

コンパイラはソースコードを1回だけスキャンし、それを実行コード(おそらくマシンコード)に変更します。次回プログラムを実行するときは、ソースコードを分析せずに実行コードを直接実行するので効率的です。

ただし、インタプリタは、プログラムを実行するたびにソースコードを分析します。

この最適化は、プログラムが複数回実行される場合にのみ意味があります。

@Eli Barzilayが言ったように、「の方がはるかに良い名前analyzecompile」です。分析された関数は実行コードのようなものです。再帰関数は、複数回実行されるプログラムのようなものです。

于 2013-09-11T03:36:53.947 に答える
0

analyze構文分析を1回実行し、変換されたものなどを、関連するプロシージャの実行時に直接definition使用できる環境に格納します。lookup-variable-value

対照的に、元のメタサーキュラーエバリュエーターは構文解析と実行をひねり、各実行で構文解析も呼び出されるようにします。

このリンクは役立つかもしれません: http ://www.cs.brandeis.edu/~mairson/Courses/cs21b/Handouts/feeley-notes.pdf

于 2014-09-10T08:17:15.257 に答える