알고리즘/백준[baekjoon]
백준 1743번 : 음식물 피하기 (by python) - BFS
코딩하는이씨
2024. 8. 22. 20:40
728x90
반응형
https://www.acmicpc.net/problem/1743
문제를 보고 바로 BFS를 이용해 상하좌우에 이어진 쓰래기를 탐색해 최대(Max)를 구하면되겠다고 생각했다.
처음 코드 (메모리 초과)
from collections import deque
import sys
input = sys.stdin.readline
dx = [-1, 1, 0, 0]
dy = [0, 0, -1, 1]
result = 0
n, m, k = map(int, input().split())
trash = [[False]*m for _ in range(n)]
for _ in range(k):
x, y =map(int, input().split())
trash[x-1][y-1] = True
def bfs(x, y):
cnt = 0
q = deque()
q.append((x, y))
while q:
x, y = q.popleft()
trash[x][y] = False
cnt += 1
for i in range(4):
nx = x + dx[i]
ny = y + dy[i]
if 0 <= nx < n and 0 <= ny < m and trash[nx][ny]:
q.append((nx, ny))
return cnt
for i in range(n):
for j in range(m):
if trash[i][j]:
result = max(bfs(i, j), result)
print(result)
trash 배열을 전부 만들어 trash가 있는 위치를 입력받을 때 True를 넣어 위치를 표시하고 BFS 탐색을 진행했다.
테스트 케이스는 맞출 수 있었지만, 메모리 초과가 발생했다.
실패 원인
문제의 원인은 조건에 맞아 큐에 추가할 때 trash방문처리를 해주지 않고 queue에서 pop 이후에 처리해주기 때문에 발생했다.
하지만,,, 이 사실을 모르던 나는 M, N의 크기가 너무 큰 입력이 들어와 배열이 크게 만들어지나 생각했다.
물론... 조건을 자세히 보면 그럴일은 없지만 .. 쉬운문제라고 생각해 문제를 쓱 훓고 바로 풀이에 들어간 점이 문제였다.
그래서 생각해낸 방법이 배열을 만들지 않고 해결하기였다.
정답 코드(Set 이용)
from collections import deque
import sys
input = sys.stdin.readline
dx = [-1, 1, 0, 0]
dy = [0, 0, -1, 1]
result = 0
n, m, k = map(int, input().split())
trash = set()
for _ in range(k):
x, y = map(int, input().split())
trash.add((x-1, y-1))
def bfs(x, y):
cnt = 0
q = deque()
q.append((x, y))
trash.remove((x, y)) # 방문한 좌표를 trash 집합에서 제거
while q:
x, y = q.popleft()
cnt += 1
for i in range(4):
nx = x + dx[i]
ny = y + dy[i]
if (nx, ny) in trash:
q.append((nx, ny))
trash.remove((nx, ny)) # 방문한 좌표를 즉시 제거
return cnt
for x, y in list(trash): # 집합을 순회하면서 bfs 실행
if (x, y) in trash:
result = max(result, bfs(x, y))
print(result)
Set을 이용해 trash를 담고 현재 좌표가 trash안에 있는지 확인하는 방식으로 구현했다.
(이때는 또 큐에 넣고 바로 방문 처리..)
이렇게 해결하고 이전 코드 문제점을 찾기 위해 한줄씩 꼼꼼히 뇌에서 코딩해본결과... 큐에 방문했던 좌표를 다시 넣을 수 있게된다는 사실을알고 고쳤다.
처음 풀이의 개선
from collections import deque
import sys
input = sys.stdin.readline
dx = [-1, 1, 0, 0]
dy = [0, 0, -1, 1]
result = 0
n, m, k = map(int, input().split())
trash = [[0]*m for _ in range(n)]
for _ in range(k):
x, y =map(int, input().strip().split())
trash[x-1][y-1] = 1
def bfs(x, y):
cnt = 0
q = deque()
q.append((x, y))
trash[x][y] = 0
while q:
x, y = q.popleft()
cnt += 1
for i in range(4):
nx = x + dx[i]
ny = y + dy[i]
if 0 <= nx < n and 0 <= ny < m and trash[nx][ny]:
trash[nx][ny] = 0 # 방문 표시를 0으로 변경하여 다시 탐색되지 않도록 함
q.append((nx, ny))
return cnt
for i in range(n):
for j in range(m):
if trash[i][j]:
result = max(bfs(i, j), result)
print(result)
느낀점
쉬운 문제라도 문제와 조건을 꼼꼼히 읽고 시간복잡도와 메모리를 신경써서 풀이를 진행해야겠다.
728x90
반응형