Divide and Conquer의 방식으로, recursive하게 두 개의 정렬된 리스트를 merge하여 정렬을 합니다.
Divide and Conquer란, 큰 문제를 작은 문제 단위로 분할하여 해결한 뒤, 해결한 작은 문제들을 다시 합쳐서 원래 문제를 해결하는 방식을 말한다.
"""
리스트를 반으로 나누어 각각을 merge sort한 뒤, 정렬된 각 부분 리스트를 다시 merge하는 함수
Args:
list: 정렬하고자 하는 전체 리스트
left: 현재 리스트의 가장 왼쪽 index
right: 현재 리스트의 가장 오른쪽 index
"""
def MSort(list, left, right):
if left < right:
mid = int((left + right) / 2)
MSort(list, left, mid)
MSort(list, mid+1, right)
Merge(list, left, mid, right)
"""
정렬된 두 리스트를 merge하는 함수
Args:
list: 정렬하고자 하는 전체 리스트
left: merge하고자 하는 리스트 중 왼쪽 리스트의 가장 왼쪽 index
right: merge하고자 하는 리스트 중 오른쪽 리스트의 가장 오른쪽 index
mid: merge하고자 하는 두 개의 리스트를 구분하는 가운데 index
"""
def Merge(list, left, mid, right):
left_list = list[left: mid+1] # 정렬할 리스트 중 왼쪽 리스트
right_list = list[mid+1: right+1] # 정렬할 리스트 중 오른쪽 리스트
sorted_list = [] # 두 리스트를 정렬한 결과를 담을 리스트
left_index = 0 # 현재 비교해야 하는 왼쪽 리스트 숫자의 index
right_index = 0 # 현재 비교해야 하는 오른쪽 리스트 숫자의 index
while(left_index < len(left_list) and right_index < len(right_list)):
if left_list[left_index] < right_list[right_index]:
sorted_list.append(left_list[left_index])
left_index += 1
else:
sorted_list.append(right_list[right_index])
right_index += 1
if left_index < len(left_list):
sorted_list += left_list[left_index:]
if right_index < len(right_list):
sorted_list.extend(right_list[right_index:])
list[left: right + 1] = sorted_list
def main():
# 아래의 리스트를 정렬
list = [21, 40, 1, 66, 12, 10, 3, 19]
MSort(list, 0, len(list) - 1)
# 출력 : [1, 3, 10, 12, 19, 21, 40, 66]
print(list)
main()
left
부터 mid
까지, 두 번째 리스트는 mid+1
부터 right
까지입니다. 🔔 두 리스트를 merge하기 위해서는 새로운 임의의 리스트(sorted_list
)가 하나 필요합니다.
sorted_list
에 추가합니다.sorted_list
에 추가합니다.
👇 정렬된 두 리스트를 merge하는 예시
sorted_list
와 같은 임시 리스트/배열이 필요합니다.