본문 바로가기
Algorithm

[분할정복/DQ] 백준 1992 쿼드트리 - 파이썬(Python)

by jangThang 2022. 3. 7.
반응형

백준 온라인 저지

 

[ Contents ]

     

     

    1. 문제 (링크 참조)

     

    1992번: 쿼드트리

    첫째 줄에는 영상의 크기를 나타내는 숫자 N 이 주어진다. N 은 언제나 2의 제곱수로 주어지며, 1 ≤ N ≤ 64의 범위를 가진다. 두 번째 줄부터는 길이 N의 문자열이 N개 들어온다. 각 문자열은 0 또

    www.acmicpc.net

     

     

     

    2. 문제 풀이

     영상 압축방법인 쿼드 트리를 구현하는 문제입니다.

     

    2022.01.29 - [Algorithm] - [Algorithm] 분할정복(DQ, Divide-and-Conquer), 각개격파 알고리즘

     

    [Algorithm] 분할정복(DQ, Divide-and-Conquer), 각개격파 알고리즘

    각개격파(各個擊破): 적을 하나하나 따로 떼어 무찌름  유독 외세의 침략을 많이 받았던 우리 민족의 대표적인 전술은 '매복'과 '각개격파'였습니다. 70%가 산악지형인 점을 이용해서, 산개된 적

    star7sss.tistory.com

     해당 영역이 모두 0이면 0, 1이면 1을 출력하고 섞여있으면 4분할로 나누어서 판별하는 분할정복 문제입니다. 모두 0 혹은 1이면 그대로 출력하면 되고, 4분할할 때만 '(' 1사분면 + 2사분면 + 3사분면 + 4사분면 ')' 결과를 출력하면 됩니다.

     

     

     

    3. 코드

    import sys
    input = sys.stdin.readline
    
    #입력
    N = int(input())
    video = []
    for _ in range(N):
        video.append(list(map(int, input().rstrip())))
    
    #분할정복(x, y, 입력크기)
    def quadTree(x, y, n):
        #모든 영역이 0 혹은 1
        if x := isSame(x, y, n):
            return str(x-1)
    
        #4분할로 분리
        else:
            return '('+quadTree(x, y, n//2)+quadTree(x, y+n//2, n//2)+quadTree(x+n//2, y, n//2)+quadTree(x+n//2, y+n//2, n//2) +')'
    
    #영역확인 (x, y, 입력크기)
    def isSame(x, y, n):
        pixelSum = 0
        for i in range(x, x+n):
            for j in range(y, y+n):
                pixelSum += video[i][j]
    
        if pixelSum == n*n: #전부 1
            print(f"{n}크기: {pixelSum}, ({y+1}, {x+1}) => 1")
            return 2
        elif pixelSum == 0: #전부 0
            print(f"{n}크기: {pixelSum}, ({y+1}, {x+1}) => 0")
            return 1
        else: #섞임
            print(f"{n}크기: {pixelSum}, ({y+1}, {x+1}) => 4분할")
            return 0
    
    print(quadTree(0, 0, N))

     본래 판별함수와 분할함수를 나누어서 구현했으나, 자꾸 순서가 뒤바뀌는 경우가 있어 하나로 통합했습니다.

     

     

    import sys
    input = sys.stdin.readline
    
    # 입력
    N = int(input())
    video = []
    for _ in range(N):
        video.append(list(map(int, input().rstrip())))
    
    
    # 분할정복(x, y, 입력크기)
    def quadTree(x, y, n):
        for i in range(x, x + n):
            for j in range(y, y + n):
                # 같지 않으면 4분할
                if video[x][y] != video[i][j]:
                    return '(' + quadTree(x, y, n // 2) + quadTree(x, y + n // 2, n // 2) + quadTree(x + n // 2, y, n // 2) + quadTree(x + n // 2, y + n // 2, n // 2) + ')'
        #모두 같으면 출력
        return str(video[x][y])
    
    print(quadTree(0, 0, N))

     위 코드는 통합버전입니다.

     

    star가 되고나서 Tistory

    반응형

    댓글