计算理论:如何确定给定DFA所接受的语言?
状态标注递归法
给每个状态定义一个集合,代表从该状态出发能走到接受状态的所有串。然后根据状态转移规则,写出每个集合的递归表达式,最后解这些表达式得到正则语言。
比如:设S(q)是从状态q出发可到达接受状态的串集合,起始状态q0,接受状态qf。如果q0读0到q0,读1到q1;q1读0到qf,读1到q0;qf读任意字符都留在qf,那就能写出:S(q0) = 0S(q0) + 1S(q1) S(q1) = 0S(qf) + 1S(q0) S(qf) = ε + 0S(qf) + 1S(qf)解这些式子就能得到最终的语言描述。
状态含义归纳法
先分析每个状态对应的“特征”:比如有的状态记录已读1的个数是奇数还是偶数,有的记录是否已经出现过至少两个1,或者已读0的数量模某个数的值。
结合你已经发现的规律——含单个1的串不被接受、q0接任意0仍在q0,可以先给每个状态标注它代表的特征:比如q0可能是“1的个数为0,或者1的个数≥2且满足某个后续条件”,q1可能是“1的个数为1”,再看转移规则里每个字符会怎么改变这个特征,进而总结接受串的规律。反例归纳验证法
除了找被接受的串,多找不被接受的串,总结它们的共性,反过来推导接受串的规则。
比如你已经知道单个1的串不被接受,那再看10、100这类串是否被拒绝,11、101是否被接受,对比两者的差异,就能缩小规律范围,再用更多例子验证。状态消除法生成正则表达式
把DFA的状态转移图逐步简化:每次移除一个中间状态(非起始、非接受状态),把所有经过这个状态的路径合并成直接转移的正则表达式。
比如有状态q0→q1→q2、q0→q2,移除q1后,q0到q2的转移就变成“q0到q1的字符 +q1到q2的字符的闭包”加上原来的直接转移,直到只剩起始和接受状态,最后得到的表达式就是语言的正则描述。
内容的提问来源于stack exchange,提问作者dthnick

