proxsuite 0.7.2
The Advanced Proximal Optimization Toolbox
 
All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Pages
Loading...
Searching...
No Matches
core.hpp
Go to the documentation of this file.
1
2//
3// Copyright (c) 2022 INRIA
4//
5#ifndef PROXSUITE_LINALG_SPARSE_LDLT_CORE_HPP
6#define PROXSUITE_LINALG_SPARSE_LDLT_CORE_HPP
7
10#include <type_traits>
11#include <Eigen/SparseCore>
12
13#define SPARSE_LDLT_CONCEPT(...) \
14 VEG_CONCEPT_MACRO(::proxsuite::linalg::sparse::concepts, __VA_ARGS__)
15#define SPARSE_LDLT_CHECK_CONCEPT(...) \
16 VEG_CONCEPT_MACRO(::proxsuite::linalg::sparse::concepts, __VA_ARGS__)
17
18namespace proxsuite {
19namespace linalg {
20namespace sparse {
23
26
29
30using proxsuite::linalg::veg::mut;
32using proxsuite::linalg::veg::ref;
34
35inline namespace tags {
36using proxsuite::linalg::veg::Unsafe;
37using proxsuite::linalg::veg::unsafe;
38
39using proxsuite::linalg::veg::from_raw_parts;
40using proxsuite::linalg::veg::FromRawParts;
41VEG_TAG(from_eigen, FromEigen);
42} // namespace tags
43
44namespace concepts {
45} // namespace concepts
46
47namespace _detail {
48template<typename I, bool = sizeof(I) < sizeof(int)>
49struct WrappingPlusType;
50
51template<typename I>
52struct WrappingPlusType<I, true>
53{
54 using Promoted = unsigned;
55};
56template<typename I>
57struct WrappingPlusType<I, false>
58{
59 using Promoted = typename std::make_unsigned<I>::type;
60};
61} // namespace _detail
62namespace util {
63namespace nb {
65{
66 template<typename I>
67 auto operator()(I a, I b) const noexcept -> I
68 {
69 using U = typename _detail::WrappingPlusType<I>::Promoted;
70 return I(U(a) + U(b));
71 }
72};
74{
75 template<typename I>
76 auto operator()(I a, I b) const noexcept -> I
77 {
78 return (VEG_ASSERT(wrapping_plus{}(a, b) >= a), //
79 wrapping_plus{}(a, b));
80 }
81};
82
84{
85 template<typename I>
86 auto operator()(RefMut<I> a) const noexcept -> I
87 {
88 return a.get() = wrapping_plus{}(a.get(), I(1));
89 }
90};
92{
93 template<typename I>
94 auto operator()(RefMut<I> a) const noexcept -> I
95 {
96 return a.get() = wrapping_plus{}(a.get(), I(-1));
97 }
98};
100{
101 template<typename I>
102 auto operator()(I a) const noexcept -> usize
103 {
104 return usize(isize(typename std::make_signed<I>::type(a)));
105 }
106};
108{
109 template<typename I>
110 auto operator()(I a) const noexcept -> usize
111 {
112 return usize(typename std::make_unsigned<I>::type(a));
113 }
114};
115} // namespace nb
116VEG_NIEBLOID(wrapping_plus);
117VEG_NIEBLOID(checked_non_negative_plus);
118VEG_NIEBLOID(wrapping_inc);
119VEG_NIEBLOID(wrapping_dec);
120VEG_NIEBLOID(sign_extend);
121VEG_NIEBLOID(zero_extend);
122} // namespace util
123
124template<typename T>
126{
127 DenseVecRef() = default;
128 DenseVecRef(FromRawParts /*from_raw_parts*/,
129 T const* data,
130 isize len) noexcept
131 : _{ data, len }
132 {
133 }
134 template<typename V>
135 DenseVecRef(FromEigen /*from_eigen*/, V const& v) noexcept
136 : _{ v.data(), v.rows() }
137 {
138 static_assert(V::InnerStrideAtCompileTime == 1, ".");
139 static_assert(V::ColsAtCompileTime == 1, ".");
140 }
141
142 auto as_slice() const noexcept -> Slice<T>
143 {
144 return {
145 unsafe,
146 from_raw_parts,
147 _.ptr,
148 _.size,
149 };
150 }
151 auto nrows() const noexcept -> isize { return _.size; }
152 auto ncols() const noexcept -> isize { return 1; }
153
154 auto to_eigen() const noexcept -> Eigen::Map<Eigen::Matrix<T, -1, 1> const>
155 {
156 return { _.ptr, _.size };
157 }
158
159private:
160 struct
161 {
162 T const* ptr;
164 } _ = {};
165};
166
167template<typename T>
169{
170 DenseVecMut() = default;
171 DenseVecMut(FromRawParts /*from_raw_parts*/, T* data, isize len) noexcept
172 : _{ data, len }
173 {
174 }
175 template<typename V>
176 DenseVecMut(FromEigen /*from_eigen*/, V&& v) noexcept
177 : _{ v.data(), v.rows() }
178 {
179 static_assert(
182 ".");
183 }
184
185 auto as_slice() const noexcept -> Slice<T>
186 {
187 return {
188 unsafe,
189 from_raw_parts,
190 _.ptr,
191 _.size,
192 };
193 }
194 auto as_slice_mut() noexcept -> SliceMut<T>
195 {
196 return {
197 unsafe,
198 from_raw_parts,
199 _.ptr,
200 _.size,
201 };
202 }
203
204 auto as_const() const noexcept -> DenseVecRef<T>
205 {
206 return { from_raw_parts, _.ptr, _.size };
207 }
208 auto nrows() const noexcept -> isize { return _.size; }
209 auto ncols() const noexcept -> isize { return 1; }
210
211 auto to_eigen() const noexcept -> Eigen::Map<Eigen::Matrix<T, -1, 1>>
212 {
213 return { _.ptr, _.size };
214 }
215
216private:
217 struct
218 {
219 T* ptr;
221 } _ = {};
222};
223
224template<typename T, typename I = isize>
225struct VecRef
226{
228 FromRawParts /*from_raw_parts*/,
229 isize nrows,
230 isize nnz,
231 I const* row_indices,
232 T const* values)
233 : _{ nrows, nnz, row_indices, values }
234 {
235 }
236
237 auto nrows() const noexcept -> isize { return _.nrows; }
238 auto ncols() const noexcept -> isize { return 1; }
239 auto nnz() const noexcept -> isize { return _.nnz; }
240
241 auto row_indices() const noexcept -> I const* { return _.row; }
242 auto values() const noexcept -> T const* { return _.val; }
243
244private:
245 struct
246 {
249 I const* row;
250 T const* val;
251 } _;
252};
253
254namespace _detail {
255template<typename D, typename I>
257{
258private:
259 template<typename U = D>
260 auto _() const noexcept -> decltype((VEG_DECLVAL(U const&)._))
261 {
262 return static_cast<D const*>(this)->_;
263 }
264
265public:
266 auto nrows() const noexcept -> isize { return _().nrows; }
267 auto ncols() const noexcept -> isize { return _().ncols; }
268 auto nnz() const noexcept -> isize { return _().nnz; }
269
270 auto col_ptrs() const noexcept -> I const* { return _().col; }
271 auto nnz_per_col() const noexcept -> I const* { return _().nnz_per_col; }
272 auto is_compressed() const noexcept -> bool
273 {
274 return nnz_per_col() == nullptr;
275 }
276
277 auto row_indices() const noexcept -> I const* { return _().row; }
278
279 auto col_start(usize j) const noexcept -> usize
280 {
281 return VEG_ASSERT(j < usize(ncols())), util::zero_extend(_().col[j]);
282 }
283 auto col_start_unchecked(Unsafe /*unsafe*/, usize j) const noexcept -> usize
284 {
285 return VEG_DEBUG_ASSERT(j < usize(ncols())), util::zero_extend(_().col[j]);
286 }
287 auto col_end(usize j) const noexcept -> usize
288 {
289 return VEG_ASSERT(j < usize(ncols())), col_end_unchecked(unsafe, j);
290 }
291 auto col_end_unchecked(Unsafe /*unsafe*/, usize j) const noexcept -> usize
292 {
293 return VEG_DEBUG_ASSERT(j < usize(ncols())),
294 util::zero_extend(is_compressed()
295 ? _().col[j + 1]
296 : I(_().col[j] + _().nnz_per_col[j]));
297 }
298};
299template<typename D, typename I>
301{
302private:
303 template<typename U = D>
304 auto _() noexcept -> decltype((VEG_DECLVAL(U&)._))
305 {
306 return static_cast<D*>(this)->_;
307 }
308
309public:
310 auto col_ptrs_mut() noexcept -> I* { return _().col; }
311 auto nnz_per_col_mut() noexcept -> I* { return _().nnz_per_col; }
312 auto row_indices_mut() noexcept -> I* { return _().row; }
313};
314} // namespace _detail
315
316template<typename I = isize>
318{
320 SymbolicMatRef(FromRawParts /*from_raw_parts*/,
321 isize nrows,
322 isize ncols,
323 isize nnz,
324 I const* col_ptrs,
325 I const* nnz_per_col,
326 I const* row_indices)
327 : _{
329 }
330 {
331 }
332
333private:
334 struct
335 {
339 I const* col;
340 I const* nnz_per_col;
341 I const* row;
342 } _;
343};
344template<typename I = isize>
346{
349 SymbolicMatMut(FromRawParts /*from_raw_parts*/,
350 isize nrows,
351 isize ncols,
352 isize nnz,
353 I* col_ptrs,
354 I* nnz_per_col,
355 I* row_indices)
356 : _{
358 }
359 {
360 }
361
362 auto as_const() const noexcept -> SymbolicMatRef<I>
363 {
364 return {
365 from_raw_parts, this->nrows(), this->ncols(), this->nnz(),
366 this->col_ptrs(), this->nnz_per_col(), this->row_indices(),
367 };
368 }
369
370private:
371 struct
372 {
376 I* col;
378 I* row;
379 } _;
380};
381
382template<typename T, typename I = isize>
384{
386 MatRef(FromRawParts /*from_raw_parts*/,
387 isize nrows,
388 isize ncols,
389 isize nnz,
390 I const* col_ptrs,
391 I const* nnz_per_col,
392 I const* row_indices,
393 T const* values)
394 : _{
396 }
397 {
398 }
399
400 template<typename M>
401 MatRef(FromEigen /*from_eigen*/, M const& m)
402 : _{
403 m.rows(),
404 m.cols(),
405 m.nonZeros(),
406 m.outerIndexPtr(),
407 m.innerNonZeroPtr(),
408 m.innerIndexPtr(),
409 m.valuePtr(),
410 }
411 {
412 static_assert(!bool(M::IsRowMajor), ".");
413 }
414
415 auto values() const noexcept -> T const* { return _.val; }
416 auto symbolic() const noexcept -> SymbolicMatRef<I>
417 {
418 return {
419 from_raw_parts, this->nrows(), this->ncols(), this->nnz(),
420 this->col_ptrs(), this->nnz_per_col(), this->row_indices(),
421 };
422 }
423
424 auto to_eigen() const noexcept
425 -> Eigen::Map<Eigen::SparseMatrix<T, Eigen::ColMajor, I> const>
426 {
427 return { _.nrows, _.ncols, _.nnz, _.col, _.row, _.val, _.nnz_per_col };
428 }
429
430private:
431 struct
432 {
436 I const* col;
437 I const* nnz_per_col;
438 I const* row;
439 T const* val;
440 } _;
441};
442
443template<typename T, typename I = isize>
445{
448 MatMut(FromRawParts /*from_raw_parts*/,
449 isize nrows,
450 isize ncols,
451 isize nnz,
452 I* col_ptrs,
453 I* nnz_per_col,
454 I* row_indices,
455 T* values)
456 : _{
458 }
459 {
460 }
461
462 template<typename M>
463 MatMut(FromEigen /*from_eigen*/, M&& m)
464 : _{
465 m.rows(),
466 m.cols(),
467 m.nonZeros(),
468 m.outerIndexPtr(),
469 m.innerNonZeroPtr(),
470 m.innerIndexPtr(),
471 m.valuePtr(),
472 }
473 {
474 static_assert(!bool(proxsuite::linalg::veg::uncvref_t<M>::IsRowMajor), ".");
475 }
476
477 auto values() const noexcept -> T const* { return _.val; }
478 auto values_mut() const noexcept -> T* { return _.val; }
479 auto is_compressed() const noexcept -> bool
480 {
481 return _.nnz_per_col == nullptr;
482 }
483
484 auto as_const() const noexcept -> MatRef<T, I>
485 {
486 return {
487 from_raw_parts, this->nrows(), this->ncols(),
488 this->nnz(), this->col_ptrs(), this->nnz_per_col(),
489 this->row_indices(), this->values(),
490 };
491 }
492 auto symbolic() const noexcept -> SymbolicMatRef<I>
493 {
494 return {
495 from_raw_parts, this->nrows(), this->ncols(), this->nnz(),
496 this->col_ptrs(), this->nnz_per_col(), this->row_indices(),
497 };
498 }
499 auto symbolic_mut() const noexcept -> SymbolicMatRef<I>
500 {
501 return {
502 from_raw_parts, this->nrows(),
503 this->ncols(), this->nnz(),
504 this->col_ptrs_mut(), this->nnz_per_col_mut(),
505 this->row_indices_mut(),
506 };
507 }
508 auto to_eigen() const noexcept
509 -> Eigen::Map<Eigen::SparseMatrix<T, Eigen::ColMajor, I>>
510 {
511 return { _.nrows, _.ncols, _.nnz, _.col, _.row, _.val, _.nnz_per_col };
512 }
513 void _set_nnz(isize new_nnz) noexcept { _.nnz = new_nnz; }
514
515private:
516 struct
517 {
521 I* col;
523 I* row;
524 T* val;
525 } _;
526};
527} // namespace sparse
528} // namespace linalg
529} // namespace proxsuite
530
531#endif /* end of include guard PROXSUITE_LINALG_SPARSE_LDLT_CORE_HPP */
#define VEG_DEBUG_ASSERT(...)
Definition assert.hpp:38
#define VEG_ASSERT(...)
#define VEG_TAG(Name, Type)
Definition macros.hpp:550
#define VEG_NIEBLOID(Name)
Definition macros.hpp:545
#define VEG_DECLVAL(...)
Definition macros.hpp:131
typename _detail::_meta::uncvlref< T & >::type uncvref_t
Definition macros.hpp:887
decltype(sizeof(0)) usize
Definition macros.hpp:702
_detail::_meta::make_signed< usize >::Type isize
Definition typedefs.hpp:43
auto nrows() const noexcept -> isize
Definition core.hpp:208
auto as_const() const noexcept -> DenseVecRef< T >
Definition core.hpp:204
auto as_slice() const noexcept -> Slice< T >
Definition core.hpp:185
DenseVecMut(FromEigen, V &&v) noexcept
Definition core.hpp:176
auto ncols() const noexcept -> isize
Definition core.hpp:209
DenseVecMut(FromRawParts, T *data, isize len) noexcept
Definition core.hpp:171
auto to_eigen() const noexcept -> Eigen::Map< Eigen::Matrix< T, -1, 1 > >
Definition core.hpp:211
auto as_slice_mut() noexcept -> SliceMut< T >
Definition core.hpp:194
auto ncols() const noexcept -> isize
Definition core.hpp:152
DenseVecRef(FromEigen, V const &v) noexcept
Definition core.hpp:135
auto nrows() const noexcept -> isize
Definition core.hpp:151
DenseVecRef(FromRawParts, T const *data, isize len) noexcept
Definition core.hpp:128
auto to_eigen() const noexcept -> Eigen::Map< Eigen::Matrix< T, -1, 1 > const >
Definition core.hpp:154
auto as_slice() const noexcept -> Slice< T >
Definition core.hpp:142
void _set_nnz(isize new_nnz) noexcept
Definition core.hpp:513
auto is_compressed() const noexcept -> bool
Definition core.hpp:479
MatMut(FromRawParts, isize nrows, isize ncols, isize nnz, I *col_ptrs, I *nnz_per_col, I *row_indices, T *values)
Definition core.hpp:448
auto values() const noexcept -> T const *
Definition core.hpp:477
auto as_const() const noexcept -> MatRef< T, I >
Definition core.hpp:484
auto symbolic() const noexcept -> SymbolicMatRef< I >
Definition core.hpp:492
auto values_mut() const noexcept -> T *
Definition core.hpp:478
auto to_eigen() const noexcept -> Eigen::Map< Eigen::SparseMatrix< T, Eigen::ColMajor, I > >
Definition core.hpp:508
auto symbolic_mut() const noexcept -> SymbolicMatRef< I >
Definition core.hpp:499
auto symbolic() const noexcept -> SymbolicMatRef< I >
Definition core.hpp:416
MatRef(FromRawParts, isize nrows, isize ncols, isize nnz, I const *col_ptrs, I const *nnz_per_col, I const *row_indices, T const *values)
Definition core.hpp:386
auto to_eigen() const noexcept -> Eigen::Map< Eigen::SparseMatrix< T, Eigen::ColMajor, I > const >
Definition core.hpp:424
auto values() const noexcept -> T const *
Definition core.hpp:415
MatRef(FromEigen, M const &m)
Definition core.hpp:401
auto as_const() const noexcept -> SymbolicMatRef< I >
Definition core.hpp:362
SymbolicMatMut(FromRawParts, isize nrows, isize ncols, isize nnz, I *col_ptrs, I *nnz_per_col, I *row_indices)
Definition core.hpp:349
SymbolicMatRef(FromRawParts, isize nrows, isize ncols, isize nnz, I const *col_ptrs, I const *nnz_per_col, I const *row_indices)
Definition core.hpp:320
auto row_indices() const noexcept -> I const *
Definition core.hpp:241
VecRef(FromRawParts, isize nrows, isize nnz, I const *row_indices, T const *values)
Definition core.hpp:227
auto nnz() const noexcept -> isize
Definition core.hpp:239
auto values() const noexcept -> T const *
Definition core.hpp:242
auto nrows() const noexcept -> isize
Definition core.hpp:237
auto ncols() const noexcept -> isize
Definition core.hpp:238
auto col_start(usize j) const noexcept -> usize
Definition core.hpp:279
auto col_end(usize j) const noexcept -> usize
Definition core.hpp:287
auto col_ptrs() const noexcept -> I const *
Definition core.hpp:270
auto row_indices() const noexcept -> I const *
Definition core.hpp:277
auto col_end_unchecked(Unsafe, usize j) const noexcept -> usize
Definition core.hpp:291
auto nnz_per_col() const noexcept -> I const *
Definition core.hpp:271
auto col_start_unchecked(Unsafe, usize j) const noexcept -> usize
Definition core.hpp:283
auto operator()(I a) const noexcept -> usize
Definition core.hpp:102
auto operator()(RefMut< I > a) const noexcept -> I
Definition core.hpp:94
auto operator()(RefMut< I > a) const noexcept -> I
Definition core.hpp:86
auto operator()(I a, I b) const noexcept -> I
Definition core.hpp:67
auto operator()(I a) const noexcept -> usize
Definition core.hpp:110