-1

Hello I am trying a simple reverse integer operation in c++. Code below:

#include <iostream>
#include <algorithm>
#include <climits>

using namespace std;

class RevInteger {

public:
    int reverse(int x) 
    {
        int result = 0;
        bool isNeg = x > 0 ? false : true;
        x = abs(x);

        while (x != 0) 
        {
            result = result * 10 + x % 10;
            x = x / 10;
        }

        if (isNeg) 
            result *= -1;

        if (result > INT_MAX || result < INT_MIN)
            return 0;
        else
            return (int)result;
    }
};

When I give it an input as 1534236469; I want it to return me 0, instead it returns me some junk values. What is wrong in my program. Also, I am trying to use the climits lib for the purpose, is there a simpler way of doing the same?

Khalil Khalaf
  • 9,259
  • 11
  • 62
  • 104
blackmamba591
  • 151
  • 2
  • 11
  • 3
    I am afraid it is unclear what you are asking for. What did you mean by "_reverse_"? `0` is not the reverse of `1534236469`. so what do you want the relation between your Inputs and Outputs to be? – Khalil Khalaf Sep 13 '16 at 19:39
  • The right tool to solve such problems is your debugger. You should step through your code line-by-line *before* asking on Stack Overflow. For more help, please read [How to debug small programs (by Eric Lippert)](https://ericlippert.com/2014/03/05/how-to-debug-small-programs/). At a minimum, you should \[edit] your question to include a [Minimal, Complete, and Verifiable](http://stackoverflow.com/help/mcve) example that reproduces your problem, along with the observations you made in the debugger. – πάντα ῥεῖ Sep 13 '16 at 19:41
  • 1
    `result` is an `int`. It can never be larger than `INT_MAX` or less than `INT_MIN`. – M.M Sep 13 '16 at 20:05
  • @FirstStep ... for integer values for eg : 123 I should receive the reverse 321 or for -123 i should have -321. however , when there is such a long integer it should just throw a 0. Hope it is clear. – blackmamba591 Sep 14 '16 at 01:55
  • @πάνταῥεῖ .. I have used break points and checked my results step by step. It never checks the if condition for the result to be bigger than INT_MAX or INT_MIN – blackmamba591 Sep 14 '16 at 01:57
  • @ArunavaNag the compiler will remove those checks because it is impossible – M.M Sep 14 '16 at 02:07
  • @M.M changed result to long long ... thanks – blackmamba591 Sep 14 '16 at 02:07

4 Answers4

2

The simplest approach is to use long long in place of int for the result, and check for overflow at the end:

long long result = 0;
/* the rest of your code */
return (int)result; // Now the cast is necessary; in your code you could do without it

Another approach is to convert the int to string, reverse it, and then use the standard library to try converting it back, and catch the problems along the way (demo):

int rev(int n) {
    auto s = to_string(n);
    reverse(s.begin(), s.end());
    try {
        return stoi(s);
    } catch (...) {
        return 0;
    }
}

If you must stay within integers, an approach would be to check intermediate result before multiplying it by ten, and also checking for overflow after the addition:

while (x != 0) {
    if (result > INT_MAX/10) {
        return 0;
    }
    result = result * 10 + x % 10;
    if (result < 0) {
        return 0;
    }
    x = x / 10;
}
Sergey Kalinichenko
  • 714,442
  • 84
  • 1,110
  • 1,523
  • Thanks @dasblinkenlight , converting the result to long long works. However in VS2015 it throws a warning C4244: 'argument': conversion from '__int64' to 'int', possible loss of data – blackmamba591 Sep 14 '16 at 02:05
  • @ArunavaNag The warning is OK after a check that the value is less than or equal to INT_MAX. – Sergey Kalinichenko Sep 14 '16 at 08:25
1
class Solution {
public:
    int reverse(int x) {
        int reversed = 0;

        while (x != 0) {
            if (reversed > INT_MAX / 10 || reversed < INT_MIN / 10) return 0;
            reversed = reversed * 10 + (x % 10);
            x /= 10;
        }        
        return reversed;
    }
};

If reversed bigger than 8 digit INT_MAX (INT_MAX / 10), then if we add 1 digit to reversed, we will have an int overflow. And similar to INT_MIN.

Xcoder
  • 1,433
  • 3
  • 17
  • 37
sploitem
  • 11
  • 3
0

As suggested by @daskblinkenlight; changing the result as long long and type casting at the end solves the problem.

Working class:

class intReverse {

public:
int reverse(int x) {

    long long result = 0;  // only change here
    bool isNeg = x > 0 ? false : true;
    x = abs(x);
    while (x != 0) {
        result = result * 10 + x % 10;
        x = x / 10;
    }
    if (isNeg) {
        result *= -1;
    }
    if (result > INT_MAX || result < INT_MIN)
    {
        return 0;
    }
    else
    {
        return (int) result;
    }

  }
};
blackmamba591
  • 151
  • 2
  • 11
0
int reverse(int x) {
        int pop = 0;
        int ans = 0;
        while(x) {
            // pop
            pop = x % 10;
            x /= 10;

            // check overflow
            if(ans > INT_MAX/10 || ans == INT_MAX/10 && pop > 7) return 0;
            if(ans < INT_MIN/10 || ans == INT_MIN/10 && pop < -8) return 0;

            // push
            ans = ans * 10 + pop;

        }
        return ans;
    }
Ahmed Eid
  • 192
  • 1
  • 8