看《编程珠玑》看的郁闷毁了~ 木有激情啊~
这里描述第8章的一道题:求子串最大和:
一个具有n个浮点数的向量x,要求输出相邻子向量的最大和,如图:
程序返回值应为x[2..6]的总和,即187。
在这里直接给出最适合简单的解法:
从数组的最左边x[0]开始扫描,一直到最右端x[n-1]。记录所有遇到的最大总和子向量maxendinghere。数组的最大总和maxsofar的初始值为0。
int MaxChildSum(int X[],int n)
{
int maxsofar = 0;
int maxendinghere = 0;
for (int i=0; i<n; i++)
{
maxendinghere = max(maxendinghere+X[i], 0);
maxsofar = max(maxendinghere, maxsofar);
}
cout<<maxsofar<<endl;
return maxsofar;
}
这个程序的思想就是利用maxendinghere这个变量,它保存这结束位置为i-1的最大子向量和,赋值语句:maxendinghere = max(maxendinghere+X[i], 0);,
判断maxendinghere+X[i],:若为正值,则将maxendinghere增大到i;若为负值,将maxendinghere重新置零。
复杂度只有O(n)。
算法的思量是求累加数组
题目扩展:
查找总和最接近0的子序列?
void MostNearZero(int X[],const int& n)
{
int temp[10];
for (int i=0; i<n; i++)
{
temp[i] += X[i];
}
int minSub=10000,tmp=0;
int left,right;
for(int i=0; i<n; i++)
{
for(int j=i+1; j<n; j++)
{
tmp = abs(temp[i]-temp[j]);
if (tmp<minSub)
{
minSub=tmp;
left=i;right= j;
}
}
}
}
利用累加数组temp[i],temp[i]为元素0到i的和,temp[i]与temp[j]的差,当temp[i]-temp[j]=0时,则元素i到j-1的总和为0。