【问题标题】:second scanf inside function does not work....program does not stop at second scanf?第二个scanf内部函数不起作用....程序不会在第二个scanf处停止?
【发布时间】:2012-12-31 04:16:57
【问题描述】:
   #include<stdio.h>
   #include<conio.h>
   void sstring();
    int main()
    {
     char ch1[10],ch2;
     printf("Enter the value of first character : ");
     scanf("%s",&ch1);
     sstring(); 

     getch();
     return 0; 
    } 

    void sstring()
    {    char ch2;
         printf("Enter the value of second character : ");
         scanf("%c",&ch2);   

         printf("Got the second character"); 
    }

函数内部的第二个 scanf 不起作用....程序不会在第二个 scanf 处停止?

【问题讨论】:

  • 请注意,虽然您声明了sstring(),但您并没有为其指定原型。在 C(但不是 C++)中,sometype function(); 形式的声明声明存在一个返回 sometype 但参数列表未指定的函数(但它不是可变长度参数列表)。要为不带参数的函数声明函数原型,请编写 sometype function(void);。为了保持一致性,我建议也使用显式 (void) 表示法定义函数。
  • 另外,最好检查scanf() 的返回值,以确保它成功。例如,您可以使用if (scanf("%9s", ch1) != 1) ...read failed...。请注意数组名称上没有&amp;。从技术上讲,您传递的是一个数组的地址(char (*)[10] 类型),而不是scanf() 所期望的char *。你的编译器应该警告类型不匹配;如果不是,请了解如何使它这样做或获得更好的编译器。然后注意警告!
  • 能否请您为我推荐一个适用于 c 和 c++ 的 Windows 的良好编译器...请与我分享我可以从哪里获得它的链接...
  • 嗯,我希望可以说服 MSVC 提供这样的 cmets,但 GCC 肯定可以。我在带有 GCC 的 Windows 上愉快地使用了 Cygwin;还有可以与 GCC 一起使用的 MinGW。

标签: c scanf


【解决方案1】:

首先,那不是因为第二个 scanf 在函数内部。

那是因为来自第一个 scanf(您输入 enter)的 0xA(返回)仍在标准输入缓冲区中。请注意,%s 参数不会读取输入的最终“\n”。为了不影响以后可能对 scanf 的调用,您应该始终读取字符串和行分隔符。

char string[10], linedelim;
scanf("%s%c", string, &linedelim);

你的例子又来了,现在工作了。

#include<stdio.h>
#include<conio.h>

void sstring();
int main()
{
 char ch1[10],ch2, linedelim;
 printf("Enter the value of first character : ");
 // read both the string and line delim
 scanf("%s%s",&ch1, &linedelim);
 sstring(); 
 getch();
 return 0; 
} 

void sstring()
{    char ch2;
     printf("Enter the value of second character : ");
     // read the second input
     scanf("%c",&ch2);   
     printf("Got the second character"); 
}

另请注意,您的示例非常脆弱,因为当用户输入超过 10 个字符时,它很容易导致缓冲区溢出。想象一下下面的命令行很容易破坏你的程序:

$ perl -e 'print "A" x 1000000' | ./a.out 

比使用 scanf() 从输入读取字符串更好的方法可能是使用 fgets(),因为您可以控制输入的大小。

【讨论】:

  • 所以在每次 scanf 之后我们需要放 fflush?....我的意思是在哪里使用 fflush 而在哪里不使用?
  • @kks 忘记我之前提到的 fflush。输入流上的 fflush() 将导致未定义的行为。只使用另一个 scanf() 来吃换行符
  • 还有其他方法可以做到这一点吗?我的意思是如果有一些其他的功能可以避免两个scanf语句并且程序正确运行
  • 请注意,输入流上的fflush() 在 Windows 中有意义,但在 Unix 中没有意义。
  • @JonathanLeffler 是的,我也意识到了这一点。我不是“日常使用”的 C 专家。但是在 C 中实现“简单”任务总是很有趣的! :)
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2021-04-07
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多