반응형
https://www.acmicpc.net/problem/13460
13460번: 구슬 탈출 2
첫 번째 줄에는 보드의 세로, 가로 크기를 의미하는 두 정수 N, M (3 ≤ N, M ≤ 10)이 주어진다. 다음 N개의 줄에 보드의 모양을 나타내는 길이 M의 문자열이 주어진다. 이 문자열은 '.', '#', 'O', 'R', 'B'
www.acmicpc.net
해결 방법 : BFS
- 10번까지 판을 기울이는 모든 경우를 탐색한다.
- 중복 탐색을 허용한다면 최악의 경우 $4^10$ 만큼을 탐색하게 되므로, visited 해쉬테이블을 만들어 구슬의 위치가 이전의 어떤 시점과 동일하다면 더 이상 탐색하지 못하도록 한다.
- 한 번의 탐색 마다 빨간 구슬과 파란 구슬을 상하좌우로 벽에 부딪힐 때까지 움직이며, 움직이는 과정에 빨간 구슬만 구멍에 들어갔다면 현재 count 를 반환한다.
- 빨간 구슬과 파란 구슬이 겹쳐지는 경우를 방지하기 위한 방법으로 조건문을 두었다.
import sys
input = sys.stdin.readline
from collections import deque
def solution(N, M, board):
D = [(0,1), (1,0), (0,-1), (-1,0)] # 상하좌우 이동 가중치
for r in range(N): # 최초 빨간 구슬, 파란 구슬 위치 찾기
for c in range(M):
if board[r][c] == 'R':
redRow, redCol = r, c
if board[r][c] == 'B':
blueRow, blueCol = r, c
Q = deque([(redRow, redCol, blueRow, blueCol, 0)])
visited = dict() # 중복 탐색 방지
visited[(redRow, redCol, blueRow, blueCol)] = True
while Q:
RR, RC, BR, BC, count = Q.popleft()
if count == 10: return -1 # 종료 조건
for d in D: # 상하좌우 기울이기
redGoal = blueGoal = False # 각 구슬이 구멍에 들어갔는지를 나타내는 변수
nRR, nRC, nBR, nBC = RR, RC, BR, BC
while board[nRR + d[0]][nRC + d[1]] != '#': # 벽에 부딪힐 때까지
nRR += d[0]
nRC += d[1]
if board[nRR][nRC] == 'O': # 구멍에 들어감
redGoal = True
while board[nBR + d[0]][nBC + d[1]] != '#':
nBR += d[0]
nBC += d[1]
if board[nBR][nBC] == 'O':
blueGoal = True
if redGoal and not blueGoal: # 빨간 구슬만 구멍에 들어간 경우
return count + 1
if blueGoal: # 파란 구슬이 구멍에 들어간 경우 현재 탐색은 무효
continue
if nRR == nBR and nRC == nBC: # 빨간 구슬과 파란 구슬이 겹쳐진 경우,
if RR == BR and RC < BC:
if d[1] == 1: nRC -= 1
else: nBC += 1
elif RR == BR and RC > BC:
if d[1] == 1: nBC -= 1
else: nRC += 1
elif RC == BC and RR < BR:
if d[0] == 1: nRR -= 1
else: nBR += 1
else:
if d[0] == 1: nBR -= 1
else: nRR += 1
if visited.get((nRR, nRC, nBR, nBC)) is None: # 탐색하지 않은 구슬 위치일 경우,
visited[(nRR, nRC, nBR, nBC)] = True
Q.append((nRR, nRC, nBR, nBC, count + 1)) # 탐색 Q에 push
return -1
if __name__ == '__main__':
N, M = map(int, input().split())
board = [input() for _ in range(N)]
result = solution(N, M, board)
print(result)
반응형
'IT study > 알고리즘 문제 풀이' 카테고리의 다른 글
백준 1311 : 할 일 정하기1 (0) | 2021.09.22 |
---|---|
백준 1799 : 비숍 (0) | 2021.09.16 |
백준 9009 : 피보나치 (0) | 2021.08.19 |
백준 7507 : 올림픽 게임 (0) | 2021.08.19 |
백준 1003 : 피보나치 함수 (백준 4150 : 피보나치 수) (0) | 2021.08.17 |