Algorithm

백준 1652 누울 자리를 찾아라

김디니 2022. 8. 4. 16:43

1652 누울 자리를 찾아라

영식이가 누울 수 있는 자리에는 조건이 있다. 똑바로 연속해서 2칸 이상의 빈 칸이 존재하면 그 곳에 몸을 양 옆으로 쭉 뻗으면서 누울 수 있다. 가로로 누울 수도 있고 세로로 누울 수도 있다. 

# 1652 누울 자리를 찾아라

n = int(input())                    
metrix = []                         # 행렬 저장
row_cnt = 0                         # 가로 누울 자리 횟수 저장
col_cnt = 0                         # 세로 누울 자리 횟수 저장
check1 = []                         # 가로 입력값 검열 리스트 ('.' or 'X')
check2 = []                         # 세로 입력값 검열 리스트 ('.' or 'X')

for _ in range(n):                  # 행렬 입력
    line = list(input())
    metrix.append(line)
    
for i in range(n):     
    check1.clear()                  # (가로눕기)행 바꿀 시 검열 리스트를 초기화한다
    check2.clear()                  # (세로눕기)행 바꿀 시 검열 리스트를 초기화한다
    for j in range(n): #col 

        #가로눕기
        check1.append(metrix[i][j]) # 각 행의 값을 cheak1 리스트에 넣어준다
    
        if 'X' in check1:           # 만약 'X'가 나온다면
            check1.clear()          # 검열 리스트를 초기화
            
        elif check1.count('.') == 2: # 검열 리스트에 '.'이 두개라면 
            row_cnt += 1            # (가로) 누울 자리 하나 추가
                                    # 2개 이상이 아닌 ==2로 끝내는 이유는 '.'이 3개 이상이 될 경우 cnt가 계속 늘어나기 때문
        # 세로눕기
        check2.append(metrix[j][i]) # 각 열의 값을 cheak2 리스트에 넣어준다
    
        if 'X' in check2:           # 만약 'X'가 나온다면
            check2.clear()          # 검열 리스트를 초기화
            
        elif check2.count('.') == 2: # 검열 리스트에 '.'이 두개라면 
            col_cnt += 1             # (세로)누울 자리 하나 추가
            
print(row_cnt, col_cnt)             # 최종적으로 누울 자리의 개수 출력
# 입력 값
5
....X
..XX.
.....
.XX..
X....

위의 입력값을 보았을 때 X는 누울 수 없는 곳이다. 

즉, '.'이 2개 이상이라면 누울 자리 1개가 되는 것이다.

가로, 세로 모두 누울 자리를 탐색해야 하기 때문에 행/렬 모두 탐색해야 한다. 

 

#가로눕기
        check1.append(metrix[i][j]) # 각 행의 값을 cheak1 리스트에 넣어준다
    
        if 'X' in check1:           # 만약 'X'가 나온다면
            check1.clear()          # 검열 리스트를 초기화
            
        elif check1.count('.') == 2: # 검열 리스트에 '.'이 두개라면 
            row_cnt += 1            # (가로) 누울 자리 하나 추가

check1 리스트를 통해 행의 값을 하나씩 넣어주며 '.' 와 'X'를 검열한다. 

check1에 차례대로 값을 넣어주는데 '.'가 연속적으로 2개가 들어간다면 누울 자리를 세는 row_cnt에 1을 추가한다. 

문제 지문에서 '2 이상'으로 명시되어 있지만, '== 2'로 구현한 이유는 각 행/열에서 '.'가 2개이든 3개이든 상관없이 1개의 누울 자리가 되기 때문이다. 

' >= 2'로 구현할 경우 연속된 '.'이 3개, 4개로 늘어날 경우 자리 수가 하나씩 늘어난다. 

 

만약 'X'가 나온다면 검열 리스트를 초기화하여 새로운 누울 자리를 탐색한다. 

['.', '.', 'X', '.', '.'] X를 기준으로 양 옆에 '.' 두개씩 있는 경우 2개의 자리로 인식해야하기 때문이다. 

 

for i in range(n):     
    check1.clear()                  # (가로눕기)행 바꿀 시 검열 리스트를 초기화한다
    check2.clear()                  # (세로눕기)행 바꿀 시 검열 리스트를 초기화한다

j의 순회가 끝났다면 위에 있는 i로 돌아오게 되는데, 

이 때 모든 검열 리스트를 초기화하여 각 행/열을 탐색하도록 한다. 

 

# 세로눕기
check2.append(metrix[j][i])

가로눕기의 코드와 동일하지만, 

열을 탐색해야 하므로 기준이 되는 인덱스를 다시 설정하여 [j][i]로 명시한다. 

 

'Algorithm' 카테고리의 다른 글

[이론] 힙 Heap, 셋 Set  (0) 2022.08.06
[이론] 스택 Stack, 큐 Queue  (0) 2022.08.06
백준 1236, 5533  (0) 2022.08.03
백준 1269, 2750, 5063, 11286 / 프로그래머스 81301  (1) 2022.08.02
백준 2161, 2902, 9012  (0) 2022.08.01