티스토리 뷰
문제 출처 : algospot.com :: BOGGLE
algospot.com :: BOGGLE
보글 게임 문제 정보 문제 보글(Boggle) 게임은 그림 (a)와 같은 5x5 크기의 알파벳 격자인 게임판의 한 글자에서 시작해서 펜을 움직이면서 만나는 글자를 그 순서대로 나열하여 만들어지는 영어
algospot.com
1. 내가 생각한 풀이 방법
board = [['U', 'R', 'L', 'P', 'M'], ['X', 'P', 'R', 'E', 'T'], ['G', 'I', 'A', 'E', 'T'], ['X', 'T', 'N', 'Z', 'Y'], ['X', 'O', 'Q', 'R', 'S']]
visited = [[0] * 5 for _ in range(5)]
# 좌상, 상, 우상, 우, 우하, 하, 좌하, 좌
dr = [-1, -1, -1, 0, 1, 1, 1, 0]
dc = [-1, 0, 1, 1, 1, 0, -1, -1]
def hasWord(r, c, word):
if len(word) == 1:
return True
if board[r][c] == word[0]:
visited[r][c] = 1
for i in range(8):
nr = r + dr[i]
nc = c + dc[i]
if nr >= 0 and nr < 5 and nc >= 0 and nc < 5:
if board[nr][nc] == word[1] and visited[nr][nc] == 0:
return hasWord(nr, nc, word[1:])
else:
for i in range(8):
nr = r + dr[i]
nc = c + dc[i]
if nr >= 0 and nr < 5 and nc >= 0 and nc < 5:
return hasWord(nr, nc, word)
return False
print(hasWord(0, 0, 'PRETTY'))
2. 틀린 이유
(1) 기저 사례를 올바르게 정의하지 못함
- 나는 남은 단어의 길이가 1인 경우만 기저 사례로 생각했다.
(2) 재귀 호출의 각 단계에서 반환하는 방법을 잘 못 지정함
- 반드시 return으로 재귀 함수를 호출하는 방법만 있는 것이 아니다.
3. 해설 풀이 방법
def hasWord(r, c, word):
# 기저 사례 1: 시작 위치가 범위 밖이면 실패
if r < 0 or r >= 5 or c < 0 or c >= 5:
return False
# 기저 사례 2 : 첫 글자가 일치하지 않으면 실패
if board[r][c] != word[0]:
return False
# 기저 사례 3 : 남은 단어의 수가 1이면 성공
if len(word) == 1:
return True
# 인접한 8칸 검사
for i in range(8):
nr = r + dr[i]
nc = c + dc[i]
if nr >= 0 and nr < 5 and nc >= 0 and nc < 5:
if hasWord(nr, nc, word[1:]):
return True
return False
4. 해설
(1) 기저 사례는 총 3가지
- 첫 번째, 탐색 시작 위치가 2차원 리스트의 범위 밖이면 False 반환
- 두 번째, 단어의 첫 글자와 2차원 리스트에서 가리키는 첫 글자가 일치하지 않으면 False 반환
- 세 번째, 남은 단어의 수가 1인 경우 True 반환
(2) 2차원 리스트에서 특정 위치에서 인접한 8칸(좌상, 상, 우상, 우, 우하, 하, 좌하, 좌)을 검사
- 인접한 8개의 다른 단어들에 대해서 재귀적으로 함수 반복
- 재귀적으로 함수를 반복 할때는 단어에서 현재 인덱스의 글자를 제외한 다음 인덱스부터의 단어를 검사함
5. 내가 생각한 풀이와 다른 점
(1) 기저 사례
- 나는 기저 사례를 1가지만 생각했지만, 정답은 3개의 기저 사례를 염두해두고 있었다.
(2) 방문 여부 저장
- 나는 방문 여부를 저장하는 또 다른 2차원 리스트를 생성해서 탐색 했지만, 오히려 필요 없었고 옳은 방법도 아니었다.
6. 시간 복잡도 분석
- 단어의 길이가 N일 때, 탐색은 N-1번 진행한다.
- 각 칸에는 최대 8개의 인접한 알파벳이 존재한다.
- 따라서, 검사하는 후보의 수는 8^(N-1) 번
- Big-O 표기법에 따라, O(8^N)
7. 후기
아직 문제를 보고 직감으로 해결하려고 하거나 아무런 생각없이 한 줄 한 줄 적으며 그때 상황에 따라 문제를 해결하려는 경향이 많이 남아있음을 느꼈다. 책의 초장에 나와있는 단계들(문제를 정확히 이해하고, 계획을 세우고, 검증하고 코드를 작성하는 단계 등)을 몸에 익히는 연습이 더 필요함을 느낄 수 있었다.
특히, 문제를 대충 이해하고 넘어가거나 재귀 함수의 기저 사례를 너무 섣부르게 생각하고 결정하여 코드를 작성하다보니 결과적으로 문제를 푸는데 실패한 꼴을 보이고 말았다.
LeeSeok-Jun/Algorithmic_Problem_Soving_Strategies
프로그래밍 대회에서 배우는 알고리즘 문제해결 전략. Contribute to LeeSeok-Jun/Algorithmic_Problem_Soving_Strategies development by creating an account on GitHub.
github.com
'프로그래밍 대회에서 배우는 알고리즘 문제해결 전략 > 6장_무식하게 풀기' 카테고리의 다른 글
| 6.8 문제 : 시계 맞추기(Python) (0) | 2021.03.04 |
|---|---|
| 6.7 예제 : 최적화 문제 - 여행하는 외판원 문제(Python) (0) | 2021.03.04 |
| 6.5 문제 : 게임판 덮기(Python) (0) | 2021.03.04 |
| 6.3 문제 : 소풍(Python) (0) | 2021.02.25 |
- Total
- Today
- Yesterday
- 구현
- 프로그래밍 대회에서 배우는 알고리즘 문제 해결 전략
- 마르코프 연쇄
- 프로그래밍 대회에서 배우는 알고리즘 문제해결 전략
- 프로그래머스
- 난이도:중
- 파이썬
- 프로그래밍 대회에서 배우는 알고리즘 문제해결전략
- k번째 답 계산하기
- 탐욕법
- 비트 마스크
- 난이도:하
- 동적 계획법
- 카카오
- 종만북
- 그리디
- 난이도:상
- python
| 일 | 월 | 화 | 수 | 목 | 금 | 토 |
|---|---|---|---|---|---|---|
| 1 | 2 | 3 | 4 | 5 | 6 | |
| 7 | 8 | 9 | 10 | 11 | 12 | 13 |
| 14 | 15 | 16 | 17 | 18 | 19 | 20 |
| 21 | 22 | 23 | 24 | 25 | 26 | 27 |
| 28 | 29 | 30 | 31 |