1749. Maximum Absolute Value of Sum of Arbitrary Subarrays

The gods are silent-personal CSDN blog post catalog
force buckle brush question notes

insert image description here

insert image description here

1. Violent search

Directly use 2 pointers to find the last index starting from index 0, the time complexity is about O ( n 2 ) O(n^2)O ( n2 )Well, in short, this is not possible, the following are some typical failure cases I wrote in Python

class Solution:
    def maxAbsoluteSum(self, nums: List[int]) -> int:
        max_abs=0
        nums_len=len(nums)
        for pointer1 in range(nums_len):
            for pointer2 in range(pointer1,nums_len):
                sub_nums=nums[pointer1:pointer2+1]
                max_abs=max(max_abs,abs(sum(sub_nums)))
        return max_abs

↑It will time out, which I think should be sum()the problem, so I made an improvement:

class Solution:
    def maxAbsoluteSum(self, nums: List[int]) -> int:
        sum_table=[[0 for _ in range(len(nums))] for _ in range(len(nums))]
        for i in range(len(nums)):
            sum_table[i][i]=nums[i]
        for i in range(len(nums)):
            for j in range(i+1,len(nums)):
                sum_table[i][j]=sum_table[i][j-1]+nums[j]
        max_abs=0
        for i in sum_table:
            for j in i:
                max_abs=max(max_abs,abs(j))
        return max_abs

↑This will explode the memory again, I will curse.
I guessed this at first because there were too many 0s, so I deleted all the parts that were always 0:

class Solution:
    def maxAbsoluteSum(self, nums: List[int]) -> int:
        sum_table=[[0 for _ in range(len(nums)-i)] for i in range(len(nums))]
        for i in range(len(nums)):
            sum_table[i][0]=nums[i]
        for i in range(len(nums)):
            for j in range(1,len(nums)-i):
                sum_table[i][j]=sum_table[i][j-1]+nums[j+i]
        max_abs=0
        for i in sum_table:
            for j in i:
                max_abs=max(max_abs,abs(j))
        return max_abs

↑It will still burst the memory
and continue to shrink:

class Solution:
    def maxAbsoluteSum(self, nums: List[int]) -> int:
        max_abs=0
        for i in range(len(nums)):
            pre_sum=nums[i]
            max_abs=max(max_abs,abs(pre_sum))
            for j in range(i+1,len(nums)):
                pre_sum=pre_sum+nums[j]
                max_abs=max(max_abs,abs(pre_sum))
        return max_abs

timeout this time

2. Dynamic programming

Then I went to see the solution.

From the official solution: https://leetcode.cn/problems/maximum-absolute-sum-of-any-subarray/solutions/2372374/ren-yi-zi-shu-zu-he-de-jue-dui-zhi- de-zu-qerr/

The maximum absolute value in a set of numbers, which may be the absolute value of the largest value or the absolute value of the smallest value.
So to find the maximum value of the subarray and absolute value, it is necessary to find the largest subarray sum and the smallest subarray sum.
So the solution is to calculate these two cases separately: when looking for the largest sub-array sum, traverse the array, keep the maximum sum of the global sub-array up to the previous number global_max+ the maximum sum of the sub-array with the previous number sumable_max or 0 (0 means to get rid of the previous number), if the new number + sumable_max is higher than positiveMax, update global_max; if this number is added to sumable_max greater than 0, then for subsequent numbers, adding sumable_max can be larger (What I'm talking about, that's what I mean anyway), otherwise it's better to just reopen it.
When looking for the smallest sub-array sum, it is completely reversed: keep the global minimum sum global_min + add the minimum sum sumable_min or 0, if the new number + sumable_min<global_min, update global_min; if the new number + sumable_min > 0, then give it for nothing, and immediately restart open.

Time complexity O ( n ) O(n)O ( n ) , space complexityO ( 1 ) O(1)O(1)

class Solution:
    def maxAbsoluteSum(self, nums: List[int]) -> int:
        global_max=0
        sumable_max=0
        global_min=0
        sumable_min=0
        for i in nums:
            sumable_max+=i
            global_max=max(global_max,sumable_max)
            sumable_max=max(0,sumable_max)
            
            sumable_min+=i
            global_min=min(global_min,sumable_min)
            sumable_min=min(0,sumable_min)
        return max(abs(global_max),abs(global_min))

Official Java code:

class Solution {
    
    
    public int maxAbsoluteSum(int[] nums) {
    
    
        int positiveMax = 0, negativeMin = 0;
        int positiveSum = 0, negativeSum = 0;
        for (int num : nums) {
    
    
            positiveSum += num;
            positiveMax = Math.max(positiveMax, positiveSum);
            positiveSum = Math.max(0, positiveSum);
            negativeSum += num;
            negativeMin = Math.min(negativeMin, negativeSum);
            negativeSum = Math.min(0, negativeSum);
        }
        return Math.max(positiveMax, -negativeMin);
    }
}

3. Prefix and

The prefix sum refers to adding a 0 at the front of the array, the sum from the first number to the current number, any sub-array sum is obviously the difference between two prefix sums, and the largest sub-array sum is obviously the largest in absolute value Prefix sum - minimum prefix sum (if the minimum value <0, it is directly the maximum value - the minimum value, if the minimum value > 0, use that 0)

Python 3 has built-in functions:

class Solution:
    def maxAbsoluteSum(self, nums: List[int]) -> int:
        s = list(accumulate(nums, initial=0))  # nums 的前缀和
        return max(s) - min(s)

Example of Java implementation:

class Solution {
    
    
    public int maxAbsoluteSum(int[] nums) {
    
    
        int n=nums.length;
        int pre=0;
        int max=0;
        int min=0;
        for(int i=0;i<n;i++){
    
    
            pre+=nums[i];
            max=Math.max(max,pre);
            min=Math.min(min,pre);
        }
        return max-min;
    }
}

Guess you like

Origin blog.csdn.net/PolarisRisingWar/article/details/132178311