标签:拓扑排序
题意:n个姓名,按照某种“字典序”。
问如果存在这样的字典序,输出字典序‘a‘到‘z’26个字母的顺序。
思路:拓扑排序。对于str[i]和str[i+1]如果在位置k出现不同,那么x=str[i][k]-‘a‘+1,y=str[i+1][k]-‘a‘+1,从x->y连一条边,y的入度in[y]++。
然后拓扑排序,如果形成环,就说明不行,不然依次输出对应字符。(ps:len1为str[i]的长度,len2为str[i+1]的长度,如果len1>len2且前len2个均相同,也说明不行)详见代码:
/*********************************************************
file name: codeforces510C.cpp
author : kereo
create time: 2015年02月03日 星期二 16时03分28秒
*********************************************************/
#include<iostream>
#include<cstdio>
#include<cstring>
#include<queue>
#include<set>
#include<map>
#include<vector>
#include<stack>
#include<cmath>
#include<string>
#include<algorithm>
using namespace std;
typedef long long ll;
const int sigma_size=26;
const int N=100+50;
const int MAXN=100000+50;
const int inf=0x3fffffff;
const double eps=1e-8;
const int mod=100000000+7;
#define L(x) (x<<1)
#define R(x) (x<<1|1)
#define PII pair<int, int>
#define mk(x,y) make_pair((x),(y))
int n,edge_cnt;
char str[N][N];
int head[N],in[N],ans[N],vis[N][N];
struct Edge{
int v,next;
}edge[N];
void init(){
edge_cnt=0;
memset(in,0,sizeof(in));
memset(vis,0,sizeof(vis));
memset(head,-1,sizeof(head));
}
void addedge(int u,int v){
edge[edge_cnt].v=v;
edge[edge_cnt].next=head[u]; head[u]=edge_cnt++;
}
int main(){
while(~scanf("%d",&n)){
init();
for(int i=0;i<n;i++)
scanf("%s",str[i]);
int flag=1;
for(int i=0;i<n-1;i++){
int len1=strlen(str[i]),len2=strlen(str[i+1]);
int tag=0;
for(int j=0;j<len1 && j<len2;j++){
if(str[i][j]!=str[i+1][j]){
tag=1;
int u=str[i][j]-'a'+1,v=str[i+1][j]-'a'+1;
if(!vis[u][v]){
vis[u][v]=1; in[v]++; addedge(u,v);
}
break;
}
}
if(!tag && len1>len2){
flag=0;
break;
}
}
if(!flag){
printf("Impossible\n");
continue;
}
int cnt=0;
queue<int>Q;
while(!Q.empty()){
Q.pop();
}
for(int i=1;i<=sigma_size;i++)
if(!in[i])
Q.push(i);
while(!Q.empty()){
int u=Q.front(); Q.pop();
ans[cnt++]=u-1;
for(int i=head[u];i!=-1;i=edge[i].next){
int v=edge[i].v;
--in[v];
if(!in[v])
Q.push(v);
}
}
if(cnt != sigma_size)
printf("Impossible\n");
else{
for(int i=0;i<sigma_size;i++)
printf("%c",'a'+ans[i]);
printf("\n");
}
}
return 0;
}codeforces 510C Fox And Names 拓扑
标签:拓扑排序
原文地址:http://blog.csdn.net/u011645923/article/details/43488333