给定一个长度为N的整数数组,只允许用乘法,计算任意(N-1)个数的组合乘积中最大的一组。
通过判断数组中0的个数,负数的个数,正数的个数,来求出最大乘积。复杂度为O(N)。
//给定一个长度为N的整数数组,只允许用乘法,计算任意(N-1)个数的组合乘积中最大的一组,并
//写出算法的时间复杂度。
public class MaxMutilCombination {
public static void main(String[] args) {
int[]a={5, 1, 12, -2, 3,-4};
int ex=shouldExculed(a);
for(int i=0;i<a.length;i++){
if(ex==i)continue;
System.out.print(a[i]+" ");
}
}
//返回应该排除的数的序号
public static int shouldExculed(int [] a){
int p,q,r;//p:0的个数 q:负数的个数 r:正数的个数
int i0;//0元素所在的下标
int imin;//最小正数的下标
int mimax,mimin;//最大负数,最小负数的下标
p=q=r=i0=imin=mimax=mimin=0;
for(int i=0;i<a.length;i++){//遍历计算p,q ,r的值,并保存最大值最小值的位置
if(a[i]==0){//0的个数
p++;
i0=i;
}
else if(a[i]<0){//负数的个数
q++;
if(q==1)mimax=mimin=i;
else{
if(a[i]>a[mimax])mimax=i;
if(a[i]<a[mimin])mimin=i;
}
}
else {//正数的个数
r++;
if(r==1)imin=i;
else {
if(a[i]<a[imin])imin=i;
}
}
//1.有两个0时,可以提前结束
if(p==2)return i;//如果有两个0,随便返回一个下标即可,任何组合的积都为0
}
//2.有一个0时
if(p==1){//有一个0,并且奇数个负数时,最大乘积为0,随便去掉一个数即可
return isOdd(q)?mimax:i0;//如果负数的个数为偶数时,则去掉0
}
//3.q=0,全为正数,去掉最小的一个正数即可
if(q==0)return imin;
//4.q为奇数,去掉最大的负数即可,
if(isOdd(q))return mimax;
else if(r>0) return imin;//5.如果正数个数不为0 ,最小的正数
else return mimin;//6.全为负数且是奇数个,去掉最小的负数
}
private static boolean isOdd(int q) {
return 1==(q&0x01);
}
}