【问题标题】:Ignoring leading newline("\n") in c忽略c中的前导换行符(“\ n”)
【发布时间】:2018-02-04 21:47:20
【问题描述】:

我目前正在练习。我的程序正在运行,我只是想让它更健壮和万无一失。代码如下:

printf("Enter Name : ");
memset(userinput, '\0', 50);
fgets(userinput, 50, stdin);

我不小心按了回车键(换行符),对于我的程序,系统只是悬在那里,无法再接受输入。我只能使用fgets。那么有什么方法可以拒绝\n 作为字段输入?

【问题讨论】:

  • 不,fgets 在输入字符串的末尾保留换行符,你必须忽略它或remove it。请张贴Minimal, Complete, and Verifiable example,显示您尝试过的内容。
  • 您可以检查第一个字符是否是换行符并再次询问
  • 如果用户点击空白然后换行,您可能不想接受它作为名称。您可能也不愿意接受“@#!%%&”作为名称。你需要仔细考虑你想从这段代码中得到什么。
  • @JonathanLeffler True, always sanitize user input

标签: c newline fgets


【解决方案1】:

一种方法是检查第一个字符是否为换行符:

do {
    printf("Enter Name : ");
    memset(userinput, '\0', 50);
    fgets(userinput, 50, stdin);
}
while ( userinput[0] == '\n'); 

printf("Hello %s", userinput);

这仍然会让您使用空格 + 换行符,但这是第一次开始。

【讨论】:

  • 注意:你不需要memset()
  • 在这样的提示下按Ctrl-Z (Windows) 或Ctrl-D (Linux-likes) 会发生什么? (这稍微超出了 OP 的问题,但 OP 似乎又没有意识到这一点。)添加一个额外的测试,而不是简单的 Return。
  • 你需要测试fgets()的返回值,才能知道是遇到EOF还是错误。如果它确实发现了其中任何一种情况,您将永远循环。
【解决方案2】:

那么有什么方法可以拒绝 \n 作为字段输入吗?
...使其更加健壮和万无一失。

代码不应阻止 '\n'fgets() 读取。相反,代码应该评估该输入的有效性。领先的'\n' 可能只是一个问题。使代码易于更新,因为有效名称的标准肯定会不断发展。

我建议单独进行名称测试。

bool ValidNameInputTest(const char *userinput) {
  if (*userinput == '\n') return false; // fail
  // add other tests as needed
  return true;
}

在循环中,根据需要进行测试和重复。代码应在成功时退出循环。当发生文件结尾或输入错误时,代码也应该检测/处理它。

...
char userinput[50];

do {
  printf("Enter Name : ");
  fflush(stdout);   // add to insure above output is seen before reading input
  //memset(userinput, '\0', 50);// Commented out as not needed - although useful for debug

  // Check return value and used a derived size
  //fgets(userinput, 50, stdin);
  if (fgets(userinput, sizeof userinput, stdin) == NULL) {
    Handle_EndOfFile_or_Error();
  }
} while (!ValidNameInputTest(userinput));

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2019-03-13
    • 1970-01-01
    • 2015-07-01
    • 1970-01-01
    • 2017-10-15
    • 1970-01-01
    • 2020-05-20
    • 2021-06-17
    相关资源
    最近更新 更多