版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/HaloTrriger/article/details/80615869
题目大意是这样,给出一串数字,求出所有子串中最大的和。
我的第一感觉是穷举法,默认第一个数字为最大值Max。从第一个开始,找出由它构成所有子串的和,依次和Max比较,更新Max值;然后第二个数字开始向后找由它构成所有子串的和,依次和Max比较,更新Max值;然后是第三个…。最后Max就是最大的了。(为什么从每个数字向后找子串不加它之前的?因为之前的数字早就算过当时包括它的子串和了。)
代码如下:
int FindMaxSumOfSubArray(int array[], int size)
{
//给Max赋值,默认第一个是最大
int Max = array[0];
for (int i = 0; i < size; i++)//穷举找出
{
//每次都判断arr[i]是否大于Max
int tmp = array[i];
if (Max < tmp)
Max = tmp;
//向arr[i]后面的所有子串找最大值
for (int j = i + 1; j < size; j++)
{
tmp += array[j];
if (tmp > Max)
Max = tmp;
}
}
return Max;
}
当然,聪明的人用的是另一种高明的方法
定义两个变量,一个curMax,一个finalMax。curMax记录当前最大值,finalMax记录最终的最大值。
curMax将之前值的和记录下来(此时curMax是之前和的最大的值)。如果小于0,置为当前值;否则,累加。如果curMax大于finalMax,更新finaMax(finalMax是最终的最大值)。
代码如下:
int FindMaxSumOfSubArray(int array[], int size)
{
int curMax = array[0];
int finalMax = array[0];
//之前的最大值小于0,丢弃,置为现在的值
//curMax小于0的话,若array[i]大于0,最大值为array[i],
//若array[i]小于0,可以用保存着之前最大值finalMax和curMax比较
for (int i = 1; i < size; i++)
{
if (curMax < 0)
curMax = array[i];
else
curMax += array[i];
//如果当前最大值大于之前最大,更新最大值
if (curMax > finalMax)
finalMax = curMax;
}
return finalMax;
}
为什么curMax小于0就丢弃呢?
因为curMax是负数。
1. arr[i] 是正数,arr[i] 和 arr[i] 与负数的和相比,大者应选arr[i]。
2. arr[i] 是负数,
①如果 arr[i] 比curMax大,arr[i] 和两个负数之和相比,大者应该选arr[i]。
②如果 arr[i] 比curMax小,arr[i] 赋给curMax,此时curMax并不是最大的。而之后与finalMax的判断语句,恰好与之前最大值作比较,将此时的curMax丢弃。做到了fianlMax始终保持着最大和。
最后,有什么疑问,或者质疑,欢迎留言给我。