LeetCode-LCS 01. 下载插件
Posted ZSYL
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了LeetCode-LCS 01. 下载插件相关的知识,希望对你有一定的参考价值。
题目描述
小扣打算给自己的 VS code 安装使用插件,初始状态下带宽每分钟可以完成 1 个插件的下载。假定每分钟选择以下两种策略之一:
- 使用当前带宽下载插件
- 将带宽加倍(下载插件数量随之加倍)
请返回小扣完成下载 n 个插件最少需要多少分钟。
注意:实际的下载的插件数量可以超过 n 个
示例 :
输入:n = 4
输出:3
解释:
最少需要 3 分钟可完成 4 个插件的下载,以下是其中一种方案:
第一分钟带宽加倍,带宽可每分钟下载 2 个插件;
第二分钟下载 2 个插件;
第三分钟下载 2 个插件。
贪心选择
贪心算法:判断当前下载量1分钟是否可以搞定,如果可以就不需要加倍,反之加倍便是最优选择。
class Solution {
public int leastMinutes(int n) {
int res = 0;
int cur = 1;
while (n > 0) {
if (n <= cur) {
n -= cur;
} else {
cur <<= 1;
}
res++;
}
return res;
}
}
回溯算法
每步可以选当前数和不选当前数(加倍)
算法超时
class Solution {
int ans = Integer.MAX_VALUE;
public int leastMinutes(int n) {
backTrack(n, 0, 0, 1);
return ans;
}
public void backTrack(int n, long cur, int idx, long cnt) {
if (idx >= ans) // 剪枝操作
return;
if (cur >= n) {
ans = (ans > idx) ? idx: ans;
return;
}
if (cnt > Integer.MAX_VALUE)
return;
backTrack(n, cur+cnt, idx+1, cnt);
backTrack(n, cur, idx+1, cnt*2);
}
}
动态规划
令 dp[i] 表示下载 i 个插件需要的最少分钟数,则 dp[i] = dp[(i + 1) / 2] + 1;
状态转移方程:dp[i] = dp[(i + 1) / 2] + 1;
等同于第四种数学方法,优先加倍宽带,那个+1就代表只用1天来完成,以10为例,dp【10】=dp【5】+1,dp【5】=dp【3】+1。。。dp【2】=dp【1】+1为止.
class Solution {
public int leastMinutes(int n) {
// dp[i] 表示下载 i 个插件需要的最少分钟数
int[] dp = new int[n+1];
dp[1] = 1;
for (int i = 2; i <= n; i++) {
dp[i] = dp[(i+1)/2]+1;
}
return dp[n];
}
}
数学
一直加倍到大于等于目标值,这时进行一次使用带宽下载即可。
class Solution {
public int leastMinutes(int n) {
return (int)(Math.ceil(Math.log(n)/Math.log(2)) + 1);
}
}
以上是关于LeetCode-LCS 01. 下载插件的主要内容,如果未能解决你的问题,请参考以下文章