https://www.acmicpc.net/problem/4344
import sys
ssr = sys.stdin.readline
c = int(ssr())
for _ in range(c):
n_s = list(map(int, ssr().split()))
m = sum(n_s[1:])/n_s[0]
cnt = 0
for i in range(n_s[0]):
if n_s[i+1] > m:
cnt += 1
ans = cnt/n_s[0]*100*1000
if ans - int(ans) < 0.5:
ans = int(ans)
else:
ans = int(ans) + 1
print(f'{str(ans)[:-3]}.{str(ans)[-3:]}%')
최근에 재채점되는 문제들이 많네요. 딱히 어려운 문제가 아니었는데 틀렸다고 하길래 아 예전에 풀어서 round로 반올림 에러 나나보다 하고 그냥 코드를 새로 작성했습니다. 근데 코드를 다 짜고나서 보니 예전에 짰던 코드에 문제가 없어 보이는데 왜 틀렸다고 하는거지 싶어서 틀렸다는 코드를 그대로 복사 붙여넣기 했더니 다시 맞다고 해주네요... 뭔가 시스템 상에 문제가 있던가 아니면 모두를 오답처리 해버린게 아닌가 하는 의심이 듭니다. 그래도 이왕 짠 코드니까 간단하게 설명을 드리고 넘어가볼까 합니다.
평균을 구하고 평균을 넘는 학생들의 숫자를 구하는 것 까지는 대부분 비슷할 것 같은데 학생의 비율을 계산하는 부분에서 조금 고민을 하게 되는 문제라고 생각합니다. 그냥 반올림을 해버리면 소수점 아래 3자리까지 출력을 못시키는 경우가 생기니까 이 부분을 해결하는게 이 문제의 주안점이 되겠죠. 제가 새로 사용했던 방법은 예전에 친구와 함께 고민해서 알게 된 방법으로 필요한 자리수 만큼 더 큰 수를 만들고 중간에 문자열 '.'을 삽입하는 방법이었습니다. 예를 들어 예제 1의 첫번째 입력의 경우 답이 40.000%인데 그냥 계산하고 출력하면 40.0%가 나오니 차라리 1000을 곱해서 40000을 만들고 40뒤에 점을 찍어서 40.000%로 출력하도록 하는 방식이죠. 그리고 round를 썼을 때 생기는 문제(반올림 하는 자리의 숫자가 5일 경우 가까운 짝수로 반올림 함. 예) round(2.5) = 2, round(3.5) = 4) 때문에 굳이 비교 연산을 하는 과정도 추가되었구요. 참신하기는 하지만 효율적으로 보이지는 않습니다.
하지만 기존에 짰던 코드가 훨씬 합리적인 것 같습니다. 문자열 포맷팅을 사용하는 것인데요.
거의 1년 전에 짰던 코드라 변수명이 다릅니다만 print문을 읽어보면 f-string법을 이용해서 단순하게 해결한 것을 볼 수 있습니다. f'{변수이름:.원하는자리수f}'로 하면 round의 규칙이 아닌 우리가 일반적으로 아는 사사오입의 반올림이 이뤄집니다. 위에서 작성한 코드보다 출력을 위한 노동이 훨씬 덜 드는 거죠.
괜히 새로 짜느라 헛고생을 한 것 같기도 하지만 예전에 친구랑 나눴던 얘기도 떠오르고 나쁘지 않았습니다.
수정// 문자열 포맷팅을 이용하여도 파이썬의 반올림 규칙인 오사오입을 따릅니다. 파이썬은 자체적으로 사사오입을 할 수 있는 방법은 없고 계산 결과에 영향이 가지 않는 만큼의 작은 수를 더해서 우리가 원하는 방향으로 반올림을 할 수 있도록 하는 테크닉을 사용해야 합니다. 혹시 기존의 포스팅을 보셨다 혼동이 오셨을 분들에게 사과드리겠습니다.
ex)
round(2.5)
>> 2
round(2.5 + 0.000000001)
>> 3
'Problem Solving > BOJ' 카테고리의 다른 글
[BOJ][Python]1021 풀이 (0) | 2023.07.01 |
---|---|
[BOJ][Python]1004 풀이 (0) | 2023.06.29 |
[BOJ][Python]1015 풀이 (0) | 2023.06.27 |
[BOJ][Python]1094 풀이 (0) | 2023.06.26 |