繁体   English   中英

While循环不会在C中执行

[英]While Loop will not Execute in C

当我运行该程序时,除了while循环块的末尾之外,其他所有内容都将执行。 我被问到“每行要打印的符号数”,然后程序结束。 任何帮助将不胜感激。

#include <stdio.h>

int main(void) {
    int num_lines;
    printf("Enter a number of lines, greater than or equal to 7, to print :  ");
    scanf("%d", &num_lines);

    if (num_lines < 7) {
        while ( num_lines < 7 ) {
            printf("Enter the number of lines to print\nMust be greater than or equal to 7 :  ");
            scanf("%d", &num_lines);
        }
    }

    char symbol;
    printf("Choose a symbol/character to be displayed */&/+/0/x :  ");
    scanf("%s", &symbol);

    int num_symbols;
    printf("Enter the number of symbols to print per line :  ");
    scanf("%d", &num_symbols);

    if (num_symbols < 7 || num_symbols > 27) {
        num_symbols = 19;
    }

    while (num_lines > 0) {
        while (num_symbols > 0) {
            printf("%s", symbol);
            --num_symbols;
        }
        printf("\n");
        --num_lines;
    }
    return;
}

您的代码有一个非常严重的错误,

char symbol;
scanf("%s", &symbol);

是未定义的行为,因为"%s"期望指向至少大小为2的char数组的指针。在您的情况下,您正在将指针传递给单个char ,此类代码的作用是不确定的。

相反,它可能是( 至少

char symbol[2];
scanf("%1s", symbol);

或者,请参阅@ BLUEPIXY的建议。

调用未定义的行为后 ,程序的内存可能会损坏,因此程序的其余部分可能由于多种原因而失败。

您也不要检查scanf("%d", ...)是否成功可能是导致未定义行为的另一原因。

始终检查scanf()返回正确的值。

在此代码段中

char symbol;
printf("Choose a symbol/character to be displayed */&/+/0/x :  ");
scanf("%s", &symbol);

使用了无效的格式说明符%s 而是使用格式说明符" %c"

char symbol;
printf("Choose a symbol/character to be displayed */&/+/0/x :  ");
scanf(" %c", &symbol);

同样在printf的调用中

       printf("%s", symbol);

您必须使用格式说明符%c

       printf("%c", symbol);

提供这些循环将正常工作

   while (num_lines > 0) {
       while (num_symbols > 0) {
           printf("%s", symbol);
           --num_symbols;
       }
       printf("\n");
       --num_lines;
   }

您需要使用一个中间变量来存储外循环迭代之间的num_symbols值。 例如

   while (num_lines > 0) {
       int n = num_symbols; 
       while (n > 0) {
           printf("%c", symbol);
           --n;
       }
       printf("\n");
       --num_lines;
   }

让我们将问题归结为它的核心:您正在覆盖调用堆栈上的num_lines,因为您在真正想要一个字符时要求读取字符串。 当scanf创建字符串时,它将以null终止...,因此在堆栈上的单个char之后添加一个null字符 在C语言中使用指针的乐趣之一。

(这不是堆栈溢出,而只是堆栈覆盖。)

这是失败的最小示例。 只需将%s更改为%c ,一切都会起作用:

#include <stdio.h>
int main(void) {
  int num_lines;
  sscanf("7", "%d", &num_lines);
  printf("at first, num_lines is %d\n", num_lines);
  char symbol;
  sscanf("x", "%s", &symbol);
  printf("but now, num_lines has become %d\n", num_lines);
  printf("value changed because the second sscanf overwrote\n");
  printf("      num_lines on the call stack!!!\n");
  return; 
}

您会发现我很懒。 在测试过程中使用sscanf可以减少烦人的输入。

运行它,您会得到:

$ gcc scan.c ; ./a.out
at first, num_lines is 7
but now, num_lines has become 0
value changed because the second sscanf overwrote
      num_lines on the call stack!!!

您的问题是char变量symbol 您将symbol声明为字符变量,并将其读取为字符串。 还有一个问题。 使用scanf同时读取字符串或字符和数字时,请始终在读取数字值之前读取字符串或char值。 原因是scanf还会再读取一个字符\\n ,这总是会造成问题。

现在更改您的代码,如下所示:-

#include <stdio.h>

int main(void) {
    int num_lines;
    char symbol;
    printf("Choose a symbol/character to be displayed */&/+/0/x :  ");
    scanf("%c", &symbol);
    printf("Enter a number of lines, greater than or equal to 7, to print :  ");
    scanf("%d", &num_lines);

if (num_lines < 7) {
    while ( num_lines < 7 ) {
        printf("Enter the number of lines to print\nMust be greater than or equal to 7 :  ");
        scanf("%d", &num_lines);
    }
}   

int num_symbols;
printf("Enter the number of symbols to print per line :  ");
scanf("%d", &num_symbols);

if (num_symbols < 7 || num_symbols > 27) {
    num_symbols = 19;
}

while (num_lines > 0) {
    while (num_symbols > 0) {
        printf("%s", symbol);
        --num_symbols;
    }
    printf("\n");
    --num_lines;
 }
  return 0;//you have to return a value
}

如果仍然给您带来任何问题,只需硬编码symbol = '*'; 并尝试。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM