poj_2513 Colored Sticks
来源:互联网 发布:linux开启smb服务 编辑:程序博客网 时间:2024/06/06 12:35
Colored Sticks
Time Limit: 5000MS
Memory Limit: 128000K
Total Submissions: 24502
Accepted: 6431
题目链接:http://poj.org/problem?id=2513
Description
You are given a bunch of wooden sticks. Each endpoint ofeach stick is colored with some color. Is it possible to align the sticks in astraight line such that the colors of the endpoints that touch are of the samecolor?
Input
Input is a sequence of lines, each line contains twowords, separated by spaces, giving the colors of the endpoints of one stick. Aword is a sequence of lowercase letters no longer than 10 characters. There isno more than 250000 sticks.
Output
If the sticks can be aligned in the desired way, output asingle line saying Possible, otherwise output Impossible.
Sample Input
blue red
red violet
cyan blue
blue magenta
magenta cyan
Sample Output
Possible
Hint
Huge input,scanf is recommended.
Source
The UofA Local2000.10.14
解题思路:
这个题目主要用的是并查集+字典树+欧拉路完成的,用字典树来存放每一个单词,每个单词的最后一个字符存放每个单词对应的编号,用并查集来判断图是否连通,在用欧拉路来判断是否符合
代码:
#include <iostream>#include<stdio.h>#include<string.h>#include<stdlib.h>#define MAX 510000#define maxn 27using namespace std;int g[MAX];int indegree[MAX];int outdegree[MAX];int set[MAX];int num=0;//建立字典树方便查找struct Trie{ Trie *next[maxn];int id; char data;};//查询某个单词是否在字典树中,如果存在,返回id,不存在,返回-1int IsExist(Trie *root,char *str){ int len =strlen(str); int i; Trie *p=root; for(i=0;i<len;i++) { int id=str[i]-'a'; if(p->next[id]==NULL) return -1;p=p->next[id];if(i==len-1){return p->id;} }return -1;}//把字符串插入字典树root中void build(Trie *root,char *str){ Trie *p=root; Trie *q; int len=strlen(str); for(int i=0;i<len;i++) {//把每个字符都插入到字典树中 int id=str[i]-'a'; if(p->next[id]!=NULL) { p=p->next[id]; continue ; } //没有该节点 q=(Trie *)malloc(sizeof(Trie)); q->data=str[i]; for(int j=0;j<maxn;j++) { q->next[j]=NULL; }if(i==len-1){q->id=num;}elseq->id=-1; p->next[id]=q; p=p->next[id]; }num++;}void init(){memset(g,0,sizeof(g)); memset(indegree,0,sizeof(indegree)); memset(outdegree,0,sizeof(outdegree));for(int i=0;i<MAX;i++){set[i]=i;}}int findSet(int x){if(x!=set[x])set[x]=findSet(set[x]);return set[x];}void unionSet(int x,int y){int a=findSet(x);int b=findSet(y);if(a==b)return;if(set[a]<set[b]){set[b]=a;}else{set[a]=b;}}int main(){ int i;Trie *root; root=(Trie *)malloc(sizeof(Trie));for(int j=0;j<=maxn;j++) { root->next[j]=NULL; } init(); //输入 char ch1[12]; char ch2[12]; while(scanf("%s%s",ch1,ch2)!=EOF) { int s; int e;s=IsExist(root,ch1);if(s==-1){build(root,ch1);s=num-1;}e=IsExist(root,ch2);if(e==-1){build(root,ch2);e=num-1;} g[s]=1; g[e]=1; //点s和点e的度数自加 indegree[e]++; outdegree[s]++; //将点s和e连接起来 unionSet(s,e); } int count=0; int flag=0; //判断图是否连通——变量一遍所有节点,如果每一个节点的父亲都是相同的,那么图是连通的 for(i=0;i<=num;i++) { //如果超过一个点的父亲是他本身,那么表示不连通 if(g[i]==1 && set[i]==i) { flag++; } } if(flag>1)//图不连通 { printf("Impossible\n"); return 0; } //如果图连通,判读是否是欧拉路径 /*无向图中,除源点和汇点为奇数除外,其余点的度数都为偶数,或者所有点的度数为偶数,那么存在欧拉路径*/ for(i=0;i<=num;i++) { if(g[i]==1) { if((indegree[i]+outdegree[i])%2!=0) { count++; } } } if(count==0 || count==2) printf("Possible\n"); else printf("Impossible\n"); return 0;}
- poj_2513 Colored Sticks
- poj_2513 Colored Sticks(字典树+并查集+欧拉通路)
- Colored Sticks
- Colored Sticks
- Colored Sticks
- poj_2513
- PKU 2513 Colored Sticks
- pku 2513 Colored Sticks
- POJ 2513 Colored Sticks
- poj 2513 Colored Sticks
- POJ 2513 Colored Sticks
- poj 2513 colored sticks
- Q - Colored Sticks
- Poj 2513 Colored Sticks
- POJ 2513 Colored Sticks
- POJ 2513 Colored Sticks
- POJ 2513 Colored Sticks
- poj 2513 Colored Sticks
- FileZilla Server搭建
- C语言的那些小秘密——字节对齐
- 输入外挂
- 工作中需要注意的15个问题。
- uva 10098 - Generating Fast
- poj_2513 Colored Sticks
- C语言的那些小秘密——动态数组
- QSingleApplication类
- C++中vector的clear方法对于内存的释放方法
- 牛排生熟程度 英语说法
- C语言的那些小秘密——断言
- poj_2560 Freckles
- C语言的那些小秘密——const修饰符
- ping程序