感謝網友淺水清流投遞本稿。
併發演算法是多核時代開始流行的技術趨勢,比如tbb,ppl都提供了大量有用的併發演算法。
經典演算法中,排序是乙個很適合採用分治法併發的場合,比如快速排序。
常規的快速排序,先在陣列中選取乙個基準點,將陣列分割槽為小於基準點和大於基準點(相同的數可以到任一邊),對分割槽的子陣列遞迴的執行分割槽的操作,當子陣列長度為1時退出遞迴。此時陣列就完成了排序過程。
01
int
partition(
int
* array,
int
left,
int
right)
02
11
swap(array[right], array[index]);
12
return
index;
13
}
14
15
void
qsort
(
int
* array,
int
left,
int
right)
16
對快排的過程分析可以發現,分割槽以及對子陣列排序的過程均可以併發執行,這裡首先對陣列進行分割槽,生成分割槽陣列,為了保證不同分割槽不受到影響需要先完成分割槽再進行排序。
01
template
<
typename
key,
typename
container >
void
parallel_sort(container & _container)
template
<
typename
key,
typename
container >
02
void
partition_less(std::vector* vless, container * _container, key privot)
07
}
08
}
09
10
template
<
typename
key,
typename
container >
11
void
partition_more(std::vector* vmore, container * _container, key privot)
16
}
17
}
在完成分割槽之後,遞迴執行排序操作,並將排序好的分割槽重新寫入待排序陣列。
01
template
<
typename
key,
typename
container >
02
int
sort_less(container * _container, std::vector& vless, boost::atomic_uint32_t * depth)
08
09
return
0;
10
}
11
12
template
<
typename
key,
typename
container >
13
int
sort_more(container * _container, std::vector& vmore, boost::atomic_uint32_t * depth)
20
21
return
0;
22
}
23
24
template
<
typename
key,
typename
container >
25
void
parallel_sort_impl(container * _container, boost::atomic_uint32_t & depth)
else
40
}
這裡採取了乙個有趣的策略,就是通過陣列的大小,計算出排序好的元素在原陣列中的位置(這樣即使是併發的訪問陣列,但是因為不同的執行緒各自訪問的自己的下標位置,所以仍然是執行緒安全的),然後將排序好的陣列直接寫入到原陣列,完成整個排序。
這裡的併發採用了c++11中的promise:
並行快速排序
感謝淺水清流投遞本稿。併發演算法是多核時代開始流行的技術趨勢,比如tbb,ppl都提供了大量有用的併發演算法。經典演算法中,排序是乙個很適合採用分治法併發的場合,比如快速排序。常規的快速排序,先在陣列中選取乙個基準點,將陣列分割槽為小於基準點和大於基準點 相同的數可以到任一邊 對分割槽的子陣列遞迴的...
erlang 實現並行快速排序
在保證尾遞迴的情況下,使用乙個輔助函式 handl 對parallel qsort進行包裝,則parallel qsort只管 分發任務即可,計算好了 再進行樹形通訊合併,之前一直在糾 結於是不是要使用程序字典,來儲存有哪些程序,程序字典,在erlang program一書中,不建議採用,因為其提供...
用Parallel For進行並行快速排序
用parallel for 進行並行快速排序 注 本文主要內容摘自筆者所著的 多核計算與程式設計 一書,略有修改,後續還會繼續發布系列文章,如有需要,可以考慮將一下位址加入到您的瀏覽器收藏夾中 http software.intel.com zh cn blogs category multicor...