어른 상어 파이썬 백준 19237
문제
input
첫 줄에는 N, M, k가 주어진다. (2 ≤ N ≤ 20, 2 ≤ M ≤ N2, 1 ≤ k ≤ 1,000)
그 다음 줄부터 N개의 줄에 걸쳐 격자의 모습이 주어진다. 0은 빈칸이고, 0이 아닌 수 x는 x번 상어가 들어있는 칸을 의미한다.
그 다음 줄에는 각 상어의 방향이 차례대로 주어진다. 1, 2, 3, 4는 각각 위, 아래, 왼쪽, 오른쪽을 의미한다.
그 다음 줄부터 각 상어의 방향 우선순위가 상어 당 4줄씩 차례대로 주어진다. 각 줄은 4개의 수로 이루어져 있다. 하나의 상어를 나타내는 네 줄 중 첫 번째 줄은 해당 상어가 위를 향할 때의 방향 우선순위, 두 번째 줄은 아래를 향할 때의 우선순위, 세 번째 줄은 왼쪽을 향할 때의 우선순위, 네 번째 줄은 오른쪽을 향할 때의 우선순위이다. 각 우선순위에는 1부터 4까지의 자연수가 한 번씩 나타난다. 가장 먼저 나오는 방향이 최우선이다. 예를 들어, 우선순위가 1 3 2 4라면, 방향의 순서는 위, 왼쪽, 아래, 오른쪽이다.
맨 처음에는 각 상어마다 인접한 빈 칸이 존재한다. 따라서 처음부터 이동을 못 하는 경우는 없다.
output
1번 상어만 격자에 남게 되기까지 걸리는 시간을 출력한다. 단, 1,000초가 넘어도 다른 상어가 격자에 남아 있으면 -1을 출력한다.
TODO
direction = [0,상,하,좌,우]
d = 1:상, 2:하, 3:좌, 4:우
딕셔너리 형태로 상어 아이디 별 방향 우선순위 저장.
아이디는 1~M
상어우선순위[id] = [방향우선순위_1, ..., 방향우선순위_4]
아이디 별 냄새 남기기
1초마다 -1 지금 상어가 있는 곳은 k로 설정
한 칸에 상어 아이디와 냄새 남은 시간 저장
[[id,k],[id,k-1]...]
상어 아이디 별 위치 저장
상어위치[id] = [x,y]
상어 방향 저장
상어방향 =[d1,d2,...,dm]
방향 고려해서 우선순위 별 상어 움직이기
상어 내쫓기 -> 상어 아이디 삭제
CODE
import sys
n,m,k = map(int,sys.stdin.readline().split())
space = [list(map(int,sys.stdin.readline().split())) for _ in range(n)] # x번 상어 0은 빈칸
shark_position = {}
for i in range(n):
for j in range(n):
if space[i][j] != 0 :
shark_position[space[i][j]] = [i,j]
space[i][j] = [space[i][j],0]
# 위, 아래, 좌 우
shark_dir = list(map(int,sys.stdin.readline().split()))
shark_pri= {}
for i in range (1,m+1):
shark_pri[i] = [0]
for _ in range(4) :
shark_pri[i].append(list(map(int,sys.stdin.readline().split())))
# 1상 2하 3좌 4우 우선순위
direction = [0,(-1,0),(1,0),(0,-1),(0,1)]
def shark_move(shark_position,shark_pri, shark_dir,space):
#n x n m마리 k초동안 냄새 유지
t = 0
while t<=1000 and len(shark_position) >1 :
t+=1
temp_space = [[0 for _ in range(n)] for _ in range(n)]
len_shark_list = len(shark_position)
shark_key_list = list(shark_position.keys())
for q in range(len_shark_list):
key = shark_key_list[q]
x,y = shark_position[key]
d = shark_dir[key-1]
space[x][y][1] = k
change_first = False
change_second = False
tx,ty,td = 0,0,d
for nd in shark_pri[key][d] :
px,py = direction[nd]
nx,ny = x+px,y+py
if 0<=nx<n and 0<=ny<n and space[nx][ny][0] ==0 :
shark_position[key] = [nx,ny]
shark_dir[key-1] = nd
space[nx][ny][1] = -1
if temp_space[nx][ny] == 0 : #상어 잡아먹기
temp_space[nx][ny] = key
else :
if temp_space[nx][ny] < key :
del shark_position[key]
else :
del shark_position[temp_space[nx][ny]]
temp_space[nx][ny] = key
change_first = True
break
if 0<=nx<n and 0<=ny<n and not(change_first or change_second) and space[nx][ny][0] == space[x][y][0] :
change_second = True
tx,ty,td = nx,ny,nd
if (not change_first) and change_second :
shark_position[key] = [tx,ty]
shark_dir[key-1] = td
space[tx][ty][1] = -1
if temp_space[tx][ty] == 0 :
temp_space[tx][ty] = key
else :
if temp_space[tx][ty] < key :
del shark_position[key]
else :
del shark_position[temp_space[tx][ty]]
for i in range(n):
for j in range(n):
if space[i][j][1] == -1 :
space[i][j][1] = k
space[i][j][0] = temp_space[i][j]
elif space[i][j][1] != 0 :
space[i][j][1] -= 1
if space[i][j][1] == 0:
space[i][j][0] = 0
return t
t=shark_move(shark_position,shark_pri,shark_dir,space)
if t != 1001 :
print(t)
else :
print(-1)
회고
방향 별 우선순위
냄새안나는곳 -> 자신의 냄새가 나는곳을 한 번에 처리하느라 머리가 아팟다
x,y
px,py -> plus x, plus y
nx,ny -> new x, new y
tx,ty -> temp x, temp y
문제가 너무 길고.. 구현문제는 디버깅하기 힘든건가 쉬운건가..
Author And Source
이 문제에 관하여(어른 상어 파이썬 백준 19237), 우리는 이곳에서 더 많은 자료를 발견하고 링크를 클릭하여 보았다 https://velog.io/@ifelifelse/어른-상어-파이썬-백준-19237저자 귀속: 원작자 정보가 원작자 URL에 포함되어 있으며 저작권은 원작자 소유입니다.
우수한 개발자 콘텐츠 발견에 전념 (Collection and Share based on the CC Protocol.)