Leetcode-颠倒整数
给定一个范围为 32 位 int 的整数,将其颠倒。
例 1:
输入: 123 输出: 321
例 2:
输入: -123 输出: -321
例 3:
输入: 120 输出: 21
注意:
假设我们的环境只能处理 32 位 int 范围内的整数。根据这个假设,如果颠倒后的结果超过这个范围,则返回 0。
转自 https://www.cnblogs.com/ariel-dreamland/p/8706403.html
解题思路:
C++参考答案一:
1 /** 2 * Correct but can refactor the code. 3 */ 4 class Solution { 5 public: 6 int reverse(int x) { 7 long long res = 0; 8 bool isPositive = true; 9 if (x < 0) { 10 isPositive = false; 11 x *= -1; 12 } 13 while (x > 0) { 14 res = res * 10 + x % 10; 15 x /= 10; 16 } 17 if (res > INT_MAX) return 0; 18 if (isPositive) return res; 19 else return -res; 20 } 21 };
仔细一想,实验证明正负号不影响计算,而且没有用long long型数据,感觉写的更好一些,那么解法如下:
C++参考答案二:
1 class Solution { 2 public: 3 int reverse(int x) { 4 int res = 0; 5 while (x != 0) { 6 if (abs(res) > INT_MAX / 10) return 0; 7 res = res * 10 + x % 10; 8 x /= 10; 9 } 10 return res; 11 } 12 };
在贴出答案的同时,OJ还提了一个问题 To check for overflow/underflow, we could check if ret > 214748364 or ret < –214748364 before multiplying by 10. On the other hand, we do not need to check if ret == 214748364, why? (214748364 即为 INT_MAX / 10)
为什么不用check是否等于214748364呢,因为输入的x也是一个整型数,所以x的范围也应该在 -2147483648~2147483647 之间,那么x的第一位只能是1或者2,翻转之后res的最后一位只能是1或2,所以res只能是 2147483641 或 2147483642 都在int的范围内。但是它们对应的x为 1463847412 和 2463847412,后者超出了数值范围。所以当过程中res等于 214748364 时, 输入的x只能为 1463847412, 翻转后的结果为 2147483641,都在正确的范围内,所以不用check。
我们也可以用long long型变量保存计算结果,最后返回的时候判断是否在int返回内,参见代码如下:
C++参考答案三:
1 class Solution { 2 public: 3 int reverse(int x) { 4 long long res = 0; 5 while (x != 0) { 6 res = 10 * res + x % 10; 7 x /= 10; 8 } 9 return (res > INT_MAX || res < INT_MIN) ? 0 : res; 10 } 11 };
下面这种方法是上面解法二的变形,其实也不难理解,因为都是用int型的,如果超出了范围,其除以10的结果就不会跟之前的结果一致,通过这点也可以进行区分,参见代码如下:
C++参考答案四:
1 class Solution { 2 public: 3 int reverse(int x) { 4 int res = 0; 5 while (x != 0) { 6 int t = res * 10 + x % 10; 7 if (t / 10 != res) return 0; 8 res = t; 9 x /= 10; 10 } 11 return res; 12 } 13 };
基础知识回顾:
一、
INT_MIN在标准头文件limits.h中定义。
1 #define INT_MAX 2147483647 2 #define INT_MIN (-INT_MAX - 1)
在C/C++语言中,不能够直接使用-2147483648来代替最小负数,因为这不是一个数字,而是一个表达式。表达式的意思是对整数21473648取负,但是2147483648已经溢出了int的上限,所以定义为(-INT_MAX -1)。
C中int类型是32位的,范围是-2147483648到2147483647 。
(1)最轻微的上溢是INT_MAX + 1 :结果是 INT_MIN;
(2)最严重的上溢是INT_MAX + INT_MAX :结果是-2;
(3)最轻微的下溢是INT_MIN - 1:结果是是INT_MAX;
(4)最严重的下溢是INT_MIN + INT_MIN:结果是0 。
二、
求数字的绝对值,vc++提供的库函数的支持,当必须包含:#include <math.h>
其中又分好几种类型:abs、_abs64、fabs、fabsf、labs、_cabs。详细说明如下:
//Calculate the absolute value.
int abs( int n ); long abs( long n ); // C++ only double abs( double n ); // C++ only long double abs( long double n ); // C++ only float abs( float n ); // C++ only __int64 _abs64( __int64 n );
//Calculates the absolute value of the floating-point argument.
double fabs( double x ); float fabs( float x ); // C++ only long double fabs( long double x ); // C++ only float fabsf( float x );
//Calculates the absolute value of a long integer.
long labs( long n );
//Calculates the absolute value of a complex number.
double _cabs( struct _complex z );
以上函数的原型说明来自MSDN2008,可以看出,abs()函数有很多重载形式。一般用abs()就可以满足要求(c++),其它的各种都是一些特例。