※ 글쓴이는 취미로 코딩을 익혀보는 사람이라 정확하지 않은 내용을 담고 있을 수 있다 ※
이번에 볼 문제는 백준 25188번 문제인 1, 3, 모 나누기이다.
문제는 아래 링크를 확인하자.
https://www.acmicpc.net/problem/25188
25188번: 1, 3, 모 나누기
첫째 줄에 수열의 길이 $N$이 주어진다. ($1 \le N \le 2\,000$) 둘째 줄에는 수열 $a_1,a_2, \cdots, a_N$ 이 주어진다. ($-10^9 \le a_i \le 10^9$)
www.acmicpc.net
dp[i][j]를 i~k번째 수들의 합의 최솟값이라 하자. (단, k는 i 이상 j 이하이고, 그 값이 음수라면 0을 채워넣는다.)
이제 주어진 배열을 [1,L-1], [L,R], [R+1,N]의 셋으로 쪼개고 각 구간의 dp[i][j]값들을 더한 것의 최댓값을 구하면 답을 구해낼 수 있다.
단, 위와 같이 배열을 셋으로 쪼갤 수 있으려면 배열의 크기가 3 이상이어야 하므로 크기가 2 이하인 배열은 예외처리를 해주자.
아래는 제출한 소스코드이다.
#include <iostream>
using namespace std;
typedef long long ll;
int N;
ll arr[2002];
ll dp[2002][2002]; // [i][j]: "i번에서 시작해서 k(<=j)에서 끝나는 구간합"의 최댓값
void solve() {
for (int i = 1; i <= N; i++) {
ll psum = 0, mx = 0;
for (int j = i; j <= N; j++) {
psum += arr[j];
mx = max(mx, psum);
dp[i][j] = mx;
}
}
ll ans = 0;
for (int L = 2; L < N; L++) {
for (int R = L; R < N; R++) {
ans = max(ans, dp[1][L - 1] + dp[L][R] + dp[R + 1][N]);
}
}
cout << ans;
}
int main() {
ios::sync_with_stdio(0);
cin.tie(0);
cin >> N;
for (int i = 1; i <= N; i++) cin >> arr[i];
if (N == 1) cout << max(arr[1], 0LL);
else if (N == 2) cout << max(max(arr[1], arr[2]), max(arr[1] + arr[2], 0LL));
else solve();
}
728x90
'BOJ' 카테고리의 다른 글
[BOJ 14647 // C++] 준오는 조류혐오야!! (0) | 2022.08.21 |
---|---|
[BOJ 25189 // C++] 시니컬한 개구리 (0) | 2022.08.20 |
[BOJ 25187 // C++] 고인물이 싫어요 (0) | 2022.08.18 |
[BOJ 17020 // C++] Train Tracking 2 (0) | 2022.08.17 |
[BOJ 6137 // C++] 문자열 생성 (0) | 2022.08.16 |