scanf 的工作并检查输入是否为 int

2024-01-07

我想检查给定的输入是否是整数输入。我不想将输入存储在字符串中。在看到 stackoverflow 上的几个问题以及点击和试用后,我创建了以下代码

while(scanf("%d%c",&num,&a) != 2 || a != '\n')
{
    printf("Please enter an integer only : ");
    if(a == '\n')
        scanf("%c",&a);
    else
    {
        while(a != '\n')
            scanf("%c",&a);
    }
}

它有效,但根据我的理解,以下内容也应该有效

while(scanf("%d%c",&num,&a) != 2 || a != '\n')
{
    printf("Please enter an integer only : ");
    while(a != '\n')
        scanf("%c",&a);
}

有人可以告诉我为什么上面的方法不起作用吗?另外,如果有人有更好的解决方案,也请提供。

注意:我也认为 12qwe 是无效输入。我只想要整数。


问题在于

while(scanf("%d%c",&num,&a) != 2 || a != '\n')
{
    printf("Please enter an integer only : ");
    while(a != '\n')
        scanf("%c",&a);
}

是如果a恰好包含'\n'扫描之前,扫描失败,内部while循环根本不运行。所以

  • 如果扫描尝试解析失败int来自输入流,因为输入是例如"ab c\n",有问题的输入保留在输入流中,下一个scanf在外while循环控制无法解析int again, a遗迹'\n', 重复。

  • 如果在从流中读取字符之前发生输入错误a, the scanf在外循环中,由于流损坏,控制失败,重复。

在另一个版本中,

while(scanf("%d%c",&num,&a) != 2 || a != '\n')
{
    printf("Please enter an integer only : ");
    if(a == '\n')
        scanf("%c",&a);
    else
    {
        while(a != '\n')
            scanf("%c",&a);
    }
}

只要有输入要从流中读取,您至少会取得一些进展,因为无论什么a包含,在尝试下一次解析之前,您至少从输入流中读取一个字符int。如果输入流损坏/关闭/过早结束,也会导致无限循环,例如如果您从空文件重定向标准输入。您可以让该循环也输出多个"Please enter an integer only : "通过提供诸如“a\nb\nc\nd\n”之类的输入来发送消息。

所以你应该检查是否scanf在从输入转换任何内容之前遇到流的结尾或其他一些读取错误,并在这种情况下中止:

int reads;
while(((reads = scanf("%d%c", &num, &a)) != 2 && reads != EOF) || a != '\n')
{
    printf("Please enter an integer only : ");
    // read at least one character until the next newline
    do {
        reads = scanf("%c", &a);
    }while(reads != EOF && a != '\n');
}
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

scanf 的工作并检查输入是否为 int 的相关文章

  • 从 C# 调用非托管 dll。拿2

    我编写了一个 C 程序 它调用一个 C DLL 将命令行参数回显到文件中 当使用 rundll32 命令调用 c 时 它显示命令行参数没有问题 但是当从 c 内部调用它时 它不会显示 我问了这个问题 https stackoverflow
  • 将 System.Drawing.Image 转换为 System.Windows.Media.ImageSource 但没有结果

    我想在我的 WPF 应用程序中将 Image 转换为 ImageSource 我使用正常工作的 Code128 库 已在 WinForms 应用程序中检查 下面的函数返回具有适当大小的 ImageSource 但没有任何内容可见 priva
  • 即使我没有#include ,为什么仍然可以使用 std::max 和 std::min ?

    include
  • 自定义可视化 Web 部件属性 sharepoint

    我在 Visual Studio 2012 中创建可视 Web 部件属性时遇到问题 我被提及http msdn microsoft com en us library ee231551 aspx http msdn microsoft co
  • 将数据集导出到 EXCEL

    我使用以下代码将数据库表中的字段导出到 Excel 中 我想要做的是能够编写一条 SQL 语句从多个表中检索字段并将其导出到 Excel 中 这段代码只允许我导出一张表 另外 如何显示保存提示对话框 示例代码将不胜感激 非常感谢 prote
  • 如何查找boost运行时版本

    我正在编写一个使用 boost 的 C 库 在这个库中 我想包含有关用于编译我的库的二进制版本的 boost 版本的信息 我可以使用宏BOOST VERSION这很好 我还想确定哪个是 boost 的运行时版本 以便我可以与用于编译我的库的
  • 实体框架 - 循环更新属性

    我正在尝试找到一种方法来循环 EF 对象的属性并更新这些属性的值 更具体地说 我有 50 个字段 其中最多填充 50 个下拉列表 所有 50 个可能都需要填充 也可能不需要填充 为了解决这个问题 我有一个中继器 最多可以创建 50 个 DD
  • 每个 CPU 核心处于 C0 电源状态的时间

    任何帮助弄清楚如何做到这一点都会很棒 在过去一秒内 每个 CPU 核心处于 C0 电源状态的时间有多少 这是针对 Mac 应用程序的 因此需要 Objective C cocoa 和 c OS X 没有任何公开 CPU c 状态的 API
  • 线程安全的get(访问器方法)

    我目前正在使用以下代码对变量进行线程安全访问 int gnVariable void getVariableValue int pnValue acquireLock Acquires the protection mechanism pn
  • 无法使用 Unity 函数在 Visual Studio Code 中获得完整的 Intellisense

    好吧 我知道这个问题已经被问过并回答过很多次了 但我花了大约 3 天的时间试图解决这个问题 但到目前为止我所做的一切都没有奏效 我基本上在 Visual Studio Code 中有部分智能感知 也就是说 它似乎只识别 Unity 类和变量
  • 尝试将元素推入向量

    在头文件 我没有编写 中 已经定义了一个结构体 如下所示 struct MemoryMessage public boost counted base public FastAlloc explicit MemoryMessage Memo
  • 使用 Thread.Sleep() 时,异步编程如何与线程一起工作?

    假设 前言 在之前的问题中 我们注意到Thread Sleep阻塞线程参见 什么时候使用Task Delay 什么时候使用Thread Sleep https stackoverflow com questions 20082221 whe
  • c#Registry to XML无效字符问题

    我在尝试从注册表创建 XML 文件时遇到问题 在我的笔记本电脑 W7 64b 上它工作正常 生成了 xml 文件 但在另一台计算机 Xp 32b 上抛出异常 System ArgumentException 十六进制值 0x00 是无效字符
  • 我应该使用函数还是无状态函子?

    这两段代码做同样的事情 如您所见 它将用于排序函数 哪个更好 我通常写后一种 但我看到一些程序员像以前那样做 struct val lessthan binary function
  • 使用 cryptoapi CryptImportKey 导入公钥时出错

    我想将公钥 blob 导入到 CSP 但发生了错误 BYTE pbData 0xEB 0x2A 0x38 0x56 0x86 0x61 0x88 0x7F 0xA1 0x80 0xBD 0xDB 0x5C 0xAB 0xD5 0xF2 0x
  • 允许 .NET WebApi 忽略 DOCTYPE 声明

    我正在尝试通过 WebApi 方法将 XML 反序列化为对象 我有以下课程 XmlRoot IsNullable false public class MyObject XmlElement Name public string Name
  • gcc 中的“假设”子句

    gcc 最新版本 4 8 4 9 是否有类似于以下的 假设 子句 assume 内置icc支持吗 例如 assume n 8 0 从 gcc 4 8 2 开始 gcc 中没有 assume 的等效项 我不知道为什么 这会非常有用 马夫索建议
  • jquery ajax“发布”调用

    我是 jQuery 和 Ajax 的新手 并且在 发布 方面遇到问题 我正在使用 jQuery Ajax post 调用将数据保存到数据库 当我尝试保存数据时 它将 null 传递给我的 C 方法 jQuery 看起来像这样 functio
  • 如果未返回,则在一段时间后终止线程

    我有一个线程从网络或串行端口获取一些数据 如果 5 秒内没有收到数据 则线程必须终止 或返回 false 换句话说 如果线程运行时间超过 5 秒 则必须停止 我用 C 编写 但任何 NET 语言都可以 有两种方法 1 封装超时 从网络或串行
  • 使用 wmi 获取活动会话(Win32_LogonSession 还返回非活动/旧会话)

    有没有办法只显示 wmi 的活动会话 问题是 Win32 LogonSession 还显示不活动 断开连接的会话 ManagementScope scope new ManagementScope ManagementPath Defaul

随机推荐