"""
基於分治的思想
1.選中陣列中間元素為分界點
2.遞迴排序分界點的左邊和右邊
3.歸併兩個有序的陣列,合二為一(難點)
歸併排序需要建立額外的陣列
"""def
merge_sort
(q, l, r)
:if l >= r:
return
mid =
(l + r)//2
# 這裡取陣列的中間元素作為分界點
merge_sort(q, l, mid)
# 歸併分界點左邊的元素
merge_sort(q, mid +
1, r)
# 歸併分界點右邊的元素
temp =
i = l
j = mid +
1while i <= mid and j <= r:
if q[i]
< q[j]:)
i +=
1else:)
j +=
1# 兩個陣列比較,可能會出現,乙個陣列的元素全部新增進temp陣列了,乙個沒有完全新增進去,將剩下的陣列中的元素全部新增進temp陣列
while i <= mid:
) i +=
1while j <= r:
) j +=
1# 將本次遞迴中temp陣列中的有序元素複製到原陣列相應的位置中
i = l # q的指標,從left開始
j =0# temp的指標,從0開始
while i <= r:
q[i]
= temp[j]
i +=
1 j +=
1def
main()
: n =
int(
input()
)# 輸入陣列長度
q =[int
(x)for x in
input()
.split()]
# 用生成式,將第二行的輸入轉成陣列,以空格為分隔符
merge_sort(q,
0, n -1)
for elem in q:
print
(elem, end=
' ')
if __name__ ==
'__main__'
: main(
)
"""
基於分治的思想
1.選中陣列中間元素為分界點
2.遞迴排序分界點的左邊和右邊
3.歸併兩個有序的陣列,合二為一(難點)
歸併排序需要建立額外的陣列
"""def
merge_sort
(q, l, r)
:if l >= r:
return
mid =
(l + r)//2
# 這裡取陣列的中間元素作為分界點
merge_sort(q, l, mid)
# 歸併分界點左邊的元素
merge_sort(q, mid +
1, r)
# 歸併分界點右邊的元素
i = l
j = mid +
1 cur =
0while i <= mid and j <= r:
if q[i]
< q[j]
: temp[cur]
= q[i]
i +=
1 cur +=
1else
: temp[cur]
= q[j]
j +=
1 cur +=
1# 兩個陣列比較,可能會出現,乙個陣列的元素全部新增進temp陣列了,乙個沒有完全新增進去,將剩下的陣列中的元素全部新增進temp陣列
while i <= mid:
temp[cur]
= q[i]
i +=
1 cur +=
1while j <= r:
temp[cur]
= q[j]
j +=
1 cur +=
1 i, j = l,
0while i <= r:
q[i]
= temp[j]
j +=
1 i +=
1if __name__ ==
'__main__'
: n =
int(
input()
)# 輸入陣列長度
temp =[0
]* n
q =[int
(x)for x in
input()
.split()]
# 用生成式,將第二行的輸入轉成陣列,以空格為分隔符
merge_sort(q,
0, n -1)
for elem in q:
print
(elem, end=
' ')
2021/1/20:
下面這種寫法省去了最後將ans陣列複製到原陣列中的步驟,直接將他返回就好了。區別就是,他在merge_sort的過程中,是將原陣列切片成許多個小陣列,然後用歸併的思想,每兩個,從前往後進行。至於和前面的區別(就是為啥可以直接返回),暫時還沒想透。先放這,等想透了在補上。
(已補,我覺得是對的
吧 心虛~~~)
# 2021/1/23更新
defmerge_sort
(q):
length =
len(q)
if length <=1:
return q
mid =
(length -1)
>>
1 ql = merge_sort(q[
:mid +1]
)# ql指左邊已經排序好的部分
qr = merge_sort(q[mid +1:
])# qr指右邊已經排序好的部分
# 定義乙個空列表存放待會比較後的資料 因為遞迴到最後 就是將原陣列分成兩部分進行比較 前面一部分排序好的 後面一部分排序好的
# 所以最後ans列表中最後存放的就是最終的資料 可以直接返回
ans =
i = j =
0while i <
len(ql)
and j <
len(qr)
:if ql[i]
<= qr[j]:)
i +=
1else:)
j +=
1if i <
len(ql)
: ans.extend(ql[i:])
if j <
len(qr)
: ans.extend(qr[j:])
return ans
if __name__ ==
'__main__'
: n =
int(
input()
) q =
list
(map
(int
,input()
.split())
)print
(' '
.join(
map(
str, merge_sort(q)))
)
2021/1/23:
今天重寫了一下歸併,發現不理解的基礎上強記的確不好受,在腦子裡微薄的「理解」基礎上寫了一遍後,報錯,用**對比工具一行行的對著,發現忽略了幾個小點,導致我寫的歸併是個錯誤弟弟。具體如下:
tip:暫時腦子裡就這麼多,以後有想到的糾錯的會繼續更。菜菜默淚,上圖。
演算法筆記 歸併排序02
步驟為 歸併排序是採用分治法的乙個非常典型的應用。歸併排序的思想就是先遞迴分解陣列,再合併陣列。將陣列分解最小之後,然後合併兩個有序陣列,基本思路是比較兩個陣列的最前面的數,誰小就先取誰,取了後相應的指標就往後移一位。然後再比較,直至乙個陣列為空,最後把另乙個陣列的剩餘部分複製過來即可。usr bi...
歸併排序(2 路歸併排序)
遞迴寫法 include define maxn 100 void merge int a,int l1,int r1,int l2,int r2 將陣列a的區間 l1,r1 和區間 l2,r2 合併為乙個有序區間 else while i r1 while j r2 for int i 0 i非遞...
python歸併排序 python 歸併排序
排序思路 1.將陣列分成兩組a,b,建立臨時陣列 c,c長度 a b 2.i,j分別屬於a,b 3.若a i b j 將b j 放入c,j 否則 a i 放入c,i 4.迴圈3步驟,將a或b中剩餘的元素放入c,再將c複製到陣列中 5.遞迴3 4直到a,b序列的長度 1 歸併排序 class merg...