-
-
Save sooop/d450a85b706e04cc211f0db3712152bc to your computer and use it in GitHub Desktop.
Project Euler 84
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
from random import randrange | |
def play(face=6): | |
M = 300 # 게임당 주사위 굴리는 횟수 | |
pos = 0 # 시작위치 | |
rooms = ('GO', 'A1', 'CC1', 'A2', 'T1', 'R1', 'B1', 'CH1', 'B2', 'B3', | |
'JAIL', 'C1', 'U1', 'C2', 'C3', 'R2', 'D1', 'CC2', 'D2', 'D3', | |
'FP', 'E1', 'CH2', 'E2', 'E3', 'R3', 'F1', 'F2', 'U2', 'F3', | |
'G2J', 'G1', 'G2', 'CC3', 'G3', 'R4', 'CH3', 'H1', 'T2', 'H2') | |
result = dict() | |
deck = [ | |
['GO', 'JAIL'] + [''] * 14, # GO, JAIL외 다른 카드 14장 | |
['GO', 'JAIL', 'C1', 'E3', 'H2', 'R1', 'NR', 'NR', 'NU','-3'] +\ | |
[''] * 6 | |
] | |
'''카드 덱 섞기: 임의의 카드와 첫번째 카드를 서로 바꿈''' | |
for d in range(2): | |
for _ in range(100): | |
i = randrange(len(deck[d]) - 1) + 1 | |
deck[d][0], deck[d][i] = deck[d][i], deck[d][0] | |
def run_dice(): | |
'''주사위를 굴리기: 두 개의 주사위를 굴려서 각 결과를 튜플로 반환''' | |
return (randrange(face) + 1, randrange(face) + 1) | |
def flip_card(p:int, d:int) -> int: | |
'''카드를 하나 뒤집고, 그 결과에 따라 이동한 방번호를 리턴한다. | |
''' | |
c = deck[d].pop(0) | |
deck[d].append(c) | |
if c == '': # 이동과 관련없는 키드 | |
pass | |
elif c == 'NR': # 다음 R | |
i = (([x[0] for x in rooms] * 2)[p+1:]).index('R') + 1 | |
p = (p + i) % 40 | |
elif c == 'NU': # 다음 U | |
i = (([x[0] for x in rooms] * 2)[p+1:]).index('U') + 1 | |
p = (p + i) % 40 | |
elif c == '-3': | |
p = (p + 37) % 40 | |
else: | |
p = rooms.index(c) | |
return p | |
def visit(p:int) -> int: | |
'''특정 칸에 방문했을 때, 헤딩 칸에서의 액션을 수행한다. 리턴값은 액션 수행 후의 방의 위치''' | |
if rooms[p] == 'G2J': | |
p = 10 | |
elif rooms[p][:2] in ('CC', 'CH'): | |
p = flip_card(p, 0 if rooms[p][1] == 'C' else 1) | |
return p | |
def move(p:int, dd:int=0) -> (int, int): | |
'''현재위치, 누적더블수를 인자로 받고 주사위를 굴려 이동한 위치와 누적더블수를 리턴한다.''' | |
a, b = run_dice() | |
if a == b: | |
dd += 1 | |
if dd == 3: | |
return (10, 0) | |
else: | |
dd = 0 | |
p = visit((p + a + b) % 40) | |
return p, dd | |
for _ in range(M): | |
d = 0 | |
while True: | |
pos, d = move(pos, d) | |
result[pos] = result.get(pos, 0) + 1 | |
if d is 0: | |
break | |
return result | |
def main(face=6): | |
d = {} | |
for _ in range(1000): | |
xs = play(face) | |
for k, v in xs.items(): | |
d[k] = d.get(k, 0) + v | |
print('-' * 80) | |
s = sum(d.values()) | |
result = [x for x in sorted(d.items(), key=lambda x: x[1], reverse=True)[:3]] | |
print(''.join(str(k) for k, _ in result)) | |
main(4) | |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment