两个图论题,第一个根据给的不确定根的树输出树的prufer code
第二个根据给的prufer code 构建出一棵树,树的格式定义如下:
T ::= "(" N S ")" S ::= " " T S | empty N ::= number
两个都是考验输出格式的变态题啊。。。特别记住第一题如果输入(),也就是空树,要输出一个空行,也就是木有prufer code
第二题,如果输入空行,那说明只有一个节点,输出一行(1)//第二题要不是没想到空行今天上午就该ac了。。。
先是第一题代码
#include<iostream>
#include<cstdio>
#include<string>
#include<string.h>
#include<cmath>
using namespace std;
struct node{
int father,outdegree;
//int n;
//int a[4000];
}nodes[4000];
string s,num;
int query[4000];
int mini,maxi,k,rear,head,save,prre;
bool flag[4000];
int main(){
while(getline(cin,s)){
memset(nodes,0,sizeof(nodes));
maxi=head=0;
rear=2;
query[1]=0;
memset(flag,true,sizeof(flag));
for(int i=0;i<s.length();i++)
if(flag[i]){
if(s[i]=='('){
head++;
}
else if(s[i]==')'){
head--;
}
if(s[i]>='0'&&s[i]<='9'){
num="";
int j=i;
while(s[j]>='0'&&s[j]<='9'){
flag[j]=false;
num+=s[j++];
}
//i=j-1;
k=0;
//cout<<num<<endl;
for(int j=num.length()-1;j>=0;j--){
//cout<<num.length()-1-j<<" "<<num[j]-'0'<<endl;
k+=(int)pow(10,num.length()-1-j)*(num[j]-'0');
}
//cout<<k<<endl;
query[head+1]=k;
nodes[k].father=query[head];
//nodes[k].indegree++;
nodes[nodes[k].father].outdegree++;
//nodes[nodes[k].father].a[nodes[nodes[k].father].n++]=k;
if(maxi<k) maxi=k;
}
}
/*for(int i=0;i<=maxi;i++){
cout<<i<<" "<<nodes[i].father<<endl;
//for(int j=0;j<nodes[i].n;j++)
// cout<<nodes[i].a[j]<<" ";
cout<<endl;
}*/
save=maxi;
mini=nodes[save].father;
prre=0;
while(1){
//cout<<save<<" 's father is: "<<mini<<endl;
//cout<<save<<" new father is: "<<prre<<endl;
if(mini!=0){
nodes[save].outdegree++;
nodes[mini].outdegree--;
}
nodes[save].father=prre;
prre=save;
save=mini;
mini=nodes[save].father;
if(save==0) break;
}
/*for(int i=1;i<=maxi;i++){
cout<<i<<" "<<nodes[i].father<<" "<<nodes[i].outdegree;
//for(int j=0;j<nodes[i].n;j++)
// cout<<nodes[i].a[j]<<" ";
cout<<endl;
}*/
memset(flag,false,sizeof(flag));
for(int i=0;i<maxi-1;i++){
mini=10000;
for(int j=1;j<=maxi;j++)
if(!flag[j]&&nodes[j].outdegree==0&&j<mini)
mini=j;
//cout<<mini<<endl;
//if(i!=maxi-2)
printf("%d ",nodes[mini].father);
//else
//printf("%d\n",nodes[mini].father);
flag[mini]=true;
nodes[nodes[mini].father].outdegree--;
}
printf("\n");
//if(s!="")
//printf("%d\n",maxi);
}
return 0;
}
第二题代码
#include<iostream>
#include<cstdio>
#include<string>
#include<string.h>
#include<math.h>
using namespace std;
struct node{
int father,indegree;
int n;
int a[400];
}nodes[400];
int maxi,k,a[400];
int order[400],sum;
bool flag[400];
string s,num;
void dfs(int x){
printf("(%d",x);
for(int i=0;i<nodes[x].n;i++){
printf(" ");
dfs(nodes[x].a[i]);
}
printf(")");
}
int main(){
while(getline(cin,s))
if(s=="") printf("(1)\n");
else{
maxi=sum=0;
memset(a,0,sizeof(a));
memset(nodes,0,sizeof(nodes));
memset(flag,true,sizeof(flag));
for(int i=0;i<s.length();i++)
if(s[i]>='0'&&s[i]<='9'&&flag[i]){
num="";
int j=i;
while(s[j]>='0'&&s[j]<='9'){
flag[j]=false;
num+=s[j++];
}
k=0;
for(int j=num.length()-1;j>=0;j--){
k+=(int)pow(10.0,(double)num.length()-1-j)*(num[j]-'0');
}
//cout<<k<<endl;
a[k]++;
order[sum++]=k;
//query[head+1]=k;
//nodes[k].father=query[head];
//nodes[nodes[k].father].outdegree++;
if(maxi<k) maxi=k;
}
memset(flag,true,sizeof(flag));
for(int i=0;i<sum;i++){
//cout<<order[i]<<endl;
for(int j=1;j<=maxi;j++)
if(a[j]==0&&flag[j]){
k=j;
flag[j]=false;
break;
}
//cout<<k<<endl;
nodes[k].father=order[i];
nodes[k].indegree++;
a[order[i]]--;
nodes[order[i]].a[nodes[order[i]].n++]=k;
}
/*for(int i=1;i<=maxi;i++){
cout<<i<<" :";
for(int j=0;j<nodes[i].n;j++)
cout<<nodes[i].a[j]<<" ";
//cout<<i<<" 's father is: "<<nodes[i].father<<endl;
cout<<endl;
}*/
for(int i=1;i<=maxi;i++)
if(nodes[i].indegree==0)
k=i;
dfs(k);
printf("\n");
}
return 0;
}
pe请吃饭啊,血的教训啊。。。。以此文祭奠我即将阵亡的rmb。。。