leetcode 650. 2 Keys Keyboard

来源:互联网 发布:linux 看网站访问ip 编辑:程序博客网 时间:2024/05/24 03:21

Initially on a notepad only one character 'A' is present. You can perform two operations on this notepad for each step:

  1. Copy All: You can copy all the characters present on the notepad (partial copy is not allowed).
  2. Paste: You can paste the characters which are copied last time.

Given a number n. You have to get exactly n 'A' on the notepad by performing the minimum number of steps permitted. Output the minimum number of steps to get n 'A'.

Example 1:

Input: 3Output: 3Explanation:Intitally, we have one character 'A'.In step 1, we use Copy All operation.In step 2, we use Paste operation to get 'AA'.In step 3, we use Paste operation to get 'AAA'.

Note:

  1. The n will be in the range [1, 1000].

这道题是典型的递归题啊。

我的思路是,要得到 n 个 A,必然要先得到 n 的整数除数个A ,然后再粘贴而来。比如说要得到 18个A 的最小步数。 
可以是:先得到 9个A 的最小步数,再复制 粘贴1次。
也可以是:先得到 6个A 的最小步数,再复制 粘贴2次。
也可以是:先得到 3个A 的最小步数,再复制 粘贴5次。等等等等。

public int minSteps(int n) {int[] memo=new int[n+1];memo[1]=0;return helper(n, memo);}public int helper(int n,int[] memo){if(n==1||memo[n]>0){ //因为memo[1]=0return memo[n];}memo[n]=n;for(int i=2;i<=n/2;i++){if(n%i==0){int times=n/i;//复制1次+粘贴(times-1)次memo[n]=Math.min(memo[n], helper(i, memo)+times);}}return memo[n];}
我的方法中只求了所有能整除 n 的数的 minSteps,还有大神用的传统 DP,从 2~n 的数都求了一遍。
    public int minSteps(int n) {        int[] dp = new int[n+1];        for (int i = 2; i <= n; i++) {            dp[i] = i;            for (int j = i-1; j > 1; j--) {                if (i % j == 0) {                    dp[i] = dp[j] + (i/j);                    break;                }                            }        }        return dp[n];    }
还有大神用了一种 no 递归,no DP 的方法。

我们先算出前几个数的结果:
1: 0
2: 2
3: 3
4: 4
5: 5
6: 5
7: 7
8: 6
9: 6
10: 7
11: 11
12: 7
13: 13
14: 9
15: 8

现在,让我们举例:
Eg: n=6
To get 6, we need to copy 3 'A's two time. (2)
To get 3 'A's, copy the 1 'A' three times. (3)
So the answer for 6 is 5

Now, take n=9.
We need the lowest number just before 9 such that (9% number =0). So the lowest number is 3.
So 9%3=0. We need to copy 3 'A's three times to get 9. (3)
For getting 3 'A's, we need to copy 1 'A' three times. (3)
So the answer is 6

Finally to analyse the below code, take n=81.
To get 81 we check
if (81 % 2 ==0) No
if (81 % 3 ==0) Yes
So we need to copy 81/3 = 27 'A's three times (3)
Now to get 27 'A's, we need to copy 27/3= 9 'A's three times (3)
To get 9 'A's, we need to copy 9/3=3 'A's three times (3)
And to get 3 'A's, we need to copy 3/3=1 'A's three times (3)
Final answer is 3+3+3+3 = 12

Last Example, n=18
18/2 = 9 Copy 9 'A's 2 times (2)
9/3=3 Copy 3 'A's 3 times (3)
3/3=1 Copy 1'A's 3 times (3)
Answer: 2+3+3= 8

public int minSteps(int n) {    int res = 0;    for(int i=2;i<=n;i++){        while(n%i == 0){            res+= i;            n=n/i;        }    }    return res;}

的情形 发生在 当 n 一直在减少时,这个方法的时间复杂度几乎是 O(log(n))

比如,当 n = 1024 那么 n 将被 2 除,在 10 次除的循环后结束,这种情况会比 O(n) DP 方法要快。

的情形发生在 当 n 是大质数,或者是大质数的乘积时,比如 n = 997 不过这种情况比较少见。


原创粉丝点击