• <ins id="pjuwb"></ins>
    <blockquote id="pjuwb"><pre id="pjuwb"></pre></blockquote>
    <noscript id="pjuwb"></noscript>
          <sup id="pjuwb"><pre id="pjuwb"></pre></sup>
            <dd id="pjuwb"></dd>
            <abbr id="pjuwb"></abbr>
            隨筆-341  評(píng)論-2670  文章-0  trackbacks-0

                這篇文章的代碼所描述的算法在這里有詳細(xì)的說明。

                Epsilon-NFA到NFA的目標(biāo)主要是產(chǎn)生一個(gè)沒有Epsilon邊的,跟原狀態(tài)圖等價(jià)的新狀態(tài)圖。過程不復(fù)雜,首先從起始狀態(tài)開始,尋找所有Epsilons邊到達(dá)的對(duì)象的集合,然后復(fù)制這個(gè)集合的所有狀態(tài)包含的非Epsilon狀態(tài)。其實(shí)狀態(tài)做完之后,尋找所有能夠產(chǎn)生非Epsilon邊的狀態(tài)然后重復(fù)這個(gè)過程,最后NFA就出來了。代碼如下:

             1         Automaton::Ref EpsilonNfaToNfa(Automaton::Ref source, bool(*epsilonChecker)(Transition*))
             2         {
             3             Automaton::Ref target=new Automaton;
             4             Dictionary<State*, State*> stateMap;
             5             Dictionary<State*, State*> reverseStateMap;
             6             List<State*> epsilonStates;
             7             stateMap.Add(source->startState, target->NewState());
             8             reverseStateMap.Add(stateMap[source->startState], source->startState);
             9             target->startState=target->states[0].Obj();
            10             CopyFrom(target->captureNames.Wrap(), source->captureNames.Wrap());
            11 
            12             for(int i=0;i<target->states.Count();i++)
            13             {
            14                 State* targetState=target->states[i].Obj();
            15                 State* sourceState=reverseStateMap[targetState];
            16                 if(sourceState->finalState)
            17                 {
            18                     targetState->finalState=true;
            19                 }
            20                 epsilonStates.Clear();
            21                 epsilonStates.Add(sourceState);
            22 
            23                 for(int j=0;j<epsilonStates.Count();j++)
            24                 {
            25                     State* currentState=epsilonStates[j];
            26                     for(int k=0;k<currentState->transitions.Count();k++)
            27                     {
            28                         Transition* transition=currentState->transitions[k];
            29                         if(epsilonChecker(transition) && !epsilonStates.Contains(transition->target))
            30                         {
            31                             if(transition->target->finalState)
            32                             {
            33                                 targetState->finalState=true;
            34                             }
            35                             epsilonStates.Add(transition->target);
            36                         }
            37                     }
            38                 }
            39                 
            40                 for(int j=0;j<epsilonStates.Count();j++)
            41                 {
            42                     State* epsilonState=epsilonStates[j];
            43                     for(int k=0;k<epsilonState->transitions.Count();k++)
            44                     {
            45                         Transition* nonEpsilonTransition=epsilonState->transitions[k];
            46                         if(!epsilonChecker(nonEpsilonTransition))
            47                         {
            48                             if(!stateMap.Keys().Contains(nonEpsilonTransition->target))
            49                             {
            50                                 stateMap.Add(nonEpsilonTransition->target, target->NewState());
            51                                 reverseStateMap.Add(stateMap[nonEpsilonTransition->target], nonEpsilonTransition->target);
            52                             }
            53                             Transition* newTransition=target->NewTransition(targetState, stateMap[nonEpsilonTransition->target]);
            54                             newTransition->capture=nonEpsilonTransition->capture;
            55                             newTransition->index=nonEpsilonTransition->index;
            56                             newTransition->range=nonEpsilonTransition->range;
            57                             newTransition->type=nonEpsilonTransition->type;
            58                         }
            59                     }
            60                 }
            61             }
            62             return target;
            63         }

                我們來看一個(gè)例子:(/+|-)?/d+(./d+)?

               
            這是一個(gè)判斷一個(gè)字符串是不是小數(shù)的正則表達(dá)式,首先是Epsilon-NFA:
             1 [START]State<0>
             2     To State<2> : <Epsilon>
             3     To State<4> : <Epsilon>
             4     To State<1> : <Epsilon>
             5 State<1>
             6     To State<6> : <Epsilon>
             7 State<2>
             8     To State<3> : <Char : 43[+- 43[+]>
             9 State<3>
            10     To State<1> : <Epsilon>
            11 State<4>
            12     To State<5> : <Char : 45[-- 45[-]>
            13 State<5>
            14     To State<1> : <Epsilon>
            15 State<6>
            16     To State<7> : <Char : 48[0- 57[9]>
            17 State<7>
            18     To State<8> : <Epsilon>
            19     To State<10> : <Epsilon>
            20 State<8>
            21     To State<9> : <Char : 48[0- 57[9]>
            22 State<9>
            23     To State<7> : <Epsilon>
            24 State<10>
            25     To State<11> : <Char : 46[.] - 46[.]>
            26     To State<13> : <Epsilon>
            27 State<11>
            28     To State<12> : <Epsilon>
            29 State<12>
            30     To State<13> : <Char : 48[0- 57[9]>
            31 [FINISH]State<13>
            32     To State<14> : <Epsilon>
            33 State<14>
            34     To State<15> : <Char : 48[0- 57[9]>
            35 State<15>
            36     To State<13> : <Epsilon>
            37 

                然后是NFA,也就是今天這個(gè)算法的結(jié)果:
             1 [START]State<0>
             2     To State<1> : <Char : 43[+- 43[+]>
             3     To State<2> : <Char : 45[-- 45[-]>
             4     To State<3> : <Char : 48[0- 57[9]>
             5 State<1>
             6     To State<3> : <Char : 48[0- 57[9]>
             7 State<2>
             8     To State<3> : <Char : 48[0- 57[9]>
             9 [FINISH]State<3>
            10     To State<4> : <Char : 48[0- 57[9]>
            11     To State<5> : <Char : 46[.] - 46[.]>
            12     To State<6> : <Char : 48[0- 57[9]>
            13 [FINISH]State<4>
            14     To State<4> : <Char : 48[0- 57[9]>
            15     To State<5> : <Char : 46[.] - 46[.]>
            16     To State<6> : <Char : 48[0- 57[9]>
            17 State<5>
            18     To State<7> : <Char : 48[0- 57[9]>
            19 [FINISH]State<6>
            20     To State<6> : <Char : 48[0- 57[9]>
            21 [FINISH]State<7>
            22     To State<6> : <Char : 48[0- 57[9]>
            23 

                接下來就是NFA到DFA的生成了。
            posted on 2009-10-28 04:34 陳梓瀚(vczh) 閱讀(2381) 評(píng)論(7)  編輯 收藏 引用 所屬分類: VL++3.0開發(fā)紀(jì)事

            評(píng)論:
            # re: Vczh Library++3.0之正則表達(dá)式引擎(Epsilon-NFA到NFA) 2009-11-03 18:34 | SonicLing
            博主的編碼風(fēng)格變了,由Dephi轉(zhuǎn)向C#了。  回復(fù)  更多評(píng)論
              
            # re: Vczh Library++3.0之正則表達(dá)式引擎(Epsilon-NFA到NFA) 2009-12-08 17:38 | 河的第三條岸
            你好,請(qǐng)問把epsilon nfa 轉(zhuǎn)化為 nfa 的意義是什么呢? 這個(gè)算法和子集構(gòu)造算法有什么區(qū)別?謝謝  回復(fù)  更多評(píng)論
              
            # re: Vczh Library++3.0之正則表達(dá)式引擎(Epsilon-NFA到NFA) 2009-12-10 03:42 | 陳梓瀚(vczh)
            @河的第三條岸
            意義在于程序?qū)懫饋砗?jiǎn)單,不知道什么是子集構(gòu)造算法。  回復(fù)  更多評(píng)論
              
            # re: Vczh Library++3.0之正則表達(dá)式引擎(Epsilon-NFA到NFA) 2009-12-10 04:49 | 河的第三條岸
            @陳梓瀚(vczh)
            謝謝回復(fù)。
            子集構(gòu)造算法(powerset construction or subset construction) 是把nfa轉(zhuǎn)為dfa的標(biāo)準(zhǔn)算法。
            我的程序在把正則表達(dá)式編譯成dfa時(shí)速度太慢了(200個(gè)的話要10分鐘左右),所以想把nfa化簡(jiǎn)一下,看到了你的文章,所以想問問你化簡(jiǎn)nfa的方法
              回復(fù)  更多評(píng)論
              
            # re: Vczh Library++3.0之正則表達(dá)式引擎(Epsilon-NFA到NFA) 2009-12-11 09:57 | 陳梓瀚(vczh)
            @河的第三條岸
            最普通的算法,就是記錄所有出現(xiàn)過的nfa狀態(tài)集合。話說沒那么夸張吧,我認(rèn)為是你代碼的問題,不是你算法的問題。  回復(fù)  更多評(píng)論
              
            # re: Vczh Library++3.0之正則表達(dá)式引擎(Epsilon-NFA到NFA) 2009-12-12 00:20 | 河的第三條岸
            @陳梓瀚(vczh)
            謝謝。
            代碼應(yīng)該是有一些問題,我也正在找。但是編譯器的問題也很大,vc,gcc運(yùn)行時(shí)間差異也很大。  回復(fù)  更多評(píng)論
              
            # re: Vczh Library++3.0之正則表達(dá)式引擎(Epsilon-NFA到NFA) 2009-12-12 22:25 | 陳梓瀚(vczh)
            @河的第三條岸
            你要精通各自的優(yōu)化選項(xiàng)  回復(fù)  更多評(píng)論
              
            久久91综合国产91久久精品| 人妻丰满AV无码久久不卡 | 亚洲综合伊人久久大杳蕉| 久久最近最新中文字幕大全| 国产成人久久AV免费| 亚洲国产精品无码久久SM| 久久中文字幕人妻丝袜| 久久久91人妻无码精品蜜桃HD| 久久婷婷国产麻豆91天堂| 久久国产精品久久久| AV狠狠色丁香婷婷综合久久| 999久久久无码国产精品| 久久久久国产精品熟女影院| 久久99精品久久久久子伦| 久久精品无码一区二区无码| 久久国产色AV免费看| 久久国产欧美日韩精品| 国产99久久精品一区二区| 久久精品国产精品青草app| 中文字幕亚洲综合久久2| 国产一区二区精品久久岳| 三级韩国一区久久二区综合| 伊人久久大香线蕉精品不卡| 伊人久久大香线蕉av不变影院| 无码国产69精品久久久久网站| 久久久久无码精品国产不卡| 丁香五月网久久综合| 国产成人精品久久亚洲高清不卡 国产成人精品久久亚洲高清不卡 国产成人精品久久亚洲 | 91精品国产综合久久精品| 久久91精品国产91久久麻豆| 国产精品熟女福利久久AV| 亚洲欧美一级久久精品| 久久久久亚洲av无码专区| 国产精品熟女福利久久AV| 国产成人精品久久| 久久免费精品视频| 婷婷久久综合| 久久99精品国产| 亚洲精品无码久久毛片| 久久无码人妻一区二区三区午夜| 久久免费美女视频|