CH138 兔子和兔子 题解报告
【题目大意】
给定一个字符串$S$,有$m$次询问,每次询问给出四个整数$l1,r1,l2,r2$,判断$S[l1~r1]$是否与$S[l2~r2]$相同。
【思路分析】
$Hash$板子题
$hsh[i]$表示从$S[1]$到$S[i]$的字符串的$Hash$值,然后要求$S[l~r]$的$Hash$值则$hsh[r]-hsh[l-1]*base^{r-l+1}$,要注意一点就是如果用了$unsigned\ long\ long$就不要再加膜运算了。
【代码实现】
1 #include<cstdio> 2 #include<iostream> 3 #include<cstring> 4 #include<algorithm> 5 #include<cmath> 6 #include<queue> 7 #define g() getchar() 8 #define rg register 9 #define go(i,a,b) for(rg int i=a;i<=b;i++) 10 #define back(i,a,b) for(rg int i=a;i>=b;i--) 11 #define db double 12 #define ll long long 13 #define il inline 14 #define pf printf 15 #define sf scanf 16 #define mem(a,b) memset(a,b,sizeof(a)) 17 using namespace std; 18 int fr(){ 19 int w=0,q=1; 20 char ch=g(); 21 while(ch<'0'||ch>'9'){ 22 if(ch=='-') q=-1; 23 ch=g(); 24 } 25 while(ch>='0'&&ch<='9') w=(w<<1)+(w<<3)+ch-'0',ch=g(); 26 return w*q; 27 } 28 const int N=1000002; 29 const int base=131; 30 const ll mod=20190826270251; 31 int n,m,a[N]; 32 char s[N]; 33 unsigned ll hsh[N],f[N]; 34 int main(){ 35 //freopen("","r",stdin); 36 //freopen("","w",stdout); 37 sf("%s",s+1);n=strlen(s+1); 38 f[0]=1;go(i,1,n) f[i]=f[i-1]*base,a[i]=s[i]-'a';//预处理 39 go(i,1,n) hsh[i]=hsh[i-1]*base+a[i]; 40 m=fr(); 41 while(m--){ 42 rg int l1=fr(),r1=fr(),l2=fr(),r2=fr(); 43 unsigned ll as1=hsh[r1]-hsh[l1-1]*f[r1-l1+1]; 44 unsigned ll as2=hsh[r2]-hsh[l2-1]*f[r2-l2+1]; 45 if(as1==as2) puts("Yes"); 46 else puts("No"); 47 } 48 return 0; 49 }