Using uint64_t to store a 18 digit number, why this code does not produce desired output

Viewed 69

This is a CSES problem, named number spiral here, I know this is not the efficient way to do this, but it should however work, Can Someone explain to me why it's partially not working, I even tried the same thing with python its giving me timelimitExceeded

#include <bits/stdc++.h>
using namespace std;
int main()
{
    int T;
    cin >> T; //no of test cases
    while(T--){
        uint64_t x, y; //I also tried using long long, but the output is same
        cin >> x >> y;
        if(x%2==0 && y%2!=0 && y< x){
            cout << fixed <<((x*x)-y)+1 << "\n";
        }else if(x%2==0 && y%2!=0 && y>x){
            cout << fixed << ((y*y)-x)+1 << "\n";
        }else if(x%2==0 && y%2==0 && y<x){
            cout << fixed << ((y*y)-x)+1 << "\n";
        }else if(x%2==0 && y%2==0 && y>x){
            cout << fixed << ((pow((y*y)-1, 2))+x)-1 << "\n";
        }else if(x%2!=0 && y%2==0 && y<x){
            cout << fixed << ((y*y)+x)-1 << "\n";
        }else if(x%2!=0 && y%2==0 && y>x){
            cout << fixed << (pow((y-1), 2))+x << "\n";
        }else if(x%2!=0 && y%2!=0 && y<x){
            cout << fixed << (pow((x-1), 2))+y << "\n";
        }else if(x%2!=0 && y%2!=0 && y>x){
            cout << fixed << ((y*y)-x)+1 << "\n";
        }
    }
    return 0;
}

On input : 689913499 770079066
result : 593021767041187712.000000
instead of : 593021767041187724

1 Answers

Using uint64_t to store a 18 digit number

That is reasonable (even a 19 digit number would fit), but it's not what happened, what actually happened is that the pow calls convert the input to a double and also give their result as a double, and a 18-digit number does not quite fit in a double.

Changing the pow calls to a proper integer square fixed the problem for me, at least for this input.

For example:

#include <bits/stdc++.h>
using namespace std;

uint64_t square(uint64_t x)
{
    return x * x;
}

int main()
{
    int T;
    cin >> T; //no of test cases
    while(T--){
        uint64_t x, y;
        cin >> x >> y;
        if(x%2==0 && y%2!=0 && y< x){
            cout << fixed <<((x*x)-y)+1 << "\n";
        }else if(x%2==0 && y%2!=0 && y>x){
            cout << fixed << ((y*y)-x)+1 << "\n";
        }else if(x%2==0 && y%2==0 && y<x){
            cout << fixed << ((y*y)-x)+1 << "\n";
        }else if(x%2==0 && y%2==0 && y>x){
            cout << fixed << ((square((y*y)-1))+x)-1 << "\n";
        }else if(x%2!=0 && y%2==0 && y<x){
            cout << fixed << ((y*y)+x)-1 << "\n";
        }else if(x%2!=0 && y%2==0 && y>x){
            cout << fixed << (square((y-1)))+x << "\n";
        }else if(x%2!=0 && y%2!=0 && y<x){
            cout << fixed << (square((x-1)))+y << "\n";
        }else if(x%2!=0 && y%2!=0 && y>x){
            cout << fixed << ((y*y)-x)+1 << "\n";
        }
    }
    return 0;
}

The result was 593021767041187724, as seen on ideone.

By the way, including bits/std++.h and using namespace std are both generally non-recommended.

Related