아기 상어

최민수·2023년 4월 7일
0

알고리즘

목록 보기
49/94
⭐️
from collections import deque


# BFS
def bfs():
    q = deque()
    distList, minDist = [], 987654321
    q.append([sharkRow, sharkCol, 0])
    visit = [[False for i in range(N)] for j in range(N)]
    visit[sharkRow][sharkCol] = True

    while q:
        item = q.popleft()
        curRow, curCol, dist = item[0], item[1], item[2]

        for dx, dy in [(0, 1), (0, -1), (1, 0), (-1, 0)]:
            new_row, new_col = curRow + dx, curCol + dy

            if 0 <= new_row < N and 0 <= new_col < N and not visit[new_row][new_col]:
                if sharkSize >= maps[new_row][new_col]:
                    visit[new_row][new_col] = True
                    if 1 <= maps[new_row][new_col] < sharkSize:
                        minDist = dist
                        distList.append((dist+1, new_row, new_col))
                    else:
                        q.append([new_row, new_col, dist + 1])

    if distList:
        distList.sort()
        return distList[0]
    else:
        return False


def update(updateRow, updateCol):
    global fishSum, sharkRow, sharkCol, sharkSize

    maps[sharkRow][sharkCol] = 0
    sharkRow, sharkCol = updateRow, updateCol
    fishSum += 1
    maps[sharkRow][sharkCol] = 9

    # 상어 몸집 업데이트
    if sharkSize <= fishSum:
        fishSum -= sharkSize
        sharkSize += 1


N = int(input())
maps = [list(map(int, input().split())) for i in range(N)]
count, fishCount = 0, 0
sharkSize, fishSum = 2, 0
sharkRow, sharkCol = -1, -1
fishRow, fishCol = -1, -1

for rowIdx, i in enumerate(maps):
    for idx, j in enumerate(i):
        if j == 9:
            sharkRow, sharkCol = rowIdx, idx
            break

while True:
    value = bfs()
    # 먹을 수 있는 물고기가 존재
    if value:
        moved, targetX, targetY = value[0], value[1], value[2]
        update(targetX, targetY)
        count += moved
    # 먹을 수 없음
    else:
        break

print(count)

구현 문제를 풀 때, 자꾸 예외 상황을 처리하려고 조건문을 거는 습관이 있는데 그러면 로직이 너무 복잡해지고 디버깅도 까다롭고 시간도 많이 걸린다.

예를 들면, 처음에 풀 때 일단 맵에 물고기가 존재하는지 search 함수 로 확인을 하고 존재한다면 bfs 를 돌리는데 여기서 또 후보가 1마리인 경우와 그 이상인 경우로 나눠서 풀고 이런 식이었다.

하지만 그냥 bfs 함수가 저 기능들을 한번에 할 수 있도록 살짝만 응용해 주면 된다. bfs 의 반환값이 false 면 아무것도 못찾았다. 그리고 값이 있는 경우는 (최소거리, target_x, target_y) 정보를 차례로 sorting 된 값을 넘기면 다 해결된다.

너무 엣지 케이스를 생각하고 먼저 처리해 버리지 말자.

큰 로직을 먼저 생각하고 최대한 한 묶음으로 처리해서 시간도 단축하고 디버깅 지옥에 빠지지 말자.


문제 출처: https://www.acmicpc.net/problem/16236

profile
CS, 개발 공부기록 🌱

0개의 댓글