Skip to content

Commit 6cda92f

Browse files
committed
Fixes + reduce std::vector usage for better target("avx2") support
1 parent 4266a29 commit 6cda92f

21 files changed

+96
-89
lines changed

cp-algo/geometry/closest_pair.hpp

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,14 +1,14 @@
11
#ifndef CP_ALGO_GEOMETRY_CLOSEST_PAIR_HPP
22
#define CP_ALGO_GEOMETRY_CLOSEST_PAIR_HPP
33
#include "../random/rng.hpp"
4+
#include "../util/big_alloc.hpp"
45
#include "point.hpp"
56
#include <vector>
67
#include <map>
78
namespace cp_algo::geometry {
89
// Rabin & Lipton
9-
template<typename ftype>
10-
auto closest_pair(std::vector<point_t<ftype>> const& r) {
11-
using point = point_t<ftype>;
10+
auto closest_pair(auto const& r) {
11+
using point = std::decay_t<decltype(r[0])>;
1212
size_t n = size(r);
1313
int64_t md = 1e18;
1414
for(size_t i = 0; i < n / 100; i++) {
@@ -21,7 +21,7 @@ namespace cp_algo::geometry {
2121
}
2222
}
2323
}
24-
std::map<point, std::vector<size_t>> neigs;
24+
std::map<point, big_vector<size_t>> neigs;
2525
md = (int64_t)ceil(sqrt((double)md));
2626
for(size_t i = 0; i < n; i++) {
2727
neigs[r[i] / md].push_back(i);

cp-algo/geometry/convex_hull.hpp

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,19 +1,19 @@
11
#ifndef CP_ALGO_GEOMETRY_CONVEX_HULL_HPP
22
#define CP_ALGO_GEOMETRY_CONVEX_HULL_HPP
33
#include "point.hpp"
4+
#include "../util/big_alloc.hpp"
45
#include <algorithm>
56
#include <utility>
67
#include <vector>
78
#include <ranges>
89
namespace cp_algo::geometry {
9-
template<typename ftype>
10-
std::vector<point_t<ftype>> convex_hull(std::vector<point_t<ftype>> r) {
11-
using point = point_t<ftype>;
10+
auto convex_hull(auto r) {
11+
using point = std::decay_t<decltype(r[0])>;
1212
std::ranges::sort(r);
1313
if(size(r) <= 1 || r[0] == r.back()) {
14-
return empty(r) ? r : std::vector{r[0]};
14+
return empty(r) ? big_vector<point>{} : big_vector{r[0]};
1515
}
16-
std::vector<point> hull = {r[0]};
16+
big_vector<point> hull = {r[0]};
1717
for(int half: {0, 1}) {
1818
size_t base = size(hull);
1919
for(auto it: std::views::drop(r, 1)) {

cp-algo/graph/euler.hpp

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
#ifndef CP_ALGO_GRAPH_EULER_HPP
22
#define CP_ALGO_GRAPH_EULER_HPP
33
#include "base.hpp"
4+
#include "../util/big_alloc.hpp"
45
#include <algorithm>
56
#include <iostream>
67
#include <optional>
@@ -10,7 +11,7 @@
1011
namespace cp_algo::graph {
1112
template<graph_type graph>
1213
std::optional<node_index> euler_start(graph const& g) {
13-
std::vector<int> deg(g.n());
14+
big_vector<int> deg(g.n());
1415
std::optional<node_index> default_start = 0;
1516
for(auto v: g.nodes()) {
1617
for(auto e: g.outgoing(v)) {
@@ -47,7 +48,7 @@ namespace cp_algo::graph {
4748
std::deque<edge_index> try_euler_trail(graph const& g, node_index v0) {
4849
std::deque<edge_index> trail;
4950
enum state { unvisited, visited };
50-
std::vector<state> state(g.m());
51+
big_vector<state> state(g.m());
5152
auto const& adj = g.incidence_lists();
5253
auto head = adj.head;
5354

cp-algo/graph/mst.hpp

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -6,12 +6,12 @@
66
#include <algorithm>
77
namespace cp_algo::graph {
88
template<weighted_undirected_graph_type graph>
9-
std::pair<int64_t, std::vector<edge_index>> mst(graph const& g) {
9+
std::pair<int64_t, big_vector<edge_index>> mst(graph const& g) {
1010
struct edge {
1111
edge_index idx;
1212
node_index v;
1313
};
14-
std::vector<edge> edges;
14+
big_vector<edge> edges;
1515
for(auto v: g.nodes()) {
1616
for(auto e: g.outgoing(v)) {
1717
if (v < g.edge(e).traverse(v)) {
@@ -24,7 +24,7 @@ namespace cp_algo::graph {
2424
});
2525
structures::dsu me(g.n());
2626
int64_t total = 0;
27-
std::vector<edge_index> mst;
27+
big_vector<edge_index> mst;
2828
for(auto [idx, v]: edges) {
2929
if(me.uni(v, g.edge(idx).traverse(v))) {
3030
total += g.edge(idx).w;

cp-algo/graph/shortest_path.hpp

Lines changed: 8 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -5,8 +5,8 @@
55
#include <queue>
66
namespace cp_algo::graph {
77
struct shortest_path_context {
8-
std::vector<int64_t> dist;
9-
std::vector<edge_index> pre;
8+
big_vector<int64_t> dist;
9+
big_vector<edge_index> pre;
1010
static constexpr int64_t inf = 1e18;
1111
shortest_path_context(int n)
1212
: dist(n, inf), pre(n) {}
@@ -42,7 +42,7 @@ namespace cp_algo::graph {
4242

4343
struct spfa_context: shortest_path_context {
4444
std::queue<node_index> que;
45-
std::vector<char> flags;
45+
big_vector<char> flags;
4646
static constexpr char in_queue = 1;
4747
static constexpr char invalidated = 2;
4848

@@ -73,7 +73,7 @@ namespace cp_algo::graph {
7373
edge_index e;
7474
node_index v;
7575
};
76-
std::vector<std::basic_string<traverse_edge>> dependents;
76+
big_vector<std::basic_string<traverse_edge>> dependents;
7777

7878
deep_spfa_context(int n) : spfa_context(n), dependents(n) {}
7979

@@ -85,7 +85,7 @@ namespace cp_algo::graph {
8585
}
8686

8787
void invalidate_subtree(node_index v) {
88-
std::vector<node_index> to_invalidate = {v};
88+
big_vector<node_index> to_invalidate = {v};
8989
while (!empty(to_invalidate)) {
9090
node_index u = to_invalidate.back();
9191
to_invalidate.pop_back();
@@ -144,8 +144,8 @@ namespace cp_algo::graph {
144144
return negative_edges ? deep_spfa(g, s) : dijkstra(g, s);
145145
}
146146

147-
std::vector<edge_index> recover_path(auto const& g, auto const& pre, node_index s, node_index t) {
148-
std::vector<edge_index> path;
147+
big_vector<edge_index> recover_path(auto const& g, auto const& pre, node_index s, node_index t) {
148+
big_vector<edge_index> path;
149149
node_index v = t;
150150
while(v != s) {
151151
path.push_back(pre[v]);
@@ -156,7 +156,7 @@ namespace cp_algo::graph {
156156
}
157157

158158
template<weighted_graph_type graph>
159-
std::optional<std::pair<int64_t, std::vector<edge_index>>> shortest_path(graph const& g, node_index s, node_index t) {
159+
std::optional<std::pair<int64_t, big_vector<edge_index>>> shortest_path(graph const& g, node_index s, node_index t) {
160160
auto [dist, pre] = single_source_shortest_path(g, s);
161161
if (dist[t] == shortest_path_context::inf) {
162162
return std::nullopt;

cp-algo/linalg/frobenius.hpp

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -16,8 +16,8 @@ namespace cp_algo::linalg {
1616
using polyn = math::poly_t<base>;
1717
assert(A.n() == A.m());
1818
size_t n = A.n();
19-
std::vector<polyn> charps;
20-
std::vector<vec_t> basis, basis_init;
19+
big_vector<polyn> charps;
20+
big_vector<vec_t> basis, basis_init;
2121
while(size(basis) < n) {
2222
size_t start = size(basis);
2323
auto generate_block = [&](auto x) {
@@ -78,7 +78,7 @@ namespace cp_algo::linalg {
7878
template<typename base>
7979
auto with_frobenius(matrix<base> const& A, auto &&callback) {
8080
auto [T, Tinv, charps] = frobenius_form<full>(A);
81-
std::vector<matrix<base>> blocks;
81+
big_vector<matrix<base>> blocks;
8282
for(auto charp: charps) {
8383
matrix<base> block(charp.deg());
8484
auto xk = callback(charp);

cp-algo/linalg/matrix.hpp

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -15,10 +15,10 @@ namespace cp_algo::linalg {
1515
math::modint_type<base_t>,
1616
modint_vec<base_t>,
1717
vec<base_t>>>
18-
struct matrix: std::vector<_vec_t> {
18+
struct matrix: big_vector<_vec_t> {
1919
using vec_t = _vec_t;
2020
using base = base_t;
21-
using Base = std::vector<vec_t>;
21+
using Base = big_vector<vec_t>;
2222
using Base::Base;
2323

2424
matrix(size_t n): Base(n, vec_t(n)) {}
@@ -90,7 +90,7 @@ namespace cp_algo::linalg {
9090
}
9191
}
9292

93-
static matrix block_diagonal(std::vector<matrix> const& blocks) {
93+
static matrix block_diagonal(big_vector<matrix> const& blocks) {
9494
size_t n = 0;
9595
for(auto &it: blocks) {
9696
assert(it.n() == it.m());
@@ -283,7 +283,7 @@ namespace cp_algo::linalg {
283283
// variables into pivots and free
284284
auto sort_classify(size_t lim) {
285285
size_t rk = 0;
286-
std::vector<size_t> free, pivots;
286+
big_vector<size_t> free, pivots;
287287
for(size_t j = 0; j < lim; j++) {
288288
for(size_t i = rk + 1; i < n() && row(rk)[j] == base(0); i++) {
289289
if(row(i)[j] != base(0)) {

cp-algo/math/combinatorics.hpp

Lines changed: 7 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1,14 +1,15 @@
11
#ifndef CP_ALGO_MATH_COMBINATORICS_HPP
22
#define CP_ALGO_MATH_COMBINATORICS_HPP
33
#include "../math/common.hpp"
4+
#include "../util/big_alloc.hpp"
45
#include <cassert>
56
#include <ranges>
67
namespace cp_algo::math {
78
// fact/rfact/small_inv are caching
89
// Beware of usage with dynamic mod
910
template<typename T>
1011
T fact(auto n) {
11-
static std::vector<T> F(maxn);
12+
static big_vector<T> F(maxn);
1213
static bool init = false;
1314
if(!init) {
1415
F[0] = T(1);
@@ -22,7 +23,7 @@ namespace cp_algo::math {
2223
// Only works for modint types
2324
template<typename T>
2425
T rfact(auto n) {
25-
static std::vector<T> F(maxn);
26+
static big_vector<T> F(maxn);
2627
static bool init = false;
2728
if(!init) {
2829
int t = (int)std::min<int64_t>(T::mod(), maxn) - 1;
@@ -36,8 +37,8 @@ namespace cp_algo::math {
3637
}
3738
template<typename T, int base>
3839
T pow_fixed(int n) {
39-
static std::vector<T> prec_low(1 << 16);
40-
static std::vector<T> prec_high(1 << 16);
40+
static big_vector<T> prec_low(1 << 16);
41+
static big_vector<T> prec_high(1 << 16);
4142
static bool init = false;
4243
if(!init) {
4344
init = true;
@@ -52,8 +53,8 @@ namespace cp_algo::math {
5253
return prec_low[n & 0xFFFF] * prec_high[n >> 16];
5354
}
5455
template<typename T>
55-
std::vector<T> bulk_invs(auto const& args) {
56-
std::vector<T> res(std::size(args), args[0]);
56+
big_vector<T> bulk_invs(auto const& args) {
57+
big_vector<T> res(std::size(args), args[0]);
5758
for(size_t i = 1; i < std::size(args); i++) {
5859
res[i] = res[i - 1] * args[i];
5960
}

cp-algo/math/cvector.hpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,7 @@ namespace cp_algo::math::fft {
2020
}
2121

2222
struct cvector {
23-
std::vector<vpoint, big_alloc<vpoint>> r;
23+
big_vector<vpoint> r;
2424
cvector(size_t n) {
2525
n = std::max(flen, std::bit_ceil(n));
2626
r.resize(n / flen);

cp-algo/math/factorials.hpp

Lines changed: 2 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,7 @@
99

1010
namespace cp_algo::math {
1111
template<bool use_bump_alloc = false, int maxn = -1>
12-
auto facts(auto const& args) {
12+
[[gnu::target("avx2")]] auto facts(auto const& args) {
1313
static_assert(!use_bump_alloc || maxn > 0, "maxn must be set if use_bump_alloc is true");
1414
constexpr int max_mod = 1'000'000'000;
1515
constexpr int accum = 4;
@@ -27,7 +27,7 @@ namespace cp_algo::math {
2727
constexpr int limit_reg = max_mod / 64;
2828
int limit_odd = 0;
2929

30-
std::vector<base, big_alloc<base>> res(size(args), 1);
30+
big_vector<base> res(size(args), 1);
3131
const int mod = base::mod();
3232
const int imod = -math::inv2(mod);
3333
for(auto [i, xy]: std::views::zip(args, res) | std::views::enumerate) {
@@ -56,13 +56,10 @@ namespace cp_algo::math {
5656
static std::array<u32x8, subblock> prods[accum];
5757
for(int z = 0; z < accum; z++) {
5858
for(int j = 0; j < simd_size; j++) {
59-
#pragma GCC diagnostic push
60-
#pragma GCC diagnostic ignored "-Wmaybe-uninitialized"
6159
cur[z][j] = uint32_t(b + z * block + j * subblock);
6260
cur[z][j] = proj(cur[z][j]);
6361
prods[z][0][j] = cur[z][j] + !cur[z][j];
6462
prods[z][0][j] = uint32_t(uint64_t(prods[z][0][j]) * bi2x32.getr() % mod);
65-
#pragma GCC diagnostic pop
6663
}
6764
}
6865
for(int i = 1; i < block / simd_size; i++) {

0 commit comments

Comments
 (0)