728x90
https://www.acmicpc.net/problem/12848
24/05/16
간단한 스프라그-그런디 정리 응용 문제로, 게임판 분할에 관한 개념을 알고 있으면 쉽게 해결할 수 있는 문제이다.
문제 접근 방식:
막대기를 게임판 위에 더 이상 둘 수 없는 사람이 지는 게임이다.
다행히도 막대기는 가로 모양 밖에 존재하지 않아서, 각 행 별로 게임이 분리된다는 사실은 쉽게 알 수 있다.
또한, 장애물이 있는 곳에는 막대기를 둘 수 없다는 제한 조건 때문에, 장애물이 놓여 있는 곳 별로 게임이 분리된다는 사실 또한 쉽게 알 수 있다.
따라서, 각 행 별로, 각 막대기가 놓여진 곳 별로 게임을 분리하여, 각 게임 별 그런디 수를 구하면 된다.
n>k이고, 길이 n짜리 게임 판이 주어질 때, 여기에 길이 k짜리 막대기를 놓는다고 하면, 게임판이 분리되는 경우가 생긴다.
예를 들어, 길이 10짜리 게임 판에 길이 5짜리 막대기를 놓는다고 하면, 3과 2로 분리되는 경우가 생긴다.
이러한 게임 판 분리 경우도 모두 고려하여 할 수 있는 행동들을 모두 따져주어 그런디 수를 구하면 된다.
아래는 내가 위의 접근 방식과 같이 작성한 파이썬 코드이다. 더보기를 누르면 확인할 수 있다.
더보기
더보기
# 12848번 막대기 게임
# 스그
'''
접근 방법:
스그
'''
import sys
input = sys.stdin.readline
def mex(S):
for i, j in zip(sorted(S), range(len(S))):
if i != j:
return j
return len(S)
N, M = map(int, input().split())
Game = [list(map(lambda x: len(x), input().rstrip().split('@'))) for _ in range(N)]
K = int(input())
P = sorted(map(int, input().split()))
DP = [0 for _ in range(1001)]
for i in range(1, 1001):
S = set()
for j in range(K):
if i < P[j]:
break
else:
for k in range(i-P[j]+1):
S.add(DP[k]^DP[i-P[j]-k])
DP[i] = mex(S)
ans = 0
for i in range(N):
for j in Game[i]:
ans ^= DP[j]
print('nein' if ans else 'hyo123bin')
'알고리즘 > 백준 문제 풀이' 카테고리의 다른 글
[Python] 12070번 gNumbers (Small) / 12071번 gNumbers (Large) (0) | 2024.06.03 |
---|---|
[Python] 3878번 점 분리 (0) | 2024.06.02 |
[Python] 28218번 격자 게임 (0) | 2024.05.31 |
[Python] 8170번 Pebbles (추후 보강 예정) (0) | 2024.05.30 |
[Python] 5981번 Cow Checkers (0) | 2024.05.29 |