本文是對編譯原理中NFA到DFA的轉換作的總結,該代碼參考了編譯原理中詞法分析的相關內容.
閉包
NFA即不肯定有窮狀態機,而DFA是肯定有窮狀態機。spa
從本質上講NFA與利用其構造而成的DFA是等價的,但由於NFA某一狀態離開的路徑可能有多條,所以經常在構造出NFA後將前面的狀態集合作一抽象以構建對於每一狀態離開路徑只有一條的DFA。code
NFA到DFA的構造方法經常使用到兩點,即子集構造法與閉包傳遞.it
1.0-closure(s) 可以從NFA的狀態S開始只經過0轉換到達的NFA的狀態集合 2.0-closure(T) 可以從T中的某個NFA狀態s開始只經過0轉換到達的NFA的狀態集合 3.move(T,a) 可以從T中某個狀態s觸發只經過標號爲a的轉換轉換達到的NFA狀態集合 /**子集構造法*/ NFA-DFA-CONVERT(nfa, dfa) s0 -> nfa的開始狀態 U -> 0-closure(s0) push U into dfa without mark while ( T -> find one in dfa without mark){ mark T; for(every possible intput a) U' -> 0-closure(move(T, a)) if(U' is not in dfa) push U' into dfa without mark set dfa[T, a]->U' } /**計算0-closure(T)的閉包傳遞*/ CLOSURE(T) push all status in T into stack S push all status in T into U while(S is not empty){ t->pop one from S; for(每一個從t狀態能經過空串轉換獲得的狀態U') if(U'不在U中){ push U' into U; push U' into S; } } return U;
總結
dfa的每一個狀態是對nfa狀態集合的二次抽象.以此達到每一個狀態只有一條離開路徑.
編譯