Reputation: 647
Whenever I input an age of 65 or less, I get a number somewhere less than 2,100,000. However, when I input an age of 68 or higher, the result is instantly put at 18,446,744,071,590,568,320, which is the maximum value for uint64_t. I have no idea why there is this jump in results. It works fine all the way until about 2,100,000.
// How many seconds have I lived?
#include <stdio.h>
#include <string>
#include <cstdint>
using namespace std;
string addCommas(uint64_t answer);
int main ()
{
int seconds = 60, minutes = 60, hours = 24, days = 365;
int years; uint64_t secondsLived, secondsAwake;
printf("How many years have you lived? ");
scanf("%d",&years);
secondsLived = seconds*minutes*hours*days*years;
secondsAwake = (float)secondsLived*0.666;
printf("\nYou have existed for %s seconds\n",addCommas(secondsLived).c_str());
printf("You have been awake for %s seconds\n",addCommas(secondsAwake).c_str());
}
string addCommas(uint64_t answer){
string num = to_string(answer);
int insertplace = (int)num.length() - 3;
while (insertplace > 0) {
num.insert(insertplace, ",");
insertplace-=3;
}
return num;
}
Here are a couple outputs:
How many years have you lived? 67
You have existed for 2,112,912,000 seconds
You have been awake for 1,407,199,392 seconds
How many years have you lived? 69
You have existed for 18,446,744,071,590,568,320 seconds
You have been awake for 12,285,531,553,090,562,048 seconds
Upvotes: 0
Views: 175
Reputation: 727077
Since seconds
, minutes
, hours
, days
, and years
are all signed integers, the entire computation is done in signed integers. When you enter a large number of years, it overflows int
. When the overflown result gets converted to unsigned 64-bit integer, you get a very large number because of the way that negative numbers are represented in two's complement system.
Declaring any of the unit variables (say, years
) a uint64_t
would fix this problem:
int seconds = 60, minutes = 60, hours = 24, days = 365;
uint64_t years, secondsLived, secondsAwake;
Upvotes: 2
Reputation: 207006
In this line:
secondsLived = seconds*minutes*hours*days*years;
You are multiplying a number of int
s together and then you assign the result to the uint_64
. The computation on int
s overflows.
Cast at least one of the values to uint_64
before multiplying them together, so that the computation is done on uint_64
values:
secondsLived = (uint_64)seconds*minutes*hours*days*years;
Upvotes: 4
Reputation: 182883
secondsLived = seconds*minutes*hours*days*years;
The fact that you assign the result to a uint64_t
has no effect on how it's computed.
Upvotes: 3