LeetCode:最大子序和 (分治法+动态规划)

二分法

将nums[0:n]分解为nums【left:center】,nums【center+1:right】 ,分三种情况求解

 

  1. LEFT:nums【left:right】= nums【left:center】
  2. RIGHT:nums【left:right】= nums【center:right】
  3. MIDDLE:nums【left:right】=s1+s2

对于3,nums【center】和nums【center+1】一定在序列中,从center向左求最大值,center+1向右求最大值,相加。

 

class Solution {
public:
    int maxSubArray(vector& nums) {
        if(nums.size() == 0) return 0;
        return (max_sub(nums,0,nums.size()-1));
    }
    
    int max_sub(vector& nums,int left,int right)
    {
        if(left == right)
            return nums[left];
            
        int center,left_sum,right_sum,s1=INT_MIN,s2=INT_MIN,l=0,r=0;
        center = (left + right)/2;
        
        left_sum=max_sub(nums,left,center);//left
        
        right_sum=max_sub(nums,center+1,right);//right
        
        for(int i = center;i>=left;i--)//middle
        {
            l = l+nums[i];
            if(s1 right_sum && left_sum > (s1+s2))//judge
            return left_sum;
        else if(right_sum > (s1+s2))
            return right_sum;
        else return s1+s2;
    }
};

动态规划

用result[i]保存以数字nums[i]结尾的最大子序和,以nums【0】结尾的只有nums【0】本身,result【0】=nums【0】

result【1】=MAX(nums【1】,result【0】+nums【1】)

以此类推

 

 

class Solution {
public:
    int maxSubArray(vector& nums) {
        vector result(nums.size(),INT_MIN);
        result[0] = nums[0];
        int max=nums[0];
        
        for(int i = 1;i0)
                result[i]=nums[i]+result[i-1];
            else
                result[i]=nums[i];
            if(result[i]>max)
                max = result[i];
        }
        
        return max;
        
    }
};

 

你可能感兴趣的:(基础,LeetCode)