最大子数组二
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了最大子数组二相关的知识,希望对你有一定的参考价值。
一、实验思路:
1.定义一个整型数组num[n],随机生成数组中元素的值
2.把这个整形数组连成环,就是把这个数组中的每一个元素都当一次头,邻接的左元素做尾,遍历一次数组,找出每一个元数组的子数组最大和,存放在max_a[]中
3.定义一个二维数组dpo[n][2],dpo[i][0]不包含num[i]子数组之和最大值,dpo[i][1]包含num[i]子数组之和最大值
4.采用循环递归的方式,调用max函数计算dpo[i][0],dpo[i][1],计算包含数组元素本身和不包含本身的前子数组最大和的情况,循环递归求出max_a[j],定义数组arr[i][j]用来存放最大和子数组,通过比较
dpo[i][0],dpo[i][1]最大子数组中的元素,存放在arr[i][j]中,j表示子数组的位置
5.比较max_a[]中元素的最大值,找出最大和赋给Max,同时返回元素的位置,就是最大和数组的位置,救是arr[i][j]在哪个元数组中
6.通过条件比较过滤到arr[i][j]中空元素,并将其倒序存放arr_1[]中,然后将arr_1[]倒序输出,救是最大子数组。
1 #include<iostream> 2 #include<string> 3 #include<time.h> 4 #define N 1000 5 using namespace std; 6 int main() 7 { 8 srand((unsigned)time(NULL)); 9 int num[N],dpo[N][2]; 10 int n; 11 cout<<"请输入数组的长度:"<<endl; 12 cin>>n; 13 cout<<"这个数组为:"<<endl; 14 for(int i=0;i<n;i++) 15 { 16 num[i]=-5+rand()%15; 17 if(num[i]==0) 18 { 19 num[i]=1+rand()%15; 20 } 21 cout<<num[i]<<" "; 22 } 23 cout<<endl; 24 cout<<"最大和子数组为:"<<endl; 25 int front,Max=-300,arr[100][100],max_a[N];//front是指数值环中的每一个元素都可以当头,Max指输出的最大值,max_a用来存放每个元数组的最大值 26 for(int j=0;j<n;j++) 27 { 28 front=num[0]; 29 for(int i=1;i<n;i++) 30 { 31 num[i-1]=num[i]; 32 } 33 num[n-1]=front; //在数组环中让每一个元素当头,左边的元素当尾,遍历元数组 34 dpo[0][0]=0; 35 dpo[0][1]=num[0]; 36 for(int i=0;i<n;i++) //找出每一个元数组的子数组最大和,存放在max_a[]中 37 { 38 dpo[i][0]=max(dpo[i-1][0],dpo[i-1][1]); 39 dpo[i][1]=max(dpo[i-1][1]+num[i],num[i]); 40 max_a[j]=max(dpo[i][0],dpo[i][1]); 41 if(dpo[i][0]<=dpo[i][1]) //找每一个元数组的最大和子数组,采用循环比较的方法 42 { 43 if(num[0]<0) 44 { 45 arr[0][j]=NULL; 46 } 47 arr[i][j]=num[i]; 48 } 49 if(dpo[i][0]>dpo[i][1]) 50 { 51 if((dpo[i][1]==dpo[i-1][1]+num[i])&&(dpo[i][1]>0)) 52 { 53 arr[i][j]=num[i]; 54 } 55 else 56 arr[i][j]=NULL; 57 } 58 } 59 } 60 int p=n-1,arr_1[N],m=0,k,j; //arr[]用来存放最大子数组 61 for(int i=0;i<n;i++) //比较每一个元数组的最大子数组的和,把最大的和赋给Max, 62 { 63 if(max_a[i]>Max) 64 { 65 Max=max_a[i]; 66 j=i; //找出最大和所在的元数组 67 } 68 } 69 while(p>=0) //把最大和的子数组过滤出倒序存放在arr_1[]中 70 { 71 if(arr[p][j]==NULL) 72 { 73 p--; 74 } 75 if(arr[p][j]!=NULL) 76 { 77 while((arr[p][j]!=NULL)&&(p>=0)) 78 { 79 arr_1[m]=arr[p][j]; 80 m++; 81 k=m; 82 p--; 83 } 84 p=-1; 85 } 86 } 87 for(int i=k-1;i>=0;i--) //输出最大和子数组 88 { 89 cout<<arr_1[i]<<" "; 90 } 91 cout<<endl; 92 cout<<"最大数组和为:"<<endl; 93 cout<<Max<<endl; 94 }
二、实验截图:
三、实验日志:
项目记录 日志:
|
听课 |
编写程序 |
阅读相关书籍 |
网上查找资料 |
日总计 |
周一 |
2 |
0 |
0 |
0 |
2 |
周二 |
0 |
1 |
1 |
0 |
2 |
周三 |
0 |
3 |
0.5 |
1 |
4.5 |
周四 |
2 |
0.5 |
0.5 |
0 |
3 |
周五 |
0 |
3 |
0.5 |
1 |
4.5 |
周六 |
0 |
1 |
0 |
1 |
2 |
周日 |
0 |
3 |
1 |
0 |
4 |
周总计 |
4 |
12.5 |
3.5 |
3 |
22 |
时间记录日志
日期 |
开始 时间 |
结束时间 |
中断时间 |
净时间 |
活动 |
备注 |
星期一 |
14:00 |
16:00 |
10 |
100 |
上课 |
软件工程 |
星期二 |
16:00 |
17:00 |
0 |
60 |
编程 |
数组问题 |
|
19:00 |
20:00 |
0 |
60 |
阅读书籍
|
构建之法 |
星期三 |
13:00 |
17:00 |
60 |
180 |
编程 |
|
|
19:00 |
21:00 |
30 |
90 |
阅读书籍 |
构建之法 |
星期四 |
14:00 |
16:00 |
10 |
100 |
上课 |
软件工程 |
|
19:00 |
20:00 |
0 |
60 |
编程 查找资料 |
数组问题 |
星期五 |
13:00 |
17:00 |
60 |
180 |
编程 |
数组问题 |
|
17:00 |
18:00 |
0 |
60 |
上网 |
查资料 |
星期六 |
12:00 |
14:00 |
30 |
90 |
编程 |
数组问题 |
星期日 |
9:00 |
11:00 |
0 |
180 |
编程 |
数组问题二 |
缺陷记录日志:
日期 |
编号 |
类型 |
引入阶段 |
排除阶段 |
修复阶段 |
修复缺陷 |
3/27 |
1 |
数组变环阶段 |
|
|
30min |
|
在数组连接成环时,让数组中的每一个元素都当一次头,循环遍历一次 |
||||||
2 |
最大和子数组的返回 |
|
|
3h |
|
|
在编写这一步骤时遇到困难,我返回的方法比较笨拙,在遍历最大和的时候,做出最大和子数组所在的元数组,在元数组循环遍历求最大和时,通过比较dpo[i][0],dpo[i][1]的大小,来找出最大子数组 |
四、实验总结:
在这次实验中,我们遇到了两个难题,一是如何将数组连成环,二是如何返回最大和数组的值,这两个问题我们讨论了很久,虽然思路还是不太简单,但是还是解出来了,我觉得结对开发在我们做项目时效率要提高很多,一个人的能力毕竟是有限的,两个人相互合作,相互补充,才能在更短的时间内,更高效率的而完成工作。
我的伙伴 鲁鑫:http://www.cnblogs.com/LUXIN123/
以上是关于最大子数组二的主要内容,如果未能解决你的问题,请参考以下文章
NC41 最长无重复子数组/NC133链表的奇偶重排/NC116把数字翻译成字符串/NC135 股票交易的最大收益/NC126换钱的最少货币数/NC45实现二叉树先序,中序和后序遍历(递归)(代码片段