思路:当时学长讲了之后,似乎有点思路----------就是倒着建一个 二叉搜索树
代码1:超时
详见超时原因
#include<iostream> #include<cstring> #include<stdio.h> using namespace std; char c[100][100]; struct node { char c; node *lchild; node *rchild; }; void f(node *p)//前序遍历输出,用递归 { printf("%c",p->c); if(p->lchild!=NULL) f(p->lchild); if(p->rchild!=NULL) f(p->rchild); } int main() { int i; int j; int exit; exit=0; while(1) { memset(c,' ',sizeof(c)); i=0; while(1) { scanf("%s",c[i]); if(c[i][0]=='*'||c[i][0]=='$') { if(c[i][0]=='$') exit=1; break; } i++; } i--; node *p=new node; p->c=c[i][0]; p->lchild=NULL; p->rchild=NULL; i--; node *p2; while(1)//遍历i { j=0; while(1)//遍历j { p2=p; node *p3=new node;//存储字母节点 p3->c=c[i][j]; p3->lchild=NULL; p3->rchild=NULL; while(1)//把字母挂到树中 { if(p3->c < p2->c) { if(p2->lchild==NULL) { p2->lchild=p3; break; } else if(p2->lchild!=NULL)//超时原因 p2=p2->lchild; } else if(p3->c > p2->c)//超时原因 { if(p2->rchild==NULL) { p2->rchild=p3; break; } else if(p2->rchild!=NULL)//超时原因,这三处的 else if() 判断多余,应直接写成else p2=p2->rchild; } } j++; if(c[i][j]==' ') break; } i--; if(i==-1)//修正超时原因后,此处会造成 runtime error,因为i为 -1时 也会 进入此while循环,数组越界 break; } f(p); printf(" "); if(exit==1) break; } return 0; }
修正代码:
1.
当时也是看了一下网上的一篇代码,看到他用的是一个结构体数组,我在考虑是不是动态开辟结构体浪费了时间,于是我改成用结构体数组,结果还是超时。
看来并非单单是数组这个原因造成我的代码超时( 当然我感觉,数组应该确实 比动态 开辟 省点时间)
2.
然后我继续想。。。
我突然间想到一个问题,那就是在我的代码中,有几句这样的 语句
if(p2->lchild==NULL) { p2->lchild=p3; break; } else if(p2->lchild!=NULL)//超时原因 p2=p2->lchild;
看到没有? 就是有一些没必要的判断,
在 if(p2->lchild==NULL) 这一句判断完之后,
下面的 else if(p2->lchild!=NULL)//超时原因 这一句纯属多余
于是我就抱着试试看的心态改了一下。
改过来之后 ,发现超时原因的确如此。
之所以这么写,我还是感觉自己容易出错,有时候考虑不周,所以都加上了 if() 条件判断,当时是为了避免出错 ,才这么写的。
所以养成了一点点的习惯这么写。
没想到。。。。这么写后造成超时,看来还是得改正这种写法,没必要的判断别用 -----------直接用 else 语句
代码2:正确
#include<iostream> #include<cstring> #include<stdio.h> using namespace std; char c[100][100]; struct node { char c; node *lchild; node *rchild; }; void f(node *p)//前序遍历输出,用递归 { printf("%c",p->c); if(p->lchild!=NULL) f(p->lchild); if(p->rchild!=NULL) f(p->rchild); } int main() { int i; int j; int exit; exit=0; while(1) { memset(c,' ',sizeof(c)); i=0; while(1) { scanf("%s",c[i]); if(c[i][0]=='*'||c[i][0]=='$') { if(c[i][0]=='$') exit=1; break; } i++; } i--; node *p=new node; p->c=c[i][0]; p->lchild=NULL; p->rchild=NULL; i--; node *p2; while(i>=0)//遍历i --------此处为修改的上面代码 ( 修改前出现了 runtime error ),应该 把 i > = 0 的 判断放在前面 { j=0; while(1)//遍历j { p2=p; node *p3=new node;//存储字母节点 p3->c=c[i][j]; p3->lchild=NULL; p3->rchild=NULL; while(1)//把字母挂到树中 { if(p3->c < p2->c) { if(p2->lchild==NULL) { p2->lchild=p3; break; } else // 修正 上面代码 p2=p2->lchild; } else // 修正 上面代码 { if(p2->rchild==NULL) { p2->rchild=p3; break; } else // 修正 上面代码 p2=p2->rchild; } } j++; if(c[i][j]==' ') break; } i--; } f(p); printf(" "); if(exit==1) break; } return 0; }
ps:再看这段代码,其实超时原因不是因为else if
而是p3->c > p2->c应该为p3->c >= p2->c
。。。