終於掙扎回到了博客。由於一些煩心事而影響到了本身,深感不安與羞愧。明天在此博開更。html
-------------------編譯原理之詞法分析-------------------------正則表達式
在以前的一篇博文上有說過,編譯器接受一串字符流(即源程序代碼),而後進行詞法分析,雨大分析,語義分析,而後生成中間代碼,最後生成目標代碼。ui
今天就要說編譯器的第一個步驟,詞法分析。詞法分析(lexical analysis)也可稱爲掃描(scaning)。詞法分析器(lexical anylizer)讀入源程序代碼,而且將他們組成有意義的詞素(lexeme)序列,對於每一個詞素,詞法分析器產生一個詞法單元(token),即最後會輸出一個詞法單元序列。token以下形式:<token-name,attribute-value>。第一個份量token-name是一個由詞法分析步驟使用的抽象符號,第二個份量attribute-value指向符號表中關於這個詞法單元的條目。spa
先了解一下編譯器符號表:.net
一、編譯過程當中編譯程序不斷聚集和反覆查證出如今源程序中各類名字的屬性和特徵信息等有關信息。unix
這些信息一般記錄在一張或幾張符號表中。code
二、符號表的每一項有兩部分:htm
一部分是名字(標識符);一部分是名字屬性(標識符的有關信息)。blog
三、編譯過程當中,每當掃描器(詞法分析器)識別出一個名字後,編譯程序就查閱符號表,看其是否在符號表中。token
若是它是一個新名字就將它填進表裏。
它的有關信息將在詞法分析和語法-語義分析過程當中陸續填入表中。
四、符號表是邊填邊用。
在整個編譯期間,對於符號表的操做大體可概括爲五類:
一、對給定名字,查詢此名是否已在表中;
二、往表中填入一個新名字;
三、對給定名字,訪問它的某些信息;
四、對給定名字,往表中填寫或更新它的某些信息;
五、刪除一個或一組無用的項。
(參考 http://blog.chinaunix.net/uid-27004869-id-3330093.html ,若是想了解詳細,可參考 http://metc.gdut.edu.cn/compile/nandian/n-9.htm)
再來看一下這一段代碼:
int a, b, c;
a = b + c * 60;
在這段代碼下,詞法分析器首先會自動忽略空白字符,如space,tab,換行符,而後將a看作一個詞素,=符號看作一個詞素,b看作一個詞素,以此類推,組成一個詞素序列。
而後,對應的,每一個詞素生成一個詞法單元,如詞素a生成詞法單元<id,1>,1表示a在符號表中條目的位置。id是表示標識符,由於a是變量名,id就是它的標識符,b和c的標識符也是id。因此b,c的詞法單元分別爲<id,2>,<id,3>。但數字60的標識符是number,因此詞法單元爲<number,60>,但通常來講能夠簡寫爲<60>。而符號+,=,* 由於沒有屬性,只需保留名字(通常用詞素自己做爲名字),因此能夠簡單表示爲<+><=><*>。因此,標識符id對應的符號表大概結構以下:
(名字右邊記錄的是類型,值,地址等屬性)
因此最後詞法分析器輸出的詞法單元序列爲:<id,1><+><id,2><+><id,3><*><60>
到這裏,詞法分析簡單的瞭解就結束了。下面咱們具體瞭解它的實現方法。
--------------詞法分析之正則表達式--------------
若是要正確得識別一個詞素,好比if表明的是變量i和變量f,仍是if?判斷詞素有不少種方式。利用正則表達式就是一個。若是對正則表達式不瞭解的同窗能夠看一下這個這個網頁,http://deerchao.net/tutorials/regex/regex.htm , 十分詳細。