题号如标题所示,题目内容百度即可。
最大子序列问题,即求出所给一个数列中的最大的子序列和并输出该和以及该子序列的首项位置以及末项位置。
具体代码如下:
import java.util.Scanner; public class MaxSum { public static void main(String[] args){ Scanner input = new Scanner(System.in); int T = input.nextInt(); for (int i=1;i<=T;i++){ int N = input.nextInt(); int Se; int Sum=0,Maxsum=-1001; int first=0,second=0; for (int j=0,k=0;j<N;j++){ Se = input.nextInt(); Sum += Se; if (Sum>Maxsum){ Maxsum = Sum; first = k; second = j; } if (Sum<0){ Sum = 0; k = j+1; } } System.out.println("Case "+ i +":"); System.out.println(Maxsum + " "+ (first+1) + " "+ (second+1)); if (i != T){ System.out.println(); } } } }
在数据结构与算法分析一书第一章中介绍过最大子序列问题。并且提出了四种算法,本代码用了书中所写的最后一种算法,也是最简单效率最高的一种。
主要解决的问题在于每输入一次数列的某一项都进行一次计算得出目前的子序列和,并于目前的最大子序列和进行比较。另外,当子序列和小于0时,需要舍弃以前的计算并重新开始。
而有一种很好理解但是效率并不高的算法,就是从第一项开始用多层循环嵌套的方式将每个子序列都进行计算并且比较得出最大的一个,最后输出即可。
另外两种算法详见《数据结构与算法分析C语言描述》一书。
最后需要在提及一点,该题目中所给的数列中各个项的取值范围为-1000~1000,所以,
千万千万要在最开始的时候将Maxsum,也就是最后要输出的最大子序列和初始化为一个小于-1000的数!!!
因为这个原因Wrong了好些次!
注意认真!
Over。