2659 십자카드 문제

hey hey·2022년 3월 13일
0

알고리즘

목록 보기
38/57
post-thumbnail

문제

위와 같은 십자모양의 한 장의 카드에서, 네 모서리에 1 이상 9 이하의 숫자가 하나씩 씌여 있다. 이 네 개의 숫자 중에는 같은 숫자도 있을 수 있다.

모든 가능한 십자 카드가 주어질 때, 각각의 카드는 다음과 같은 '시계수'라는 번호를 가진다. 시계수는 카드의 숫자들을 시계 방향으로 읽어서 만들어지는 네 자리 수들 중에서 가장 작은 수이다. 위 그림의 카드는 시계방향으로 3227, 2273, 2732, 7322로 읽을 수 있으므로, 이 카드의 시계수는 가장 작은 수인 2273이다.

입력으로 주어진 카드의 시계수를 계산하여, 그 시계수가 모든 시계수들 중에서 몇 번째로 작은 시계수인지를 알아내는 프로그램을 작성하시오.

예를 들어서, 다음과 같은 십자 카드의 시계수는 1122이며, 이 시계수보다 작은 시계수들은 1111, 1112, 1113, 1114, 1115, 1116, 1117, 1118, 1119 뿐이므로 1122는 10번째로 작은 시계수다. (여기서 십자카드는 0 이 나타날 수 없으므로 1120은 시계수가 될 수 없다. 또한 1121 이 적혀있는 카드의 시계수는 1112이므로, 1121은 시계수가 될 수 없다.

입력

입력은 한 줄로 이루어지며, 이 한 줄은 카드의 네 모서리에 씌여있는 1 이상 9 이하의 숫자 4개가 시계 방향으로 입력된다. 각 숫자 사이에는 빈칸이 하나 있다.

출력

입력된 카드의 시계수가 모든 시계수들 중에서 몇 번째로 작은 시계수인지를 출력한다.

풀이

실버 3문제가 맞나 싶긴한데... 내가 실력이 줄었나 ㅎ
풀이 방법 :
1. 네자리 수를 시계방향으로 돌려서 나오는 네자리수 4개 중 가장 작은 수를 찾는 함수를 만든다.
2. 1~9 까지를 사용한 네자리 수 전부를 가지는 중복 순열을 만든다 . => itertools에 product 사용
3. 이 모든 값들을 1번의 함수로 돌려서 중복되지 않게 정렬시킨 후
4. 입력으로 들어온 값도 1번의 함수로 돌려서 3번의 값에서 몇번째에 위치해 있는지 찾아준다.

import sys
sys.stdin = open('input.txt')
from itertools import product
from collections import deque
# 중복 순열

numlist = list(range(1,10))

perlist = list(product(numlist,numlist,numlist,numlist))
# 1~9까지의 값들로 이루어진 4자리 중복순열

def crossCard(list) : # 시계방향으로 네번 돌려서 네자리 수 중 가장 작은 수를 찾아내는 함수
    Nlist = deque(list) # 로테이트를 위한 데큐 사용
    small = 10000
    for _ in range(4): # 시계방향으로 4번 돌리기
        Nlist.rotate()
        num = ''
        for i in Nlist:
            num += str(i)
        if small>= int(num):
            small = int(num)
    return small

result = []

for ilist in perlist:   # 중복순열 하나씩 다 확인해서
    result.append(crossCard(ilist)) # 결과값만 저장해준다.

result = list(set(result)) # 중복값을 빼주기 위한 list(set()) 함수 사용
result.sort()               # 정렬시켜주고

input = list(map(int,input().split()))
tmp = crossCard(input)      # input으로 들어온 값의 위치가 어딨는지 찾아준다.
print(result.index(tmp) +1)
profile
FE - devp

0개의 댓글