后缀数组学习笔记--height数组

显然单一个后缀数组是没有什么软用的,加上height才有用。。

height[i]表示sa[i]和sa[i-1]的最长公共前缀,这东西求起来快同时好用,主要有三条性质:

定义LCP(i,j)=lcp(Suffix(SA[i]),Suffix(SA[j])。

1.对任意1<=i<j<k<=n,LCP(I,k)=min{LCP(I,j),LCP(j,k)}

2.设i<j,LCP(i,j)=min{LCP(k-1,k)|i+1<=k<=j}  (是由1的推论)

求出1.2两性质可得,计算LCP(I,j)等同于询问一维数组height中下标在i+1到j范围内的所有元素的最小值。如果height数组是固定的,这就是求区间最小,随便st表搞一下就可以。(1.2两性质主要决定它的用处)

3.设h[i]=height[Rank[i]](其实h[i]就是说下标为i的位置的height),那么对于i>1且Rank[i]>1,一定有h[i]>=h[i-1]-1。(这一性质决定了h数组能在O(n)的时间内快速求出,而h数组和height关系就如同sa和rnk,也是互逆的)

具体求法:

若Rank[i]=1,则h[i]=0。字符比较次数为0.

 若i=1或者h[i-1]<=1,则直接将Suffix(i)和Suffix(Rank[i]-1)从第一个字符开始依次比较直到有字符不同,由此算出h[i]。

 否则,说明i>1,Rank[i]>1,h[i-1]>1,根据性质3,Suffix(i)和Suffix(Rank[i]-1)至少有前h[i-1]-1个字符是相同的,于是字符比较可以从h[i-1]开始,直到某个字符不相同,由此计算出h[i]。

参考资料:https://www.cnblogs.com/ECJTUACM-873284962/p/6618870.html

代码:(短的飞起)

int k=0;
for(int i=1,j;i<=n;i++)
{
	if(rnk[i]==1){ht[1]=k=0;continue;}
	if(k)--k;j=sa[rnk[i]-1];
	while(i+k<=n&&j+k<=n&&s[i+k]==s[j+k])++k;
	ht[rnk[i]]=k;
}

 

 

  • 1
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值