我正在研究玩具語言的解釋器,以瞭解有關構建解釋器的信息。我已經爲生成解析樹的語法實現了一個簡單的解析器。現在,評估分析樹的常用方法是使用解析樹的節點上的多態性,用代碼,看起來像下面(在Python):在編碼表達式分析樹/評估器時使用多態性存在疑問
class Node:
def __init__(self,left,right):
self.left=left
self.right=right
def evaluate(self):
print "throw an exception"
class AddNode(Node):
def evaluate(self):
return evaluate(self.left)+evaluate(self.right)
class SubNode(Node):
def evaluate(self):
return evaluate(self.left)-evaluate(self.right)
的方法評估在每個後代覆蓋的節點,並捍衛行爲的需要。只需在根上調用evaluate()即可找到表達式的值。
另一種方法是在節點中沒有任何評估函數,而是生成一個簡單地將類型分配給節點的分析樹。評估代碼在一個單獨的函數中完成,遞歸檢查每個節點並決定如何評估它。這將導致帶有大量「if else」結構,開關或跳轉表的函數。
幾乎在我看的每一個地方,以及我在大學教過的東西,似乎都表明第一種方法總是更好。我不完全理解的是爲什麼第一種方法應該優於第二種方法。爲什麼在這種情況下多態必然更好?帶有大「if else」表的函數不存在,但基本上相同的代碼仍然存在,但移動到不同的地方並散佈在許多不同的類中。
這引起了我的注意,因爲我想我以後可能需要更改某些操作符的含義,甚至允許運算符在運行時重新定義。我也將函數調用和運算符一樣對待,所以像運行一個跳轉表一樣可以在運行時添加的東西會很好。
第一種方法可能有一些顯着的優點,我現在沒有看到。有人可以指出嗎?
謝謝。每當我需要爲該語言添加一個新操作符時,必須更改解析器和評估器的好處。 – MAK 2009-12-22 16:46:27