接上面那个文章哈,这篇文章是针对于我们通过简单的方法去求解next数组的问题,我们通过暴力for循环的方法求解next数组虽然解决了问题,但是却还仍然有很多的回溯问题,比如我们对abcabcab这个字符串进行处理的时候,第二个b对应的next数组是不是2,则代表着此时遍历到第二个c的位置时,他前面的两个字符与字符串开头的两个字符是相等的,这个时候我们上面的for循环在对第二个c的next的数值进行确定时还应该前缀从第一个位置便利,后缀从第四个位置便利,但是事实上,我们完全可以避免这一操作,直接将c和第三个字符比较,你自己想一想是不是这个道理,这就引起了我们的递归方法,为什么我叫做它递归呢,就是因为我们在确定next的值时需要借助上一个next的值处理才行。
这就引出了我们下面的代码
void getnext(string target_str,int next[])
{
int j=0,k=-1;
next[0]=-1;
while(j<target_str.size())
{
if(k==-1 || str[j]==str[k])
{
j++;
k++;
next[j]=k;
}
else
{
k=next[k];
}
}
}
//怎么去解释这篇代码呢,它是利用了上一次的next的值
//首先我们需要知道next每个位置的值存储的是在子链中这个下标之前的子串的最大前缀和后缀的长度。
void getnext(int next[],sqlist s)
{
next[0]=-1;
int j=0,k=-1;
while(j<s.length)
{
if(k=-1 || s[j]==s[k])
{
j++;
k++;
next[j]=k;
}
else
{
k=next[k]; //是前缀的下标往前移,k既代表下标,又记录了这个next的值
}
}
}
//每个next里面的值存下的都是前面的字符串的最长前后缀的长度
为什么是两篇代码呢,因为第一篇是我借鉴别人的,第二篇是我在本子上的画了一下这个过程理解之后敲下的,感觉相对而言这种方式更好理解一些,大家根据需求自取吧,最好还是自己根据代码画一下这个过程。