[ BOJ / Python ] 10026번 적록색약

황승환·2022년 1월 31일
0

Python

목록 보기
139/498


이번 문제는 깊이우선탐색으로 해결하였다. 우선 그래프에서 4개의 방향으로 나아가며 검사할 수 있으므로 4개의 방향에 대한 리스트를 따로 정의해주고, 일반인의 경우 재귀호출 조건을 현재와 같은 색이고 방문처리 되어있지 않을 경우로 지정해주고, 적록색약의 경우 재귀호출 조건을 현재가 파랑이 아니라면 확인하려는 위치도 파랑이 아니고 방문처리 되어있지 않을 경우, 현재가 파랑이라면 확인하려는 위치도 파랑이고 방문처리 되어있지 않을 경우로 지정해준다.

최대 재귀 호출 제한을 넘어 재귀 에러가 발생하였고 이를 sys.setrecursionlimit(10**9)를 통해 해결하였다.

  • 최대 재귀 호출 제한을 늘려준다.
  • n을 입력받는다.
  • 그리드를 저장할 리스트 grid를 선언한다.
  • n번 반복하는 for문을 돌린다.
    -> 문자열을 입력받고 이를 리스트로 변경하여 grid에 넣어준다.
  • 4가지 방향을 저장할 리스트 dh, dw를 선언하고 4가지 방향을 짝지어 넣어준다.
  • 일반인의 방문처리에 사용할 리스트 RGB_visited를 선언하고 False를 n*n으로 채워준다.
  • 적록색약의 방문처리에 사용할 리스트 RG_visited를 선언하고 False를 n*n으로 채워준다.
  • 일반인이 보는 구역의 수를 저장할 변수 RGB_cnt를 0으로 선언한다.
  • 적록색약이 보는 구역의 수를 저장할 변수 RG_cnt를 0으로 선언한다.
  • 일반인이 보는 구역을 체크할 함수 RGB_dfs를 h,w를 인자로 갖도록 선언한다.
    -> RGB_visited[h][w]를 True로 갱신한다.
    -> 4번 반복하는 i에 대한 for문을 돌린다.
    --> 구역을 확인할 다음 인덱스를 저장할 임시변수 next_h, next_w를 선언하고 h+dh[i], w+dw[i]를 저장한다.
    --> 만약 next_h와 next_w가 0보다 크거나 같고, next_h가 h보다 작고, next_w가 w보다 작을 경우,
    ---> 만약 grid[next_h][next_w]grid[h][w]와 같고 방문처리 되어있지 않을 경우 RGB_dfs(next_h, next_w)를 재귀호출한다.
  • 적록색약이 보는 구역을 체크할 함수 RG_dfs를 h,w를 인자로 갖도록 선언한다.
    -> RG_visited[h][w]를 True로 갱신한다.
    -> 4번 반복하는 i에 대한 for문을 돌린다.
    --> 구역을 확인할 다음 인덱스를 저장할 임시변수 next_h, next_w를 선언하고 h+dh[i], w+dw[i]를 저장한다.
    --> 만약 next_h와 next_w가 0보다 크거나 같고, next_h가 h보다 작고, next_w가 w보다 작을 경우,
    ---> 만약 grid[h][w]가 B가 아니고 grid[next_h][next_w]가 B가 아니고 방문처리 되어있지 않을 경우 RG_dfs(next_h, next_w)를 재귀호출한다.
    ---> 만약 grid[h][w]가 B이고, grid[next_h][next_w]가 B이고 방문처리 되어있지 않을 경우 RG_dfs(next_h, next_w)를 재귀호출한다.
  • n번 반복하는 i에 대한 for문을 돌린다.
    -> n번 반복하는 j에 대한 for문을 돌린다.
    --> 만약 RGB_visited[i][j]가 False일 경우,
    ---> RGB_dfs(i, j)를 재귀호출한다.
    ---> RGB_cnt를 1 증가시킨다.
    --> 만약 RG_visited[i][j]가 False일 경우,
    ---> RG_dfs(i, j)를 재귀호출한다.
    ---> RG_cnt를 1 증가시킨다.
  • RGB_cnt, RG_cnt를 출력한다.

Code

import sys
sys.setrecursionlimit(10**9)
n=int(input())
grid=[]
for _ in range(n):
    grid.append(list(str(input())))
dh=[1, -1, 0, 0]
dw=[0, 0, 1, -1]
RGB_visited=[[False]*n for _ in range(n)]
RG_visited=[[False]*n for _ in range(n)]
RGB_cnt=0
RG_cnt=0
def RGB_dfs(h, w):
    RGB_visited[h][w]=True
    for i in range(4):
        next_h=h+dh[i]
        next_w=w+dw[i]
        if next_h>=0 and next_w>=0 and next_h<n and next_w<n:
            if grid[next_h][next_w]==grid[h][w] and RGB_visited[next_h][next_w]==False:
                RGB_dfs(next_h, next_w)
def RG_dfs(h, w):
    RG_visited[h][w]=True
    for i in range(4):
        next_h = h + dh[i]
        next_w = w + dw[i]
        if next_h>=0 and next_w>=0 and next_h<n and next_w<n:
            if grid[h][w]!='B' and grid[next_h][next_w]!='B' and RG_visited[next_h][next_w]==False:
                RG_dfs(next_h, next_w)
            if grid[h][w]=='B' and grid[next_h][next_w]=='B' and RG_visited[next_h][next_w]==False:
                RG_dfs(next_h, next_w)
for i in range(n):
    for j in range(n):
        if RGB_visited[i][j]==False:
            RGB_dfs(i, j)
            RGB_cnt+=1
        if RG_visited[i][j]==False:
            RG_dfs(i, j)
            RG_cnt+=1
print(RGB_cnt, RG_cnt)

profile
꾸준함을 꿈꾸는 SW 전공 학부생의 개발 일기

0개의 댓글