DUNE PDELab (unstable)

matrixindexset.hh
1// SPDX-FileCopyrightText: Copyright © DUNE Project contributors, see file LICENSE.md in module root
2// SPDX-License-Identifier: LicenseRef-GPL-2.0-only-with-DUNE-exception
3// -*- tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 2 -*-
4// vi: set et ts=4 sw=2 sts=2:
5#ifndef DUNE_ISTL_MATRIXINDEXSET_HH
6#define DUNE_ISTL_MATRIXINDEXSET_HH
7
8#include <algorithm>
9#include <cstddef>
10#include <cstdint>
11#include <set>
12#include <variant>
13#include <vector>
14
15#include <dune/common/overloadset.hh>
16
17namespace Dune {
18
19 namespace Impl {
20
40 class RowIndexSet {
41 using Index = std::uint_least32_t;
42 class Vector : public std::vector<Index> {
43 // store max size within class so that variant uses less memory
44 size_type maxVectorSize_;
45 friend class RowIndexSet;
46 };
47
49 static Index getMaxVectorSize(const RowIndexSet::Vector& v) {
50 return v.maxVectorSize_;
51 }
52
53 public:
54 using size_type = Index;
55
67 static constexpr size_type defaultMaxVectorSize = 2048;
68
75 RowIndexSet(size_type maxVectorSize = defaultMaxVectorSize) : storage_{Vector()}
76 {
77 std::get<Vector>(storage_).maxVectorSize_ = maxVectorSize;
78 }
79
88 void insert(size_type col){
89 std::visit(Dune::overload(
90 // If row is stored as set, call insert directly
91 [&](std::set<size_type>& set) {
92 set.insert(col);
93 },
94 // If row is stored as vector only insert directly
95 // if maxVectorSize_ is not reached. Otherwise switch
96 // to set storage first.
97 [&](Vector& sortedVector) {
98 auto it = std::lower_bound(sortedVector.cbegin(), sortedVector.cend(), col);
99 if (it == sortedVector.cend() or (*it != col)) {
100 if (sortedVector.size() < getMaxVectorSize(sortedVector)) {
101 sortedVector.insert(it, col);
102 } else {
103 std::set<size_type> set(sortedVector.cbegin(), sortedVector.cend());
104 set.insert(col);
105 storage_ = std::move(set);
106 }
107 }
108 }
109 ), storage_);
110 }
111
118 bool contains(const Index& col) const {
119 return std::visit(Dune::overload(
120 [&](const std::set<Index>& set) {
121 return set.contains(col);
122 },
123 [&](const std::vector<Index>& sortedVector) {
124 return std::binary_search(sortedVector.cbegin(), sortedVector.cend(), col);
125 }
126 ), storage_);
127 }
128
134 const auto& storage() const {
135 return storage_;
136 }
137
143 size_type size() const {
144 return std::visit([&](const auto& rowIndices) {
145 return rowIndices.size();
146 }, storage_);
147 }
148
152 void clear() {
153 std::visit([&](auto& rowIndices) {
154 rowIndices.clear();
155 }, storage_);
156 }
157
158 private:
159 std::variant<Vector, std::set<Index>> storage_;
160 };
161 }
162
163
181 {
182 public:
183 using size_type = typename Impl::RowIndexSet::size_type;
184
196 static constexpr size_type defaultMaxVectorSize = Impl::RowIndexSet::defaultMaxVectorSize;
197
203 MatrixIndexSet(size_type maxVectorSize=defaultMaxVectorSize) noexcept : rows_(0), cols_(0), maxVectorSize_(maxVectorSize)
204 {}
205
213 MatrixIndexSet(size_type rows, size_type cols, size_type maxVectorSize=defaultMaxVectorSize) : rows_(rows), cols_(cols), maxVectorSize_(maxVectorSize)
214 {
215 indices_.resize(rows_, Impl::RowIndexSet(maxVectorSize_));
216 }
217
219 void resize(size_type rows, size_type cols) {
220 rows_ = rows;
221 cols_ = cols;
222 indices_.resize(rows_, Impl::RowIndexSet(maxVectorSize_));
223 }
224
232 void add(size_type row, size_type col) {
233 indices_[row].insert(col);
234 }
235
237 size_type size() const {
238 size_type entries = 0;
239 for (size_type i=0; i<rows_; i++)
240 entries += rowsize(i);
241 return entries;
242 }
243
245 size_type rows() const {return rows_;}
246
248 size_type cols() const {return cols_;}
249
259 const auto& columnIndices(size_type row) const {
260 return indices_[row].storage();
261 }
262
264 size_type rowsize(size_type row) const {
265 return indices_[row].size();
266 }
267
274 template <class MatrixType>
275 void import(const MatrixType& m, size_type rowOffset=0, size_type colOffset=0) {
276
277 typedef typename MatrixType::row_type RowType;
278 typedef typename RowType::ConstIterator ColumnIterator;
279
280 for (size_type rowIdx=0; rowIdx<m.N(); rowIdx++) {
281
282 const RowType& row = m[rowIdx];
283
284 ColumnIterator cIt = row.begin();
285 ColumnIterator cEndIt = row.end();
286
287 for(; cIt!=cEndIt; ++cIt)
288 add(rowIdx+rowOffset, cIt.index()+colOffset);
289
290 }
291
292 }
293
299 template <class MatrixType>
300 void exportIdx(MatrixType& matrix) const {
301
302 matrix.setSize(rows_, cols_);
303 matrix.setBuildMode(MatrixType::random);
304
305 for (size_type row=0; row<rows_; row++)
306 matrix.setrowsize(row, rowsize(row));
307
308 matrix.endrowsizes();
309
310 for (size_type row=0; row<rows_; row++) {
311 std::visit([&](const auto& rowIndices) {
312 matrix.setIndicesNoSort(row, rowIndices.begin(), rowIndices.end());
313 }, indices_[row].storage());
314 }
315
316 matrix.endindices();
317
318 }
319
320 private:
321
322 std::vector<Impl::RowIndexSet> indices_;
323
324 size_type rows_, cols_;
325 size_type maxVectorSize_;
326
327 };
328
329
330} // end namespace Dune
331
332#endif
Stores the nonzero entries for creating a sparse matrix.
Definition: matrixindexset.hh:181
void resize(size_type rows, size_type cols)
Reset the size of an index set.
Definition: matrixindexset.hh:219
static constexpr size_type defaultMaxVectorSize
Default value for maxVectorSize.
Definition: matrixindexset.hh:196
size_type rows() const
Return the number of rows.
Definition: matrixindexset.hh:245
void exportIdx(MatrixType &matrix) const
Initializes a BCRSMatrix with the indices contained in this MatrixIndexSet.
Definition: matrixindexset.hh:300
void add(size_type row, size_type col)
Add an index to the index set.
Definition: matrixindexset.hh:232
MatrixIndexSet(size_type rows, size_type cols, size_type maxVectorSize=defaultMaxVectorSize)
Constructor setting the matrix size.
Definition: matrixindexset.hh:213
MatrixIndexSet(size_type maxVectorSize=defaultMaxVectorSize) noexcept
Constructor with custom maxVectorSize.
Definition: matrixindexset.hh:203
const auto & columnIndices(size_type row) const
Return column indices of entries in given row.
Definition: matrixindexset.hh:259
size_type rowsize(size_type row) const
Return the number of entries in a given row.
Definition: matrixindexset.hh:264
size_type size() const
Return the number of entries.
Definition: matrixindexset.hh:237
size_type cols() const
Return the number of columns.
Definition: matrixindexset.hh:248
auto overload(F &&... f)
Create an overload set.
Definition: overloadset.hh:61
Dune namespace.
Definition: alignedallocator.hh:13
constexpr std::integral_constant< std::size_t, sizeof...(II)> size(std::integer_sequence< T, II... >)
Return the size of the sequence.
Definition: integersequence.hh:75
constexpr std::bool_constant<((II==value)||...)> contains(std::integer_sequence< T, II... >, std::integral_constant< T, value >)
Checks whether or not a given sequence contains a value.
Definition: integersequence.hh:137
Creative Commons License   |  Legal Statements / Impressum  |  Hosted by TU Dresden & Uni Heidelberg  |  generated with Hugo v0.111.3 (Sep 3, 22:42, 2025)