Colored Sticks poj 2513 字典树

来源:互联网 发布:叉叉助手软件更新 编辑:程序博客网 时间:2024/05/22 15:23
Colored Sticks
Time Limit: 5000MS Memory Limit: 128000KTotal Submissions: 36344 Accepted: 9509

Description

You are given a bunch of wooden sticks. Each endpoint of each stick is colored with some color. Is it possible to align the sticks in a straight line such that the colors of the endpoints that touch are of the same color?

Input

Input is a sequence of lines, each line contains two words, separated by spaces, giving the colors of the endpoints of one stick. A word is a sequence of lowercase letters no longer than 10 characters. There is no more than 250000 sticks.

Output

If the sticks can be aligned in the desired way, output a single line saying Possible, otherwise output Impossible.

Sample Input

blue redred violetcyan blueblue magentamagenta cyan

Sample Output

Possible

Hint

Huge input,scanf is recommended.




//#include <iostream>
//#include <cstdio>
//#include <cstring>
//#include <algorithm>
//#include <map>
//using namespace std;
//const int N = 15;
//const int M = 1000010;
//
//struct Trie{
//    int num;
//    Trie *next[26];
//}*Head;
//Trie trie[M];
//char u[N],v[N];
//int num,n,top,total,flag;
//int pre[M],in[M];
//
//int Find_set(int x){
//    return pre[x] == -1 ? x : (pre[x] = Find_set(pre[x]));
//}
//
//void Make_Set(int x,int y){
//    int root1 = Find_set(x);
//    int root2 = Find_set(y);
//    if (root1 != root2)
//        pre[root2] = root1;
//}
//
//int Insert(char *str){
//    Head = &trie[0];
//    int len = strlen(str);
//    for (int i = 0; i < len; i++){
//        int temp = str[i] - 'a';
//        if (Head->next[temp] == NULL)
//            Head->next[temp] = &trie[++num];
//        Head = Head->next[temp];
//    }
//    if (Head->num == 0)
//        Head->num = top++;
//    return Head->num;
//}
//
//void init(){
//    num = total = 0,top = 1,flag = 1;
//    memset(in,0,sizeof(in));
//    memset(pre,-1,sizeof(pre));
//    for (int i = 0; i < 20; i++){
//        trie[i].num = 0;
//        for (int j = 0; j < 26; j++)
//            trie[i].next[j] = NULL;
//    }
//}
//
//int main(){
//    int tmp,temp;
//    init();
//    while (scanf("%s %s",u,v) != EOF){
//        tmp = Insert(u),temp = Insert(v);
//        in[tmp]++,in[temp]++;
//        Make_Set(tmp,temp);
//    }
//    int root = Find_set(1);
//    for (int i = 1; i < top; i++){
//        if (root != Find_set(i)){
//            flag = 0;
//            break;
//        }
//        if (in[i] & 1)
//            total++;
//        if (total > 2)
//            break;
//    }
//    if ((total == 0 || total == 2) && flag == 1)
//        printf("Possible\n");
//    else printf("Impossible\n");
//    return 0;
//}
#include<cstdio>
#include<cstring>
#include<iostream>
using namespace std;
const int Maxn=500005;
int tot;
int f[Maxn];
int num[Maxn];
struct trie
{
  trie *next[30];
  int id;
  trie()
  {
     for(int i=0;i<30;i++)
     next[i]=NULL;
     id=0;
  }
};
trie *root;
int Find(int i)
{
  if(i==f[i])
  return f[i];
  f[i]=Find(f[i]);
  return f[i];
}
int build(char *str)
{
   int len=strlen(str);
   trie *p=root;
   for(int i=0;i<len;i++)
   {
     int id=str[i]='a';
     if(p->next[id]==NULL)
     p->next[id]=new trie;
     p=p->next[id];
   }
   if(p->id==0)
   p->id=tot++;
   return p->id;
}
int maiN()
{
  char s1[22],s2[22];
  int a,b,fr,ed;
  int i;
  for(i=0;i<Maxn;i++)
  {
    f[i]=i;
    num[i]=0;
  }
  tot=1;
  int tt=0,ff=0;
  root=new trie;
  while(scanf("%s%s",s1,s2)!=-1)
  {
    a=build(s1);
    b=build(s2);
    fr=Find(a);
    ed=Find(b);
    if(fr!=ed)
    f[fr]=ed;
    num[a]++;
    num[b]++;
  }
  for(i=1;i<tot;i++)
  if(num[i]%2==1)
  tt++;
  for(i=1;i<tot;i++)
  if(f[i]==i)
  ff++;
  if(((tt==0)||(tt==2))&&(ff==1||ff==0))
  printf("Possible\n");
  else
  printf("Impossible\n");
}



























































0 0