题目

给定一个由N个整数元素组成的数组arr,数组中有正数也有负数,这个数组不是一般的数组,其首尾是相连的。数组中一个或多个连续元素可以组成一个子数组,其中存在这样的子数组arr[i],…arr[n-1],arr[0],…,arr[j],现在请你这个ACM_Lover用一个最高效的方法帮忙找出所有连续子数组和的最大值(如果数组中的元素全部为负数,则最大和为0,即一个也没有选)。

输入:

输入包含多个测试用例,每个测试用例共有两行,第一行是一个整数n(1<=n<= 100000),表示数组的长度,第二行依次输入n个整数(整数绝对值不大于1000)。

输出:

对于每个测试用例,请输出子数组和的最大值。

样例输入:

6
1 -2 3 5 -1 2
5
6 -1 5 4 -7

样例输出:

10
14

思路一

与[LeetCode]53.Maximum Subarray题目相类似,唯一区别是本题是首尾相连,首尾相连的数组难点是到达尾部后继续从头开始,比类似题目稍微复杂些。
这里采用拉长数组的方法避免了这些问题:将数组平铺为一个长度为2倍原先长度的的新数组,这样问题就变成了:求一个整型数组中长度不超过len(原数组长度)的子数组和的最大值,降低了难度。

代码

       /*---------------------------------------------*   日期:2015-02-20*   作者:SJF0115*   题目: 求首尾相连数组的最大子数组和*   来源:淘宝*   博客:-----------------------------------------------*/#include <iostream>#include <vector>#include <algorithm>using namespace std;class Solution {public:int MaxSubarray(int a[],int n){if(n <= 0){return 0;}//ifint size = 2*n;// 构造2倍长度数组vector<int> num(a,a+n);for(int i = 0;i < n;++i){num.push_back(a[i]);}//forint max = 0;int sum = 0,start = 0,end = 0;for(int i = 0;i < size;++i){sum += num[i];if(sum < 0){sum = 0;start = i+1;}//ifif(start >= n || (i - start + 1) > n){break;}//ifif(max < sum){max = sum;end = i;}//if}//forcout<<"最大数组["<<start%n<<","<<end<<"]"<<endl;return max;}};int main() {Solution solution;int num[] = {-1,-5,-4,-7};int result = solution.MaxSubarray(num,4);cout<<result<<endl;}

思路二

可以把问题的解分为两种情况:
(1)解没有跨过A[n-1]到A[0]
(2)解跨过A[n-1]到A[0]
对于这种情况,只要找到从A[0]开始和最大的一段(A[0]…..A[j])(0 <= j < n)
以及以A[n-1]结尾的和最大的一段(A[i]…..A[n-1])(0 <= i < n)
该种情况的最大值为A[i]+…..+A[n-1]+A[0]+….+A[j]
如果i <= j 则最大值为A[0]+…..+A[n-1]否则最大值为A[i]+…..+A[n-1]+A[0]+….+A[j]
最后,取两种情况的最大值就可以了。求解跨过A[n-1]到A[0]的情况只需要遍历数组一次,故总的时间复杂度为O(N)+O(N) = O(N)

代码

    /*---------------------------------------------*   日期:2015-02-20*   作者:SJF0115*   题目: 求首尾相连数组的最大子数组和*   来源:淘宝*   博客:-----------------------------------------------*/#include <iostream>#include <vector>#include <algorithm>using namespace std;class Solution {public:int MaxSubarray(int a[],int n){if(n <= 0){return 0;}//ifint max = 0;int sum = 0,start = 0;// 第一种情况for(int i = 0;i < n;++i){sum += a[i];if(sum < 0){sum = 0;start = i+1;}//ifif((i - start + 1) > n){break;}//ifif(max < sum){max = sum;}//if}//for// 第二种情况int sumLeft = 0,sumRight = 0;int maxLeft = 0,maxRight = 0;int left = 0,right = n-1;// 以a[0]开头的最大连续和for(int i = 0;i < n;i++){sumLeft += a[i];if(sumLeft < 0){break;}//ifif(maxLeft < sumLeft){maxLeft = sumLeft;left = i;}//if}//for// 以a[n-1]结尾的最大连续和for(int j = n-1;j >= 0;--j){sumRight += a[j];if(sumRight < 0){break;}//ifif(maxRight < sumRight){maxRight = sumRight;right = j;}//if}//forif(left >= right){return max;}//ifreturn max > (maxLeft + maxRight)?max:(maxLeft+maxRight);}};int main() {Solution solution;//int num[] = {1,-2,3,5,-1,2};//int num[] = {6,-1,5,4,-7};int num[] = {-1,-3,-4};int result = solution.MaxSubarray(num,3);cout<<result<<endl;}

[经典面试题][淘宝]求首尾相连数组的最大子数组和相关推荐

  1. nyoj983 首尾相连数组的最大子数组和

    首尾相连数组的最大子数组和 时间限制:1000 ms  |  内存限制:65535 KB 难度:4 描述 给定一个由N个整数元素组成的数组arr,数组中有正数也有负数,这个数组不是一般的数组,其首尾是 ...

  2. 求二维数组中最大子数组的和

    任国庆  张博 之前我们讨论了在一维数组中求最大子数组的和,在此基础上我们开始讨论二维数组的最大子数组. 求二维数组的最大子数组思想是建立在以为数组.首先将数组的第一列看成一个一维数组,找到该列的最大 ...

  3. 结对开发2(求二维数组的最大子数组和)

    一,题目要求: 输入一个二维数组,求出此二维数组的最大子数组和. 二,设计思路: 利用for循环进行遍历,求出数组中每一个子数组的和,最终求出这些子数组的最大的一个值.程序中利用了调用函数,被调函数分 ...

  4. 求二维整数数组中最大子数组的和(结对作业)

    题目:返回一个二维整数数组中最大子数组的和 要求:(1)输入一个二维整形数组,数组里有正数也有负数. (2)二维数组中连续的一个子矩阵组成一个子数组,每个子数组都有一个和. (3)求所有子数组的和最大 ...

  5. 求一个有一千个元素的整数数组的最大子数组的和

    求一个有一千个元素的整数数组的最大子数组的和 小组成员:司宇,滕达 设计过程: 设计界面: 在c#界面添加一些控件. 程序设计: 1.使用for循环和取随机数的函数产生一千个随机数并且将其赋值到数组中 ...

  6. 结对开发——返回一个整数数组中最大子数组的和 (首尾相接版)

    一.题目及题目要求 题目:返回一个整数数组中最大子数组的和. 要求: (1)输入一个整形数组,数组里有正数也有负数. (2)数组中连续的一个或多个整数组成一个子数组,每个子数组都有一个和. (3)如果 ...

  7. 返回一个整数数组中最大子数组的和。

    一.要求: (1)输入一个整形数组,数组里有正数也有负数. (2)数组中连续的一个或多个整数组成一个子数组,每个子数组都有一个和. (3)如果数组A[0]--A[j-1]首尾相邻,允许A[i-1],. ...

  8. 课堂练习:返回一个二维数组中最大子数组的和

    1.题目: 返回一个二维数组中最大子数组的和. 2.要求: 输入一个二维整形数组,数组里有正数也有负数. 二维数组首尾相接,象个一条首尾相接带子一样. 数组中连续的一个或多个整数组成一个子数组,每个子 ...

  9. 返回一个首尾相接的二维整数数组中最大子数组的和

    题目: ·返回一个二维整数数组中最大子数组的和. 要求: ·输入一个二维整形数组,数组里有正数也有负数. ·二维数组首尾相接,象个一条首尾相接带子一样. ·数组中连续的一个或多个整数组成一个子数组,每 ...

最新文章

  1. oracle lz压缩,LZ:Oracle热备期间过量Redo生成控制
  2. 报名 | 2019年社会计算机国际会议
  3. SEO -- 搜索引擎优化
  4. RM格式转换成VCD
  5. 2019-02-22-算法-进化
  6. SSAS实践问题记录--后端数据库访问模块中存在错误。 为绑定指定的大小太小,导致一个或多个列值被截断。
  7. git sync fatal: Authentication failed for https://github.com/ did not exit cleanly (exit code 128)
  8. AssetBundle接口详解与优化
  9. 利用Fiddler作为网络代理
  10. 北大青鸟 当当网网 js 上机作业
  11. 试题 基础练习 圆的面积-蓝桥杯
  12. 计算机函数sumif实例,「稻客说函数」SUMIF函数实例详解
  13. Nacos注册中心和服务消费方式
  14. AWS之(2) RDS数据库新建
  15. 在线教育平台、网校搭建、远程教育平台搭建技术选型(268教育)
  16. python语法元素测试_基于python全局设置id 自动化测试元素定位过程解析
  17. Docker、nvidia-container-toolkit安装与常用docker命令及docker镜像和容器的更新维护
  18. 天狮集团李金元大胆决策创业,天狮直销成为中国直销走出去的典范
  19. Stream 学习
  20. Java Swing 程序设计01

热门文章

  1. 离家、失恋、职场碰壁,小伙如何守住大城市的“一张床”?
  2. 刷APP任务平台可靠吗?
  3. Chromium浏览器下载
  4. 轮播图、阅读注册协议、网页时钟、随机点名、小米搜索框、轮播图点击切换——web APIs练习
  5. Blender 画正四面体
  6. Go语言创始人从Google离职
  7. K9F1G08U0D Nand芯片
  8. Qt5气泡式聊天框——QListWidget+QPainter实现
  9. Ubuntu Server 12.04 搭建 hadoop 集群版环境——基于VirtualBox
  10. 什么是虚拟主机?虚拟主机的作用有哪些?