8#pragma message("warning: Task-based OpenMP parallelism is not well supported on windows.")
9#pragma message("warning: Thus, OpenMP-based downsampling is only partially parallelized on windows.")
12namespace gtsam_points {
18template <
typename RandomAccessIterator,
typename Compare>
19void quick_sort_omp_impl(RandomAccessIterator first, RandomAccessIterator last,
const Compare& comp) {
20 const std::ptrdiff_t n = std::distance(first, last);
22 std::sort(first, last, comp);
26 const auto median3 = [&](
const auto& a,
const auto& b,
const auto& c,
const Compare& comp) {
27 return comp(a, b) ? (comp(b, c) ? b : (comp(a, c) ? c : a)) : (comp(a, c) ? a : (comp(b, c) ? c : b));
30 const int offset = n / 8;
31 const auto m1 = median3(*first, *(first + offset), *(first + offset * 2), comp);
32 const auto m2 = median3(*(first + offset * 3), *(first + offset * 4), *(first + offset * 5), comp);
33 const auto m3 = median3(*(first + offset * 6), *(first + offset * 7), *(last - 1), comp);
35 auto pivot = median3(m1, m2, m3, comp);
36 auto middle1 = std::partition(first, last, [&](
const auto& val) {
return comp(val, pivot); });
37 auto middle2 = std::partition(middle1, last, [&](
const auto& val) {
return !comp(pivot, val); });
40 quick_sort_omp_impl(first, middle1, comp);
43 quick_sort_omp_impl(middle2, last, comp);
51template <
typename RandomAccessIterator,
typename Compare>
52void quick_sort_omp(RandomAccessIterator first, RandomAccessIterator last,
const Compare& comp,
int num_threads) {
54#pragma omp parallel num_threads(num_threads)
56#pragma omp single nowait
57 { quick_sort_omp_impl(first, last, comp); }
60 std::sort(first, last, comp);