这个使用动态规划是比较好理解的,但是这个分治法对我这种脑子不好使的来说真是难懂,现在搞懂了,记录一下。
// LeetCode53.cpp : 此文件包含 "main" 函数。程序执行将在此处开始并结束。 // #include <iostream> #include <vector> using namespace std; /* 给定一个整数数组 nums ,找到一个具有最大和的连续子数组(子数组最少包含一个元素),返回其最大和。 示例: 输入: [-2,1,-3,4,-1,2,1,-5,4], 输出: 6 解释: 连续子数组 [4,-1,2,1] 的和最大,为 6。 进阶: 如果你已经实现复杂度为 O(n) 的解法,尝试使用更为精妙的分治法求解。 */ //动态规划的方法解的 //class Solution { //public: // int maxSubArray(vector<int>& nums) { // if (nums.empty()) return 0; // if (nums.size() == 1) return nums[0]; // int start = -1, end = -1, maxNum = nums[0], sumNum = nums[0]; // if (nums[0] > 0) // { // start = 0; // } // for (size_t i = 1; i < nums.size(); i++) // { // if (start == -1 && nums[i] <= 0) // { // if (maxNum < nums[i]) // { // start = end = i; // maxNum = sumNum = nums[i]; // } // continue; // } // if (start == -1 && nums[i] > 0) // { // start = i; // end = i; // sumNum = maxNum = nums[i]; // continue; // } // if (sumNum < 0 && nums[i] >= 0 && nums[i] >= maxNum) // { // start = i; // end = i; // sumNum = maxNum = nums[i]; // continue; // } // sumNum += nums[i]; // if (sumNum > maxNum) // { // maxNum = sumNum; // end = i; // } // } // return maxNum; // } //}; //官方分治法的解法,我资质驽钝真是不大好理解 #include <algorithm> //class Solution { //public: // int maxSubArray(vector<int>& nums) { // int pre = 0, maxAns = nums[0]; // for (auto &x : nums) // { // pre = max(pre + x, x); // maxAns = max(pre, maxAns); // } // return maxAns; // } //}; //class Solution { //public: // struct Status { // int lSum, rSum, mSum, iSum; // }; // // Status pushUp(Status l, Status r) // { // int iSum = l.iSum + r.iSum; // int lSum = max(l.lSum, l.iSum + r.lSum); // int rSum = max(r.rSum, r.iSum + l.rSum); // int mSum = max(max(l.mSum, r.mSum), l.rSum + r.lSum); // Status st{ lSum, rSum, mSum, iSum }; // return st; // }; // // Status get(vector<int>& a, int l, int r) // { // Status st1 = { a[l], a[l], a[l], a[l] }; // if (l == r) return st1; // int m = (l + r) >> 1; // Status lSub = get(a, l, m); // Status rSub = get(a, m + 1, r); // return pushUp(lSub, rSub); // } // // int maxSubArray(vector<int>& nums) { // return get(nums, 0, nums.size() - 1).mSum; // } //}; //分治法,理解了默写一遍 class Solution { public: struct sumStatus { int lSum, rSum, maxSum, totalSum; }; sumStatus mergeSum(sumStatus left, sumStatus right) { int leftSum = max(left.totalSum + right.lSum, left.lSum); int rightSum = max(left.rSum + right.totalSum, right.rSum); int maxSum = max(max(left.maxSum, right.maxSum), left.rSum + right.lSum); int totalSum = left.totalSum + right.totalSum; sumStatus st = { leftSum, rightSum, maxSum, totalSum }; return st; } sumStatus getSum(vector<int>& nums, int left, int right) { sumStatus st = { nums[left], nums[left], nums[left], nums[left] }; if (left == right) { return st; } int middle = (left + right) / 2; sumStatus lsum = getSum(nums, left, middle); sumStatus rsum = getSum(nums, middle + 1, right); return mergeSum(lsum, rsum); } int maxSubArray(vector<int>& nums) { return getSum(nums, 0, nums.size() - 1).maxSum; } }; int main() { //vector<int> nums = { -2,1,-3,4,-1,2,1,-5,4 }; //vector<int> nums = { 1,-2,4,0}; vector<int> nums = { 1,-3,5,-4,2,3 }; Solution s; cout << s.maxSubArray(nums) << endl; }