3230 相似子串

2022-05-12 09:34:31 字數 1788 閱讀 1135

輸入第1行,包含3個整數n,q。q代表詢問組數。

第2行是字串s。

接下來q行,每行兩個整數i和j。(1≤i≤j)。

輸出共q行,每行乙個數表示每組詢問的答案。如果不存在第i個子串或第j個子串,則輸出-1。

5 3ababa

3 55 9

8 10

1816

-1樣例解釋

第1組詢問:兩個子串是「aba」,「ababa」。f = 32 + 32 = 18。

第2組詢問:兩個子串是「ababa」,「baba」。f = 02 + 42 = 16。

第3組詢問:不存在第10個子串。輸出-1。

資料範圍

n≤100000,q≤100000,字串只由小寫字母'a'~'z'組成

建立字尾陣列,h和pr陣列。。。

查詢字典序為i的串,我們知道以i開頭的不同的字串是n-h[i]-sa[i]那麼就可以二分的尋找i,

然後用線段樹或者st演算法預處理h,pr陣列,然後每次查詢即可。。。

**來自黃學長。。

1 #include2 #include

3 #include4 #include5 #include6 #include7 #include8 #include9

#define inf 1000000000

10#define ll long long

11using

namespace

std;

12ll read()

1316

while(ch>='

0'&&ch<='9')

17return x*f;18}

19int n,m,log[100005

];20

char ch[100005

];21

struct

sa28

void mul(int *sa,int *rk,int *sa,int *rk)

36void

getsa()50}

51void

pre()

63int query(int a,int

b)69

void

print()

72}a,b;

73int

main()

7483 id=lower_bound(a.s+1,a.s+n+1,l)-a.s;

84 a1=a.sa[a.p][id];

85 b1=a.sa[a.p][id]+a.h[id]-1+l-a.s[id-1

];86 id=lower_bound(a.s+1,a.s+n+1,r)-a.s;

87 a2=a.sa[a.p][id];

88 b2=a.sa[a.p][id]+a.h[id]-1+r-a.s[id-1

];89 ll t=(a1==a2)?inf:a.query(a1,a2);

90 t=min(t,min(b1-a1+1,b2-a2+1));ans+=t*t;

91 t=(n-b1+1==n-b2+1)?inf:b.query(n-b1+1,n-b2+1

);92 t=min(t,min(b1-a1+1,b2-a2+1));ans+=t*t;

93 printf("

%lld\n

",ans);94}

95return0;

96 }

view code

bzoj 3230 相似子串

time limit 20 sec memory limit 128 mb submit 1767 solved 438 submit status discuss 輸入第1行,包含3個整數n,q。q代表詢問組數。第2行是字串s。接下來q行,每行兩個整數i和j。1 i j 輸出共q行,每行乙個數表示...

BZOJ 3230 相似子串

給定乙個長度為 n 的字串以及 q 組查詢,每組查詢給定 a 和 b 求在所有本質不同子串中排名第 a 和第 b 的串的最長公共字首與最長公共字尾的平方和.n,q le 1 times 10 5 字尾陣列板子題.麻麻我終於會用字尾陣列辣 本來想接著用sam的.但是發現多組查詢排名為 k 的本質不同子...

BZOJ3230 相似子串

3230 相似子串 time limit 20 sec memory limit 128 mb submit 913 solved 223 submit status description input 輸入第1行,包含3個整數n,q。q代表詢問組數。第2行是字串s。接下來q行,每行兩個整數i和j。...