C如何忽略用户输入中的空行?

时间:2016-01-24 21:25:19

标签: c

这是我目前的代码:

int num = 0;
char c = '#';

scanf("%d",&num);
do{
    for (int i=0;i<num;i++){
        printf("%c",c);
    }
    printf("\n");
}
while (scanf("%d", &num) == 1);

如果用户没有输入任何内容,我怎么能拥有它,该程序不会吐出换行符?

感谢任何帮助,谢谢!

3 个答案:

答案 0 :(得分:2)

此代码适用于您想要执行的操作:

#include <stdio.h>

int main()
{
    int num = 0;
    char c = '#';
    char readLine[50];

    while ((fgets(readLine, sizeof readLine, stdin) != NULL) && sscanf(readLine, "%d", &num) == 1)
    {
        for (int i=0;i<num;i++){
                printf("%c",c);
        }
        printf("\n");
        fflush(stdout);
    }
    return 0;
}

此代码的行为如下:fgets将读取您在标准流(stdin)中输入的任何内容,并将其放入readLine数组中。然后程序将尝试读取readLine变量中的数字,并使用sscanf函数将其放入num变量中。如果读取了一个数字,程序将执行你在问题中出现的行为(写一个#字符&#34; num&#34;次),然后回到循环的开头。如果读取了除数字以外的任何内容,则循环停止。

答案 1 :(得分:0)

一般情况下,请避免scanf。在输入流上留下未经处理的残余非常容易。相反,请阅读整行,然后使用sscanf(或其他内容)来处理它。这可以保证您不会遇到部分读取线路,这些线路难以调试。

我更喜欢getlinefgets来读取行。 fgets要求您猜测输入可能有多长,输入可能会被截断。 getline将分配内存来为您读取行,以避免缓冲区溢出或截断问题。

注意:getline is it's not a C standard function, but a POSIX one和最近(2008年),尽管在此之前它是一个GNU扩展。一些较旧的编译器可能没有它。

#include <stdio.h>
#include <stdlib.h>

int main()
{
    char c = '#';
    char *line = NULL;
    size_t linelen = 0;

    /* First read the whole line */
    while( getline(&line, &linelen, stdin) > 0 ) {
        /* Then figure out what's in it */
        long num = 0;
        if( sscanf(line, "%ld", &num) > 0 ) {
            for( int i = 0; i < num; i++ ) {
                printf("%c", c);
            }
            printf("\n");
        }
    }

    free(line);

    return 0;
}

if( sscanf(line, "%ld", &num) > 0 ) {将通过检查匹配的内容来忽略与模式的任何部分不匹配的任何行,例如空行或满字的行。但它仍然会将0作为有效输入。

$ ./test
foo
bar
foo123
12
############

1
#
0

2
##

我还在循环中移动num以确保每次迭代都重新初始化,并将变量置于最小范围以避免干扰的一般原则。我将其升级为long int能够更好地处理用户可能输入的不可预测的大数字。

答案 2 :(得分:0)

以下是我多年来使用fgets()和sscanf()函数进行输入解析的方法。我不会写很多c ++,如果我可以将代码保留在旧式的ansi C中,那么我就可以。 stdio.h库中的fgets和sscanf函数是通用的,并且可以在任何平台上使用。

对于用于读取任何内容的字符数组,我通常将LINE_SIZE设置为256或512,即使我通常知道要读取的行是80个字符或更少。如今任何一台计算机都拥有超过1GB的RAM,不值得担心分配额外的500个左右的字节。显然,如果您不知道输入行有多长,那么您必须:

猜测应该设置什么LINE_SIZE而不用担心它

或在调用fgets()之后验证空字符前行[]中是否存在换行符。

# include <stdio.h>

# define LINE_SIZE  256

int main ( int argc, char *argv[] )
{
    FILE *fp;
    char line[LINE_SIZE];
    int nn;
    int value;

    fp = fopen( "somefile", "r" );

    fgets( line, LINE_SIZE, fp );

    /*
        this way to read from standard input (i.e. the keyboard)
        using fgets with stdin prevents compiler warning when using
        deprecated gets function

        fgets( line, LINE_SIZE, stdin );
    */

    if ( line[0] != '\n' )
    {
        /* definitely not a blank line */

        nn = sscanf( line, "%d", &num );

        if ( nn == 1 )
        {
            /* some number placed into num variable that met the
               %d conversion for the sscanf function
            */
        }
    }
    return 0;