子陣列的最大乘積

2021-06-23 02:29:47 字數 4442 閱讀 5589

《程式設計之美》 2.13

問題:給定乙個長度為n的整數陣列,只允許用乘法,不能用除法,計算(n-1)個數的組合乘積中最大的一組,並寫出演算法的時間複雜度。

解法一:把所有n-1個數的組合找出來,分別計算乘積,比較大小。o(n^2)。

int maxsubproducti(int a,int n)

for(j = i + 1; j < n; j++)

if (i == 0) ret = prod;

if (prod > ret) ret = prod;

} return ret;

}int maxsubproductii(int a,int n)

if (i == 0) ret = prod;

if (prod > ret) ret = prod;

} return ret;

}

解法二:利用兩個陣列s和s分別表示從陣列a的兩端開始計算的乘積,s[i] = a[0]*a[1]*...*a[i-1],t[j] = a[j]*...*a[n-1]。那麼p[i] = s[i-1] * t[i+1]。時間複雜度為o(n)。

int maxsubproductiii(int a,int n)

maxprod = (s[n-2] > t[1]) ? s[n-2] : t[1];

for(i = 1; i < n - 1; i ++)

free(s);

free(t);

return maxprod;

}

解法三:統計陣列中正數、負數和零的個數,記錄最小的正數、負數以及最大的負數。

1,如果零的個數n_zero大於1,那麼最大乘積為0;

2,如果零的個數n_zero為1:

(1),如果負數的個數n_neg為奇數,那麼最大乘積為0;

(2),如果負數的個數n_neg為偶數,那麼最大乘積計算式扣除a[zeroi];

3,如果零的個數n_zero為0:

(1),如果負數的個數n_neg為奇數,那麼最大乘積計算式扣除a[maxnegi];

(2),如果負數的個數n_neg為偶數:

1> 如果正數的個數n_pos為零,那麼最大乘積計算式扣除a[minnegi];

2> 如果正數的個數n_pos大於零,那麼最大乘積計算式扣除a[minposi];

int maxsubproductiv(int *a, int n)

else if(maxneg < a[i])

if (minneg == 0)

else if (minneg > a[i])

} else if(a[i] == 0) // a[i] is zero

else // a[i] is positive

else if(minpos > a[i])

} }

if((n_zero == 1) && (n_neg & 0x1))

else if((n_zero == 1) && !(n_neg & 0x1))

else if((n_zero == 0) && (n_neg & 0x1))

else if((n_zero == 0) && !(n_neg & 0x1))

else }

for(int i = 0; i < n; i++)

return max;

}int maxsubproductv(int *a, int n)

else if(maxneg < a[i])

if (minneg == 0)

else

} } else if(a[i] == 0) // a[i] is zero

else // a[i] is positive

else if(minpos > a[i])

} }

if (n_zero)

else

else

} for(int i = 0; i < n; i++)

return max;

}

測試程式:

#include #include #include #include int maxsubproducti(int a,int n)

for(j = i + 1; j < n; j++)

if (i == 0) ret = prod;

if (prod > ret) ret = prod;

} return ret;

}int maxsubproductii(int a,int n)

if (i == 0) ret = prod;

if (prod > ret) ret = prod;

} return ret;

}int maxsubproductiii(int a,int n)

maxprod = (s[n-2] > t[1]) ? s[n-2] : t[1];

for(i = 1; i < n - 1; i ++)

free(s);

free(t);

return maxprod;

}int maxsubproductiv(int *a, int n)

else if(maxneg < a[i])

if (minneg == 0)

else if (minneg > a[i])

} else if(a[i] == 0) // a[i] is zero

else // a[i] is positive

else if(minpos > a[i])

} }

if((n_zero == 1) && (n_neg & 0x1))

else if((n_zero == 1) && !(n_neg & 0x1))

else if((n_zero == 0) && (n_neg & 0x1))

else if((n_zero == 0) && !(n_neg & 0x1))

else }

for(int i = 0; i < n; i++)

return max;

}int maxsubproductv(int *a, int n)

else if(maxneg < a[i])

if (minneg == 0)

else

} } else if(a[i] == 0) // a[i] is zero

else // a[i] is positive

else if(minpos > a[i])

} }

if (n_zero)

else

else

} for(int i = 0; i < n; i++)

return max;

}void show(int a,int n)

printf("\n");

}int main()

show(a,n);

printf("max sub product of n-1 elements: %d .\n",maxsubproducti(a,n));

printf("max sub product of n-1 elements: %d .\n",maxsubproductii(a,n));

printf("max sub product of n-1 elements: %d .\n",maxsubproductiii(a,n));

printf("max sub product of n-1 elements: %d .\n",maxsubproductiv(a,n));

printf("max sub product of n-1 elements: %d .\n",maxsubproductv(a,n));

}

測試輸出:

2  -5 -5 -5 -7 2  

max sub product of n-1 elements: 1750 .

max sub product of n-1 elements: 1750 .

max sub product of n-1 elements: 1750 .

no zero and even negatives

max sub product of n-1 elements: 1750 .

no zero.

max sub product of n-1 elements: 1750 .

ref:

1,程式設計之美 2.13

最大乘積子陣列

程式設計之美 上有一道關於在長度為n的陣列中找到n 1個元素乘積最大的題目,不過這並不是本文要討論的。本文討論的是另一種情況,給定乙個長度為n的浮點陣列,找乙個長度任意的子陣列 子陣列的元素在原陣列中是連續存放的 這個子陣列的乘積最大。通常,找乙個滿足指定條件子陣列都會使用動態規劃。遞迴縮小問題規模...

子陣列最大乘積

給定乙個double型別的陣列arr,其中的元素可正可負可0,返回子陣列累乘的最大乘積。例如arr 2.5,4,0,3,0.5,8,1 子陣列 3,0.5,8 累乘可以獲得最大的乘積12,所以返回12。解析 此題可以運用動態規劃解決 設f i 表示以i為結尾的最大值,g i 表示以i結尾的最小值,那...

子陣列最大乘積

給定乙個double型別的陣列arr,其中的元素可正可負可0,返回子陣列累乘的最大乘積。例如arr 2.5,4,0,3,0.5,8,1 子陣列 3,0.5,8 累乘可以獲得最大的乘積12,所以返回12。分析 設f i 表示以i為結尾的最大值,g i 表示以i結尾的最小值,那麼 f i 1 的最大值與...