๐ฉ๐ปโ๐ป๋ฌธ์ ๋งํฌ
[๋ฐฑ์ค 10835] ์นด๋๊ฒ์ (Python) (๋ง์ํ)
โ๏ธIdea Sketch
์ธ์ ๋ ์ง ์ผ์ชฝ ์นด๋๋ง ํต์ ๋ฒ๋ฆด ์๋ ์๊ณ ์ผ์ชฝ ์นด๋์ ์ค๋ฅธ์ชฝ ์นด๋๋ฅผ ๋ ๋ค ํต์ ๋ฒ๋ฆด ์๋ ์๋ค. ์ด๋ ์ป๋ ์ ์๋ ์๋ค.
์ค๋ฅธ์ชฝ ์นด๋์ ์ ํ ์๊ฐ ์ผ์ชฝ ์นด๋์ ์ ํ ์๋ณด๋ค ์์ ๊ฒฝ์ฐ์๋ ์ค๋ฅธ์ชฝ ์นด๋๋ง ํต์ ๋ฒ๋ฆด ์๋ ์๋ค. ์ค๋ฅธ์ชฝ ์นด๋๋ง ๋ฒ๋ฆฌ๋ ๊ฒฝ์ฐ์๋ ์ค๋ฅธ์ชฝ ์นด๋์ ์ ํ ์๋งํผ ์ ์๋ฅผ ์ป๋๋ค.
๋ฐฑ์ค์ ํ๋ฉด์ "๋ง์์ต๋๋ค!"๊ฐ ์๋๋ผ "**์ " ์ ์๋ฅผ ๋งค๊ฒจ์ฃผ๋ ๋ฌธ์ ๋ ์ด ๋ฌธ์ ๊ฐ ์ฒ์์ด๋ค.
๋ฌธ์ ๋ฅผ ํ๋ฉด์ ๋ง์ํ์ ์ ๋ง ๋ง์ด ์ธ์ณค๋ค.
๋ค์ด๋๋ฏน ํ๋ก๊ทธ๋๋ฐ Top-down ๋ฐฉ์์ผ๋ก ๊ตฌํํ๋ค.
๋น์ ์ด 31์ ์ด๋ผ๋ฉด - ๋ฉ๋ชจ์ด์ ์ด์
์์ด ๊ตฌํํ์ ๊ฒ์ด๊ณ
๋น์ ์ด 64์ ์ด๋ผ๋ฉด์ด๋ผ๋ฉด - sys.setrecursionlimit(10**6)
์ ์๋ตํ๊ฑฐ๋ dp๋ฐฐ์ด์ 0์ผ๋ก ์ด๊ธฐํํ์ ๊ฒ์ด๋ค.
๐ฉ๐ปโ๐ป sys.setrecursionlimit()
Python์ด ์ ํ ์ต๋ ์ฌ๊ท ๊น์ด๋ณด๋ค ์ฌ๊ท์ ๊น์ด๊ฐ ๋ ๊น์ด์ง๋ฉด, RecursionError๊ฐ ๋ฐ์ํ๋ค.
์ด ๊ฒฝ์ฐ ์ต๋ ์ฌ๊ท ๊น์ด๋ฅผ ๋ณ๊ฒฝํ๋ฉด ๋๋ค.
BOJ ์ฑ์ ์๋ฒ๋ ์ต๋ ์ฌ๊ท ๊น์ด๊ฐ 1,000์ด๋ค.
import sys
sys.setrecursionlimit(10**6)
์ฐธ๊ณ
https://help.acmicpc.net/judge/rte/RecursionError
https://fuzzysound.github.io/sys-setrecursionlimit
๐ฉ๐ปโ๐ป ์ด ๋ฌธ์ ๋ dp๋ฐฐ์ด์ -1๋ก ์ด๊ธฐํํด์ผํ๋ ์ด์
dp๋ฐฐ์ด์ 0์ผ๋ก ์ด๊ธฐํํ๊ณ + ๋ฉ๋ชจ์ด์ ์ด์ ์์ 0์ ํ์ ์ ๋ฌด์ flag๋ก ์ฐ๋ ๊ฒฝ์ฐ ๋ฌธ์ ๊ฐ ์๊ธด๋ค.
if dp[x][y] != 0: # 0์ด ์๋ ๊ฒฝ์ฐ, ์ด๋ฏธ ํ์ํ๋ค๊ณ ํ๋จํ์ฌ dp๋ฐฐ์ด์ ๊ฐ์ ๋ฐํํ๋ค.
return dp[x][y]
ํ์ ๊ฒฐ๊ณผ 0์ ๋ฐํํ๋ ๊ฒฝ์ฐ, ์ด๋ฏธ ํ์ํ๋๋ฐ๋ dp๋ฐฐ์ด์ ๊ฐ์ด ๊ทธ๋๋ก 0์ด๊ธฐ ๋๋ฌธ์
ํ์๋์ง ์์๋ค๊ณ ํ๋จํ ์ ์๋ค.
๋ฐ๋ผ์ ์๊ฐ์ด๊ณผ๊ฐ ๋ฐ์ํ ์ ์๋ค.
์ฐธ๊ณ
https://www.acmicpc.net/board/view/38906
https://www.acmicpc.net/board/view/15769
๐ฉ๐ปโ๐ป ํ ๊ทธ๋ฆฌ๊ธฐ
์ด ๋ฌธ์ ๋ ํ๋ฅผ ์ง์ ๊ทธ๋ ค๋ณด๊ณ ๋์์ผ ์ ๋๋ก ์ดํดํ๋ค.
๋ฐฑ์ค ์์ ์
๋ ฅ 1๋ฒ์ ๋ค์๊ณผ ๊ฐ๋ค.
3
3 2 5
2 4 1
dfs(์ผ์ชฝ *๋ฒ์งธ ์นด๋, ์ค๋ฅธ์ชฝ *๋ฒ์งธ ์นด๋)
dfs(0, 0)์ ์ผ์ชฝ ์ฒซ๋ฒ์งธ ์นด๋, ์ค๋ฅธ์ชฝ ์ฒซ๋ฒ์งธ ์นด๋๋ฅผ ์๋ฏธํ๋ค.
dfs(0, 0) = dfs(0, 1) + 2 # ์ผ์ชฝ 3 > ์ค๋ฅธ์ชฝ 2 ์ด๋ฏ๋ก ์ค๋ฅธ์ชฝ 2 ๋ฒ๋ฆฌ๊ณ ์ ์ ํ๋
dfs(0, 1) = max(dfs(1, 1), dfs(1, 2)) # ์ผ์ชฝ 3 < ์ค๋ฅธ์ชฝ 4 ์ด๋ฏ๋ก max(์ผ์ชฝ ๋ฒ๋ฆฌ๊ธฐ, ๋ ๋ค ๋ฒ๋ฆฌ๊ธฐ) ๊ตฌํ๊ธฐ
dfs(1, 1) = max(dfs(2, 1), dfs(2, 2)) # ์ผ์ชฝ 2 < ์ค๋ฅธ์ชฝ 4 ์ด๋ฏ๋ก max(์ผ์ชฝ ๋ฒ๋ฆฌ๊ธฐ, ๋ ๋ค ๋ฒ๋ฆฌ๊ธฐ) ๊ตฌํ๊ธฐ
dfs(2, 1) = dfs(2, 2) + 4 # ์ผ์ชฝ 5 > ์ค๋ฅธ์ชฝ 4 ์ด๋ฏ๋ก ์ค๋ฅธ์ชฝ 4 ๋ฒ๋ฆฌ๊ณ ์ ์ ํ๋
dfs(2, 2) = dfs(2, 3) + 1 # ์ผ์ชฝ 5 > ์ค๋ฅธ์ชฝ 1 ์ด๋ฏ๋ก ์ค๋ฅธ์ชฝ 1 ๋ฒ๋ฆฌ๊ณ ์ ์ ํ๋
dfs(2, 3) = 0 # ์ค๋ฅธ์ชฝ ๋ค๋ฒ์งธ ์นด๋๋ ์์ผ๋ฏ๋ก 0 ๋ฐํ
...
๋ฐ๋ผ์ dfs(2, 2) = dfs(2, 3) + 1 = 1
dfs(2, 1) = dfs(2, 2) + 4 = 5
dfs(1, 1) = max(dfs(2, 1), dfs(2, 2)) = max(5, 1) = 5
...(์ค๋ต)...
์์ ๊ฐ์ ์ฐ์ฐ ๊ณผ์ ์ ๊ฑฐ์น๋ค.
right[y] | 2 | 4 | 1 | |
---|---|---|---|---|
left[x] | x \ y | 0 | 1 | 2 |
3 | 0 | 7 | 5 | -1 |
2 | 1 | -1 | 5 | 1 |
5 | 2 | -1 | 5 | 1 |
left๋ ์ผ์ชฝ ๋๋ฏธ ์นด๋, right๋ ์ค๋ฅธ์ชฝ ๋๋ฏธ ์นด๋์ด๋ค.
x, y๋ ๊ฐ๊ฐ left, right์ ์ธ๋ฑ์ค์ด๋ฉฐ 0๋ถํฐ ์์ํ๋ค. 0์ด ์ฒซ๋ฒ์งธ ์นด๋์ด๋ค.
โ๏ธ์์ค์ฝ๋
import sys
sys.setrecursionlimit(10**6)
def dfs(x, y):
if x >= n or y >= n:
return 0
if dp[x][y] != -1:
return dp[x][y]
if left[x] > right[y]:
dp[x][y] = dfs(x, y+1) + right[y] # ์ค๋ฅธ์ชฝ ๋ฒ๋ฆฌ๊ธฐ
else:
discard_left = dfs(x+1, y)
discard_both = dfs(x+1, y+1)
dp[x][y] = max(discard_left, discard_both) # max(์ผ์ชฝ ๋ฒ๋ฆฌ๊ธฐ, ๋ ๋ค ๋ฒ๋ฆฌ๊ธฐ)
return dp[x][y]
if __name__ == "__main__":
n = int(input())
left = list(map(int, sys.stdin.readline().rstrip().split()))
right = list(map(int, sys.stdin.readline().rstrip().split()))
dp = [[-1 for _ in range(n)] for _ in range(n)]
dfs(0, 0)
print(dp[0][0])