LCD 처럼 숫자를 표시하는 코드를 만들어 보자
크기와 출력할 숫자를 입력받는다. 크기는 LCD 표시 요소 하나의 크기를 가리킨다. (크기는 1~10, 숫자는 0~99,999,999) 가로선은 -, 세로선은 | 문자를 통해서 표현하며, 사이즈만큼 길이가 길어진다. 따라서 하나의 문자를 표시하기 위해서는 가로는 size + 2, 세로는 size * 2 + 3 만큼의 공간이 필요하다.
예시 – 출력: 0123456789. size: 3--- --- --- --- --- --- --- --- | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | --- --- --- --- --- --- --- | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | --- --- --- --- --- --- ---
접근
즉 0번 패널이 켜져야 하는 숫자는 아래 그림에서 알 수 있듯이, 0, 2, 3, 4, 6, 7, 8, 9 가 된다. 같은 방식으로 각 패널마다 어떤 숫자에 켜져야 할 것인지를 미리 정해두도록 하자.
이렇게 각 패널마다 켜져야 하는 숫자들을 정리하는 것은 생각보다 간단하다. 위 그림을 이용해서 쉽게 리스트를 완성할 수 있다.
masks = ("02356789", "045689", "01234789", "2345689", "02689", "013456789", "0235689")
이제 숫자를 출력할 차례이다. 우선 한개의 숫자를 출력하는 과정을 생각해보자. 숫자를 출력하는 과정은 가로선을 표현하는 구간 3군데와 세로선을 표현하는 구간 2군데로 나뉜다.
가로선 표현
패널 1개의 크기가 S인 숫자의 폭은 S + 2 (양쪽의 1씩 세로선이 표시되어야 하므로)이다. 따라서 가로선의 경우 표시하려는 숫자의 해당 가로 패널이 켜지는 경우에는 (공백) + (-) * S + (공백)을 출력하게 된다. 만약 패널이 꺼져 있는 경우에는 (-) 대신에 공백이 출력될 것이다. 따라서 맨 위에 가로선을 표시하는 것은 출력하려는 숫자 d 에 따라서 다음과 같은 문자열을 만들게 된다.
' ' + ('-' if d in masks[0] else ' ') * s + ' '
## "#---#" 또는 "#####"
세로선 표현
세로선을 표현할 때는 한 줄에 1번 2번 혹은 4번 5번 패널을 같이 판단해야 한다. 표시되는 문자의 상황은 가로선과 반대로 양끝에 패널이 있고 가운데는 크기 값 만큼의 공백이 들어온다. 따라서 사이즈 3일 때의 둘째줄은 다음과 같이 만들어진다.
('|' if d in masks[1] else ' ') + ' ' * s + ('|' if d in masks[2] else ' ')
그리고 이렇게 만들어지는 세로선은 사이즈 값만큼 반복하여 라인을 만들어야 한다. 사이즈 3인 경우에는 2,3,4 번 줄이 같은 내용을 반복 출력한다.
이후 가운데 가로선과, 다시 아래쪽 세로선, 마지막으로 바닥자리 가로선을 같은 식으로 표시한다.
정리
한 번에 한 글자에 대해서 한줄씩 문자열을 만드는 방법을 알아보았으니, 이번에는 여러 글자를 출력할 때 한줄은 어떻게 만드는지에 대해서 알아보자. 이미 모든 글자는 같은 규격으로 생성되며, 매번 줄을 만드는 방법을 알았다. 따라서 여러 글자의 경우에는 각 글자에서 해당줄의 문자열을 생성하고 공백으로 구분하여 하나로 합치면 된다. 이는 str.join()
을 이용하면 된다. 출력해야하는 숫자 문자열을 digits 라고 하면, 해당 코드는 리스트 축약을 통해서 손쉽게 표현할 수 있다.
## 가로줄
' '.join(
[(' ' + ('-' if d in mask[0] else ' ') * s + ' ') for d in digits]
}
## 세로줄
' '.join(
[('|' if d in mask[1] else ' ') + ' ' * s + ('|' if d in mask[2] else ' ')\
for d in digits]
)
이렇게 각 줄을 생성하여 리스트에 담고 개행문자를 끼워서 하나로 합치면 출력해야하는 최종 문자열이 완성된다. 이제 코드를 정리해보자.
def make_presentation(digits, s=1):
masks = ("02356789", "045689", "01234789",
"2345689", "02689", "013456789", "0235689")
result = []
## 윗줄
result.append(' '.join([' '+('-' if d in masks[0] else '-') * s + ' '\
for d in digits]))
## 위쪽 세로줄
for _ in range(s):
result.append(' '.join([ ('|' if d in masks[1] else ' ') + ' ' * s +\
('|' if d in masks[2] else ' ') + ' '\
for d in digits]))
## 가운데 가로줄
result.append(' '.join([' '+('-' if d in masks[3] else '-') * s + ' '\
for d in digits]))
## 위쪽 세로줄
for _ in range(s):
result.append(' '.join([ ('|' if d in masks[4] else ' ') + ' ' * s +\
('|' if d in masks[5] else ' ') + ' '\
for d in digits]))
## 바닥줄
result.append(' '.join([' '+('-' if d in masks[6] else '-') * s + ' '\
for d in digits]))
return '\n'.join(result)
def main():
digits, size = input().split()[:2]
size = int(size)
print(make_presentation(digits, size))
정리
중복되는 복잡한 코드가 너무 많아서 이를 별도의 람다식으로 빼내었다.