POJ 2513 Colored Sticks【tire tree+并查集+欧拉路】
2016-05-13 13:31
351 查看
Colored Sticks
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 red
red violet
cyan blue
blue magenta
magenta cyan
Sample Output
Possible
Hint
Huge input,scanf is recommended.
Source
The UofA Local 2000.10.14
题目大意:给你一堆小木棍 ,木棍两端是有颜色的,如果某一个木棍的尾部和某一个木棍的首部颜色相同,辣么这两个可以连接起来,问能否将给出的所有小木棍连接起来
思路:
欧拉路判断:图中奇数度的点只可能是0个或者两个。
连通判断:并查集。
字母转换成编号:字典树、POJ这个题卡了hash卡了map、正解是用字典树来解决,操作很简单》如果这个单词在树里边有编号,那么使用这个编号作为节点号,否则对应下一个节点号入树即可。
注意:初始化和空白数据,空白数据应该输出Possible
Ac代码:
#include<stdio.h>
#include<string.h>
#include<stdlib.h>
#include<map>
using namespace std;
#define maxn 26
typedef struct tree
{
int flag;
tree *next[maxn];
} tree;
tree root;
int f[510000];
int degree[510000];
int find(int a)
{
int r=a;
while(f[r]!=r)
r=f[r];
int i=a;
int j;
while(i!=r)
{
j=f[i];
f[i]=r;
i=j;
}
return r;
}
void merge(int a,int b)
{
int A,B;
A=find(a);
B=find(b);
if(A!=B)
f[B]=A;
}
void creat(char *str,int val)
{
int len=strlen(str);
tree *p=&root,*q;
for(int i=0; i<len; i++)
{
int id=str[i]-'a';
if(p->next[id]==NULL)
{
q=(tree *)malloc(sizeof(root));
for(int j=0; j<26; j++)
{
q->next[j]=NULL;
}
p->next[id]=q;
}
p=p->next[id];
if(i==len-1)p->flag=val;
}
}
int find(char *str)
{
int len=strlen(str);
tree *p=&root;
for(int i=0; i<len; i++)
{
int id=str[i]-'a';
p=p->next[id];
if(p==NULL)
return 0;
}
return p->flag;
}
int main()
{
for(int i=0; i<26; i++)
{
root.next[i]=NULL;
root.flag=0;
}
char a[100];
char b[100];
for(int i=1; i<=510000; i++)f[i]=i,degree[i]=0;
int cont=1;
while(~scanf("%s%s",a,b))
{
//if(strcmp(a,"end")==0)break;
int u=find(a);
int v=find(b);
if(u==0)
{
creat(a,cont);
u=cont;
cont++;
}
if(v==0)
{
creat(b,cont);
v=cont;
cont++;
}
degree[u]++;
degree[v]++;
merge(u,v);
}
if(cont==1)
{
printf("Possible\n");
}
else
{
int tot=0;
for(int i=1; i<cont; i++)
{
if(f[i]==i)tot++;
}
if(tot==1)
{
int output=0;
for(int i=1; i<cont; i++)
{
if(degree[i]%2==1)output++;
}
if(output==0||output==2)
{
printf("Possible\n");
}
else printf("Impossible\n");
}
else printf("Impossible\n");
}
}
Time Limit: 5000MS | | Memory Limit: 128000K |
Total Submissions: 34615 | | Accepted: 9047 |
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 red
red violet
cyan blue
blue magenta
magenta cyan
Sample Output
Possible
Hint
Huge input,scanf is recommended.
Source
The UofA Local 2000.10.14
题目大意:给你一堆小木棍 ,木棍两端是有颜色的,如果某一个木棍的尾部和某一个木棍的首部颜色相同,辣么这两个可以连接起来,问能否将给出的所有小木棍连接起来
思路:
欧拉路判断:图中奇数度的点只可能是0个或者两个。
连通判断:并查集。
字母转换成编号:字典树、POJ这个题卡了hash卡了map、正解是用字典树来解决,操作很简单》如果这个单词在树里边有编号,那么使用这个编号作为节点号,否则对应下一个节点号入树即可。
注意:初始化和空白数据,空白数据应该输出Possible
Ac代码:
#include<stdio.h>
#include<string.h>
#include<stdlib.h>
#include<map>
using namespace std;
#define maxn 26
typedef struct tree
{
int flag;
tree *next[maxn];
} tree;
tree root;
int f[510000];
int degree[510000];
int find(int a)
{
int r=a;
while(f[r]!=r)
r=f[r];
int i=a;
int j;
while(i!=r)
{
j=f[i];
f[i]=r;
i=j;
}
return r;
}
void merge(int a,int b)
{
int A,B;
A=find(a);
B=find(b);
if(A!=B)
f[B]=A;
}
void creat(char *str,int val)
{
int len=strlen(str);
tree *p=&root,*q;
for(int i=0; i<len; i++)
{
int id=str[i]-'a';
if(p->next[id]==NULL)
{
q=(tree *)malloc(sizeof(root));
for(int j=0; j<26; j++)
{
q->next[j]=NULL;
}
p->next[id]=q;
}
p=p->next[id];
if(i==len-1)p->flag=val;
}
}
int find(char *str)
{
int len=strlen(str);
tree *p=&root;
for(int i=0; i<len; i++)
{
int id=str[i]-'a';
p=p->next[id];
if(p==NULL)
return 0;
}
return p->flag;
}
int main()
{
for(int i=0; i<26; i++)
{
root.next[i]=NULL;
root.flag=0;
}
char a[100];
char b[100];
for(int i=1; i<=510000; i++)f[i]=i,degree[i]=0;
int cont=1;
while(~scanf("%s%s",a,b))
{
//if(strcmp(a,"end")==0)break;
int u=find(a);
int v=find(b);
if(u==0)
{
creat(a,cont);
u=cont;
cont++;
}
if(v==0)
{
creat(b,cont);
v=cont;
cont++;
}
degree[u]++;
degree[v]++;
merge(u,v);
}
if(cont==1)
{
printf("Possible\n");
}
else
{
int tot=0;
for(int i=1; i<cont; i++)
{
if(f[i]==i)tot++;
}
if(tot==1)
{
int output=0;
for(int i=1; i<cont; i++)
{
if(degree[i]%2==1)output++;
}
if(output==0||output==2)
{
printf("Possible\n");
}
else printf("Impossible\n");
}
else printf("Impossible\n");
}
}
相关文章推荐
- POJ 2513-Colored Sticks(连接木棍-trie树+并查集+欧拉通路)
- 用类描述坦克
- 使用python完成公司考勤数据的邮件发送
- 高质量C编程08-预处理
- hdu 1014 Uniform Generator
- Android面试题
- Android中的事件分发机制(上)——ViewGroup的事件分发
- 安卓在Activity中获取Fragment中的控件
- php webservice实例(转载)
- Ant之MacroDef——“宏”
- 从零学习前端开发之 ―― web前端开发基础环境配置(1)
- SSM框架——使用MyBatis Generator自动创建代码,会遇到“前言中不许有内容的错误”
- ImageLoader配置
- Windows平台使用Gitblit搭建Git服务器图文教程
- 典型用户场景、用户场景描述
- C#根据汉字获取编码和根据编码获取汉字
- 读世界是数字的有感
- Some Simple Models of Neurons
- POJ 1066 Treasure Hunt 计算几何
- 解析 html