본문 바로가기
Python/백준 문제 풀이

[BOJ] 27162번 Yatch Dice

by 서원두 2023. 1. 23.

[BOJ] 27162번 Yatch Dice 문제

보드게임컵에 나왔던 문제 중 하나다.

딱 봐도 이건 많은 조건 분기라는 것을 알 수 있으며, 그 조건이 무려 12가지기 때문에 구현할 때 오류 없이 잘 짜는 것이 매우 중요하다. 실수할 가능성이 매우 높기 때문에 주석(comment)으로 이 부분은 어떤 과정인지를 작성하는 것이 하나의 큰 팁이라고 본다. 실제로 이 문제를 대회에서 풀 때 주석으로 처리하면서 풀어갔음에도 3번이나 틀렸다...

지옥의 많은 조건 분기 맞왜틀

결국엔 구현이 귀찮아서 그렇지, 막상 파고들면 그렇게 어려운 문제는 아니다.

이 문제에서의 yatch 족보는 위와 같다

먼저 이 문제는 첫 세 개의 주사위는 고정되어 있고, 나머지 두 개의 주사위 수를 무작위로 고를 수 있다. 그와 동시에 위의 12가지 족보 중 가능한 족보만으로 점수 중 최고점을 출력하면 된다. 이는 첫 번째 입력으로 주어지는 문자열을 통해 처리하면 된다.

Ones부터 Sixes, Four of a Kind, Yatch와 Choice는 구현이 간단하니 넘어가고, 핵심은 아마도 Full House, Little/Big Straight라고 생각한다. 이 셋은 구현하기 은근히 까다롭다.

이 세 가지는 집합으로 접근하여 풀었다. 굉장히 나이브(naïve)하게 짰기 때문에 이보다 더 좋은 방법이 있을 수 있음을 알린다.

  • Full House는 현재 고정한 주사위를 set으로 묶고 len을 했을 때 2 이하의 수가 나온다면 그때 점수를 측정하게 했다. len의 결과가 2인 경우엔 요소가 두 개이므로 어떻게든 Full House를 만들 수 있다. 예를 들어 5가 둘, 6이 하나이건 5가 하나, 6이 둘이건 간에 55666 또는 55566을 만들 수 있다. 이런 경우에는 당연히 큰 수로 골라야 하기 때문에 두 개의 숫자 중 큰 수 × 3 + 작은 수 × 2를 고른다. 만약 len의 결과가 1이라면 나머지 두 수를 set 안의 수를 제외한 가장 큰 수로 채운다.
  • Little/Big Straight는 기존의 고정된 세 개의 주사위와 각각 $ \{1, 2, 3, 4, 5\} \: $와 $ \{2, 3, 4, 5, 6\} \:$와의 교집합을 한 집합의 크기가 3일 때에만 점수를 매겼다. 왜냐하면 3이 아닌 경우에는 절대로 이 족보를 만들 수가 없기 때문이다.

이를 코드로 나타내면 아래와 같다.

import sys

if __name__ == '__main__':
    zokbo = sys.stdin.readline().rstrip()
    a, b, c = map(int, sys.stdin.readline().rstrip().split())
    abc = [a, b, c]
    set_abc = set(abc)
    max_score = -1

    for i in range(12):
        if zokbo[i] == 'Y':
            # Ones
            if i == 0:
                now_score = abc.count(1) + 2
                max_score = max(max_score, now_score)
            # Twos
            elif i == 1:
                now_score = abc.count(2)*2 + 4
                max_score = max(max_score, now_score)
            # Threes
            elif i == 2:
                now_score = abc.count(3)*3 + 6
                max_score = max(max_score, now_score)
            # Fours
            elif i == 3:
                now_score = abc.count(4)*4 + 8
                max_score = max(max_score, now_score)
            # Fives
            elif i == 4:
                now_score = abc.count(5)*5 + 10
                max_score = max(max_score, now_score)
            # Sixs
            elif i == 5:
                now_score = abc.count(6)*6 + 12
                max_score = max(max_score, now_score)
            # Four of a Kind
            elif i == 6:
                now_score = 0
                if len(set_abc) == 2:
                    for now_eye in list(set_abc):
                        if abc.count(now_eye) == 2:
                            now_score = now_eye*4
                elif len(set_abc) == 1:
                    now_score = a*4
                max_score = max(max_score, now_score)
            # Full House
            elif i == 7:
                now_score = 0
                if len(set_abc) == 2:
                    now_score = max(set_abc)*3 + min(set_abc)*2
                elif len(set_abc) == 1:
                    if a == 6:
                        now_score = 6*3 + 5*2
                    else:
                        now_score = a*3 + 6*2
                max_score = max(max_score, now_score)
            # Little Straight
            elif i == 8:
                now_score = 0
                if len(set_abc & {1, 2, 3, 4, 5}) == 3:
                    now_score = 30
                max_score = max(max_score, now_score)
            # Big Straight
            elif i == 9:
                now_score = 0
                if len(set_abc & {2, 3, 4, 5, 6}) == 3:
                    now_score = 30
                max_score = max(max_score, now_score)
            # Yatch
            elif i == 10:
                now_score = 0
                if len(set_abc) == 1:
                    now_score = 50
                max_score = max(max_score, now_score)
            # Choice
            else:
                now_score = sum(abc) + 12
                max_score = max(max_score, now_score)

    print(max_score)


띄어쓰기(indent) 때문에 코드 길이가 길어졌을 뿐 헷갈리지 않게 코드만 잘 짠다면 충분히 쉽게 맞출 수 있다.

728x90

'Python > 백준 문제 풀이' 카테고리의 다른 글

[BOJ] 27648번 증가 배열 만들기  (0) 2023.03.09
[BOJ] 2468번 안전영역  (0) 2023.01.29
[BOJ] 1331번 나이트 투어  (0) 2023.01.14
[BOJ] 26517번 연속인가? ?  (0) 2023.01.07
[BOJ] 26069번 붙임성 좋은 총총이  (0) 2022.12.31

댓글