最大子列和

  • 问题描述
  • 解决方法
    • 方法一 穷举法
    • 方法二 部分存储中间值
    • 方法三 分治法
    • 方法四 在线处理
  • 测试用例

问题描述

给定n个整数的序列{a1,a2,a3,…,an},求函数f(i,j)= max{0, x}x=∑i≤k≤jakx= \sum_{\mathclap{i\le k \le j}} a_{k}x=i≤k≤j​∑​ak​
即在数组中选定 j - i + 1 个连续的整数,求这些整数的和的最大值。

解决方法

方法一 穷举法

穷举所有子列和,从中找出最大值。

int MaxSubseqSum1(int List[], int N){// :para1 输入数组// :para2 数组长度// :return 最大子列和// 穷举法,穷举所有子列和,找出最大值int i,j,k; // 循环变量int ThisSum = 0, MaxSum = 0;for(i = 0; i < N; ++i){for(j = i; j < N; ++j){ThisSum = 0; //ThisSum 是从i到j的子列和for(k = i; k <= j; ++k){ // 计算i到j的子列和ThisSum += List[k];}if(ThisSum > MaxSum){MaxSum = ThisSum;}}}return MaxSum;
}

方法二 部分存储中间值

// 部分存储中间值,减少重复运算
int MaxSubseqSum2(int List[], int N){int i,j;int ThisSum, MaxSum = 0;for(i = 0; i < N; ++i){ThisSum = 0;for(j = i; j < N; ++j){ThisSum += List[j];  // 新一轮循环只需加上新的j值索引的数组值即可。无需从i重新开始计算if(ThisSum > MaxSum){MaxSum = ThisSum;}}}return MaxSum;
}

方法三 分治法

int Max3(int A, int B, int C){// 返回三个整数的最大值return A > B ? (A > C ? A : C) : (B > C ? B : C);
}int DivideAndConquer(int List[], int left, int right){//:para1 输入数组//:para2 子列左侧//:para3 子列右侧//即求 从List[left] 到List[right]的最大子列和int MaxLeftSum, MaxRightSum; //存放左右子问题的解int MaxLeftBorderSum, MaxRightBorderSum; // 存放跨分界线的结果int LeftBorderSum, RightBorderSum;int center, i;if(left == right){  // 递归终止条件,子列只有一个数字if(List[left] > 0) return List[left];else return 0;}// 下面是‘分’的过程center = (left + right) / 2; // 找到中分点// 递归求得两边子列的最大和MaxLeftSum = DivideAndConquer(List, left, center);MaxRightSum = DivideAndConquer(List, center + 1, right);// 下面求跨分界线的最大子列和MaxLeftBorderSum = 0;LeftBorderSum = 0;for(i = center; i >= left; --i){// 从中线向左扫描LeftBorderSum += List[i];if(LeftBorderSum > MaxLeftBorderSum){MaxLeftBorderSum = LeftBorderSum;}}MaxRightBorderSum = 0;RightBorderSum = 0;for(i = center+1; i <= right; ++i){// 从中线向右扫描RightBorderSum += List[i];if(RightBorderSum > MaxRightBorderSum){MaxRightBorderSum = RightBorderSum;}}// 下面返回‘治’的结果return Max3(MaxLeftSum, MaxRightSum, MaxLeftBorderSum+MaxRightBorderSum);}int MaxSubseqSum3(int List[], int N){// 分治法,将原始序列一分为二,最大子列在左半边、右半边或横跨左右边// 1、递归求得两子列的最大和S左和S右// 2、从中分点分头向左右两边扫描,找出跨过分界线的最大子列和S中// 3、Smax = max{S左,S右,S中}return DivideAndConquer(List, 0, N-1);
}

方法四 在线处理

// 在线处理
// 每输入一个数据就即时处理。前三种是所有整数读入并存储后才可进行运算。在线处理不需要。在发现当前子列和
// 为负数时,可重新考察新的子列。
int MaxSubseqSum4(int List[], int N){int i;int ThisSum = 0, MaxSum = 0;for(i = 0; i < N; ++i){ThisSum += List[i];if(ThisSum > MaxSum) MaxSum = ThisSum;else if(ThisSum < 0) // 发现当前子列和为负数,不可能使后面的部分和增大,舍去ThisSum = 0;}return MaxSum;
}

测试用例

int main(){int List[] = { -1, 3, -2, 4, -6, 1, 6, -1 };printf("The MaxSum1 is %d\n", MaxSubseqSum1(List, 8));printf("The MaxSum2 is %d\n", MaxSubseqSum2(List, 8));printf("The MaxSum3 is %d\n", MaxSubseqSum3(List, 8));printf("The MaxSum4 is %d\n", MaxSubseqSum4(List, 8));system("pause");return 0;
}

最大子列和问题(C语言)相关推荐

  1. pta上c语言运行超时怎么解决,PTA测试题- 最大子列问题(C语言)

    原题目: 原本是不会的,不过CSDN上的大神的blog给了我启发.先上代码: #include int main() { int i,n,max = 0,Max = 0,t; scanf(" ...

  2. 最大子列和问题(JAVA)

    最大子列和 问题描述:给定N个整数的序列{A1,A2,A3,-,An},求解子列和中最大的值. 这里我们给出{-2,11,-4,13,-5,-2}这样一个序列,正确的最大子列和为20 该题是在数据结构 ...

  3. 7-1 最大子列和问题

    https://pintia.cn/problem-sets/15/problems/709 给定K个整数组成的序列{ N​1​​, N​2​​, ..., N​K​​ },"连续子列&qu ...

  4. 7-1 最大子列和问题 (20 分)

    7-1 最大子列和问题 (20 分) 给定K个整数组成的序列{ N1, N​2​​ , -, N​K​​ },"连续子列"被定义为{ N​i , Ni+1 , -, N​j​​ } ...

  5. 01-复杂度1 最大子列和问题 (20 分)

    给定K个整数组成的序列{ N​1​​, N​2​​, ..., N​K​​ },"连续子列"被定义为{ N​i​​, N​i+1​​, ..., N​j​​ },其中 1≤i≤j≤ ...

  6. 7-142 最大子列和问题 (20 分)

    7-142 最大子列和问题 (20 分) 给定K个整数组成的序列{ N1​, N2​, ..., NK​ },"连续子列"被定义为{ Ni​, Ni+1​, ..., Nj​ }, ...

  7. PTA最大子列和问题

    给定K个整数组成的序列{ N​1​​, N​2​​, ..., N​K​​ },"连续子列"被定义为{ N​i​​, N​i+1​​, ..., N​j​​ },其中 1≤i≤j≤ ...

  8. 01-复杂度1 最大子列和问题(剑指offer和PAT)

    01-复杂度1 最大子列和问题   (20分) 给定KK个整数组成的序列{ N​1​​, N​2​​, ..., N​K​​ },"连续子列"被定义为{ N​i​​, N​i+1​ ...

  9. PTA5-1 最大子列和问题

    5-1 最大子列和问题   (20分) 给定KK个整数组成的序列{ N_1N​1​​, N_2N​2​​, ..., N_KN​K​​ },"连续子列"被定义为{ N_iN​i​​ ...

  10. 【数据结构笔记03】算法实例:最大子列和

    本次笔记内容: 1.3.1 应用实例_算法1&2 1.3.2 应用实例_算法3 1.3.3 应用实例_算法4 文章目录 最大子列和问题 算法1:把所有子列拿出来比较(暴力法) 算法2:不做重复 ...

最新文章

  1. Linux环境编程 用户层定时器使用一 timerfd的使用
  2. boost::mpi模块threading::level operations
  3. 古风一棵桃花树简笔画_运用仿真树装饰效果如此浪漫
  4. 乔布斯:你须寻得所爱(转)
  5. 【课程总结】软件工程经济学简答题总结
  6. rtmp http mp4 网页播放器
  7. Delphi曾是一代王者,2020年Delphi强化WEB开发、拥抱开源、支持开发者社区,升级Delphi语言整合Python恢复昔日的跨平台开发工具王者地位
  8. (四)Selenium通过谷歌插件实现使用隧道代理
  9. 分享超好用的截动图工具ScreenToGif
  10. JavaWeb程序填空题
  11. 贪心算法之田忌赛马(超详细)
  12. ubuntu16.04的WPS不识别jpeg图片格式
  13. C语言学习日记(yzy):socket(TCP)网络连接
  14. android sensor hal,Android Sensor详解(3)porting drvier
  15. springboot使用rocketmq-spring-boot-starter整合RocketMQ
  16. Java系统环境变量配置
  17. autojs海贼王之家免root脚本
  18. Flash文件加密器
  19. 关于GRLDR标题的修改之晨枫 ——(五四青年修改版)
  20. restful api http动词含义

热门文章

  1. 如何更改Eclipse中Properties文件编码格式
  2. selenium 确实是好东西,使用selenium-server 加快执行速度,对速度有很大提升,同时可以拆分服务,进行集群部署。
  3. 已有的MGR集群上配置InnoDB Cluster
  4. iOS开发音频格式转换
  5. php 省市区县 四级联动,GitHub - yupoxiong/region: ThinkPHP5/6省市区(县)街道四级联动扩展...
  6. 淘宝API接口 item_search - 按关键字搜索淘宝商品
  7. 鸿蒙蕴含的哲理,苏轼最不该被忽视哲理名句:“人生到处知何似,应似飞鸿踏雪泥”...
  8. 社交仅发送图片和视频 -设计测试用例
  9. 8 项目沟通管理和干系人管理
  10. K线形态识别—双K线之卖出型双日K线组合