zoukankan      html  css  js  c++  java
  • [BZOJ2780][SPOJ8093]Sevenk Love Oimaster

    bzoj
    luogu

    题面

    给定n个模板串,以及m个查询串。
    依次查询每一个查询串是多少个模板串的子串。

    sol

    广义后缀自动机裸题?
    先建出(SAM),然后记录一下每个节点分别在多少个模板串里出现过。
    对于询问直接在(SAM)上跑匹配就行了。

    code

    #include<cstdio>
    #include<algorithm>
    #include<iostream>
    #include<cstring>
    using namespace std;
    const int N = 2e5+5;
    int n,m,last=1,tot=1,tr[N][26],fa[N],len[N],cnt[N],vis[N];
    string s[N],ss;
    void extend(int c)
    {
    	int v=last,u=++tot;last=u;
    	len[u]=len[v]+1;
    	while (v&&!tr[v][c]) tr[v][c]=u,v=fa[v];
    	if (!v) fa[u]=1;
    	else{
    		int x=tr[v][c];
    		if (len[x]==len[v]+1) fa[u]=x;
    		else{
    			int y=++tot;
    			memcpy(tr[y],tr[x],sizeof(tr[y]));
    			fa[y]=fa[x];fa[x]=fa[u]=y;len[y]=len[v]+1;
    			while (v&&tr[v][c]==x) tr[v][c]=y,v=fa[v];
    		}
    	}
    }
    int main()
    {
    	ios::sync_with_stdio(false);
    	cin>>n>>m;
    	for (int i=1,l;i<=n;++i)
    	{
    		cin>>s[i];l=s[i].length();
    		last=1;
    		for (int j=0;j<l;++j) extend(s[i][j]-'a');
    	}
    	for (int i=1;i<=n;++i)
    		for (int j=0,l=s[i].length(),now=1;j<l;++j)
    		{
    			now=tr[now][s[i][j]-'a'];
    			int t=now;
    			while (t&&vis[t]!=i) cnt[t]++,vis[t]=i,t=fa[t];
    		}
    	while (m--)
    	{
    		cin>>ss;int l=ss.length(),now=1;
    		for (int i=0;i<l;++i)
    			now=tr[now][ss[i]-'a'];
    		printf("%d
    ",cnt[now]);
    	}
    	return 0;
    }
    
  • 相关阅读:
    JavaScript 操作页面元素
    各系地图坐标互相转换
    手机测试 wamp/appSer
    mvc 过滤器
    MVC 网站发布
    渐变色彩 省略标记 嵌入字体 文本阴影
    边框
    CSS 水平居中总结
    CSS 颜色值 长度值
    CSS 布局模型
  • 原文地址:https://www.cnblogs.com/zhoushuyu/p/8695358.html
Copyright © 2011-2022 走看看