1. 기둥과 보 설치
- 난이도
- 중하
- 풀이 시간
- 50분
- 시간 제한
- 5초
- 메모리 제한
- 128 MB
- 출처
A. 문제
- 중하
- 50분
- 5초
- 128 MB
위 프로그래머스 사이트에 접속하여 문제를 확인해주세요.
B. 내 답안
a. 1차 시도 (실패)
def solution(n, build_frame):
game_map = [[5] * (n + 1) for _ in range(n + 1)]
for bf in build_frame:
x, y, a, b = bf
y = n - y
# game_map[y][x]
if b == 1:
# 설치
if a == 0:
# 기둥
if y == 5 or game_map[y][x] == 0 or game_map[y][x] == 1:
game_map[y][x] = 0
game_map[y - 1][x] = 0
elif a == 1:
# 보
if game_map[y][x] == 0 or game_map[y][x] == 1 or game_map[y][x - 1] == 1:
game_map[y][x] = 1
game_map[y][x + 1] = 1
elif b == 0:
# 삭제
if a == 0:
# 기둥
if game_map[y-1][x] != 0 or game_map[y-1][x] != 1:
game_map[y][x] = 5
# game_map[y - 1][x] = 5
elif a == 1:
# 보
if game_map[y][x+1] == 0 or (game_map[y][x-1] != 1 and game_map[y][x+1] != 1):
game_map[y][x] = 5
# game_map[y][x + 1] = 5
print(*game_map, sep='\n')
print()
answer = []
for row in range(n+1):
for column in range(n+1):
if game_map[column][5-row] != 5:
# print(game_map[(n-row)][column])
answer.append([column, 5-row, game_map[column][5-row]])
print(answer)
return b
b. 2차 시도 (실패)
def check(answer):
for i in range(len(answer)):
x, y, a = answer[i]
if a == 0:
# 기둥
if 0 <= y or [x - 1, y, 1] in answer or [x, y, 1] in answer or [x, y - 1, 0] in answer:
return True
elif a == 1:
# 보
if [x, y - 1, 0] in answer or [x + 1, y - 1, 0] in answer or ([x - 1, y, 1] in answer and [x + 1, y, 1] in answer):
return True
return False
def solution(n, build_frame):
answer = []
for i in range(len(build_frame)):
x, y, a, b = build_frame[i]
if b == 0:
print(answer)
answer.remove([x, y, a])
if check(answer) == False:
answer.append([x, y, a])
elif b == 1:
print(answer)
answer.append([x, y, a])
if check(answer) == False:
answer.remove([x, y, a])
answer.sort()
return answer
c. 회고
내 풀이
- 문제에 나온 그림을 보고 좌표평면에 그리는 문제라고 생각하고서 좌표평면을 그렸다.
- 이 방법은 접근 자체가 잘못되었다.
![[Chap 12. 구현 - Q12. 기둥과 보 설치_잘못된 접근법.png]]
- 풀면서도 의문이 들었다. 이걸 좌표로 다시 표현할 수 있을까? 왜냐하면 그림으로 그리는 과정에서 불필요한 부분이 포함되었기 때문이다.
반성
- 잘못풀었다는 것을 인지하고도 떠오르는 방법이 없어서, 다른 방식으로 풀 생각을 하지 못했다.
결론
- 정말 많이 경험해봐야겠다. 그림이 있다고 전부 좌표에 점찍어서 푸는 문제가 아닌 것을 빨리 파악할 수 있는 경험을 쌓아야겠다.
C. 문제 해설
이해한 내용을 바탕으로 작성했습니다.
- 설치와 삭제를 구분하여 처리한다.
- 기둥과 보의 규칙에 따라 설치 유무를 결정한다.
- 기둥은 밑에서 위로 설치되고 보는 왼쪽에서 오른쪽 방향으로 설치된다.
- 기둥의 규칙 (OR)
- 바닥 위에 있어야 한다.
- y == 0
- 보의 한쪽 끝 부분 위에 있어야 한다.
- x-1, y, 1
- x, y, 1
- 다른 기둥 위에 있어야 한다.
- x, y-1, 0
- 보의 규칙 (OR)
- 한쪽 끝 부분이 기둥 위에 있어야 한다.
- x, y-1, 0
- x+1, y-1, 0
- 양쪽 끝 부분이 다른 보와 동시에 연결되어 있어야 한다.
- x-1, y, 1
- x+1, y, 1
- 기둥과 보를 막대기로 생각하지말고 점으로 생각해보자.
def solution(n, build_frame):
game_map = [[5] * (n + 1) for _ in range(n + 1)]
for bf in build_frame:
x, y, a, b = bf
y = n - y
# game_map[y][x]
if b == 1:
# 설치
if a == 0:
# 기둥
if y == 5 or game_map[y][x] == 0 or game_map[y][x] == 1:
game_map[y][x] = 0
game_map[y - 1][x] = 0
elif a == 1:
# 보
if game_map[y][x] == 0 or game_map[y][x] == 1 or game_map[y][x - 1] == 1:
game_map[y][x] = 1
game_map[y][x + 1] = 1
elif b == 0:
# 삭제
if a == 0:
# 기둥
if game_map[y-1][x] != 0 or game_map[y-1][x] != 1:
game_map[y][x] = 5
# game_map[y - 1][x] = 5
elif a == 1:
# 보
if game_map[y][x+1] == 0 or (game_map[y][x-1] != 1 and game_map[y][x+1] != 1):
game_map[y][x] = 5
# game_map[y][x + 1] = 5
print(*game_map, sep='\n')
print()
answer = []
for row in range(n+1):
for column in range(n+1):
if game_map[column][5-row] != 5:
# print(game_map[(n-row)][column])
answer.append([column, 5-row, game_map[column][5-row]])
print(answer)
return b
b. 2차 시도 (실패)
def check(answer):
for i in range(len(answer)):
x, y, a = answer[i]
if a == 0:
# 기둥
if 0 <= y or [x - 1, y, 1] in answer or [x, y, 1] in answer or [x, y - 1, 0] in answer:
return True
elif a == 1:
# 보
if [x, y - 1, 0] in answer or [x + 1, y - 1, 0] in answer or ([x - 1, y, 1] in answer and [x + 1, y, 1] in answer):
return True
return False
def solution(n, build_frame):
answer = []
for i in range(len(build_frame)):
x, y, a, b = build_frame[i]
if b == 0:
print(answer)
answer.remove([x, y, a])
if check(answer) == False:
answer.append([x, y, a])
elif b == 1:
print(answer)
answer.append([x, y, a])
if check(answer) == False:
answer.remove([x, y, a])
answer.sort()
return answer
c. 회고
내 풀이
- 문제에 나온 그림을 보고 좌표평면에 그리는 문제라고 생각하고서 좌표평면을 그렸다.
- 이 방법은 접근 자체가 잘못되었다.
![[Chap 12. 구현 - Q12. 기둥과 보 설치_잘못된 접근법.png]]
- 풀면서도 의문이 들었다. 이걸 좌표로 다시 표현할 수 있을까? 왜냐하면 그림으로 그리는 과정에서 불필요한 부분이 포함되었기 때문이다.
반성
- 잘못풀었다는 것을 인지하고도 떠오르는 방법이 없어서, 다른 방식으로 풀 생각을 하지 못했다.
결론
- 정말 많이 경험해봐야겠다. 그림이 있다고 전부 좌표에 점찍어서 푸는 문제가 아닌 것을 빨리 파악할 수 있는 경험을 쌓아야겠다.
C. 문제 해설
이해한 내용을 바탕으로 작성했습니다.
- 설치와 삭제를 구분하여 처리한다.
- 기둥과 보의 규칙에 따라 설치 유무를 결정한다.
- 기둥은 밑에서 위로 설치되고 보는 왼쪽에서 오른쪽 방향으로 설치된다.
- 기둥의 규칙 (OR)
- 바닥 위에 있어야 한다.
- y == 0
- 보의 한쪽 끝 부분 위에 있어야 한다.
- x-1, y, 1
- x, y, 1
- 다른 기둥 위에 있어야 한다.
- x, y-1, 0
- 보의 규칙 (OR)
- 한쪽 끝 부분이 기둥 위에 있어야 한다.
- x, y-1, 0
- x+1, y-1, 0
- 양쪽 끝 부분이 다른 보와 동시에 연결되어 있어야 한다.
- x-1, y, 1
- x+1, y, 1
- 기둥과 보를 막대기로 생각하지말고 점으로 생각해보자.
def check(answer):
for i in range(len(answer)):
x, y, a = answer[i]
if a == 0:
# 기둥
if 0 <= y or [x - 1, y, 1] in answer or [x, y, 1] in answer or [x, y - 1, 0] in answer:
return True
elif a == 1:
# 보
if [x, y - 1, 0] in answer or [x + 1, y - 1, 0] in answer or ([x - 1, y, 1] in answer and [x + 1, y, 1] in answer):
return True
return False
def solution(n, build_frame):
answer = []
for i in range(len(build_frame)):
x, y, a, b = build_frame[i]
if b == 0:
print(answer)
answer.remove([x, y, a])
if check(answer) == False:
answer.append([x, y, a])
elif b == 1:
print(answer)
answer.append([x, y, a])
if check(answer) == False:
answer.remove([x, y, a])
answer.sort()
return answer
내 풀이
- 문제에 나온 그림을 보고 좌표평면에 그리는 문제라고 생각하고서 좌표평면을 그렸다.
- 이 방법은 접근 자체가 잘못되었다. ![[Chap 12. 구현 - Q12. 기둥과 보 설치_잘못된 접근법.png]]
- 풀면서도 의문이 들었다. 이걸 좌표로 다시 표현할 수 있을까? 왜냐하면 그림으로 그리는 과정에서 불필요한 부분이 포함되었기 때문이다.
반성
- 잘못풀었다는 것을 인지하고도 떠오르는 방법이 없어서, 다른 방식으로 풀 생각을 하지 못했다.
결론
- 정말 많이 경험해봐야겠다. 그림이 있다고 전부 좌표에 점찍어서 푸는 문제가 아닌 것을 빨리 파악할 수 있는 경험을 쌓아야겠다.
C. 문제 해설
이해한 내용을 바탕으로 작성했습니다.
- 설치와 삭제를 구분하여 처리한다.
- 기둥과 보의 규칙에 따라 설치 유무를 결정한다.
- 기둥은 밑에서 위로 설치되고 보는 왼쪽에서 오른쪽 방향으로 설치된다.
- 기둥의 규칙 (OR)
- 바닥 위에 있어야 한다.
- y == 0
- 보의 한쪽 끝 부분 위에 있어야 한다.
- x-1, y, 1
- x, y, 1
- 다른 기둥 위에 있어야 한다.
- x, y-1, 0
- 보의 규칙 (OR)
- 한쪽 끝 부분이 기둥 위에 있어야 한다.
- x, y-1, 0
- x+1, y-1, 0
- 양쪽 끝 부분이 다른 보와 동시에 연결되어 있어야 한다.
- x-1, y, 1
- x+1, y, 1
- 기둥과 보를 막대기로 생각하지말고 점으로 생각해보자.
이해한 내용을 바탕으로 작성했습니다.
- 기둥은 밑에서 위로 설치되고 보는 왼쪽에서 오른쪽 방향으로 설치된다.
- 기둥의 규칙 (OR)
- 바닥 위에 있어야 한다.
- y == 0
- 보의 한쪽 끝 부분 위에 있어야 한다.
- x-1, y, 1
- x, y, 1
- 다른 기둥 위에 있어야 한다.
- x, y-1, 0
- 바닥 위에 있어야 한다.
- 보의 규칙 (OR)
- 한쪽 끝 부분이 기둥 위에 있어야 한다.
- x, y-1, 0
- x+1, y-1, 0
- 양쪽 끝 부분이 다른 보와 동시에 연결되어 있어야 한다.
- x-1, y, 1
- x+1, y, 1
- 한쪽 끝 부분이 기둥 위에 있어야 한다.
문제 지문에 정정이 필요한 구문이 있는 것 같다.
- 기둥은 바닥 위에 있거나 (X) => 기둥은 바닥에 있거나
- 바닥 위에 라고 해서 y >= 0 경우를 생각했다가 헤맸다.
a. 책 답안
python-for-coding-test/6.py at master · ndb796/python-for-coding-test (github.com)
참고문헌
[1] 나동빈, "이것이 취업을 위한 코딩 테스트다 with 파이썬", 초판, 2쇄, 한빛미디어, 2020년
[2] 코딩테스트 연습 - 기둥과 보 설치 | 프로그래머스 (programmers.co.kr). Programmers. (accessed Sep 16, 2021)
Ghost