BOJ 12735 Boat

BOJ 12735 Boat

문제 링크:

문제 내용

NN개의 (ai,bi)(a_i, b_i)의 정수 쌍이 주어집니다. 1x1<x2<<xkN1 \le x_1 < x_2 < \cdots < x_k \le Nk>0k>0개의 정수를 골라서 axjcjbxja_{x_j} \le c_j \le b_{x_j}의 범위 내에서 정수 c1,c2,,ckc_1, c_2, \cdots, c_k를 뽑았을 때 c1<c2<<ckc_1 < c_2 < \cdots < c_k를 충족하는 경우의 수를 구하세요.

입력

첫 줄에는 NN이 주어집니다. (1N5001 \le N \le 500) 다음 NN줄에는 aia_ibib_i가 주어집니다. (1aibi1091 \le a_i \le b_i \le 10^9)

출력

문제의 정답을 109+710^9+7로 나눈 나머지를 출력합니다.

문제 풀이

스포일러

마지막으로 뽑은 원소의 인덱스가 xx이고 그 값이 yy일 때, 그러한 경우의 수를 f(x,y)f(x, y)라고 합시다. 편의상 아무것도 뽑지 않은 경우를 f(0,0)=1f(0, 0) = 1, a0=b0=0a_0 = b_0 = 0으로 두면 다음이 성립합니다.

f(x,y)={i=0x1j=0y1f(i,j)if axybx0otherwisef(x, y) = \begin{cases} \sum_{i=0}^{x-1} \sum_{j=0}^{y-1} f(i,j) &\text{if } a_x \le y \le b_x \\ 0 &\text{otherwise} \end{cases}

그리고 s(x,y)=i=0xj=0yf(i,j)s(x, y) = \sum_{i=0}^{x} \sum_{j=0}^{y} f(i,j)로 정의하면 f(x,y)0f(x, y) \neq 0인 경우 f(x,y)=s(x1,y1)f(x, y) = s(x-1, y-1)이 됩니다.

그러나 yy10910^9까지 커질 수 있는 상황이므로, 특정 상황을 건너뛰어서 계산할 아이디어가 필요합니다.

1xN1 \le x \le N에 대해 f(x,y1)f(x, y_1)을 모두 알고 있고, y1yy2y_1 \le y \le y_2에서 f(x,y)0f(x, y) \neq 0xx의 집합이 x1,x2,x_1, x_2, \cdots로 모두 동일하다면, DP 테이블의 y1y_1번째 줄에서 y2y_2번째 줄로 다음과 같이 건너뛸 수 있습니다.

f(x1,y2)=f(x1,y1)f(x2,y2)=f(x2,y1)+(y2y11)f(x1,y1)f(x3,y2)=f(x3,y1)+(y2y11)f(x2,y1)+(y2y1+12)f(x1,y1)\begin{align*} f(x_1, y_2) &= f(x_1, y_1) f(x_2, y_2) &= f(x_2, y_1) + {{y_2 - y_1}\choose{1}} f(x_1, y_1) f(x_3, y_2) &= f(x_3, y_1) + {{y_2 - y_1}\choose{1}} f(x_2, y_1) + {{y_2 - y_1 + 1}\choose{2}} f(x_1, y_1) &\cdots \end{align*}s(x1,y2)=s(x1,y1)+((y2y1+11)1)f(x1,y1)s(x2,y2)=s(x2,y1)+((y2y1+11)1)f(x2,y1)+((y2y1+22)1)f(x1,y1)s(x3,y2)=s(x3,y1)+((y2y1+11)1)f(x3,y1)+((y2y1+22)1)f(x2,y1)+((y2y1+33)1)f(x1,y1)\begin{align*} s(x_1, y_2) &= s(x_1, y_1) + ({{y_2 - y_1 + 1}\choose{1}} - 1) f(x_1, y_1) s(x_2, y_2) &= s(x_2, y_1) + ({{y_2 - y_1 + 1}\choose{1}} - 1) f(x_2, y_1) + ({{y_2 - y_1 + 2}\choose{2}} - 1) f(x_1, y_1) s(x_3, y_2) &= s(x_3, y_1) + ({{y_2 - y_1 + 1}\choose{1}} - 1) f(x_3, y_1) + ({{y_2 - y_1 + 2}\choose{2}} - 1) f(x_2, y_1) + ({{y_2 - y_1 + 3}\choose{3}} - 1) f(x_1, y_1) &\cdots \end{align*}

그리고 f(x,y2)=0f(x, y_2) = 0인 경우, xx 이하이면서 f(xi,y2)0f(x_i, y_2) \neq 0인 가장 큰 xix_i에 대해 다음이 성립합니다.

s(x,y2)=s(x,y1)+(s(xi,y2)s(xi,y1))s(x, y_2) = s(x, y_1) + (s(x_i, y_2) - s(x_i, y_1))

이들을 종합하면, xx의 집합이 바뀌는 시점들을 찾아서 그러한 구간은 한 줄씩 전이해주고 그렇지 않은 구간은 O(N2)\mathcal{O}(N^2)의 시간에 건너뜀으로써 O(N3)\mathcal{O}(N^3) 시간에 답을 구할 수 있습니다.

Last updated on