KMP算法本质——DFA匹配

问题描述

字符串匹配。给你两个字符串,寻找其中一个字符串是否包含另一个字符串,如果包含,返回包含的起始位置。
如下面两个字符串:

char *str = "bacbababadababacambabacaddababacasdsd";
char *ptr = "ababaca";

KMP算法

KMP算法的描述复杂,前缀后缀及next[]数组求解十分不直观,实际上该过程就是当ptr前后有相同子字符串,如果前面已经匹配成功,则不需要像暴力算法那样将ptr逐字符串往后跳,而可以一次多跳几个,从而加快了匹配速度。
个人认为觉得用KMP算法本质上与DFA匹配完全一样,DFA匹配更容易理解,通过下面的例子用DFA匹配解释该过程。

DFA匹配

DFA

  • 首先根据字符串ptr画出对应发DFA

  • 这里写图片描述

  • 由上图可以看出转换过程,比如进入状态6时候,如果下一个字符是C,则可以进入状态3,相当于KMP算法中将字符串ptr向后挪4位再重新匹配,再比如进入状态3时,如果下一个字符是B,说明要重新开始,进入状态0,相当于KMP中将ptr向后移动3位。

  • 利用自动机的好处是不用考虑挪动字符串等,直接扫描一遍字符串,按照状态就可以知道是否匹配成功。

  • DFA 状态机表示:可以用一个二维数组 dp[j][c]=next,其中 0 <= j < M(ptr的长度) 表示当前所在状态,0 <= c < 256 表示遇到的字符,0 <= next < M 表示下一个转移到的状态。根据 ptr 得到 dp 后可以用该 dp 矩阵指导任意 str 匹配 ptr。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值