哈希 字符串匹配 https://loj.ac/problem/103
#include<cstdio>
#include<cstring>
#define ULL unsigned long long
char s[1001000],st[1001000];
ULL pow[1001000],sum[1001000],b=97;
int main()
{
pow[0]=1;
for(int i=1;i<=1000000;i++) pow[i]=pow[i-1]*b;
int n,m;
scanf("%s %s",st+1,s+1);
n=strlen(st+1),m=strlen(s+1);
sum[0]=0;
for(int i=1;i<=n;i++) sum[i]=sum[i-1]*b+(ULL)(st[i]-'A'+1);
ULL ss=0; for(int i=1;i<=m;i++) ss=ss*b+(ULL)(s[i]-'A'+1);
int ans=0;
for(int l=0;l<=n-m;l++)
{
if(ss==sum[l+m]-sum[l]*pow[m]) ans++;
}printf("%d",ans);
return 0;
}
KMP 字符串匹配 https://loj.ac/problem/10043
#include<cstdio>
#include<cstring>
char a[1010],b[1010];
int next[1010];
int main()
{
while(1)
{
scanf("%s",a+1); int la=strlen(a+1); if(a[1]=='#' && la==1) break;
scanf("%s",b+1); int lb=strlen(b+1);
next[1]=0;
for(int i=1,j=0;i<lb;i++)
{
while(j>0 && b[i+1]!=b[j+1]) j=next[j];
if(a[i+1]==b[j+1]) j++;
next[i+1]=j;
}int i=0,j=0,ans=0;
while(i<la){
while(j>0 && a[i+1]!=b[j+1]) j=next[j];
if(a[i+1]==b[j+1]){j++;
if(j==lb) { ans++; j=0; }
}i++;
}printf("%d\n",ans);
}
return 0;
}
字典树 查找最长由给出单词拼接的前缀 https://loj.ac/problem/10053
#include<cstdio>
#include<cstring>
char st[101],t[4001000];
struct node{int son[27];bool end;}tr[1500010];
int len=0,n,l;
void bt(){
int now=0,s;
for(int i=1;i<=l;i++){
s=st[i]-'a';
if(tr[now].son[s]==0) tr[now].son[s]=++len;
now=tr[now].son[s];
}tr[now].end=true;
}
bool flag[4001000];
void find()
{
int now=0,s,ans=0;
for(int i=1;i<=l;i++) flag[i]=false;
flag[0]=true;
for(int i=0;i<=l;i++){
if(flag[i]) ans=i; else continue;
for(int j=i+1;j<=l;j++){
s=t[j]-'a';
now=tr[now].son[s];
if(now==0) break;
if(tr[now].end) flag[j]=true;
}
}printf("%d\n",ans);
}
int main()
{
int n,m;
scanf("%d %d",&n,&m);
for(int i=1;i<=n;i++){
scanf("%s",st+1);
l=strlen(st+1); bt();
}
for(int i=1;i<=m;i++){
scanf("%s",t+1);
l=strlen(t+1); find();
}
return 0;
}
01字典树 求树上最大异或和 树上路径异或和=x到根异或和^y到根异或和
https://loj.ac/problem/10056
#include<cstdio>
#include<cstring>
struct node{int son[2],end;}tr[3200000];
int er[32],len=0;
int maxx(int x,int y) { return x>y?x:y; }
void m_er() { er[0]=1; for(int i=1;i<=30;i++) er[i]=er[i-1]*2; }
int first[100100],blen=0;
struct bian{int y,c,gg;}b[200100];
void ins(int x,int y,int c){
b[++blen].y=y;b[blen].c=c;
b[blen].gg=first[x];
first[x]=blen;
}
int d[100100];
void dfs(int x,int fa){
for(int i=first[x];i>0;i=b[i].gg){
int y=b[i].y;
if(y!=fa){
d[y]=d[x]^b[i].c;
dfs(y,x);
}
}
}
void bt(int x){
int now=0,z,o=x;
for(int i=30;i>=0;i--){
z=o/er[i];
if(z==1) o-=er[i];
if(tr[now].son[z]==0) tr[now].son[z]=++len;
now=tr[now].son[z];
}tr[now].end=x;
}
int find(int x){
int now=0,z,o=x;
for(int i=30;i>=0;i--){
z=o/er[i];
if(z==1) o-=er[i];
if(tr[now].son[1-z]) z=1-z;
now=tr[now].son[z];
}return tr[now].end^x;
}
int main()
{
m_er();
int x,y,c,ans=0,n;
scanf("%d",&n);
for(int i=1;i<n;i++){
scanf("%d %d %d",&x,&y,&c);
ins(x,y,c);ins(y,x,c);
}d[1]=0;dfs(1,0);
for(int i=1;i<=n;i++) bt(d[i]);
for(int i=1;i<=n;i++) ans=maxx(ans,find(d[i]));
printf("%d",ans);
return 0;
}
AC自动机 文章匹配多单词 https://loj.ac/problem/10057
#include<cstdio>
#include<cstring>
char s[60],st[1000100];
struct tree{int son[26],end;}tr[500010];
int len=1,fail[500010];
int t,n,m;
void bt(int l){
int now=0,c;
for(int i=1;i<=l;i++){
c=s[i]-'a';
if(tr[now].son[c]==0) tr[now].son[c]=++len;
now=tr[now].son[c];
}tr[now].end++;
}
void bfs_fail(){
int li[501000],tou=1,wei=1;
int s,now=0;fail[0]=0;
for(int i=0;i<26;i++){
if(tr[now].son[i]!=0){
fail[tr[now].son[i]]=0;
li[wei++]=tr[now].son[i];
}
}
while(tou!=wei){
now=li[tou];
for(int i=0;i<26;i++){
s=tr[now].son[i];
if(s!=0)
{
fail[s]=tr[fail[now]].son[i];
li[wei++]=s;
}else tr[now].son[i]=tr[fail[now]].son[i];
}tou++;
}
}
int find(){
int now=0,ans=0,z;
for(int i=1;i<=m;i++){
z=now=tr[now].son[st[i]-'a'];
while(z>1 && tr[z].end>-1){
if(tr[z].end) ans+=tr[z].end,tr[z].end=-1;
z=fail[z];
}
}return ans;
}
int main()
{
scanf("%d",&t);
while(t--){
scanf("%d",&n);
for(int i=1;i<=n;i++){
scanf("%s",s+1);
bt(strlen(s+1));
}
bfs_fail();
scanf("%s",st+1);m=strlen(st+1);
printf("%d\n",find());
for(int i=1;i<=500000;i++){
tr[i].end=0;for(int j=0;j<26;j++) tr[i].son[j]=0;
}
}
return 0;
}