Next 值与 Nextval 值的计算

KMP算法对模式串求解其Next值和Nextval值的计算方法



模式串S = “abaabcac” ,求其 Next 数值序列

12345678
abaabcac

Next值的计算

Next值的计算,首先将串的字符进行标号,如下:
第一位的Next值为 0
第二位的Next值为 1

12345678
abaabcac
01122312

方法一

标准求解方法

  • 第三位:前一位(第二位)的Next值为1 → 1对应的标号1的字符为a → (第二位)的字符b与标号1的字符a不同 → 但无法再找前一位匹配 → 所以第三位是 1

  • 第四位:前一位(第三位)的Next值为1 → 对应标号字符为a → (第三位)的字符a与标号1的字符a相同 → 第四位Next值为第三位的Next值+1 = 2

  • 第五位:前一位(第四位)的Next值为2 → 对应标号字符为b → (第四位)的字符a与标号2的字符b不同 → b的Next值为1 → 对应标号字符aa与(第四位)字符相同 → 第五位Next 值为第二位 b Next值1+1=2

  • 第六位:前一位(第五位)的Next值为2 → 对应标号字符为b → (第五位)的字符b与标号2的字符b相同 → 第六位Next值为第五位的Next值+1 = 3

  • 第七位:前一位(第六位)的Next值为3 → 对应标号字符为a → (第六位)的字符c与标号3的字符a不同 → a的Next值为1 → 对应标号字符aa与(第六位)字符不同 → 但由于已经匹配到头 → 第七位的Next 值为1

  • 第八位:前一位(第七位)的Next值为1 → 对应标号字符为a → (第七位)的字符a与标号1的字符a相同 → 第八位Next值为第七位的Next值+1 = 2

方法二

刷题时遇到的别人的解法,感觉很不错,记录一下
简述:Next 值就是字符串s的最长相同前缀后缀子字符串的长度

12345
babab
01

首先前两位0、1 是固定不变的

  • 第三位:字符串是"bab",前缀有b, ba;后缀有ab,b,前后缀相等的最长字符串为b,长度为1,所以第三位Next值为1

  • 第四位:字符串"baba",前缀有b, ba, bab;后缀有aba, ba, a,前后缀相等的最长字符串为ba,长度为2,所以第三位Next值为2

  • 第五位:字符串"babab",前缀有b, ba, bab, baba;后缀有abab, bab, ab, b,前后缀相等的最长字符串为bab,长度为3,所以第三位Next值为3

注:经验证:使用方法二算出的S = "abaabcac"的Next值与使用方法一得到的值不同,所以方法二的正确性待确定

Nextval值的计算

Nextval是对Next的优化


简述: NextVal值就是字符串s的的最长相同且满足后续字符不同的前缀和后缀子字符串的长度。

上述字符串计数时时从1开始计数,那么从零开始的呢?

  • 首先可以看到从 1 开始的,其 Next 值为:
i123456789
sababaabab
Next[i]012234234
  • 然后从 0 开始的,Next 值为:
i012345678
sababaabab
Next[i]-100123123
Nextval[i]-10-10-130-10

注意:可以看出,Next 值并不是第一个求得的值依次减一所对应的。

C2CrrD.jpg

过程详述

  • Nextval[0] = -1 ,和Next[0]的值一样

  • Nextval[1] ,Next[1] = 0 , s[0] = a ,a ≠ b(s[1]),则Nextval[1] = Next[1] = 0

  • Nextval[2] ,Next[2] = 0 , s[0] = a ,a = a(s[2]),则Nextval[1] = Nextval[0] = -1

  • Nextval[3] ,Next[3] = 1 , s[1] = b ,b = b(s[3]),则Nextval[3] = Nextval[1] = 0

  • Nextval[4] ,Next[4] = 2 , s[2] = a ,a = a(s[4]),则Nextval[4] = Nextval[2] = -1

  • Nextval[5] ,Next[5] = 3 , s[3] = b ,b ≠ a(s[5]),则Nextval[5] = Next[5] = 3

  • Nextval[6] ,Next[6] = 1 , s[1] = b ,b = b(s[6]),则Nextval[6] = Nextval[1] = 0

  • Nextval[7] ,Next[7] = 2 , s[2] = a ,a = a(s[7]),则Nextval[7] = Nextval[2] = -1

  • Nextval[8] ,Next[8] = 3 , s[3] = b ,b = b(s[8]),则Nextval[8] = Nextval[3] = 0

  • 74
    点赞
  • 338
    收藏
    觉得还不错? 一键收藏
  • 10
    评论
模式串"abaabcac"的next数组为: |下标$i$ | 0 | 1 | 2 | 3 | 4 | 5 | 6 | 7 | |:-----:|:-:|:-:|:-:|:-:|:-:|:-:|:-:|:-:| | 字符串 | a | b | a | a | b | c | a | c | | next | -1| 0 | 0 | 1 | 1 | 2 | 0 | 1 | next数组的计算方法如下: - 求出模式串中每个位置的前缀和后缀交集的最大长度,即以该位置为结尾的最长相同前缀和后缀的长度; - 第一个位置的next定义为-1; - 从第二个位置开始,依次计算每个位置的next计算公式为:$next[i] = k$,其中$k$表示以第$i$个字符为结尾的最长相同前缀和后缀的长度,如果不存在这样的$k$,则令$next[i] = -1$。 对于模式串"abaabcac",计算过程如下: - $next[0] = -1$,因为第一个字符没有前缀和后缀; - $next[1] = 0$,因为以第二个字符为结尾的最长相同前缀和后缀的长度为0; - $next[2] = 0$,因为以第三个字符为结尾的最长相同前缀和后缀的长度为0; - $next[3] = 1$,因为以第四个字符为结尾的最长相同前缀和后缀为"a",长度为1; - $next[4] = 1$,因为以第五个字符为结尾的最长相同前缀和后缀为"ab",长度为1; - $next[5] = 2$,因为以第六个字符为结尾的最长相同前缀和后缀为"abc",长度为2; - $next[6] = 0$,因为以第七个字符为结尾的最长相同前缀和后缀的长度为0; - $next[7] = 1$,因为以第八个字符为结尾的最长相同前缀和后缀为"c",长度为1。 因此,模式串"abaabcac"的next数组为$[-1, 0, 0, 1, 1, 2, 0, 1]$。 需要注意的是,next数组的计算方法是用于KMP算法中的,而nextval数组是用于BM算法中的,两者的计算方法有所不同。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 10
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值