题目描述
给你一根长度为n的绳子,请把绳子剪成整数长的m段(m、n都是整数,n>1并且m>1),每段绳子的长度记为k[0],k[1],…,k[m]。请问k[0]xk[1]x…xk[m]可能的最大乘积是多少?例如,当绳子的长度是8时,我们把它剪成长度分别为2、3、3的三段,此时得到的最大乘积是18。
输入描述:
输入一个数n,意义见题面。(2 <= n <= 60)
输出描述:
输出答案。
示例1
输入
8
输出
18
贪心算法:
贪心算法的基本思路是从问题的某一个初始解出发一步一步地进行,根据某个优化测度,每一步都要确保能获得局部最优解。每一步只考虑一个数据,他的选取应该满足局部优化的条件。若下一个数据和部分最优解连在一起不再是可行解时,就不把该数据添加到部分解中,直到把所有数据枚举完,或者不能再添加算法停止。
解题:
题意:一段长度大于2的绳子,分成不能少于2段的绳子,求分后的绳子乘积最大值。
按照贪心算法,每次按照局部最大求解。
length=2, max=1*1=1
length=3, max=1*2=2
比4小的数差分下来做乘积都比原来的数小。
拆分4是个临界值:4=2*2。
length=4, max=2*2=4
拆分5时,5<max=2*3=6,出现拆分后的数的乘积大于原来的数。
我们尽可能多的剪长度为3的绳子:当剩下的绳子长度为4时,把绳子剪成两段长度为2的绳子。
关键:length=5,max=2*3=6
length=6, max=3*3=9
length=7, max=3*4=12
length=8, max=3*3*2=18
…
Java代码:
public int cutRope(int length) {
if (length == 2)
return 2;
else if (length == 3)
return 3;
else {
// (target>=4)
int a = length % 3;//求出拆分3之后剩下的余数
int b = length / 3;//求出有多少个3
if (a == 0)//刚好拆分3拆分完
return (int) (Math.pow(3, b));
else if (a == 1)//余数为1,说明把4拆分了;所以把3的个数减1
return (int) (Math.pow(3, b - 1) * 4);
else //(a==2)
return (int) (Math.pow(3, b) * 2);
}
}