我有问题“描述每个步骤”来自正则表达式创建NFA时。 现在的问题如下:
转换下面的正则表达式的非确定性无限状态自动机(NFA),清楚地描述了使用算法的步骤:(B | A)* B(A | B)
我做了一个简单的3个状态机,但是这是非常从直觉。 这是从我的讲师,谁也写汤普森的算法的说明中写了一个过去的考试问题: http://www.cs.may.ie/staff/jpower/Courses/Previous/parsing/node5.html
任何人都可以清理如何“清晰地描述每一步”? 这似乎只是一套基本规则,而不是要遵循的步骤的算法。
也许有一个算法我已经掩盖了地方,但到目前为止,我刚刚创建他们的猜测。
短版的一般方法。
这里有一个算法中在那里叫汤普森 - 麦克诺顿山田构造算法或有时只是“汤普森建设。” 一个建立中间的NFA,填充在沿途的片,同时尊重操作者的优先级:第一括号,然后Kleene星(例如,*),然后级联(例如,AB),然后交替(例如,A | B)。
这里有一个深入的演练建筑(B | A)* B(A | B)的NFA
大厦顶层
处理括号。 注意:在实际应用中,它可以是有意义的经由其内容的递归调用处理括号。 为了清楚起见,我将推迟括号内的任何评价。
克林星:只有一个*那里,所以我们建立称为P的占位符克莱尼明星机(后包含B | A)。 中间结论:
级联:附加P至B,并附加b键称为Q(其中将包含(一个占位符机| b)中间体结果:
有括号外没有轮换,所以我们跳过它。
现在,我们坐在一个P * BQ机器上。 (请注意,我们的占位符P和Q都只是连接的机器)。我们与NFA替换P边缘为B | A,并更换与NFA将q边缘的|通过上述步骤递归应用B。
大厦P
跳跃。 没有括号。
跳跃。 没有克莱尼明星。
跳跃。 没有contatenation。
构建交替机B | A。 中间结论:
整合有P
接下来,我们回到那个P * BQ机,我们撕出在P边缘。 我们在P边缘的来源作为在P机的起始状态, 和P边缘的目的地作为在P机的目标状态。 我们还作出这样的状态拒绝(带走它被接受状态属性)。 结果如下:
建筑Q
跳跃。 没有括号。
跳跃。 没有克莱尼明星。
跳跃。 没有contatenation。
构建交替机器A | B。 顺便说一下,在交替是可交换的,因此A | B在逻辑上等同于B | A。 (阅读:跳过这个小注脚图出于懒惰。)
集成Q
我们做什么我们做了与上述P,除与intermedtae B更换将q边缘|机器我们构建。 这是结果:
田田! 呃,我的意思是,QED。
想知道更多?
所有的图像上面的使用产生了一个在线工具用于自动转换正则表达式来非确定性有限自动机 。 你可以找到它的汤普森-麦克诺顿山田建设算法的源代码在网上。
该算法还讨论了在阿霍的编译原理,技术和工具 ,但其解释是实现细节稀疏。 您也可以借鉴在C汤普森建设的实现由优秀拉斯考克斯,谁在大约一个流行的文章描述它的一些细节正则表达式匹配 。
在下面的GitHub的库中,你可以找到一个Java的实现,其中第一个被从正则表达式创建了一个NFA,然后输入字符串正在针对NFA匹配汤普森的建设:
https://github.com/meghdadFar/regex