编程之美读书笔记2.13—子数组的最大乘积

来源:互联网 发布:忽略的网络怎么恢复 编辑:程序博客网 时间:2024/06/08 02:30

1.时间复杂度O(N^2)

2.时间复杂度O(N),组A[N],设去除第i个元素的乘积为A[0]*A[1]*…A[i-1] * A[i+1]*A[i+2]*…A[N-1],则可以写出如下算法满足复杂度为Ο(N)。  

    设f[i]=A[0]*A[1]*…A[i], r[i]=A[i]*A[i+1]*…A[N]则p[i] = f[i-1]*r[i+1]。

3.时间复杂度O(N),进一步减少计算量。子数组最大乘积问题可以分为以下几种情况。  

1.数组中有多于一个零则最大乘积为0;

2.数组中只有一个零,而有奇数个负数,则最大乘积必定为0;

3.数组中只有一个零,而有偶数个负数,则最大乘积为除去0的元素的乘积;  

4.数组中没有零,而有奇数个负数,则最大乘积为除去绝对值最小的负数的乘积;  

5.数组中没有零,而有偶数个负数,则最大乘积为除去最小的正数的乘积。

遍历一遍数组得到数组中正数、负数,零的个数,以及绝对值最小的正数和负数

#include<iostream>#include<cstdlib>#include<ctime>using namespace std;long long LevelOne(int data[],int maxsize){long long max=0;for (int i=0;i<maxsize;i++){ int ret=1;for (int j=0; j<maxsize; j++){if(i!=j){ret*=data[j];            if(data[j]==0)          break;} }  max = (max<=ret ? ret : max);}return max;}long long LevelTwo( int *d, unsigned int n){int *f=new int [n];int *r=new int [n];long long *p = new long long [n];long long max=0;long long fv=1,rv=1;for(int i=0; i<n; i++){int j = n-i-1;fv *= d[i];rv *= d[j];f[i] = fv;r[j] = rv;}max = r[1];for(int i=1; i<n-1; i++){     p[i] = f[i-1] * r[i+1]; max = max<p[i] ? p[i] : max;}delete [] f;delete [] r;delete [] p;return max;}long long LevelThree(int *d, int n){int n_zero = 0;int n_neg = 0;int maxneg = 0;int minpos = 0;int maxnegi = 0;int minposi = 0;int zeroi = 0;int out;long long max = 1;for(int i=0; i<n; i++){if(d[i] < 0){n_neg++;     //负数个数if(maxneg == 0)     //最大负数{maxneg = d[i];maxnegi = i;}else if(maxneg<d[i]){maxneg = d[i];maxnegi = i;}}else if(d[i] == 0){zeroi = i;if(++n_zero>1) return 0;  //至少两个0,返回结果0}else{if(minpos == 0){minpos = d[i];minposi = i;}else if(minpos > d[i])        //最小正数{minpos = d[i];minposi = i;}}}if(n_zero==1 && n_neg%2==1)    {return 0;}else if(n_zero==1 && n_neg%2==0){out = zeroi;}else if(n_zero==0 && n_neg%2==1){out = maxnegi;}else if(n_zero==0 && n_neg%2==0){out = minposi;}for(int i=0; i<n; i++){max *= (i==out)?1:d[i];}return max;}int main(){const int maxsize = 10;int data[maxsize];long long max1,max2,max3;srand(time(NULL));for(int i=0; i<maxsize; i++)    data[i] = ((rand()%10<2) ? -1:1) * (rand()%10);for(int i=0; i<maxsize; i++)cout<<data[i]<<" ";cout<<endl; max1 = LevelOne(data, maxsize); cout<<"max: "<<max1<<endl;  max2= LevelTwo(data, maxsize); cout<<"max: "<<max2<<endl; max3= LevelThree(data, maxsize); cout<<"max: "<<max3<<endl;return 0;}


0 0