2021.11.19 - 155.整数替换

1. 题目

在这里插入图片描述

2. 思路

(1) 递归

  • 当n为偶数时,替换次数为n/2的替换次数+1。
  • 当n为奇数时,替换次数为n-1和n+1中替换次数的最小值+1。而n-1的替换次数为(n-1)/2的替换次数+1,即n/2向下取整的替换次数+1;n+1的替换次数为(n+1)/2的替换次数+1,即n/2+1向下取整的替换次数+1。因此,n的替换次数为n/2和n/2+1中替换次数的最小值+2。

(2) 记忆化搜索

  • 由于向前递归时,会出现大量的重复递归,因此,利用全局HashMap存储已经递归过的数字及其替换次数。

(3) 贪心算法

  • 将递归转换为迭代,当n为偶数时,n=n/2,替换次数+1;当n为奇数时,分两种情况,当n%4=1时,n=n/2,替换次数+2;当n%4=3时,n=n/2+1,替换次数+2。
  • 最后单独处理n=3的情况即可。

3. 代码

import java.util.HashMap;
import java.util.Map;

public class Test {
    
    
    public static void main(String[] args) {
    
    
    }
}

class Solution {
    
    
    public int integerReplacement(int n) {
    
    
        if (n == 1) {
    
    
            return 0;
        }
        if ((n & 1) == 0) {
    
    
            return integerReplacement(n / 2) + 1;
        } else {
    
    
            return Math.min(integerReplacement(n / 2), integerReplacement(n / 2 + 1)) + 2;
        }
    }
}

class Solution1 {
    
    
    private Map<Integer, Integer> map = new HashMap<>();

    public int integerReplacement(int n) {
    
    
        if (n == 1) {
    
    
            return 0;
        }
        if (!map.containsKey(n)) {
    
    
            if ((n & 1) == 0) {
    
    
                map.put(n, integerReplacement(n / 2) + 1);
            } else {
    
    
                map.put(n, Math.min(integerReplacement(n / 2), integerReplacement(n / 2 + 1)) + 2);
            }
        }
        return map.get(n);
    }
}

class Solution2 {
    
    
    public int integerReplacement(int n) {
    
    
        int res = 0;
        while (n != 1) {
    
    
            if ((n & 1) == 0) {
    
    
                n /= 2;
                res++;
            } else {
    
    
                if (n % 4 == 1) {
    
    
                    n /= 2;
                } else {
    
    
                    if (n == 3) {
    
    
                        n = 1;
                    } else {
    
    
                        n = n / 2 + 1;
                    }
                }
                res += 2;
            }
        }
        return res;
    }
}