繁体   English   中英

cin溢出时来自cin的异常行为

[英]Unexpected behavior from cin when overflowing int

所有,这里有一些我无法解释其行为的代码。 它发布在下面。 我查看了为什么整数溢出会导致C ++ iostream错误? ,但并不能真正回答我的问题。

#include <iostream>
#include<stdio.h>
using namespace std;
int main()
{
    int x;
    scanf("%d", &x);
    cout << "Value of x = " << x << endl;
    cin >> x;
    cout << "Failure Detected = " << cin.fail() << endl;
    cout << "Value of x = " << x << endl;
    return 0;
}

因此,我期望此代码执行的操作是读入一个整数,打印出该整数的值,读入另一个整数(读入同一变量),然后打印出该整数。 如果输入7和2的输入,那么它将按预期工作。 但是,如果我为第一个和第二个输入都输入2 ^ 31(溢出int乘以1),则第一个输出将显示“ x的值= -2147483648”,第二个输出将显示“ x的值= 2147483647”。 cin.fail()也将返回true。 cin对输入做了什么? 我以为如果cin.fail()为true,则x的值应保持不变。 如果不受影响,我希望x的值像正常情况一样溢出(就像scanf一样)。 cin这是怎么回事? 为什么将值限制为整数最大值?

提前致谢!

在C ++ 98中,输入失败时变量未更改。 如果您尝试输入一个未初始化的变量,这是一个缺点。

例如:

int a;
cin >> a;
cout << a;    // UB if input failed!

在以后的标准中,当输入超出该范围时,变量将设置为可能的最大值或最小值。


对于operator>>(int& val) ,标准说[istream.formatted.arithmetic]:

转换似乎由以下代码片段执行(使用与前面的代码片段相同的表示法):

typedef num_get<charT,istreambuf_iterator<charT,traits> > numget;
iostate err = ios_base::goodbit;
long lval;
use_facet<numget>(loc).get(*this, 0, *this, err, lval);
if (lval < numeric_limits<int>::min()) {
  err |= ios_base::failbit;
  val = numeric_limits<int>::min();
} else if (numeric_limits<int>::max() < lval) {
  err |= ios_base::failbit;
  val = numeric_limits<int>::max();
} else
  val = static_cast<int>(lval);
setstate(err);
  1. 您的scanf :C ++中溢出有符号整数类型的行为是不确定的 推测幕后发生的事情是毫无意义的。 “正常溢出”尤其没有意义。

  2. 您的cin :C ++ 03之前的版本,如果x无法容纳输入,则不会更改x 因此,后续cout的行为将是不确定的,因为您将回读未初始化的变量。 从C ++ 03开始,如果超出x的范围,则将x为最大(或最小)值。 那就是第二种情况。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM