函数递归中cin与scanf效果不同的 原因?

有个椰子般的心 2017-12-19 01:35:26
最近在学习数据结构,学到了树这一部分。看过原理后感觉无比简单,创建遍历都是使用递归即可,于是我便入手写。下面是代码(只写了创建和前序遍历)。
这是纯C语言。
#include<stdio.h>
#include<malloc.h>

struct tree
{
char data;
struct tree *lchild,*rchild;
};

void creatTree(struct tree **t)
{
char ch;
scanf("%c",&ch);
if(ch=='*')
(*t)=NULL;
else
{
(*t)=(struct tree*)malloc(sizeof(struct tree));
(*t)->data=ch;
creatTree(&((*t)->lchild));
creatTree(&((*t)->rchild));
}
return;
}

void preorderPrint(struct tree *t)
{
if(!t) return;
printf("%c,",t->data);
preorderPrint(t->lchild);
preorderPrint(t->rchild);

}

int main()
{
struct tree *p;
creatTree(&p);
preorderPrint(p);
return 0;
}

因为主函数我定义的是指针,为了改变指针的值所以才在创建函数creatTree中使用的二维指针。
在开始执行后,打算建立只有根节点的树,按照函数的意思应该输入1 * *回车即可。可意外情况出现了,程序输入停不下来,如图:

程序一直悬停在输入状态。但是建立空树是没有问题的。于是我决定用打印函数来追踪函数运行。
加了个全局变量,并在函数开始处打印,如图:

然后执行,截图:

由图可见,在第一次函数开始后,我输入了一个1,然后回车,发现函数居然自动调用了两次,中间那一次的scanf为什么不会让函数悬停呢?那么这样执行,第二次函数执行时的ch变量值为多少?于是我加了一个打印函数打印每次函数中的ch变量:

然后执行,截图:

发现第二次存入的居然是个回车,居然把我输入1之后的回车读了进去,我尝试直接连续输入1**,中间不加空格:

成功了,为什么scanf有这种特性?于是我又想尝试cin的情况。
我新建了一个文件(.cpp),然后整个复制过来,不过输入语句我使用cin(当然还有头文件和命名空间),运行:

结果运行正常,没有像scanf那种情况读取回车,我又想如果cin直接输入1**会如何?

结果也是完全ok。
然后我就有个问题了,为什么scanf不能达到理想的效果呢,而且会读取所输入的回车呢?
...全文
396 3 打赏 收藏 转发到动态 举报
写回复
用AI写文章
3 条回复
切换为时间正序
请发表友善的回复…
发表回复
  • 打赏
  • 举报
回复
scanf会有输入缓冲区的问题。 一般是需要判断输入的字符如果是回车,就要处理输入的回车,这个时候让程序结束,或者跳过回车。
  • 打赏
  • 举报
回复
scanf会有输入缓冲区的问题。 一般是需要判断输入的字符如果是回车,就要处理输入的回车,这个时候让程序结束,或者跳过回车。
jiht594 2017-12-19
  • 打赏
  • 举报
回复
缓冲区还有回车 scanf之前fflush(stdin)

3,881

社区成员

发帖
与我相关
我的任务
社区描述
C/C++ 其它技术问题
社区管理员
  • 其它技术问题社区
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧