[Python] 코딩 도장 - Primary Arithmetic
Updated:
코딩 도장 사이트의 문제를 직접 풀어본 내용을 정리하여 올립니다.
코딩 도장에서 여러 문제를 확인할 수 있습니다.
난이도 순으로 차근차근 풀어보려 합니다.
[문제: Primary Arithmetic] - Lv.2
첫 번째 계산
아이들은 여러 자리 숫자들을 더하기 위해서 우에서 좌로 숫자를 하나씩 차례대로 더 하라고 배웠다. 1을 한 숫자 위치에서 다음 자리로 더하기위해 이동하는 “한자리올림”연산을 많이 발견하는 것은 중요한 도전이 된다. 당신의 일은 교육자가 그들의 어려움을 평가하기 위하여, 덧셈 문제들의 각 집합에 대해서 한자리올림 연산들의 수를 계산하는 것이다.
입력
입력의 각 라인은 10개의 숫자들보다 미만인 양의 정수들 두 개를 포함한다. 입력의 마지막 라인은 0 0 을 포한한다.
출력
마지막을 제외한 입력의 각 라인에 대해서 당신은 두 숫자들을 더한 결과에서 한자리올림 연산들의 수를 아래 처럼 보여지는 형식으로 계산하여 출력해야 한다.
입력 샘플
123 456
555 555
123 594
0 0
출력 샘플
No carry operation.
3 carry operations.
1 carry operation.
출처: https://codingdojang.com/scode/397?answer_mode=hide
[풀이]
def PrimaryArithmetic():
x = input()
a = []
count = 0
while x != "0 0":
y = x.split()
y0_len = len(y[0])
y1_len = len(y[1])
min_len = min(y0_len, y1_len)
for i in range(0, min_len):
if int(y[0][y0_len - i - 1]) + int(y[1][y1_len - i - 1]) >= 10:
count += 1
if count == 1:
a.append(f"{count} carry operation")
elif count > 1:
a.append(f"{count} carry operations")
else:
a.append("No carry operations")
count = 0
x = input()
print("-"*30)
for i in a: print(i)
PrimaryArithmetic()
123 456
45 55
23 7
0 0
------------------------------
No carry operations
1 carry operation
1 carry operation
우선 while문으로 0 0 을 입력할 때 까지 반복하였고 각 자리별 숫자를 더하여 10이 넘으면 count하는 방식을 사용했다.
입력한 두 숫자의 자릿수가 다른 경우를 반영해두었다.
다만 현재 방법의 문제는 이전 자리에서 숫자가 올라왔을 때를 반영하지 못해 45 55를 입력하면 1이 반환된다.
[추천 풀이]
all((1,0))
False
from math import log10
a,b = map(int,input('? ').split())
while all((a,b)):
print( sum( [(lambda x : int((a%x+b%x)/x))(10**(n+1)) for n in range(int(max(log10(a),log10(b)))+1)] ) )
a,b = map(int,input('? ').split())
? 123 456
0
? 45 55
2
? 23 7
1
? 0 0
이 분은 아주 간결하게 푸셨는데 압축을 너무 해서 못 알아보겠어서 하나 하나 풀어 보려고 한다.
기존 풀이는 파이썬 2.x 버전이어서 3.x 버전에 맞게 조금 수정해두었다.
print(all((1,1)))
print(all((1,0)))
print(all((0,1)))
print(all((0,0)))
True
False
False
False
우선 all()
은 모두 0이 아닐 때 True를 반환하므로 위 문제에서는 0 0을 입력할 때 까지 while이 반복된다.
단점은 굳이 100 0 이런식으로 입력하면 당연히 False가 반환되어 작동되지 않는다.
a = 100 ; b = 30
range(int(max(log10(a),log10(b)))+1)
range(0, 3)
상용로그를 사용해서 두 숫자의 자릿수 중 큰 값을 추출하고 있다.
이 부분은 그냥 len()
으로 해둬도 될 것 같다.
a = 45 ; b = 55 ; n = 1
(lambda x : int((a%x+b%x)/x))(10**(n+1))
1
앞서 생성한 range()
에 따라 10의 배수로 각 숫자를 나눠 나머지를 더한 후 다시 10의 배수로 나눠준다.
위의 경우 45 55를 10으로 나눠 (4.5 + 5.5) / 10으로 1이 나타난다.
이런 방식이기에 나와는 달리 이전 자리에서 숫자가 올라왔을 때까지 반영 된다.
또한 두 숫자의 자릿수 중 큰 값으로 추출하였기에 서로 자릿수가 달라도 잘 반영된다.
코드도 코드지만 아이디어도 좋아보이고 잘 만든 코드인 것 같다.
(lambda x: 2*x)(10)
20
참고로 위 lambda식이 복잡해 보여서 간단하게 만들어두었다.
Leave a comment