意甲冠军:

到原始字符串。给n字符串,每个字符串都有一个属性,属性0代表重叠,1代表不能重叠

请各多少次出现的字符串

思维:

为了便于建立两台机器自己主动(0一个。1一个)

然后,它可以重叠非常好做,谁做

不可重叠的话须要记录两个东西

len[i]代表每一个串的长度,used[i]代表每一个串在之前出现的位置,初始化-1

然后遍历到的时候对于当前位置 j。 必须j>=used[i]+len[i] 才干算出现。而且更新

须要注意的是:

会出现相同属性而且相同的串。

我处理的方式就是排序。按id排序大的在前

然后算一遍大的,用大的赋值给id 小的且串同样的。

代码:

#include"cstdlib"
#include"cstdio"
#include"cstring"
#include"cmath"
#include"queue"
#include"algorithm"
#include"iostream"
using namespace std;
char fuck[123456];
int ans[123456],used[123456],len[123456];
struct word
{
int x,id;
char y[7];
} dc[123456];
struct trie
{
int mark;
trie *next[27];
trie *fail;
trie()
{
mark=0;
memset(next,0,sizeof(next));
fail=NULL;
}
};
trie *root0,*root1;
void init(int key,char *v,int id)
{
trie *p;
if(key) p=root1;
else p=root0;
for(int i=0; v[i]; i++)
{
int tep=v[i]-'a';
if(p->next[tep]==NULL) p->next[tep]=new trie();
p=p->next[tep];
}
p->mark=id;
}
void del(trie *p)
{
for(int j=0; j<26; j++) if(p->next[j]!=NULL) del(p->next[j]);
free(p);
}
void getac()
{
queue<trie*>q;
q.push(root0);
while(!q.empty())
{
trie *p,*tep;
p=q.front();
q.pop();
for(int i=0; i<26; i++)
{
if(p->next[i]!=NULL)
{
if(p==root0) p->next[i]->fail=root0;
else
{
tep=p->fail;
while(tep!=NULL)
{
if(tep->next[i]!=NULL)
{
p->next[i]->fail=tep->next[i];
break;
}
tep=tep->fail;
}
if(tep==NULL) p->next[i]->fail=root0;
}
q.push(p->next[i]);
}
}
}
q.push(root1);
while(!q.empty())
{
trie *p,*tep;
p=q.front();
q.pop();
for(int i=0; i<26; i++)
{
if(p->next[i]!=NULL)
{
if(p==root1) p->next[i]->fail=root1;
else
{
tep=p->fail;
while(tep!=NULL)
{
if(tep->next[i]!=NULL)
{
p->next[i]->fail=tep->next[i];
break;
}
tep=tep->fail;
}
if(tep==NULL) p->next[i]->fail=root1;
}
q.push(p->next[i]);
}
}
}
}
void finde(char *v)
{
trie *p0=root0,*p1=root1;
for(int i=0; v[i]; i++)
{
int tep=v[i]-'a';
while(p0->next[tep]==NULL && p0!=root0)
p0=p0->fail;
p0=p0->next[tep];
if(p0==NULL) p0=root0;
trie *q0=p0;
while(q0!=root0)
{
if(q0->mark!=0) ans[q0->mark]++;
q0=q0->fail;
}
while(p1->next[tep]==NULL && p1!=root1)
p1=p1->fail;
p1=p1->next[tep];
if(p1==NULL) p1=root1;
trie *q1=p1;
while(q1!=root1)
{
if(q1->mark!=0)
{
if(i>=used[q1->mark]+len[q1->mark]) //不可重叠的推断
{
ans[q1->mark]++;
used[q1->mark]=i;
}
}
q1=q1->fail;
}
}
}
int cmp(word a,word b) //排序的cmp
{
if(a.x==b.x)
{
if(strcmp(a.y,b.y)==0)
{
if(a.id>b.id) return 1;
else return 0;
}
else
{
if(strcmp(a.y,b.y)>0) return 1;
else return 0;
}
}
else
{
if(a.x>b.x) return 1;
else return 0;
}
}
int main()
{
int cas=1;
while(scanf("%s",fuck)!=-1)
{
int n;
scanf("%d",&n);
root0=new trie();
root1=new trie();
for(int i=1; i<=n; i++)
{
int x;
char y[12];
scanf("%d%s",&x,y);
len[i]=strlen(y);
init(x,y,i);
dc[i].x=x;
strcpy(dc[i].y,y);
dc[i].id=i;
}
memset(ans,0,sizeof(ans));
memset(used,-1,sizeof(used));
getac();
finde(fuck);
sort(dc+1,dc+1+n,cmp);
int i;
for(i=1; dc[i+1].x==1; i++) //赋值给那些反复的
{
if(strcmp(dc[i].y,dc[i+1].y)==0)
ans[dc[i+1].id]=ans[dc[i].id];
}
for(i=i+1; i<n; i++)
{
if(strcmp(dc[i].y,dc[i+1].y)==0)
ans[dc[i+1].id]=ans[dc[i].id];
}
printf("Case %d\n",cas++);
for(int i=1; i<=n; i++) printf("%d\n",ans[i]);
del(root0);
del(root1);
puts("");
}
return 0;
}

版权声明:本文博客原创文章,博客,未经同意,不得转载。

[AC自己主动机] zoj Searching the String的更多相关文章

  1. ZOJ 3228 Searching the String (AC自己主动机)

    题目链接:Searching the String 解析:给一个长串.给n个不同种类的短串.问分别在能重叠下或者不能重叠下短串在长串中出现的次数. 能重叠的已经是最简单的AC自己主动机模板题了. 不能 ...

  2. ZOJ - 3228 Searching the String (AC自己主动机)

    Description Little jay really hates to deal with string. But moondy likes it very much, and she's so ...

  3. zoj 3430 Detect the Virus(AC自己主动机)

    Detect the Virus Time Limit: 2 Seconds      Memory Limit: 65536 KB One day, Nobita found that his co ...

  4. ZOJ 3494 BCD Code (AC自己主动机 + 数位DP)

    题目链接:BCD Code 解析:n个病毒串.问给定区间上有多少个转换成BCD码后不包括病毒串的数. 很奇妙的题目. . 经典的 AC自己主动机 + 数位DP 的题目. 首先使用AC自己主动机,得到b ...

  5. AC自己主动机

    AC自己主动机 AC自己主动机是KMP和Trie的结合,主要处理多模板串匹配问题.以下推荐一个博客,有助于学习AC自己主动机. NOTONLYSUCCESS  这里另一个Kuangbin开的比赛,大家 ...

  6. POJ 2778 DNA Sequence (AC自己主动机 + dp)

    DNA Sequence 题意:DNA的序列由ACTG四个字母组成,如今给定m个不可行的序列.问随机构成的长度为n的序列中.有多少种序列是可行的(仅仅要包括一个不可行序列便不可行).个数非常大.对10 ...

  7. 【UVA】1449-Dominating Patterns(AC自己主动机)

    AC自己主动机的模板题.须要注意的是,对于每一个字符串,须要利用map将它映射到一个结点上,这样才干按顺序输出结果. 14360841 1449 option=com_onlinejudge& ...

  8. POJ 3691 &amp; HDU 2457 DNA repair (AC自己主动机,DP)

    http://poj.org/problem?id=3691 http://acm.hdu.edu.cn/showproblem.php?pid=2457 DNA repair Time Limit: ...

  9. HDU 2896 病毒侵袭 AC自己主动机题解

    本题是在text里面查找key word的增强版.由于这里有多个text. 那么就不能够简单把Trie的叶子标志记录改动成-1进行加速了,能够使用其它技术.我直接使用个vis数组记录已经訪问过的节点, ...

随机推荐

  1. 【codeforces 755A】PolandBall and Hypothesis

    time limit per test2 seconds memory limit per test256 megabytes inputstandard input outputstandard o ...

  2. php如何实现读取网易有道词典输出单词的xml格式并且转化为html形式

    php实现读取网易有道词典输出单词的xml格式并且转化为html形式 一.总结 一句话总结:将xml中的文件用preg_match_all读出来,然后组合成想要的数据 1.explode除了爆炸的意思 ...

  3. 怎么实现登录之后跳转到登录之前的页面?SpringMVC+Freemarker

    项目中,想实现一个功能. 直接访问某个需要登录的url,比如/addArticle,可能会跳转到登录页面login.html. 登录成功之后,自动跳转到/addArticle这个登录前的页面,继续登录 ...

  4. 简单sql部分强化练习题

    简单查询部分sql练习题 -- 选择部门30中的全部职工 select * from emp where deptno = 30; -- 列出全部业务员(CLERK)的姓名,编号,和部门编号 sele ...

  5. js进阶 9-15 多选框如何限制选中数目

    js进阶 9-15 多选框如何限制选中数目 一.总结 一句话总结: 1.多选框如何限制选中数目? 没点击选择一次,来统计现在总共选了多少个,如果超出,就给onclick事件返回false,取消oncl ...

  6. js进阶 9-6 js如何通过name访问指定指定表单控件

    js进阶 9-6 js如何通过name访问指定指定表单控件 一.总结 一句话总结:form中控件的三种访问方式:2formElement 1document 1.form中控件的三种访问方式? 1.f ...

  7. 更改MyEclipse编辑框的背景颜色

    更改MyEclipse编辑框的背景颜色 1.未改动之前.编辑框背景色 2.依次操作,"Window--->Preferences" 3.选择"General---& ...

  8. 网站多语言转换.利用Google 语言的js.贴到网站就能用.

    <div id="google_translate_element"></div><script>function googleTranslat ...

  9. TCP可靠的传输机制

    TCP提供一种面向连接的.可靠的字节流服务.面向连接意味着两个使用TCP的应用(一般是一个客户和一个server)在彼此交换数据包之前必须先建立一个TCP连接.这一过程与打电话非常相似.先拨号振铃,等 ...

  10. 【22.73%】【codeforces 606D】Lazy Student

    time limit per test2 seconds memory limit per test256 megabytes inputstandard input outputstandard o ...