Skip to content

Commit 52d8541

Browse files
committed
Add count/radix sort
1 parent d1e06c4 commit 52d8541

File tree

2 files changed

+36
-2
lines changed

2 files changed

+36
-2
lines changed

cp-algo/util/compress_coords.hpp

+2-2
Original file line numberDiff line numberDiff line change
@@ -1,13 +1,13 @@
11
#ifndef CP_ALGO_UTIL_COMPRESS_COORDS_HPP
22
#define CP_ALGO_UTIL_COMPRESS_COORDS_HPP
3-
#include <algorithm>
3+
#include "sort.hpp"
44
#include <vector>
55
namespace cp_algo {
66
// coords is a range of reference_wrapper<T>
77
auto compress_coords(auto &coords) {
88
std::vector<int> original;
99
original.reserve(size(coords));
10-
std::ranges::sort(coords);
10+
radix_sort(coords);
1111
int idx = -1, prev = -1;
1212
for(auto &x: coords) {
1313
if(x != prev) {

cp-algo/util/sort.hpp

+34
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,34 @@
1+
#ifndef CP_ALGO_UTIL_SORT_HPP
2+
#define CP_ALGO_UTIL_SORT_HPP
3+
#include <algorithm>
4+
#include <numeric>
5+
#include <ranges>
6+
#include <vector>
7+
namespace cp_algo {
8+
void count_sort(auto &a, size_t maxc, auto &&proj = std::identity{}) {
9+
std::vector<int> cnt(maxc);
10+
for(auto &x: a) {
11+
cnt[proj(x)]++;
12+
}
13+
std::partial_sum(begin(cnt), end(cnt), begin(cnt));
14+
auto res = a;
15+
for(auto const& it: a | std::views::reverse) {
16+
res[--cnt[proj(it)]] = it;
17+
}
18+
a = std::move(res);
19+
}
20+
21+
void radix_sort(auto &a) {
22+
if(empty(a)) {
23+
return;
24+
}
25+
int base = std::bit_floor(size(a));
26+
auto mx = std::ranges::max(a);
27+
for(int64_t i = 1; i <= mx; i *= base) {
28+
count_sort(a, base, [&](auto x) {
29+
return x / i % base;
30+
});
31+
}
32+
}
33+
}
34+
#endif // CP_ALGO_UTIL_SORT_HPP

0 commit comments

Comments
 (0)