0
#include <iostream>
using namespace std;
int main()
{
  int intVar =1500000000;
  intVar = (intVar *10)/10;
  cout << "Value intVar equal "<<intVar <<endl;

  intVar =1500000000;
  intVar = (static_cast<double>(intVar)*10)/10;
  cout << "Value intVar equal " <<intVar<<endl;

  return 0;
}

In this example, the first answer must be incorrect (211509811) due limit of variable type int, but it isn`t. What is wrong?

7
  • 2
    What is a "limit" of variable type int? Did you check the output of cout << std::numeric_limits<int>::max()? Commented Aug 21, 2018 at 13:34
  • 6
    "In this example, the first answer must be incorrect" Signed integer overflow is undefined behavior.. Commented Aug 21, 2018 at 13:35
  • 2
    disable optimization and you'll see what you expected Commented Aug 21, 2018 at 13:35
  • 2
    Undefined behavior does not mean that the result must be incorrect. It means the program can do anything, including producing a result, including a result that you would mathematically expect. It can be argued that undefined behavior that appears produces the expected behavior is the most dangerous kind of undefined behavior, or at least the most treacherous. Commented Aug 21, 2018 at 13:36
  • a wrong result can still have the correct value (you just cant rely on that) Commented Aug 21, 2018 at 13:43

4 Answers 4

2

In the first case you are multiplying by 10 and dividing by 10 on the same line with nothing that can break the compiler optimizations (no function calls, variable assignments, etc.). So any decent compiler will neither multiply nor divide, the same value will be stored, and I guess that is what happened to you.

But if you break that optimization by, say, making the operation in successive calls, it may give the value you seek, e.g.:

intVar =1500000000;
intVar*=10;
intVar/=10;
cout << "Value intVar equal "<<intVar <<endl;

Possible output:

Value intVar equal 211509811

Example

But note that, in both cases, you are opening the door of Undefined Behavior. If I were you, I would not rely on the compiler optimizations or any lack thereof, especially if you work with different compilers and/or different platforms.

Sign up to request clarification or add additional context in comments.

Comments

2

In this example, the first answer must be incorrect (211509811) due limit of variable type int, but it isn`t. What is wrong?

Your expectation is wrong. The behaviour of signed integer overflow is undefined. There is no requirement for the answer to be "incorrect". After all, there is no "correct" answer for a program that has undefined behaviour.

Comments

1

Your example invokes Undefined Behavior (UB), since signed integer overflow occurs.

When UB is invoked you cannot predict with certainty what will happen. That's what happens, thus your prediction is inaccurate. And if you change your prediction completely, since UB is invoked, it will still be inaccurate.

Comments

-1

You save 1,500,000,000 in an (signed)int which can hold 2,147,483,647 so you are still within the limits of an singed int. Your operation below that will be erased by the optimizer.

1 Comment

optimizations are according to the as-if-rule. So an optmization of the *10)/10 is performed as if there was overflow (assuming *10 does overflow), thus compiler could as well "optimize" the line to intVar = 42;

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.