[alghorithm] 페어 - 프로그래머스: 과일 장수
답:
def solution(k, m, score):
result = []
answer = 0
score = sorted(score,reverse=True)
for i in range(0,len(score),m):
if len(score[i:i+m]) == m : # i+m > len(score) 이렇게 비교하는 방법도 있음!
result.append(score[i:i+m])
for idx,value in enumerate(result):
answer += result[idx][-1] * m
return answer
# print(solution(3,4,[1, 2, 3, 1, 2, 3, 1])) # 8
# print(solution(4,3,[4, 1, 2, 2, 4, 4, 4, 4, 1, 2, 4, 2])) # 33
for 문에서 list길이가 짧은 것을 찾아내어 주는 다른 방법!
for i in range(0,len(score),m):
if i+m > len(score):
result.append(score[i:i+m])
#팀원의 풀이#
https://www.notion.so/4f3c4f74af6d4e6696680f15b0d12af6?pvs=4
문제 분석 및 해석
문제 :
https://school.programmers.co.kr/learn/courses/30/lessons/135808
""" 과일 장수
한상자에 m 개씩 담은 사과
k점이 최상품 1점이 최하품
score 를 받아서 그 안에서 가장 높은 점수를 얻을 수 있는 상자 만들기
가장 낮은 점수가 p점인 경우 한상자 가격 p*m
과일장수가 얻을 수 있는 최대 이익 return
상자 단위로만 판매, 남은 사과는 버림
"""
* 내가 생각한 풀이 :
한상자에 들어가야하는 사과개수 m
score 높은 점수부터 내림차순으로 정렬하고 list범위로 끊어주기
m 개수에 따라 묶기 => 상자개수
마지막 k값 확인 및 상자 개수만큼 곱하기 => 상자 개수만큼X 사과개수만큼O!!
* 찾아본 것:
list를 범위로 자르기! : range(0,len(score),m)
range() 함수 사용
앞의 값을 생략해도 0이 default로 설정되어 0~5의 숫자가 출력되며
자기 자신보다 1개 작은 숫자까지 출력한다.
for num in range(6):
print(num)
for num in range(0, 6):
print(num)
#결과: 0 1 2 3 4 5
임의로 범위 값을 변경할 수도 있다
for num in range(2, 6):
print(num)
# 2 3 4 5
for num in range(2, 10):
print(num)
# 2 3 4 5 6 7 8 9
range의 세번째 인자에 option을 추가할 수 있다.
2만큼씩 범위를 넘어가면서 range를 탐색하도록 함.
아래 예시. 범위를 조정하여 출력하기도 가능하다
for num in range(0,6,2):
print(num)
# 0 2 4
for num in range(3, 10, 2):
print(num)
# 3 5 7 9
for num in range(0,6,7):
print(num)
# 0 =>범위를 넘어가는 숫자를 설정하면 첫번째 값만 나온다
for num in range(10, 2):
print(num)
#미출력: 숫자 범위 첫,마지막 값을 함께 주어야함
** 주의:
# 이렇게는 출력 불가!
print(num for num in range(0, 6))
#<generator object <genexpr> at 0x104aa5890> 이런 결과가 나온다!
- 과정 -
생각한 풀이대로 쭉 코드를 작성해보았다
풀이하면서 부족한 부분을 중간 중간 수정하였다ㅠㅠ
1) score 내림차순 정렬하기
score = sorted(score,reverse=True)
2) list 상자에 들어가는 사과개수 =m 만큼씩 잘라서 각각 list 에 넣기
result = []
for i in range(0,len(score),m):
# m개씩 잘라서 넣기
result.append(score[i:i+m])
# [[3, 3, 2, 2], [1, 1, 1]]
이때 result 를 출력해보니, m 개가 아닌 것도 함께 들어간 리스트가 나왔다
그래서 자른 list의 길이가 m 과 같은 경우에만 result에 담아주도록 조건문을 추가
if len(score[i:i+m]) == m :
result.append(score[i:i+m])
3) 이차원 배열 result 에서 idx 값으로 상자 빼내기,
상자마다의 마지막값을 [-1]로 조회하여 사과 개수 만큼 곱해주기!
이 부분에서 실수가 있었는데,
지문을 읽으며 (사과 값 x 사과 개수 x 상자 개수) 를 더해야한다고 생각했다.
그래서 상자개수를 곱하였고.. 상자가 1개인 첫번째 예시 값에서는 정상적으로 8 이 출력되었지만
상자가 여러개인 두번째 예시에서 48이라는 값이 나옴..
for idx,value in enumerate(result):
answer += result[idx][-1] * m * len(result)
return answer
그래서 상자 값을 빼고 출력 = 12 (???)
for idx,value in enumerate(result):
answer += result[idx][-1] * m
return answer
아하
return이 반복문 안에 들어가있는 것을 확인하고 밖으로 빼내어 주었다.
for idx,value in enumerate(result):
answer += result[idx][-1] * m
return answer
감사한 피드백:)
score = sorted(score,reverse=True)
# sorted 복사해서 새로운 리스트를 만들어주는 것이므로 다른 변수에다가 저장을 했으면 좋았을 듯
# sort 원래의 리스트를 바로 정렬해줌 // 피드백
# 아래와 같이 변경했다
score.sort(reverse=True)
느낀점:
문제가 어렵고 복잡해지는 과정에서.. 자꾸 하나씩 빼먹거나 한끗이 부족해 풀이를 완성하지 못하는 일들이 생기고 있다ㅠㅠ
풀이를 하기 전에 생각하는 단계에서 주석을 정말정말 구체적으로 적는 습관을 차라리 들여보자!
이정도면 되겠지 하고 대충 쓰다보면 이렇게 빠지는 부분이 생기는 것 같다