https://leetcode.com/problems/maximum-subarray/description/
Given an integer array nums, find the
with the largest sum, and return its sum.
Example 1:
Input: nums = [-2,1,-3,4,-1,2,1,-5,4]
Output: 6
Explanation: The subarray [4,-1,2,1] has the largest sum 6.
Example 2:
Input: nums = [1]
Output: 1
Explanation: The subarray [1] has the largest sum 1.
Example 3:
Input: nums = [5,4,-1,7,8]
Output: 23
Explanation: The subarray [5,4,-1,7,8] has the largest sum 23.
Constraints:
- 1 <= nums.length <= 105
- -104 <= nums[i] <= 104
Follow up: If you have figured out the O(n) solution, try coding another solution using the divide and conquer approach, which is more subtle.
1. Python
class Solution:
def maxSubArray(self, nums: List[int]) -> int:
curr = nums[0]
curr_max = nums[0]
for num in nums[1:]:
curr = max(num, curr+num)
curr_max = max(curr_max,curr)
return curr_max
뭔가 깔끔하긴 한데, Recursion을 쓰진 않았다.
이게 바로 카데인 알고리즘이구만 .. Kadanes Algorithm으로 DP를 쓴 것이다.
이 코드에서 사용한 방법은 **카데인 알고리즘(Kadane's Algorithm)**으로, 이는 **동적 계획법(Dynamic Programming)**을 사용한 해결 방법입니다.동작 방식:
핵심 아이디어:
|
아.. divde conquer 연습하기엔 너무 빡세다.
다른 문제를 더 찾아보자.
참고로 D & C 코드는 아래와 같다.
def max_crossing_sum(arr, left, mid, right):
# 왼쪽 부분에서 최대 합을 계산
left_sum = float('-inf')
current_sum = 0
for i in range(mid, left - 1, -1):
current_sum += arr[i]
if current_sum > left_sum:
left_sum = current_sum
# 오른쪽 부분에서 최대 합을 계산
right_sum = float('-inf')
current_sum = 0
for i in range(mid + 1, right + 1):
current_sum += arr[i]
if current_sum > right_sum:
right_sum = current_sum
# 중앙을 가로지르는 최대 합을 반환
return left_sum + right_sum
def max_sub_array_divide_and_conquer(arr, left, right):
if left == right:
# 배열이 한 개의 요소만 있을 때 그 값을 반환
return arr[left]
mid = (left + right) // 2
# 3가지 경우를 각각 재귀적으로 구함
left_sum = max_sub_array_divide_and_conquer(arr, left, mid)
right_sum = max_sub_array_divide_and_conquer(arr, mid + 1, right)
cross_sum = max_crossing_sum(arr, left, mid, right)
# 가장 큰 값을 반환
return max(left_sum, right_sum, cross_sum)
def max_sub_array(arr):
return max_sub_array_divide_and_conquer(arr, 0, len(arr) - 1)
2. C++
# C++
#include <iostream>
#include <vector>
#include <algorithm>
#include <climits>
using namespace std;
int maxCrossingSum(vector<int>& arr, int left, int mid, int right) {
int left_sum = INT_MIN;
int current_sum = 0;
// 왼쪽 부분에서 최대 합 계산
for (int i = mid; i >= left; i--) {
current_sum += arr[i];
if (current_sum > left_sum) {
left_sum = current_sum;
}
}
int right_sum = INT_MIN;
current_sum = 0;
// 오른쪽 부분에서 최대 합 계산
for (int i = mid + 1; i <= right; i++) {
current_sum += arr[i];
if (current_sum > right_sum) {
right_sum = current_sum;
}
}
// 중앙을 가로지르는 최대 합 반환
return left_sum + right_sum;
}
int maxSubArrayDivideAndConquer(vector<int>& arr, int left, int right) {
if (left == right) {
// 배열이 하나의 요소만 있을 때 그 값을 반환
return arr[left];
}
int mid = (left + right) / 2;
// 3가지 경우에 대해 각각 최대 합을 계산
int left_sum = maxSubArrayDivideAndConquer(arr, left, mid);
int right_sum = maxSubArrayDivideAndConquer(arr, mid + 1, right);
int cross_sum = maxCrossingSum(arr, left, mid, right);
// 세 경우 중 가장 큰 값을 반환
return max({left_sum, right_sum, cross_sum});
}
int maxSubArray(vector<int>& arr) {
return maxSubArrayDivideAndConquer(arr, 0, arr.size() - 1);
}
'Coding_Practice' 카테고리의 다른 글
Sort List[Linked List,Two Pointers,Divide and Conquer,Sorting,Merge Sort] (0) | 2024.10.10 |
---|---|
Majority Element[Array,Hash Table,Divide and Conquer,Sorting,Counting] (0) | 2024.10.10 |
Minimum Add to Make Parentheses Valid[M,String,Stack,Greedy] (4) | 2024.10.09 |
Minimum String Length After Removing Substrings[E,StringStackSimulation] (2) | 2024.10.07 |
Jewels and Stones[기초..] (1) | 2024.09.26 |