【问题标题】:Strcmp() in "series" [duplicate]“系列”中的 strcmp() [重复]
【发布时间】:2018-05-03 01:14:59
【问题描述】:

我想比较一些字符串,但不幸的是我没有找到任何合适的方法。

背后的想法是要求键盘输入,读取一个变量,一个符号,如果它是“y”或“n”(显然是“yes”或“no”),它会执行某些活动。如果 char 的值都不是,则再次询问问题,直到“y”或“n”中的任何一个都没有被按下。我不明白如何实现。

#include <stdio.h>
#include <string.h>

int main()
{
    char answer;

    answer='a';

    while (answer!='n'&&answer!='y')

    {

        printf("\nQuestion? (y/n) ");
        scanf("%c",&answer);

    }

    return 0;
}

这实际上效果很好,但是如果我不按'y'或'n',“while”会再次开始,由于我无法理解的原因,“printf”的执行次数比输入的长度。因此,如果我们运行此代码并应用“asdf”作为输入(四个符号),“while”中的“printf”将显示五次(四加一)。结果是:

Question? (y/n)
Question? (y/n)
Question? (y/n)
Question? (y/n)
Question? (y/n)

在我的代码中,其他的一切都非常好,但是这个......显然,这不是最好的方法。我也试过“strcmp()”:

#include <stdio.h>
#include <string.h>

int main()
{
    char answer='a';

    while (strcmp(answer,'n')!=0&&strcmp(answer,'y')!=0)

    {

        printf("Question?");
        scanf("%c",&answer);

    }

    return 0;
}

我不知道为什么,但程序甚至没有启动。很明显,我没有正确实现“strcmp”,我不明白出了什么问题。

任何想法,我应该怎么做,这样我可以避免在“while”中多次执行“printf”或让“strcmp”按我要求的方式工作?

【问题讨论】:

  • 你是否会输入 asdf+'enter' ?
  • 是的。老实说,我不知道其他方式来应用我的意见。
  • 输入是由scanf..这就是额外迭代的原因
  • 'enter' 键算作一个字符来scanf。只读取一个不输入的键取决于您的操作系统,寻找类似 kbhit() 和 getkey() 的东西。或者测试 answer=='\n' 并忽略它。
  • scanf(" %c",&amp;answer); 试试这个...这将确保 \n 被消耗。

标签: c series strcmp


【解决方案1】:

您可能想要阅读整行并将其作为一个整体进行解释。这样,当您输入包含多个字符的行时,您不会得到额外的不需要的迭代,也不会出现换行符的额外迭代。查看fgets() 函数。

scanf() 通常是除了非常简单的输入要求之外的糟糕选择,正是因为它有些模糊,并且不允许您在解析输入之前验证部分输入。

【讨论】:

  • 感谢您的回复@Dolda2000。我已将 scanf(" %c",&answer) 替换为 fgets(answer,1,stdin) 和该程序甚至没有启动。替换为 fgets(answer,2,stdin) 会导致程序在我输入符号后崩溃。 :(
  • 首先,answer 在你的例子中是一个字符,而不是一个指针,所以如果有的话,它应该是 &amp;answer 而不仅仅是 answer。但是,为了读取整行,您肯定需要一个比一个字符更大的缓冲区。
  • @ecclesiastes:另外请注意,如果您在编译时打开了警告,您的编译器很可能会告诉您fgets(answer, 1, stdin) 是错误的。
  • "警告:传递 'fgets' 的参数 1 使指针从整数不进行强制转换 [默认启用]", “警告:赋值从没有强制转换的指针中生成整数[默认启用]”你是对的。
【解决方案2】:

scanf%c 格式说明符将读取任何字符,包括换行符等空白字符。

因此,如果您输入一个字母并按 ENTER 键,scanf 将读取该字母并返回,将换行符留在输入缓冲区中。在循环的下一次迭代中,scanf 将立即使用缓冲区中剩余的换行符,answer 将包含换行符。这就是您看到提示打印两次的原因。

您需要在scanf 格式中添加前导空格:

scanf(" %c",&answer);

空格将占用输入的任何空格字符,因此answer 将只包含非空格。

strcmp 出现问题的原因是您实际上不是在比较字符串,而是在比较单个字符。 strcmp 的每个参数都应该是指向包含字符串的字符数组的指针。相反,您传递的是单个字符。然后将该字符的值解释为地址并取消引用。这会调用未定义的行为。

【讨论】:

    【解决方案3】:

    在 C 中,字符串文字以这种方式表示:"n",但您有字符文字,'n' ...它们非常不同。使用字符串文字作为参数,它应该会更好。

    【讨论】:

    • 在第一个例子中,张贴者使用的是字符——尽管在第二种情况下它们确实需要是字符串
    • 如果我理解正确,你建议用 ' 替换每个 " 。不幸的是,两个发布的脚本都没有不同的工作方式。绝对一样事情发生了。:(
    猜你喜欢
    • 2011-12-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-07-17
    • 1970-01-01
    相关资源
    最近更新 更多