숫자로 이루어진 리스트 nums가 있다고 가정해 보겠습니다. 각 숫자를 이진수로 표현했을 때 나타나는 1의 개수를 기준으로 이 리스트를 오름차순으로 정렬해야 합니다. 만약 두 숫자의 1의 개수가 서로 같다면, 값 자체를 기준으로 정렬합니다.
예를 들어 입력이 nums = [4, 1, 12, 7, 6]이라면 출력은 [1, 4, 6, 12, 7]이 됩니다. 그 이유는 다음과 같습니다.
- 4의 이진수 표현: 0100
- 1의 이진수 표현: 0001
- 6의 이진수 표현: 0110
- 12의 이진수 표현: 1100
- 7의 이진수 표현: 0111
따라서 최종 정렬 결과는 [1, 4, 6, 12, 7]입니다. 1이 맨 앞에 오는 이유는 값이 더 작기 때문이며, 6 역시 같은 이유로 12보다 앞에 배치됩니다.
해결 방법
이 문제를 해결하기 위해 다음 단계를 따릅니다.
- 숫자 n을 입력받는 비교 함수(compare)를 정의합니다.
- 이 함수는 (n의 이진수에서 1의 개수, n의 값) 형태의 튜플을 반환합니다.
- 각 값을 비교 함수에 전달한 결과를 정렬 기준(key)으로 사용하여 nums를 정렬합니다.
- 정렬된 nums를 반환합니다.
예제 코드
다음 구현 예시를 통해 더 자세히 이해해 보겠습니다.
def solve(nums):
nums.sort(key=lambda num: (bin(num).count("1"), num))
return nums
nums = [4, 1, 12, 7, 6]
print(solve(nums))입력
[4, 1, 12, 7, 6]
출력
[1, 4, 6, 12, 7]
코드 설명
이 코드의 핵심은 bin() 함수와 sort() 메서드의 key 매개변수입니다. bin(num)은 숫자를 '0b100'과 같은 이진수 문자열로 변환하며, 여기에 .count("1")을 호출하면 해당 숫자의 이진 표현에 포함된 1의 개수를 손쉽게 셀 수 있습니다.
람다 함수가 (1의 개수, 원래 값) 형태의 튜플을 반환하기 때문에, Python의 정렬 알고리즘은 먼저 튜플의 첫 번째 요소인 1의 개수를 기준으로 비교하고, 개수가 동일한 경우에는 두 번째 요소인 실제 값을 기준으로 순서를 결정합니다. 이처럼 별도의 복잡한 로직 없이 람다 키 하나만으로 조건부 정렬을 깔끔하게 구현할 수 있습니다.