检查 cin 输入流会生成一个整数

Checking cin input stream produces an integer

提问人:user2766546 提问时间:9/11/2013 最后编辑:jwwuser2766546 更新时间:12/28/2022 访问量:191180

问:

我正在输入这个,它要求用户输入两个整数,然后它们将成为变量。从那里它将执行简单的操作。

如何让计算机检查输入的内容是否为整数?如果没有,请要求用户键入一个整数。例如:如果有人输入“a”而不是 2,那么它会告诉他们重新输入一个数字。

谢谢

 #include <iostream>
using namespace std;

int main ()
{

    int firstvariable;
    int secondvariable;
    float float1;
    float float2;

    cout << "Please enter two integers and then press Enter:" << endl;
    cin >> firstvariable;
    cin >> secondvariable;

    cout << "Time for some simple mathematical operations:\n" << endl;

    cout << "The sum:\n " << firstvariable << "+" << secondvariable 
        <<"="<< firstvariable + secondvariable << "\n " << endl;

}
C++ CIN

评论

0赞 chris 9/11/2013
检查输入操作是否失败。
0赞 crush 9/11/2013
'a'仍然是一个整数值。您可以检查该值是否在 ASCII 数字范围内,即0x30-0x39

答:

42赞 Chemistpp 9/11/2013 #1

您可以像这样检查:

int x;
cin >> x;

if (cin.fail()) {
    //Not an int.
}

此外,您可以继续获取输入,直到通过以下方式获得 int:

#include <iostream>



int main() {

    int x;
    std::cin >> x;
    while(std::cin.fail()) {
        std::cout << "Error" << std::endl;
        std::cin.clear();
        std::cin.ignore(256,'\n');
        std::cin >> x;
    }
    std::cout << x << std::endl;

    return 0;
}

编辑:为了解决下面关于输入(如 10abc)的评论,可以修改循环以接受字符串作为输入。然后检查字符串中是否有任何字符,而不是数字,并相应地处理这种情况。在这种情况下,不需要清除/忽略输入流。验证字符串只是数字,将字符串转换回整数。我的意思是,这只是即兴的。也许有更好的方法。如果您接受浮点数/双精度值,这将不起作用(必须在搜索字符串中添加“.”)。

#include <iostream>
#include <string>

int main() {

    std::string theInput;
    int inputAsInt;

    std::getline(std::cin, theInput);

    while(std::cin.fail() || std::cin.eof() || theInput.find_first_not_of("0123456789") != std::string::npos) {

        std::cout << "Error" << std::endl;

        if( theInput.find_first_not_of("0123456789") == std::string::npos) {
            std::cin.clear();
            std::cin.ignore(256,'\n');
        }

        std::getline(std::cin, theInput);
    }

    std::string::size_type st;
    inputAsInt = std::stoi(theInput,&st);
    std::cout << inputAsInt << std::endl;
    return 0;
}

评论

0赞 brunocodutra 9/11/2013
@crush cin 不会将输入解释为字符,而是解析它,但“a”不能解析为整数。除了整数之外,其他任何东西都不能。
0赞 Chemistpp 9/11/2013
检查一下,伙计。使用消息编译代码。如果输入“a”,它将抛出失败位
0赞 crush 9/11/2013
看来我已经离开C++太久了。
4赞 Zac Howland 9/11/2013
if(!cin)是有效的,但它隐藏了它实际在做什么。 做同样的事情,更清楚。if (cin.fail())
1赞 natet 9/29/2017
应该注意的是,如果输入类似于 10abc,则 cin.fail 将返回 false。这 10 将被解析为 int,abc 部分将保留在流中等待读取。
1赞 nook 9/11/2013 #2

c 中有一个名为 的函数。这很适合你。例:isdigit()

int var1 = 'h';
int var2 = '2';

if( isdigit(var1) )
{
   printf("var1 = |%c| is a digit\n", var1 );
}
else
{
   printf("var1 = |%c| is not a digit\n", var1 );
}
if( isdigit(var2) )
{
  printf("var2 = |%c| is a digit\n", var2 );
}
else
{
   printf("var2 = |%c| is not a digit\n", var2 );
}

这里

评论

0赞 user2366842 9/11/2013
因此,在变量赋值中更改为字符而不是整数,然后按原样使用其余代码?(并点赞,因为经过这个轻微的调整后,答案仍然非常有用)
0赞 Zac Howland 9/11/2013
因为如果你提供一个字符,istream 将无法插入到整数中,所以你的变量中将包含之前存在的任何数据。
2赞 brunocodutra 9/11/2013
@crush OP 想要检查输入是否是整数值而不是数字
0赞 boxed__l 9/11/2013
@brunocodutra:本来打算发布同样的东西
0赞 jpenna 2/5/2018
"isdigit用于检查中的第一个字符是否为数字,因此是否为要转换为整数值的有效候选字符。stratoi
1赞 Zac Howland 9/11/2013 #3

如果 istream 插入失败,它将设置失败位。

int i = 0;
std::cin >> i; // type a and press enter
if (std::cin.fail())
{
    std::cout << "I failed, try again ..." << std::endl
    std::cin.clear(); // reset the failed state
}

您可以在 do-while 循环中进行设置,以正确插入正确的类型(在本例中)。int

欲了解更多信息,请访问:http://augustcouncil.com/~tgibson/tutorial/iotips.html#directly

评论

0赞 Zac Howland 9/11/2013
正确。我把它留给 OP 来弄清楚,但我想为了清楚起见应该添加它。
-5赞 Eduardo Floriani 11/24/2016 #4

您可以使用:

int a = 12;
if (a>0 || a<0){
cout << "Your text"<<endl;
}

我很确定它有效。

0赞 user6090272 2/13/2017 #5

您可以使用变量名称本身来检查值是否为整数。 例如:

#include <iostream>
using namespace std;

int main (){

int firstvariable;
int secondvariable;
float float1;
float float2;

cout << "Please enter two integers and then press Enter:" << endl;
cin >> firstvariable;
cin >> secondvariable;

if(firstvariable && secondvariable){
    cout << "Time for some simple mathematical operations:\n" << endl;

    cout << "The sum:\n " << firstvariable << "+" << secondvariable 
    <<"="<< firstvariable + secondvariable << "\n " << endl;
}else{
    cout << "\n[ERROR\tINVALID INPUT]\n"; 
    return 1; 
} 
return 0;    
}
3赞 Dúthomhas 12/27/2017 #6

呵呵,这是一个老问题,可以使用更好的答案。

用户输入应以字符串形式获取,然后尝试转换为所需的数据类型。方便的是,这还允许您回答诸如“我的输入是什么类型的数据”之类的问题。

这是我经常使用的功能。存在其他选项,例如在 Boost 中,但基本前提是相同的:尝试执行字符串→类型转换并观察成功或失败:

template <typename T>
auto string_to( const std::string & s )
{
  T value;
  std::istringstream ss( s );
  return ((ss >> value) and (ss >> std::ws).eof())  // attempt the conversion
    ? value                                         // success
    : std::optional<T> { };                         // failure
}

使用类型只是一种方法。您还可以在失败时引发异常或返回默认值。任何适合您情况的方法。optional

以下是使用它的示例:

int n;
std::cout << "n? ";
{
  std::string s;
  getline( std::cin, s );
  auto x = string_to <int> ( s );
  if (!x) return complain();
  n = *x;
}
std::cout << "Multiply that by seven to get " << (7 * n) << ".\n";

限制和类型识别

当然,为了使它起作用,必须存在一种方法来明确地从流中提取数据类型。这是 C++ 中事物的自然顺序——即一切照旧。所以这里没有惊喜。

下一个警告是,某些类型包含其他类型。例如,如果您尝试区分 和 ,请首先检查,因为转换为 an 的任何内容也是 .intdoubleintintdouble

0赞 Ingo Mi 6/20/2020 #7

我更喜欢用它来检查一个,直到它被通过。<limits>int

#include <iostream>
#include <limits> //std::numeric_limits

using std::cout, std::endl, std::cin;

int main() {
    int num;
    while(!(cin >> num)){  //check the Input format for integer the right way
        cin.clear();
        cin.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
        cout << "Invalid input.  Reenter the number: ";
      };

    cout << "output= " << num << endl;

    return 0;
}
0赞 Chirag 7/13/2021 #8

在 C++11 及更高版本下,我发现 std::stoi 函数对此任务非常有用。如果无法执行转换,则 STOI 会抛出 invalid_argument 异常。这可以被捕获和处理,如下面的演示函数“getIntegerValue”所示。

stoi 函数具有第二个参数“idx”,用于指示字符串中第一个字符在数字之后的位置。我们可以使用 idx 中的值来检查字符串长度,并确定输入中是否有除数字以外的任何字符。这有助于消除 10abc 或十进制值等输入。

这种方法失败的唯一情况是输入中的数字后面有尾随空格,即用户在输入数字后输入了很多空格。要处理这种情况,您可以按照本文中的描述对输入字符串进行 rtrim。

#include <iostream>
#include <string>

bool getIntegerValue(int &value);

int main(){
    
    int value{};
    bool valid{};

    while(!valid){
        std::cout << "Enter integer value: ";
        valid = getIntegerValue(value);
        if (!valid)
            std::cout << "Invalid integer value! Please try again.\n" << std::endl;
    }
    
    std::cout << "You entered: " << value << std::endl;

    return 0;
}

// Returns true if integer is read from standard input
bool getIntegerValue(int &value){
    bool isInputValid{};
    int valueFromString{};
    size_t index{};
    
    std::string userInput;
    std::getline(std::cin, userInput);

    try {
        //stoi throws an invalid_argument exception if userInput cannot be
        //converted to an integer.
        valueFromString = std::stoi(userInput, &index);

        //index being different than length of string implies additional
        //characters in input that could not be converted to an integer.
        //This is to handle inputs like 10str or decimal values like 10.12
        if(index == userInput.length()) isInputValid = true;
    }
    catch (const std::invalid_argument &arg) {
        ;       //you could show an invalid argument message here.
    }

    if (isInputValid) value = valueFromString;

    return isInputValid;
}