Given an integer array nums, find the with the largest sum, and return its sum. 找最大的子陣列和,並回傳那個和 (不需要 subarray 的其它細節)
已知有一個最佳解 Kadane’s algorithm, 但我們從頭開始。
從試著 brute-forcing 開始:把 sum for every subarray 都算出來,然後看哪個最大 TC: O(n^3),稍微改善相加的作法可以減少到 O(n^2) ,但還是會 TLE
func maxSubArray(nums []int) int {
globalMax := math.MinInt
for i := 0; i < len(nums); i++ {
localSum := 0
for j := i; j < len(nums); j++ {
localSum += nums[j]
globalMax = max(globalMax, localSum)
}
}
return globalMax
}
DP: dp[i] 代表以 i 結尾的 subarray 中的最大和
子問題是「要不要使用先前的結果?還是用現在的元素重新開始?」
func maxSubArray(nums []int) int {
// dp, dp[i] represent max sum of subarray which end at i
dp := make([]int, len(nums))
dp[0] = nums[0]
answer := nums[0]
for i := 1; i < len(nums); i++ {
dp[i] = max(nums[i], dp[i-1]+nums[i])
answer = max(answer, dp[i])
}
return answer
}Ï
可以從 DP 解進一步推導出來,可以注意到我們只需要 dp[i-1] ,並不需要整個 dp slice, 所以把它簡化成單一的變數 answer
func maxSubArray(nums []int) int {
curr := nums[0]
answer := nums[0]
for i := 1; i < len(nums); i++ {
curr = max(nums[i], curr+nums[i])
answer = max(answer, curr)
}
return answer
}