BZOJ_3012_[Usaco2012 Dec]First!_trie树+拓扑排序

题意:

给定n个总长不超过m的互不相同的字符串,现在你可以任意指定字符之间的大小关系。问有多少个串可能成为字典序最小的串,并输出这些串。n <= 30,000 , m <= 300,000
分析:
首先不考虑大小关系,如果一个串是另一个串的前缀,那么另一个串一定不能成为字典序最小的串,我们可以用trie树很好的解决。
考虑前缀相同的情况,这个串在前缀后的字符应该和含有相同前缀的串在前缀后的字符有明确的大小关系,根据这个大小关系连边,我们用拓扑排序判断是否矛盾。
以上都满足则可以成为字典序最小的串。
代码:
#include <stdio.h>
#include <string.h>
#include <algorithm>
#include <queue>
using namespace std;
#define N 30050
struct A
{
int son[30],end;
}t[N*10];
int n,tot,head[30],to[N],nxt[N],c[30],cnt=1,ans[30010];
char s[30010][310];
void add(int u,int v)
{
to[++cnt]=v;
nxt[cnt]=head[u];
head[u]=cnt;
c[v]++;
}
void insert(int x)
{
int p=1;
int len=strlen(s[x]+1);
for(int i=1;i<=len;i++)
{
int id=s[x][i]-'a'+1;
if(!t[p].son[id])t[p].son[id]=++cnt;
p=t[p].son[id];
}
t[p].end=1;
}
bool search(int x)
{
int p=1;
int len=strlen(s[x]+1);
for(int i=1;i<=len;i++)
{
if(t[p].end)return 0;
int id=s[x][i]-'a'+1;
for(int j=1;j<=26;j++)
{
if(j!=id&&t[p].son[j])
{
add(id,j);
}
}
p=t[p].son[id];
}
return 1;
}
bool topsort()
{
queue <int> q;
for(int i=1;i<=26;i++)if(c[i]==0)q.push(i);
while(!q.empty())
{
int x=q.front();q.pop();
for(int i=head[x];i;i=nxt[i])
{
c[to[i]]--;
if(c[to[i]]==0)q.push(to[i]);
}
}
for(int i=1;i<=26;i++)if(c[i])return 0;
return 1;
}
int main()
{
scanf("%d",&n);
for(int i=1;i<=n;i++)
{
scanf("%s",s[i]+1);
insert(i);
}
for(int i=1;i<=n;i++)
{
memset(head,0,sizeof(head));
memset(c,0,sizeof(c));cnt=0;
if(!search(i))continue;
if(!topsort())continue;
ans[++tot]=i;
}
printf("%d\n",tot);
for(int i=1;i<=tot;i++)
{
printf("%s\n",s[ans[i]]+1);
}
}
 

BZOJ_3012_[Usaco2012 Dec]First!_trie树+拓扑排序的更多相关文章

  1. 「Usaco2012 Dec」第一(字典树+拓扑排序)

    (我恨字符串) 惯例化简题目:给定n个字符串,可以改变字符的相对大小(在字典序中的大小),问:字符串i是否能成为最小的字符串(字典序) 解题过程: 首先你可以预处理出来26的全排列然后暴力然后你只要用 ...

  2. 【BZOJ3012】[Usaco2012 Dec]First! Trie树+拓补排序

    [BZOJ3012][Usaco2012 Dec]First! Description Bessie has been playing with strings again. She found th ...

  3. BZOJ4383 Pustynia(线段树+拓扑排序)

    线段树优化建图暴力拓扑排序即可.对于已确定的数,拓扑排序时dp,每个节点都尽量取最大值,如果仍与已确定值矛盾则无解.叶子连出的边表示大于号,其余边表示大于等于. #include<iostrea ...

  4. 洛谷P3065 [USACO12DEC]第一!First!(Trie树+拓扑排序)

    P3065 [USACO12DEC]第一!First! 题目链接:https://www.luogu.org/problemnew/show/P3065 题目描述 Bessie一直在研究字符串.她发现 ...

  5. Luogu P3065 [USACO12DEC]第一!First!【字典树/拓扑排序】By cellur925

    题意:给你许多字符串,你可以改变字母序大小,问有哪些字符串可能成为字典序最小的字符串. 我们考虑把这些字符串都塞到\(trie\)树上.之后检索每一个字符串的时候,我们看和他同一层的地方是否有字符,如 ...

  6. [USACO12DEC]第一!First! (Trie树,拓扑排序)

    题目链接 Solution 感觉比较巧的题啊... 考虑几点: 可以交换无数次字母表,即字母表可以为任意形态. 对于以其他字符串为前缀的字符串,我们可以直接舍去. 因为此时它所包含的前缀的字典序绝对比 ...

  7. Luogu5284 十二省联考2019字符串问题(后缀树+拓扑排序)

    对反串建SAM弄出后缀树,每个b串通过倍增定位其在后缀树上对应的节点,根据其长度将节点拆开.然后每个a串也找到对应的节点,由该节点向表示a串的节点连边,再把所给的边连上跑拓扑排序即可. #includ ...

  8. Codeforces Round #363 Fix a Tree(树 拓扑排序)

    先做拓扑排序,再bfs处理 #include<cstdio> #include<iostream> #include<cstdlib> #include<cs ...

  9. BZOJ3832[Poi2014]Rally——权值线段树+拓扑排序

    题目描述 An annual bicycle rally will soon begin in Byteburg. The bikers of Byteburg are natural long di ...

随机推荐

  1. 爬虫Scrapy框架运用----房天下二手房数据采集

    在许多电商和互联网金融的公司为了更好地服务用户,他们需要爬虫工程师对用户的行为数据进行搜集.分析和整合,为人们的行为选择提供更多的参考依据,去服务于人们的行为方式,甚至影响人们的生活方式.我们的scr ...

  2. JDBC基本使用

    J2EE技术规范(二)——JDBC 分类: java2012-12-03 14:25 1060人阅读 评论(8) 收藏 举报 一.了解JDBC (1) JDBC是以统一方式访问数据库的API (2) ...

  3. 布局 android

    1.线性布局 LinearLayout又称作线性布局,是一种非常常用的布局.通过android:orientation属性指定了排列方向是vertical还是horizontal. 如果LinearL ...

  4. Day6_内置函数

    定义完一个有名函数,可以直接利用函数名+括号来执行,例如:func() 有名函数: def func(x,y,z=1): return x+y+z 匿名函数: lambda x,y,z=1:x+y+z ...

  5. jsonp学习

    使用 JSONP 实现跨域通信:http://www.ibm.com/developerworks/cn/web/wa-aj-jsonp1/

  6. sqlite db数据的导出

    sqlite的db数据一般是filename.db的格式,用普通文本编辑器打开是乱码,用sqlite名令操作比较麻烦,有时版本格式问题还会起阻扰,有一个GUI工具可以对sqlite db格式数据进行管 ...

  7. Hibernate JPA 动态criteria语句针对null查询条件的特殊处理

    最近原Hibernate项目需要添加一个条件,结构有点类似下面的格式,学生和房间是多对一的关系,现在要查询所有没有房间的学生. Class Student{ @ManyToOne Room room; ...

  8. gradle 将依赖打入Jar包的方法

    使用的是IDEA,直接引入 plugins { id 'com.github.johnrengelman.shadow' version '1.2.3' } 放在build.gradle的最上面,然后 ...

  9. flash builder 4.6与myecilpse 10.7集成

    一.在flash builder 4.0以后就没有单独提供插件版的flash builder了,因此必须先安装完整版的flash builder,再进行插件集成. 二.集成过程比较简单但也有几个要注意 ...

  10. Java多线程:生命周期,实现与调度

    Java线程生命周期 Java线程实现方法 继承Thread类,重写run()方法 实现Runnable接口,便于继承其他类 Callable类替换Runnable类,实现返回值 Future接口对任 ...