난이도 : Silver2
Link : https://www.acmicpc.net/problem/5212
Tag : 구현, 시뮬레이션
풀이일자 : 2024년 8월 26일
r : 지도의 세로 길이
c : 지도의 가로 길이
지도 밖 : 바다
. : 바다
X : 육지
이 문제는 이웃한 3개의 면이 바다이거나 4면이 바다이면 50년 후에 잠긴다는 설정을 가지고 있다.
따라서 이웃한 배열에 바다인지, 지도 밖인지를 확인하면 될것이다.
또한 50년 후의 지도에서 가라앉은 육지들로 인해 좁아진 지도를 구현하는 것이 이 문제의 핵심이라고 보여진다.
지도의 크기 R과 C는 1 ~ 10의 크기를 가진다. 따라서 모든 경우의 지도를 탐색한다고 해도 100 x 100 = 10000이기 때문에 시간 복잡도상 문제는 없을 것으로 보이며 모든 배열을 검사하는 것이 상관 없어 보인다.
깊은 복사 VS 얕은 복사
이런 개념을 익히고 다음 문제를 접근했을 때 2차원 배열의 깊은 복사를 할 수 있어야 한다.
#2차원 배열 깊은 복사
a = [[1, 2], [3, 4]]
b = [arr[:] for arr in a]
import copy
a = [[1,2],[3,4]]
b = copy.deepcopy(a)
a[1].append(5)
a
[[1, 2], [3, 4, 5]]
b
[[1, 2], [3, 4]]
이렇게 두가지 방법이 존재하지만 deepcopy를 쓰는 것 보다 슬라이싱을 사용하는 것이 속도가 더 빠르기 때문에 슬라이싱을 쓰는 것을 연습해보도록 하자.
그래서 지도를 복사하여 50년 후의 지도를 answer에 변경하고자 하였다.
4방향의 인접한 바다를 찾기 위해 갈 수 있는 방향을 탐색 할 수 있는 반복문과 조건문을 통해 인접 한 바다가 몇개인지 확인해보자
가라앉은 섬까지 구현한 answer를 최대한 작게 지도를 만들어야 한다.
r, c = map(int, input().split())
map = [list(input()) for i in range(r)]
answer = [arr[:] for arr in map] #map 깊은 복사
dx = [-1, 1, 0, 0]
dy = [0, 0, -1, 1]
# 잠기는 섬 찾아내기
for i in range(r):
for j in range(c):
if map[i][j] == 'X':
cnt = 0
for k in range(4): #4방향으로 바다가 몇개인지 찾기
nx = i + dx[k]
ny = j + dy[k]
if 0 <= nx < r and 0 <= ny < c:
if map[nx][ny] == '.':
cnt += 1
else:
cnt += 1
if cnt >= 3: #바다가 3개 이상이면 잠기는 섬
answer[i][j] = '.'
#지도 줄이기
min_i = r
min_j = c
max_i = 0
max_j = 0
for i in range(r):
for j in range(c):
if answer[i][j] == 'X':
min_i = min(min_i, i)
min_j = min(min_j, j)
max_i = max(max_i, i)
max_j = max(max_j, j)
for i in range(min_i, max_i + 1):
print("".join(answer[i][min_j:max_j + 1]))