문제: https://softeer.ai/practice/info.do?eventIdx=1&psProblemId=409
문제 설명
자율주행팀 SW 엔지니어인 당신에게 장애물과 도로를 인식할 수 있는 프로그램을 만들라는 업무가 주어졌다.
[그림 1] 지도 예시
우선 [그림 1]과 같이 정사각형 모양의 지도가 있다. 1은 장애물이 있는 곳을, 0은 도로가 있는 곳을 나타낸다.
당신은 이 지도를 가지고 연결된 장애물들의 모임인 블록을 정의하고, 불록에 번호를 붙이려 한다. 여기서 연결되었다는 것은 어떤 장애물이 좌우, 혹은 아래위로 붙어 있는 경우를 말한다. 대각선 상에 장애물이 있는 경우는 연결된 것이 아니다.
[그림 2] 블록 별 번호 부여
[그림 2]는 [그림 1]을 블록 별로 번호를 붙인 것이다.
지도를 입력하여 장애물 블록수를 출력하고, 각 블록에 속하는 장애물의 수를 오름차순으로 정렬하여 출력하는 프로그램을 작성하시오.
입력 형식
입력 값의 첫 번째 줄에는 지도의 크기 N(정사각형임으로 가로와 세로의 크기는 같으며 5≤N≤25)이 입력되고, 그다음 N 줄에는 각각 N개의 자료(0 혹은 1)가 입력된다.
출력 형식
첫 번째 줄에는 총 블록 수를 출력하시오.
그리고 각 블록 내 장애물의 수를 오름차순으로 정렬하여 한 줄에 하나씩 출력하시오.
입력 예제
7
1110111
0110101
0110101
0000100
0110000
0111110
0110000
출력 예제
3
7
8
9
정답
# https://softeer.ai/practice/info.do?eventIdx=1&psProblemId=409
from collections import deque
answer = []
dx = [0, 0, 1, -1]
dy = [1, -1, 0, 0]
def bfs(x, y):
count = 1
q = deque()
q.append((x, y))
visited[x][y] = True
while q:
x, y = q.popleft()
for i in range(4):
nx, ny = x + dx[i], y + dy[i]
if -1 < nx < n and -1 < ny < n:
if not visited[nx][ny] and graph[nx][ny] == '1':
q.append((nx, ny))
visited[nx][ny] = True
count += 1
answer.append(count)
n = int(input())
graph = [input() for _ in range(n)]
visited = [[False] * n for _ in range(n)]
for i in range(n):
for j in range(n):
if not visited[i][j] and graph[i][j] == '1':
bfs(i, j)
print(len(answer))
print('\n'.join(map(str, sorted(answer))))
풀이
2차원 지도에서 장애물을 그룹별로 나눈 다음 장애물 그룹별 개수를 오름차순으로 출력하는 문제입니다.
문제를 풀기 위한 기본적인 아이디어는 BFS/DFS입니다. 저는 BFS가 구현하기 간단하다고 생각하여 BFS로 구현했으며, 탐색 방식을 DFS로 변경하고 싶으면 popleft()를 pop()으로 변경하시면 됩니다.
각 칸을 기준으로 탐색된 적이 없으면 해당 칸을 시작점으로 BFS를 수행한 다음 탐색 범위를 answer에 추가하는 방식으로 구현했습니다. BFS 혹은 DFS에 해당하는 문제들을 몇 개 풀어봤으면 해결할 수 있을 거라 생각합니다.
'알고리즘 > Softeer' 카테고리의 다른 글
Softeer - 성적 평균 / Python (0) | 2021.10.16 |
---|---|
Softeer - 금고털이 / Python (0) | 2021.10.16 |
Softeer - 바이러스 / Python (0) | 2021.10.16 |
Softeer - 8단 변속기 / Python (0) | 2021.10.16 |