24년 하반기 삼성전자 코딩테스트 준비하면서 푼 해설
import sys
# 제출 전 삭제
sys.stdin = open("input.txt")
# Solution
class Player:
def __init__(self, idx, x, y):
self.idx = idx
self.x = x
self.y = y
self.dir_idx = 0
self.priority_map = {}
def add_priority(self, idx, p1, p2, p3, p4):
self.priority_map[idx] = [p1, p2, p3, p4]
def get_dirs(self):
return self.priority_map[self.dir_idx]
def move(self, nx, ny, dir_idx):
self.x = nx
self.y = ny
self.dir_idx = dir_idx
def __repr__(self):
return f"{self.idx}"
# Step 1: player 이동
def move_player(player):
dir_idx_list = player.get_dirs()
player_map[player.x][player.y] = 0
# 1-1: 비어있는 땅으로 이동
for idx in dir_idx_list:
dx, dy = dir_dict[idx]
nx, ny = player.x + dx, player.y + dy
if in_range(nx, ny) and owner_map[nx][ny] == 0:
player.move(nx, ny, idx)
return
# 1-2: 자신의 땅으로 이동
for idx in dir_idx_list:
dx, dy = dir_dict[idx]
nx, ny = player.x + dx, player.y + dy
if in_range(nx, ny) and owner_map[nx][ny] == player.idx:
player.move(nx, ny, idx)
return
# Step 2: Update player
def update_graph():
remove_list = []
for player in player_dict.values():
if player_map[player.x][player.y] == 0:
update(player)
elif player_map[player.x][player.y] > player.idx:
remove_list.append(player_map[player.x][player.y])
update(player)
else:
remove_list.append(player.idx)
if len(remove_list) > 0:
global m
for player_idx in remove_list:
player_dict.pop(player_idx)
m -= 1
def update(player):
player_map[player.x][player.y] = player.idx
owner_map[player.x][player.y] = player.idx
remain_map[player.x][player.y] = k + 1
def reduce_k():
for i in range(n):
for j in range(n):
if remain_map[i][j] > 0:
remain_map[i][j] -= 1
if remain_map[i][j] == 0:
owner_map[i][j] = 0
def in_range(x, y):
return 0 <= x < n and 0 <= y < n
# Main
n, m, k = map(int, sys.stdin.readline().split())
player_dict = {}
player_map = [[0] * n for _ in range(n)]
owner_map = [[0] * n for _ in range(n)]
remain_map = [[0] * n for _ in range(n)]
dir_dict = {1: [-1, 0], 2: [1, 0], 3: [0, -1], 4: [0, 1]}
# get player location
for i in range(n):
row = list(map(int, sys.stdin.readline().split()))
for j in range(n):
if row[j] > 0:
player = Player(row[j], i, j)
player_map[i][j] = player.idx
player_dict[player.idx] = player
owner_map[i][j] = player.idx
remain_map[i][j] = k
# get player init direction
init_dirs = list(map(int, sys.stdin.readline().split()))
for i, dir_idx in enumerate(init_dirs, start=1):
player_dict[i].dir_idx = dir_idx
# get player dir priority
for i in range(1, m + 1):
player = player_dict[i]
for dir_idx in range(1, 5):
p1, p2, p3, p4 = map(int, sys.stdin.readline().split())
player.add_priority(dir_idx, p1, p2, p3, p4)
# game
flag = False
turn = 0
while m > 1:
if turn >= 1000:
flag = True
break
for key, player in player_dict.items():
move_player(player)
update_graph()
reduce_k()
turn += 1
if flag:
print(-1)
else:
print(turn)