【问题标题】:Using scanf and while loop with vector push_back使用带有向量 push_back 的 scanf 和 while 循环
【发布时间】:2014-09-15 05:10:28
【问题描述】:

我试图从一行动态地从用户那里获取整数,预期的输入将是:

1 2 31 4 1

上面的输入只是5个整数输入的例子,用户可以输入任意多的数字。

所以,我尝试使用向量来动态存储这些整数。这是我的代码:

#include <stdio.h>
#include <vector>

using namespace std;

int main()
{
    vector<int> s;
    int d, b;

    while(scanf("\n%d", &d) == 1)
        s.push_back(d);

    printf("\nLength : %d", s.size());

    return 0;
}

但是,它没有用。举个例子,我输入了 6 个数字并按回车,我的期望是,它会显示向量的大小,但它却要求我输入另一个输入。我只能通过按Ctrl+D来停止“输入询问”。

令我惊讶的是,这段代码运行良好:

#include <stdio.h>

int main()
{
    int d;

    while(scanf("\n%d", &d) == 1)
        printf("%d ", d);

    return 0;
}

所以我的问题是,printf 和 push_back 之间有什么不同导致我的第一个代码不起作用?

注意,scanf 中的 \n 是为了防止尾随换行问题。

【问题讨论】:

  • 使用while(scanf(" %d", &amp;d) == 1)
  • 真正的问题是什么? 首先,我得到了五个长度。第二个,它打印出五个数字。
  • 如果您正在编写 C++,为什么要使用 printfscanf?此外,"%d"scanf 格式代码会自动跳过前导空格。
  • @paxdiablo 我对上面代码的期望是,当我插入一些数字时,例如31 2 14 3,当我按下回车键时,它会显示向量的大小,但是当我按下回车键时程序没有停止,但它正在等待另一个输入
  • @JoachimPileborg 对我的代码的丑陋感到抱歉,这只是 c + c++ 代码像意大利面条一样扔掉,感谢您提供新信息

标签: c++ c vector buffer scanf


【解决方案1】:

问题是你的循环,你不能在条件中单独使用scanf,因为你循环将继续,scanf 等待输入,直到你明确给出一个文件结尾作为输入。

如果你想继续使用C代码,那么我建议你查看fgets,然后从字符串中提取值。

或者您可以使用 C++ 并使用 std::getline 读入 std::string,然后将其放入 std::istringstream 中,您可以轻松地从向量中获取数字:

std::vector<int> s;

std::string line;
while (std::getline(std::cin, line) && !line.empty())
{
    std::istringstream iss(line);

    std::copy(std::istream_iterator<int>(iss),
              std::istream_iterator<int>(),
              std::back_inserter(s));
}

只要您输入非空行,上面的代码就会循环,并用输入中的数字填充向量s

【讨论】:

    【解决方案2】:

    首先,您能告诉我们您使用的是什么编译器,版本等(不同的编译器可能有不同的行为)。

    我不知道你说的“没用”是什么意思?你的意思是“在你的控制台上打印一些东西”?

    从您的代码中,您在这里使用了 while 循环,它在读取 EOF 或遇到读取错误之前不会退出。在您的示例中,它不会命中 printf("\nLength : %d", s.size());

    int main() {
        vector<int> s;
        int d, b;
    
        while(scanf("%d", &d) == 1) {
            printf("\nLength : %d", s.size());
            s.push_back(d);
        }
    
        return 0;
    }
    

    如果您在 while 子句中移动代码,您应该能够在控制台上看到输出。

    A.如果您知道整数,则可以使用固定计数的 for 循环;或者您可以尝试使用 getline(cin, string) 读取整行。

    B.当你发现一些奇怪的东西时,也许你可以调试你的代码。

    【讨论】:

      【解决方案3】:

      scanf 在到达行尾时不会失败。在查找数字时,换行符只是空格,与空格字符或制表符或任何其他空格字符无法区分。如果您希望 scanf 失败,您需要终止输入(通过您发现的 Ctrl-D),或者输入无法解析为整数的内容。

      如果您想要面向行的输入,请使用不同的方法。既然你无论如何都在使用 C++,我建议std::getline

      【讨论】:

        猜你喜欢
        • 2017-12-09
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2020-02-16
        • 2020-01-27
        • 1970-01-01
        • 2016-10-08
        • 1970-01-01
        相关资源
        最近更新 更多