如何有步驟地實現乙個直譯器?如果採用低階語言,如 C 之類的語言來實現像 Lisp 這樣的語言,需要什麼知識和工具?

時間 2021-05-08 15:38:51

1樓:

建議先系統了解下LISp核心原理

然後實現乙個足夠小(精簡)的lisp核心出來某些高階的東西(比如oop機制,或者訊號槽機制)都能在語言層實現第一次實現的時候不用太過於糾結效率問題

另外 @大笨蛋千里冰封 我的Malt嚴格來說不是基於ast,而是基於表遍歷解析

(所以每次call 函式時得先複製乙份過程)

2樓:藥罐子千里冰封

先寫Parser,然後寫規約求值的AST,然後你就做出來了,不需要任何編譯原理知識,目錄現在就在幹這事,但他做的Lisp比我當年那個要高階很多

3樓:開源醬

直譯器啊。。。我用 C 寫過 Lisp 方言的直譯器。。。

大概就是:

read

parse

eval

print

這麼個流程(Lisp 的列表就是 AST 了不用再造 AST (說白了我還是懶

4樓:Thomson

看看Python實現的乙個簡易Lisp吧,比C可讀性更好。第一次看完的時候豁然小開朗了以下。

(How to Write a (Lisp) Interpreter (in Python))

5樓:溫悅

直譯器(interpreter)的目標是「分析源程式結構」然後「直接在'宿主語言'執行環境中執行」,沒有編譯到彙編碼、機器碼的過程;那麼假設用C來實現lisp,步驟就是:

用c分析lisp的詞法,解析出token(詞法分析)

用c實現LR或LL的語法分析(手寫建議用LL分析), 根據第1步得到的token流構建乙個反映語法結構的語法解析樹(parse tree, 這一步叫「語法分析」)

為每一種parse tree節點寫乙個函式,假設有n種parse tree節點那麼就有n個這樣的函式,這些函式互相"遞迴下降"地遍歷、處理parse tree,把parse tree變成更具有意義的、更貼近你的設計意圖的「抽象語法樹」,即「AST」(這一步其實若是物件導向語言,那麼我說"visitor"你就應該能懂了,但可惜是C語言,我就只能說"互相遞迴下降的函式")

其實如果是手寫語法分析程式,那麼大多數情況下2,3可並為一步,即直接從token流構建出AST來

再實現一套針對AST節點的「相互遞迴下降的函式」,遍歷AST,做一些該做的驗證,比如語義、特殊約束等(3,4,5可叫做語義分析)

到此為止,你得到了乙個完整的、保證正確的lisp程式的AST;那麼:跟第5步一樣,再寫一套針對AST節點的"相互遞迴下降的函式",遍歷AST,不過這次不是做驗證語義,這次是直接對碰到的每乙個節點,按照節點含義做執行,最終得出程式結果

以上;另,函式式語言由於其計算模型並非圖靈機,而是lambda演算,所以在我們現在所使用的馮氏計算機體系結構上實現他們並不是很「自然」的事情,因為函式式語言並不對應於馮氏計算機或圖靈機的「紙帶上的一條一條指令」;但是理論上是保證能夠實現的,因為lambda演算和圖靈機的計算能力是等價的,所以在馮氏計算機上實現lisp是絕對可行的..已經存在的CLisp編譯器就證明了這一點;

java如何實現同乙個瀏覽器同的乙個系統只能登入乙個賬號,如果登入了第二個,第乙個賬號自動登出?

zhangs1314 樓主的意思可能是在同乙個瀏覽器裡面的不同的標籤頁,訪問了同乙個專案,後面登入進去的賬號,把前面登入進去的賬號踢掉.以前俺的做法,一般是用ws協議做長連線.每乙個長連線的唯一標記是乙個sessionId.登入的時候,先判斷是否有sessionId被儲存過.如果有,伺服器向這個se...

如何有理有據地解釋SNH不是乙個野「雞」團?

樓裡那伍什麼的xswl,理直氣壯的給野雞這個侮辱性詞彙洗地666你說不被AKS承認是野團沒問題啊,那我請問雞什麼意思啊?對女生用雞來形容你不會不知道什麼含義吧?什麼人都能飯偶像了,你自己不就是她們嘴中的五香豆?人最悲哀的是自己被罵還自認就是,樂死了簡直 你推誰啊?敢不敢握手會當面對你推的小偶像說你是...

如何對乙個沒聽過太多搖滾的人真正地解釋清楚搖滾?

沒法解釋 搖滾的定義太廣了 搖滾的類別也太多了 搖滾其實是一種精神 我覺得很難表達 解釋不清會讓別人誤解 有很多人覺得搖滾是很吵鬧的 但是其實慢搖非常的輕柔 很多人以為朋克就是搖滾 其實這只是搖滾內最常見的一種類別 英倫迷幻也好北歐的哥特也好或者金屬也好中國的土搖也好其他等等等等 慢慢聽多了就會慢慢...