1.实践题目名称

   最大子列和问题

    2.问题描述

    

给定K个整数组成的序列{ N1​​, N2​​, …, NK​​ },“连续子列”被定义为{ Ni​​, Ni+1​​, …, Nj​​ },其中 1。“最大子列和”则被定义为所有连续子列元素的和中最大者。例如给定序列{ -2, 11, -4, 13, -5, -2 },其连续子列{ 11, -4, 13 }有最大的和20。现要求你编写程序,计算给定整数序列的最大子列和。

本题旨在测试各种不同的算法在各种数据情况下的表现。各组测试数据特点如下:

  • 数据1:与样例等价,测试基本正确性;
  • 数据2:102个随机整数;
  • 数据3:103个随机整数;
  • 数据4:104个随机整数;
  • 数据5:105个随机整数;

输入格式

输入第1行给出正整数K (≤);第2行给出K个整数,其间以空格分隔。

输出格式:

在一行中输出最大子列和。如果序列中所有整数皆为负数,则输出0。

输入样例:

6
-2 11 -4 13 -5 -2
 

输出样例:

20

    3.算法时间及空间复杂度分析(要有分析过程)

    设算法的复杂度为T(N),

    第一步分解为两个子问题为O(1)

    第二步分别求解两个子问题为O(N/2)*2

    第三步合并子问题为O(N)

    等式为:T(N)=O(1)+2T(N/2)+O(N)

    得:T(N)=O(nlogn);

    

    4.心得体会(对本次实践收获及疑惑进行总结)

    其实是对与递归算法的不熟悉和难以理解,最开始时采用了三重循环的方法写代码,但看到最后一个测试点3000多ms时间的复杂度时,才了解为什么要学习新的算法。虽然至今还是很难理解透彻递归的写法和思维。但我还是会多去模仿,多写几次就明白了

    5.代码

    

#include <iostream>
using namespace std;
int max ( int a, int b, int c )
{
if (a>b)
{
if(b>c)
return a;
else
if(a<c)
return c;
}
else if (c<a)
return b;
}

int xing ( int a[], int left, int right )
{
int maxl, maxr;
int summaxl, summaxr;
int suml, sumr;
int mid, i;

if ( left == right )
{
if ( a[left] > 0 ) return a[left];
else return 0;
}

mid = ( left + right ) / 2; //找到中分点。
maxl = xing ( a, left, mid); //递归求左子列和。
maxr = xing( a, mid+1, right ); //递归求右子列和。

summaxl = 0;suml = 0;
for ( i = mid; i >= left; i– )
{
suml += a[i];
if ( suml > summaxl )
summaxl= suml;
}//左边扫描结束。

summaxr = 0; sumr = 0;
for ( i = mid+1; i <= right; i++ )
{
sumr += a[i];
if ( sumr > summaxr )
summaxr = sumr;
}//右边扫描结束。

/*返回“治”的结果*/
return max (maxl, maxr, summaxl + summaxr );
}

int main ()
{
int n,i;
cin>>n;
int a[n];
int left=0,right=n;
for (i=1;i<=n;i++)
{
cin>>a[i];
}
cout<<xing(a,left,right);
}

 

版权声明:本文为lzchenjin原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。
本文链接:https://www.cnblogs.com/lzchenjin/p/13765553.html