LeetCodeAnimation/notes/LeetCode第342号问题:4的幂.md

110 lines
2.8 KiB
Java
Raw Normal View History

2019-05-13 09:14:17 +08:00
# LeetCode 342 号问题4 的幂
2019-05-13 09:08:48 +08:00
题目来源于 LeetCode 上第 342 号问题4 的幂题目难度为 Easy目前通过率为 45.3%
### 题目描述
给定一个整数 (32 位有符号整数)请编写一个函数来判断它是否是 4 的幂次方
**示例 1:**
```
输入: 16
输出: true
```
**示例 2:**
```
输入: 5
输出: false
```
**进阶**
你能不使用循环或者递归来完成本题吗
### 题目解析
这道题最直接的方法就是不停的去除以 4 看最终结果是否为 1 参见代码如下
```java
class Solution {
public boolean isPowerOfFour(int num) {
while ( (num != 0) && (num % 4 == 0)) {
num /= 4;
}
return num == 1;
}
}
```
不过这段代码使用了 **循环** 逼格不够高
对于一个整数而言如果这个数是 4 的幂次方那它必定也是 2 的幂次方
我们先将 2 的幂次方列出来找一下其中哪些数是 4 的幂次方
| 十进制 | 二进制 |
| ------ | ------------------------------- |
| 2 | 10 |
| 4 | **100** 1 在第 3 |
| 8 | 1000 |
| 16 | **10000**1 在第 5 |
| 32 | 100000 |
| 64 | **1000000**1 在第 7 |
| 128 | 10000000 |
| 256 | **100000000**1 在第 9 |
| 512 | 1000000000 |
| 1024 | **10000000000**1 在第 11 |
找一下规律 4 的幂次方的数的二进制表示 1 的位置都是在**奇数位**
之前在小吴的文章中判断一个是是否是 2 的幂次方数使用的是位运算 `n & ( n - 1 )`同样的这里依旧可以使用位运算将这个数与特殊的数做位运算
这个特殊的数有如下特点
* 足够大但不能超过 32 即最大为 1111111111111111111111111111111 31 1
* 它的二进制表示中奇数位为 1 偶数位为 0
符合这两个条件的二进制数是
```java
1010101010101010101010101010101
```
**如果用一个 4 的幂次方数和它做与运算得到的还是 4 的幂次方数**
将这个二进制数转换成 16 进制表示0x55555555 有没有感觉逼格更高点
![](https://bucket-1257126549.cos.ap-guangzhou.myqcloud.com/20190509194742.png)
### 图片描述
![](https://bucket-1257126549.cos.ap-guangzhou.myqcloud.com/20190510090919.jpeg)
### 代码实现
```java
class Solution {
public boolean isPowerOfFour(int num) {
if (num <= 0)
return false;
//先判断是否是 2 的幂
if ((num & num - 1) != 0)
return false;
//如果与运算之后是本身则是 4 的幂
if ((num & 0x55555555) == num)
return true;
return false;
}
}
```