打卡活动7-算法6. 整数反转

108 阅读2分钟

Offer 驾到,掘友接招!我正在参与2022春招打卡活动,点击查看活动详情

一、题目

给你一个 32 位的有符号整数 x ,返回将 x 中的数字部分反转后的结果。

如果反转后整数超过 32 位的有符号整数的范围 [−231, 231 − 1] ,就返回 0。

假设环境不允许存储 64 位整数(有符号或无符号)。

示例 1:

输入:x = 123
输出:321

示例 2:

输入:x = -123
输出:-321

示例 3:

输入:x = 120
输出:21

示例 4:

输入:x = 0
输出:0

二、我的解答

第一次解答:

这个问题最烦的是值域范围的考虑。一直纠结于边界条件判断,试图通过比较MAX_VALUE和输入数字n反转后的每一位,但是反转后发现比较过程中就出现了溢出现象,然后又想通过反转后的数字reverse与MAX_VALUE mod 10去比较,其实很接近于官方解答了,但判断条件越发复杂,代码逻辑很不优雅。直接看答案了

重点在于2^31和2^31-1最大位为2,也就是说如果数字小于10位时不用去考虑越界问题。等于10位时,只用比较反转后的数字reverse前9位与最大最小值的前9位即可。因为输入数字为10位时,最高位不可能超过2,就是说反转之后reverse的最低位最大为2,不可能超过7,所以前9位不超过最大最小值前9位时,第10位(最低位)不存在超过最大最小值最低位的情况,也就自然不用关注最低位了。

class Solution {    public static int reverse(int x) {        int xCopy = x;        if (x < 0) {            xCopy = x * -1;        }        String xString = String.valueOf(xCopy);        char[] chars = new char[xString.length()];        for (int i = 0; i < xString.length(); i++) {            chars[i] = xString.charAt(i);        }        xString = "";        for (int i = chars.length - 1; i >= 0; i--) {            xString = xString + chars[i];        }        int start = power(2, 31) - 1;        int end = -power(2, 31) ;        String positiveString = String.valueOf(start);        String negativeString = String.valueOf(end);        negativeString=negativeString.substring(1);        if (x > 0) {            if (xString.length() > positiveString.length()) {                return 0;            } else if (xString.length() == positiveString.length()) {                for (int i = 0; i <xString.length(); i++) {                    if (Integer.valueOf(xString.charAt(i)) < Integer.valueOf(positiveString.charAt(i))) {                        break;                    }else if (Integer.valueOf(xString.charAt(i)) > Integer.valueOf(positiveString.charAt(i))) {                        return 0;                    }                }            }        } else {            if (xString.length() > negativeString.length()) {                return 0;            } else if (xString.length() == negativeString.length()) {                for (int i = 0; i <xString.length(); i++) {                    //如果有一个数小于范围,就跳出循环                    if (Integer.valueOf(xString.charAt(i)) <Integer.valueOf(negativeString.charAt(i))) {                      break;                    }else  if (Integer.valueOf(xString.charAt(i)) >Integer.valueOf(negativeString.charAt(i))) {                        //如果有一个数大于范围就返回0                        return 0;                    }                }            }        }        if (x < 0) {            xString = "-" + xString;        }        return Integer.valueOf(xString);    }    private static int power(int i, int j) {        for (int w = 0; w < j-1; w++) {            i = i * 2;        }        return i;    }}

三、系统解答

方法一:数学

思路与算法

class Solution {
    public int reverse(int x) {
        int rev = 0;
        while (x != 0) {
            if (rev < Integer.MIN_VALUE / 10 || rev > Integer.MAX_VALUE / 10) {
                return 0;
            }
            int digit = x % 10;
            x /= 10;
            rev = rev * 10 + digit;
        }
        return rev;
    }
}

复杂度分析

  • 时间复杂度:O(log∣x∣)。翻转的次数即x十进制的位数。

  • 空间复杂度:O(1)。