LOJ103 子串查找
阿新 • • 發佈:2019-01-27
大寫 gist 模板題 大寫字母 字符串 getc 復雜度 bits base
題意
這是一道模板題。
給定一個字符串 A 和一個字符串 B ,求 B 在 A 中的出現次數。A 和 B 中的字符均為英語大寫字母或小寫字母。
A 中不同位置出現的 B 可重疊。
分析
參照jklover的題解。
此題用hash做的話,只需求出字符串b的hash值,在字符串a中O(n)枚舉每個長度等於|b|的子串,判斷hash值是否相等即可.
時間復雜度:線性。
代碼
#include<bits/stdc++.h> #define rg register #define il inline #define co const template<class T>il T read() { rg T data=0; rg int w=1; rg char ch=getchar(); while(!isdigit(ch)) { if(ch=='-') w=-1; ch=getchar(); } while(isdigit(ch)) { data=data*10+ch-'0'; ch=getchar(); } return data*w; } template<class T>il T read(rg T&x) { return x=read<T>(); } typedef unsigned long long ull; co int N=1e6+1; co ull Base=233; ull Hash[N],Pow[N]; char a[N],b[N]; int n,m; ull calchash(int l,int len) { return Hash[l+len-1]-Hash[l-1]*Pow[len]; } int main() { // freopen(".in","r",stdin); // freopen(".out","w",stdout); scanf("%s%s",a+1,b+1); n=strlen(a+1),m=strlen(b+1); ull hashb=0; for(int i=1;i<=m;++i) hashb=hashb*Base+b[i]; Pow[0]=1; for(int i=1;i<=n;++i) { Hash[i]=Hash[i-1]*Base+a[i]; Pow[i]=Pow[i-1]*Base; } int ans=0; for(int i=1;i+m-1<=n;++i) if(calchash(i,m)==hashb) ++ans; printf("%d\n",ans); return 0; }
LOJ103 子串查找