0

I want to get a result from casting double type to usigned long long type in c++. But that code have different result from Windows and Linux. Here's my code.

#include <iostream>
#include <cmath>
using namespace std;

int main() {
    cout << (unsigned long long) pow(10, 18) << endl;
    return 0;
}

I just used 'pow' function to get 10 to the 18, and cast it to unsigned long long type. In Windows, It has result of 99999999999999999 (10^18-1), but It has result of 1000000000000000000 (10 ^18) in Linux. I used MinGW g++ for C++11 compilation in Windows and use g++ in Linux. What's the reason of this result? Thanks.

Junhee Park
  • 143
  • 1
  • 9
  • According to [this answer](https://stackoverflow.com/a/21707185/4181011) there is no safe way to perform the cast as you want it safely. I would recommend to find a proper `ipow` implementation to safely calculate powers for integral types. (e.g. https://stackoverflow.com/questions/17719674/c11-fast-constexpr-integer-powers) – Simon Kraemer Nov 13 '17 at 08:41
  • You can also write your own function.There is another example in here https://stackoverflow.com/questions/101439/the-most-efficient-way-to-implement-an-integer-based-power-function-powint-int – Fryz Nov 13 '17 at 11:15
  • 1
    @SimonKraemer The danger happens when the floating point value is out of range for `unsigned long long`. While that is not the case for this specific example, it is something to be aware of – M.M Nov 14 '17 at 01:29
  • @M.M Yeah... I was a bit quick there. At least my comment shows a possible solution by referring to the integer arithmetic solution - though the explanation is wrong in this case. – Simon Kraemer Nov 14 '17 at 07:50

1 Answers1

2

The reason is that pow operates on floating-point values, and different implementations can produce values that differ slightly in their low bits. If you need exact integer results, do integer arithmetic.

Contrary to one of the comments in response to the question, converting the result of this call to unsigned long long is perfectly safe (for some sensible meaning of “safe”): unsigned long long can hold the value that this call to pow returns, and the resulting value will be the floating-point result with its fraction discarded.

Pete Becker
  • 74,985
  • 8
  • 76
  • 165