KMP算法中关于构造DFA部分的纠结
来源:互联网 发布:linux查看用户和组 编辑:程序博客网 时间:2024/06/15 23:07
在《算法》(Sedgewick)一书中,看到了KMP算法,看了一遍没懂,但觉得挺神奇的,就花费了几个小时深入的理解。
算法的原理其实不难,难的就是那个神奇的DFA数组,我的大部分时间也都是花费在这个数组上面的。
以下从豆瓣读书找来的问题及答案,看着不错,就给抠来了~
出处:http://book.douban.com/subject/19952400/discussion/59623403/
问:
5.3.3.4 构造DFA(p766)
图5.3.8 计算模式ABABAC的重启状态的DFA模拟
没看明白.
以致代码中的:
X = dfa[pat.charAt(j)][X] ;
也不能理解.
答:
dfa[text.charAt(i)][j]是指当文本字符串的字符s[i]与模式字符串的字符p[j]比较后下一次与文本字符串的字符s[i+1]比较的模式字符串的字符位。
当文本字符串的第i位字符与模式字符串的第j位进行匹配时,如果此两位字符匹配,则说明下一步应该为i++ j++之后再比较,也就是说当txt.charAt(i)==pat.charAt(j)时,有dfa[pat.charAt(j)][j]=j+1。
当文本字符串的第i位字符与模式字符串的第j位检测到不匹配时,设txt.charAt(i)==c,c!=pat.charAt(j),但文本字符串的s[i-j...i-1]这部分与模式字符串的p[0...j-1]这部分是匹配的。这时从文本字符串的i-j位置起已不可能出现匹配字符串,现在已不用管s[i-j]字符,现在的问题是依次输入s[i-j+1...i-1]c后会进入什么状态,由于s[i-j...i-1]这部分与模式字符串的p[0...j-1]这部分是匹配的,也就是说现在的问题是依次输入p[1...j-1]c后会进入什么状态。
引入一个状态指示数组X,X[j]是指正确输入p[1...j-1]后进入的状态,输入p[1...j-1]c后进入的状态就是dfa[c][X[j]](在X[j]状态时输入c),即dfa[c][j]=dfa[c][x[j]]。
而计算X[]数组的方法为递推方法:X[j+1]为正确输入p[1...j]后进入的状态,即正确输入p[1...j-1]p[j]后进入的状态,也就是在X[j]状态时输入p[j]时进入的状态,就是dfa[pat.charAt[j]][X[j]],即递推公式为:X[j+1]=dfa[pat.charAt[j]][X[j]],而X[0]手动初始化为0。
由于X[]数组为辅助数据,且为递推的,所以书中仅使用了一个变量X来指示当前的X[j],我觉得理解起来很不方便,所以这里由数组代替。
PS:看着这里,我还是糊里糊涂的,这个X的计算总是理解不了~哎~
- KMP算法中关于构造DFA部分的纠结
- KMP算法 (c++ 构造完整的DFA)
- 编译原理中正则表达式直接构造DFA,DFA的最小化算法
- 编译原理中正则表达式直接构造DFA,DFA的最小化算法
- (一)KMP算法的DFA解法
- 基于dfa的kmp算法思想
- 从DFA角度理解KMP算法
- KMP算法DFA方式实现解析
- 查找-基于DFA的KMP字符串匹配
- <转>KMP算法中关于next数组的探究
- KMP算法中关于next数组的探究
- 关于KMP算法中next函数的详细解析
- KMP算法中关于next数组的探究
- 关于KMP算法的理解
- 关于KMP算法的理解
- 部分KMP算法
- 关于继承的纠结
- 关于触发器的纠结
- JavaScript技巧小招数
- android——不错的网络编程知识
- Android 网络通信框架Volley简介(Google IO 2013)
- mysql基本指令
- FORM表单重复提交问题解决方法
- KMP算法中关于构造DFA部分的纠结
- SIFT-sift.m
- .NET下的内存分配机制
- 博客生涯新的开始
- 浮点数的表示
- Sephiroth Python 分割文件以及合并文件
- Recursive class initialization in Java
- Eclipse下安装GEF和AmaterasUML
- 常用正则表达式积累