APIO 2010 1번 특공대(Commando)

2015. 6. 30. 21:16알고리즘 문제풀기/DP

N개의 숫자가 있다. 이를 연속된 구간으로 나눠서, 각 구간의 수의 합을 s라고 했을 때 as²+bs+c 의 값의 합(모든 구간에서 저 값을 구한 후 다 더함)을 최대화하는 문제이다. (a, b, c가 주어짐)


=> maximize( a(s12+ s22+…sk2)+b(Σ)+c×k ).


여기서 b항의 값은 항상 일정하기 때문에 a와 c값만 중요하다.



=> maximize( a(s12+ s22+…sk2)+c×k ).


dp[i] : a[i]까지의 숫자만 있다고 할 때 저 값의 최댓값. i는 1-based.


i를 j까지 묶는다고 하자.

1≤j≤i 이다.

dp[i] = maximize( dp[j-1] + a*(sum[i]-sum[j-1])^2 + c ) for j.

=

a*(sum[i]^2)+maximize(

dp[j-1]

-2*a*sum[i]*sum[j-1]

+a*(sum[j-1]^2)+c

) for j


p[i] = -2*a*sum[i], q[i]=dp[i]+c+a*(sum[i]^2) 라고 하자.

p is increasing.

dp[i] = a*sum[i]^2 + maximize(p[j-1]*sum[i] + q[j-1]) for j

x coordinate is increasing.

convex hull trick

'알고리즘 문제풀기 > DP' 카테고리의 다른 글

행렬을 이용한 접근  (0) 2017.01.14
Convex Hull Trick  (0) 2015.01.18
냅색 알고리즘  (3) 2013.12.12
Bitonic Tour  (1) 2013.11.24
Tiling Problem  (0) 2013.11.24