题目描述
给你一根长度为 n 的绳子,请把绳子剪成整数长度的 m 段(m、n都是整数,n>1并且m>1),每段绳子的长度记为 k[0],k[1]…k[m-1] 。请问 k[0]k[1]…*k[m-1] 可能的最大乘积是多少?例如,当绳子的长度是8时,我们把它剪成长度分别为2、3、3的三段,此时得到的最大乘积是18。
示例 1:
输入: 2
输出: 1
解释: 2 = 1 + 1, 1 × 1 = 1
来源:力扣(LeetCode)
链接:https://leetcode-cn.com/problems/jian-sheng-zi-lcof
著作权归领扣网络所有。商业转载请联系官方授权,非商业转载请注明出处。
C++
这道题的动态规划真的不如数论法(实为贪心法);
class Solution {
/*
动态规划 ,Tn=O(n^2);Sn=O(n)
dp[i]表示长度为i的绳子能得到的最大乘积
不能不剪
*/
public:
int cuttingRope(int n) {
if(n<2) return 0;
if(n==2) return 1;
if(n==3) return 2;
vector<int> dp(n+1);
dp[1]=1;
dp[2]=2;
dp[3]=3;
for(int i=4;i<=n;i++){
int res=0;
for(int j=1;j<=i/2;j++)
{
res=max(dp[j]*dp[i-j],res);
}
dp[i]=res;
}
return dp[n];
}
};
class Solution {
/*
思路:只有绳子长度是给定,绳子段数是待定,求得是不同划分能够得到得长度乘积的最大值。
1.m<=n
2.每一段都大于1才会更长
3.2*3>1*5,一切数都可以由2,3,1相加得来,本题最好不含1,所以2和3越多越好,所以3越多越好
4.m>1,n>1
*/
public:
int cuttingRope(int n) {
//根据题目得,n>1
if(n==2) return 1;
if(n==3) return 2;
int sum=1;
while(n>4){ //2*2>1*3,为了一个1也不含,宁愿少个3
sum*=3;
n-=3;
}
return n*sum;
}
};