[BOJ] 14891 - 톱니바퀴

김우경·2021년 3월 30일
0

삼성기출

목록 보기
11/37

문제링크

14891 - 톱니바퀴

문제설명

8개의 톱니를 가지는 톱니바퀴 4개가 아래와 같이 배치되어있다.

각 톱니는 N극 또는 S극을 가지고, 총 K번 시계방향 또는 반시계방향으로 회전시키려고 한다. 문제에서는 어떤 톱니바퀴를 어떤 방향으로 회전시킬지 주어지는데, 맞닿은 극이 같으면 옆 톱니를 회전시키지 않고, 다르면 옆 톱니는 반대방향으로 회전시킨다. 톱니의 최초 상태와 톱니 회전 방법이 주어질때 최종 톱니의 상태는 ??

문제풀이

시도 1

import sys

input = sys.stdin.readline

def anticlockwise(sawtooth):
    zero = sawtooth[0]
    for i in range(len(sawtooth)-1):
        sawtooth[i] = sawtooth[i+1]
    sawtooth[-1] = zero
    #print(sawtooth)

def clockwise(sawtooth):
    zero = sawtooth[-1]
    for i in range(len(sawtooth)-1, 0, -1):
        sawtooth[i] = sawtooth[i-1]
    sawtooth[0] = zero
    #print(sawtooth)

def solution():
    sawtooth = [[]]
    for i in range(4):
        sawtooth.append(list(map(int, list(input().strip()))))
    K = int(input())
    rotations = []
    for i in range(K):
        rotations.append(list(map(int, input().split())))
    
    for num, dir in rotations:
        if dir == 1:
            #clockwise
            clo, anti = [num], []
            # 1. 왼쪽도 돌려야 하는지 확인
            if num-1 >= 1 and sawtooth[num][6] != sawtooth[num-1][2]:
                anti.append(num-1)
                if num-2 >= 1 and sawtooth[num-1][6] != sawtooth[num-2][2]:
                    clo.append(num-2)
                    if num-3 >= 1 and sawtooth[num-2][6] != sawtooth[num-3][2]:
                        anti.append(num-3)
    
            # 2. 오른쪽도 돌려야 하는지 확인
            if num+1 <= 4 and sawtooth[num][2] != sawtooth[num+1][6]:
                anti.append(num+1)
                if num+2 <= 4 and sawtooth[num+1][2] != sawtooth[num+2][6]:
                    clo.append(num+2)
                    if num+3 <= 4 and sawtooth[num+2][2] != sawtooth[num+3][6]:
                        anti.append(num+3)

            # 3. 회전
            for c in clo:
                    clockwise(sawtooth[c])
            for a in anti:
                anticlockwise(sawtooth[a])
            
        else:
            clo, anti = [], [num]
            # 1. 왼쪽도 돌려야 하는지 확인
            if num-1 >= 1 and sawtooth[num][6] != sawtooth[num-1][2]:
                clo.append(num-1)
                if num-2 >= 1 and sawtooth[num-1][6] != sawtooth[num-2][2]:
                    anti.append(num-2)
                    if num-3 >= 1 and sawtooth[num-2][6] != sawtooth[num-3][2]:
                        clo.append(num-3)
    
            # 2. 오른쪽도 돌려야 하는지 확인
            if num+1 <= 4 and sawtooth[num][2] != sawtooth[num+1][6]:
                clo.append(num+1)
                if num+2 <= 4 and sawtooth[num+1][2] != sawtooth[num+2][6]:
                    anti.append(num+2)
                    if num+3 <= 4 and sawtooth[num+2][2] != sawtooth[num+3][6]:
                        clo.append(num+3)

            # 3. 회전
            for c in clo:
                    clockwise(sawtooth[c])
            for a in anti:
                anticlockwise(sawtooth[a])
    result = 0

    for i in range(len(sawtooth)-1):
        if sawtooth[i+1][0] == 1:
            result += 2**i
    return result


print(solution())

문제를 똑바로 안읽어서 엉뚱한거 디버깅하느라 한참 걸렸다 ^_ㅠ,, 코드를 좀 더 효율적으로 작성하고자 중복된 부분을 제거해보았다.

시도 2

dictionary를 이용해서 각 회전마다 시계방향으로 돌릴 톱니바퀴, 반시계방향으로 돌릴 톱니바퀴를 저장했음

import sys

input = sys.stdin.readline

def anticlockwise(sawtooth):
    zero = sawtooth[0]
    for i in range(len(sawtooth)-1):
        sawtooth[i] = sawtooth[i+1]
    sawtooth[-1] = zero
    #print(sawtooth)

def clockwise(sawtooth):
    zero = sawtooth[-1]
    for i in range(len(sawtooth)-1, 0, -1):
        sawtooth[i] = sawtooth[i-1]
    sawtooth[0] = zero
    #print(sawtooth)

def solution():
    sawtooth = [[]]
    for i in range(4):
        sawtooth.append(list(map(int, list(input().strip()))))
    K = int(input())
    rotations = []
    for i in range(K):
        rotations.append(list(map(int, input().split())))
    
    for num, dir in rotations:
        rotate = {-1:[], 1:[]}
        rotate[dir].append(num)
        # 1. 왼쪽도 돌려야 하는지 확인
        if num-1 >= 1 and sawtooth[num][6] != sawtooth[num-1][2]:
            rotate[-1 * dir].append(num-1)
            if num-2 >= 1 and sawtooth[num-1][6] != sawtooth[num-2][2]:
                rotate[dir].append(num-2)
                if num-3 >= 1 and sawtooth[num-2][6] != sawtooth[num-3][2]:
                    rotate[-1 * dir].append(num-3)

        # 2. 오른쪽도 돌려야 하는지 확인
        if num+1 <= 4 and sawtooth[num][2] != sawtooth[num+1][6]:
            rotate[-1 * dir].append(num+1)
            if num+2 <= 4 and sawtooth[num+1][2] != sawtooth[num+2][6]:
                rotate[dir].append(num+2)
                if num+3 <= 4 and sawtooth[num+2][2] != sawtooth[num+3][6]:
                    rotate[-1 * dir].append(num+3)

        # 3. 회전
        for r in rotate[1]:
                clockwise(sawtooth[r])
        for r in rotate[-1]:
            anticlockwise(sawtooth[r])

    result = 0

    for i in range(len(sawtooth)-1):
        if sawtooth[i+1][0] == 1:
            result += 2**i
    return result


print(solution())
profile
Hongik CE

0개의 댓글