[TJOI2017]DNA --- 后缀数组

Posted ReMoon

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了[TJOI2017]DNA --- 后缀数组相关的知识,希望对你有一定的参考价值。

[TJOI2017]DNA

题目描述

加里敦大学的生物研究所,发现了决定人喜不喜欢吃藕的基因序列S,

有这个序列的碱基序列就会表现出喜欢吃藕的性状,但是研究人员发现对碱基序列S,任意修改其中不超过3个碱基,依然能够表现出吃藕的性状。

现在研究人员想知道这个基因在DNA链\(S_{0}\)上的位置。

所以你需要统计在一个表现出吃藕性状的人的DNA序列\(S_{0}\)上,有多少个子串可能是该基因,

即有多少个\(S_{0}\)的子串修改小于等于三个字母能够变成S。

输入输出格式

输入格式:

第一行有一个数T,表示有几组数据

每组数据第一行一个长度不超过\(10^{5}\)的碱基序列\(S_{0}\)

每组数据第二行一个长度不超过\(10^{5}\)的吃藕基因序列S

 

输出格式:

共T行,第i行表示第i组数据中,在\(S_{0}\)中有多少个与S等长的连续子串可能是表现吃藕性状的碱基序列

 

输入输出样例

输入样例#1: 
 
1
ATCGCCCTA
CTTCA
 
输出样例#1: 
 
2

说明

对于20%的数据,\(S_{0}\),S的长度不超过\(10^{4}\)

对于20%的数据,\(S_{0}\),S的长度不超过\(10^{5}\),0<T<=10

 

作为后缀数组的模板集成题来做的。

首先考虑一个比较容易想到的事情.

\(S_{0}\)大串中存在长度和\(S\)相同的串只有\(n\)个

因此只要一个一个暴力判断就好了。

怎么判断快一点??

比如串‘ACGAC‘和串‘ACAAC‘

前面的‘AC‘相同,因此可以直接调用。

到了‘G‘和‘A‘不同,来一个\(tim\)计数器表示失配了几次,此时,\(tim++\)

接下了后面的‘AC‘相同,因此这个子串和模式串只有一处不同。

可以发现,每当\(tim<=3\)匹配完成一次时,\(ans++\)

那么,怎么得到‘AC‘相同这个过程??

用后缀数组的LCP或者哈希二分LCP或后缀树跑LCP即可

 

后缀数组复杂度\(O(n \log n + n * 6)\) = \(O(n \log n)\)

 

代码在此

以上是关于[TJOI2017]DNA --- 后缀数组的主要内容,如果未能解决你的问题,请参考以下文章

[BZOJ4892][TJOI2017]DNA(后缀数组)

[TJOI2017] DNA

[HEOI2016/TJOI2016]字符串

BZOJ 4556: [Tjoi2016&Heoi2016]字符串(后缀数组 + 二分答案 + 主席树 + ST表 or 后缀数组 + 暴力)

Bzoj4556: [Tjoi2016&Heoi2016]字符串 后缀数组

[LuoguP4094] [HEOI2016] [TJOI2016]字符串(二分答案+后缀数组+ST表+主席树)