Dune Core Modules (2.7.0)

colcompmatrix.hh
1// -*- tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 2 -*-
2// vi: set et ts=4 sw=2 sts=2:
3#ifndef DUNE_ISTL_COLCOMPMATRIX_HH
4#define DUNE_ISTL_COLCOMPMATRIX_HH
5#include "bcrsmatrix.hh"
6#include "bvector.hh"
10#include <dune/common/unused.hh>
12#include <limits>
13
14namespace Dune
15{
21 template<class M>
23 {
24 public:
26 typedef M Matrix;
29
35 : m_(m)
36 {}
37
40 {
41 return m_.begin();
42 }
45 {
46 return m_.end();
47 }
48 private:
49 const Matrix& m_;
50 };
51
59 template<class M, class S>
61 {
62 public:
64 typedef M Matrix;
66 typedef S RowIndexSet;
67
74 : m_(m), s_(s)
75 {}
76
77 const Matrix& matrix() const
78 {
79 return m_;
80 }
81
82 const RowIndexSet& rowIndexSet() const
83 {
84 return s_;
85 }
86
89 : public ForwardIteratorFacade<const_iterator, const typename Matrix::row_type>
90 {
91 public:
92 const_iterator(typename Matrix::const_iterator firstRow,
93 typename RowIndexSet::const_iterator pos)
94 : firstRow_(firstRow), pos_(pos)
95 {}
96
97
98 const typename Matrix::row_type& dereference() const
99 {
100 return *(firstRow_+ *pos_);
101 }
102 bool equals(const const_iterator& o) const
103 {
104 return pos_==o.pos_;
105 }
106 void increment()
107 {
108 ++pos_;
109 }
110 typename RowIndexSet::value_type index() const
111 {
112 return *pos_;
113 }
114
115 private:
117 typename Matrix::const_iterator firstRow_;
119 typename RowIndexSet::const_iterator pos_;
120 };
121
124 {
125 return const_iterator(m_.begin(), s_.begin());
126 }
129 {
130 return const_iterator(m_.begin(), s_.end());
131 }
132
133 private:
135 const Matrix& m_;
137 const RowIndexSet& s_;
138 };
139
146 template<class M, class I = int>
147 class ColCompMatrixInitializer;
148
149 template<class M, class X, class TM, class TD, class T1>
150 class SeqOverlappingSchwarz;
151
152 template<class T, bool flag>
153 struct SeqOverlappingSchwarzAssemblerHelper;
154
160 template<class Mat, class I = int>
162 {
163 friend class ColCompMatrixInitializer<Mat, I>;
164
165 using B = typename Mat::field_type;
166
167 public:
169 using Matrix = Mat;
170
171 friend struct SeqOverlappingSchwarzAssemblerHelper<ColCompMatrix<Matrix>, true>;
172
173 typedef typename Matrix::size_type size_type;
174
175 using Index = I;
176
181 explicit ColCompMatrix(const Matrix& mat);
182
184
186 virtual ~ColCompMatrix();
187
192 size_type N() const
193 {
194 return N_;
195 }
196
197 size_type nnz() const
198 {
199 // TODO: The following code assumes that the blocks are dense
200 // and that they all have the same dimensions.
201 typename Matrix::block_type dummy;
202 const auto n = MatrixDimension<typename Matrix::block_type>::rowdim(dummy);
203 const auto m = MatrixDimension<typename Matrix::block_type>::coldim(dummy);
204 return Nnz_/n/m;
205 }
206
211 size_type M() const
212 {
213 return M_;
214 }
215
216 B* getValues() const
217 {
218 return values;
219 }
220
221 Index* getRowIndex() const
222 {
223 return rowindex;
224 }
225
226 Index* getColStart() const
227 {
228 return colstart;
229 }
230
231 ColCompMatrix& operator=(const Matrix& mat);
232 ColCompMatrix& operator=(const ColCompMatrix& mat);
233
239 virtual void setMatrix(const Matrix& mat, const std::set<std::size_t>& mrs);
241 virtual void free();
242
244 virtual void setMatrix(const Matrix& mat);
245
246 public:
247 size_type N_, M_, Nnz_;
248 B* values;
249 Index* rowindex;
250 Index* colstart;
251 };
252
253 template<class M, class I>
255 {
256 template<class IList, class S, class D>
258 public:
259 using Matrix = M;
260 using Index = I;
262 typedef typename Matrix::row_type::const_iterator CIter;
263 typedef typename Matrix::size_type size_type;
264
269 template <class Block=typename M::block_type>
271 typename std::enable_if_t<Dune::IsNumber<Block>::value>* sfinae = nullptr);
272
277 template <class Block=typename M::block_type>
279 typename std::enable_if_t<!Dune::IsNumber<Block>::value>* sfinae = nullptr);
280
282
284 {}
285
286 template<typename Iter>
287 void addRowNnz(const Iter& row) const;
288
289 template<typename Iter, typename FullMatrixIndex>
290 void addRowNnz(const Iter& row, const std::set<FullMatrixIndex>& indices) const;
291
292 template<typename Iter, typename SubMatrixIndex>
293 void addRowNnz(const Iter& row, const std::vector<SubMatrixIndex>& indices) const;
294
295 void allocate();
296
297 template<typename Iter>
298 void countEntries(const Iter& row, const CIter& col) const;
299
300 void countEntries(size_type colidx) const;
301
302 void calcColstart() const;
303
304 template<typename Iter>
305 void copyValue(const Iter& row, const CIter& col) const;
306
307 void copyValue(const CIter& col, size_type rowindex, size_type colidx) const;
308
309 virtual void createMatrix() const;
310
311 protected:
312
313 void allocateMatrixStorage() const;
314
315 void allocateMarker();
316
317 ColCompMatrix* mat;
318 size_type cols;
319
320 // Number of rows/columns of the matrix entries
321 // (assumed to be scalars or dense matrices)
322 size_type n, m;
323
324 mutable std::vector<size_type> marker;
325 };
326
327 template<class M, class I>
328 template <class Block>
330 : mat(&mat_), cols(mat_.M())
331 {
332 n = 1;
333 m = 1;
334
335 mat->Nnz_=0;
336 }
337
338 template<class M, class I>
339 template <class Block>
341 : mat(&mat_), cols(mat_.M())
342 {
343 // WARNING: This assumes that all blocks are dense and identical
344 n = M::block_type::rows;
345 m = M::block_type::cols;
346
347 mat->Nnz_=0;
348 }
349
350 template<class M, class I>
352 : mat(0), cols(0), n(0), m(0)
353 {}
354
355 template<class M, class I>
356 template<typename Iter>
357 void ColCompMatrixInitializer<M, I>::addRowNnz(const Iter& row) const
358 {
359 mat->Nnz_+=row->getsize();
360 }
361
362 template<class M, class I>
363 template<typename Iter, typename FullMatrixIndex>
364 void ColCompMatrixInitializer<M, I>::addRowNnz(const Iter& row,
365 const std::set<FullMatrixIndex>& indices) const
366 {
367 typedef typename Iter::value_type::const_iterator RIter;
368 typedef typename std::set<FullMatrixIndex>::const_iterator MIter;
369 MIter siter =indices.begin();
370 for(RIter entry=row->begin(); entry!=row->end(); ++entry)
371 {
372 for(; siter!=indices.end() && *siter<entry.index(); ++siter) ;
373 if(siter==indices.end())
374 break;
375 if(*siter==entry.index())
376 // index is in subdomain
377 ++mat->Nnz_;
378 }
379 }
380
381 template<class M, class I>
382 template<typename Iter, typename SubMatrixIndex>
383 void ColCompMatrixInitializer<M, I>::addRowNnz(const Iter& row,
384 const std::vector<SubMatrixIndex>& indices) const
385 {
386 using RIter = typename Iter::value_type::const_iterator;
387 for(RIter entry=row->begin(); entry!=row->end(); ++entry)
388 if (indices[entry.index()]!=std::numeric_limits<SubMatrixIndex>::max())
389 ++mat->Nnz_;
390 }
391
392 template<class M, class I>
393 void ColCompMatrixInitializer<M, I>::allocate()
394 {
395 allocateMatrixStorage();
396 allocateMarker();
397 }
398
399 template<class M, class I>
400 void ColCompMatrixInitializer<M, I>::allocateMatrixStorage() const
401 {
402 mat->Nnz_*=n*m;
403 // initialize data
404 mat->values=new typename M::field_type[mat->Nnz_];
405 mat->rowindex=new I[mat->Nnz_];
406 mat->colstart=new I[cols+1];
407 }
408
409 template<class M, class I>
410 void ColCompMatrixInitializer<M, I>::allocateMarker()
411 {
412 marker.resize(cols);
413 std::fill(marker.begin(), marker.end(), 0);
414 }
415
416 template<class M, class I>
417 template<typename Iter>
418 void ColCompMatrixInitializer<M, I>::countEntries(const Iter& row, const CIter& col) const
419 {
421 countEntries(col.index());
422 }
423
424 template<class M, class I>
425 void ColCompMatrixInitializer<M, I>::countEntries(size_type colindex) const
426 {
427 for(size_type i=0; i < m; ++i)
428 {
429 assert(colindex*m+i<cols);
430 marker[colindex*m+i]+=n;
431 }
432 }
433
434 template<class M, class I>
435 void ColCompMatrixInitializer<M, I>::calcColstart() const
436 {
437 mat->colstart[0]=0;
438 for(size_type i=0; i < cols; ++i) {
439 assert(i<cols);
440 mat->colstart[i+1]=mat->colstart[i]+marker[i];
441 marker[i]=mat->colstart[i];
442 }
443 }
444
445 template<class M, class I>
446 template<typename Iter>
447 void ColCompMatrixInitializer<M, I>::copyValue(const Iter& row, const CIter& col) const
448 {
449 copyValue(col, row.index(), col.index());
450 }
451
452 template<class M, class I>
453 void ColCompMatrixInitializer<M, I>::copyValue(const CIter& col, size_type rowindex, size_type colindex) const
454 {
455 for(size_type i=0; i<n; i++) {
456 for(size_type j=0; j<m; j++) {
457 assert(colindex*m+j<cols-1 || (size_type)marker[colindex*m+j]<(size_type)mat->colstart[colindex*m+j+1]);
458 assert((size_type)marker[colindex*m+j]<mat->Nnz_);
459 mat->rowindex[marker[colindex*m+j]]=rowindex*n+i;
460 mat->values[marker[colindex*m+j]]=Impl::asMatrix(*col)[i][j];
461 ++marker[colindex*m+j]; // index for next entry in column
462 }
463 }
464 }
465
466 template<class M, class I>
467 void ColCompMatrixInitializer<M, I>::createMatrix() const
468 {
469 marker.clear();
470 }
471
472 template<class F, class MRS>
473 void copyToColCompMatrix(F& initializer, const MRS& mrs)
474 {
475 typedef typename MRS::const_iterator Iter;
476 typedef typename std::iterator_traits<Iter>::value_type::const_iterator CIter;
477 for(Iter row=mrs.begin(); row!= mrs.end(); ++row)
478 initializer.addRowNnz(row);
479
480 initializer.allocate();
481
482 for(Iter row=mrs.begin(); row!= mrs.end(); ++row) {
483
484 for(CIter col=row->begin(); col != row->end(); ++col)
485 initializer.countEntries(row, col);
486 }
487
488 initializer.calcColstart();
489
490 for(Iter row=mrs.begin(); row!= mrs.end(); ++row) {
491 for(CIter col=row->begin(); col != row->end(); ++col) {
492 initializer.copyValue(row, col);
493 }
494
495 }
496 initializer.createMatrix();
497 }
498
499 template<class F, class M,class S>
500 void copyToColCompMatrix(F& initializer, const MatrixRowSubset<M,S>& mrs)
501 {
502 typedef MatrixRowSubset<M,S> MRS;
503 typedef typename MRS::RowIndexSet SIS;
504 typedef typename SIS::const_iterator SIter;
505 typedef typename MRS::const_iterator Iter;
506 typedef typename std::iterator_traits<Iter>::value_type row_type;
507 typedef typename row_type::const_iterator CIter;
508
509 typedef typename MRS::Matrix::size_type size_type;
510
511 // A vector containing the corresponding indices in
512 // the to create submatrix.
513 // If an entry is the maximum of size_type then this index will not appear in
514 // the submatrix.
515 std::vector<size_type> subMatrixIndex(mrs.matrix().N(),
517 size_type s=0;
518 for(SIter index = mrs.rowIndexSet().begin(); index!=mrs.rowIndexSet().end(); ++index)
519 subMatrixIndex[*index]=s++;
520
521 // Calculate upper Bound for nonzeros
522 for(Iter row=mrs.begin(); row!= mrs.end(); ++row)
523 initializer.addRowNnz(row, subMatrixIndex);
524
525 initializer.allocate();
526
527 for(Iter row=mrs.begin(); row!= mrs.end(); ++row)
528 for(CIter col=row->begin(); col != row->end(); ++col) {
529 if(subMatrixIndex[col.index()]!=std::numeric_limits<size_type>::max())
530 // This column is in our subset (use submatrix column index)
531 initializer.countEntries(subMatrixIndex[col.index()]);
532 }
533
534 initializer.calcColstart();
535
536 for(Iter row=mrs.begin(); row!= mrs.end(); ++row)
537 for(CIter col=row->begin(); col != row->end(); ++col) {
538 if(subMatrixIndex[col.index()]!=std::numeric_limits<size_type>::max())
539 // This value is in our submatrix -> copy (use submatrix indices
540 initializer.copyValue(col, subMatrixIndex[row.index()], subMatrixIndex[col.index()]);
541 }
542 initializer.createMatrix();
543 }
544
545#ifndef DOXYGEN
546
547 template<class Mat, class I>
548 ColCompMatrix<Mat, I>::ColCompMatrix()
549 : N_(0), M_(0), Nnz_(0), values(0), rowindex(0), colstart(0)
550 {}
551
552 template<class Mat, class I>
553 ColCompMatrix<Mat, I>
554 ::ColCompMatrix(const Matrix& mat)
555 {
556 // WARNING: This assumes that all blocks are dense and identical
557 typename Matrix::block_type dummy;
558 const auto n = MatrixDimension<typename Matrix::block_type>::rowdim(dummy);
559 const auto m = MatrixDimension<typename Matrix::block_type>::coldim(dummy);
560 N_ = n*mat.N();
561 M_ = m*mat.N();
562 Nnz_ = n*m*mat.nonzeroes();
563 }
564
565 template<class Mat, class I>
566 ColCompMatrix<Mat, I>&
567 ColCompMatrix<Mat, I>::operator=(const Matrix& mat)
568 {
569 if(N_+M_+Nnz_!=0)
570 free();
571 setMatrix(mat);
572 return *this;
573 }
574
575 template<class Mat, class I>
576 ColCompMatrix<Mat, I>&
577 ColCompMatrix<Mat, I>::operator=(const ColCompMatrix& mat)
578 {
579 if(N_+M_+Nnz_!=0)
580 free();
581 N_=mat.N_;
582 M_=mat.M_;
583 Nnz_= mat.Nnz_;
584 if(M_>0) {
585 colstart=new size_type[M_+1];
586 for(size_type i=0; i<=M_; ++i)
587 colstart[i]=mat.colstart[i];
588 }
589
590 if(Nnz_>0) {
591 values = new B[Nnz_];
592 rowindex = new size_type[Nnz_];
593
594 for(size_type i=0; i<Nnz_; ++i)
595 values[i]=mat.values[i];
596
597 for(size_type i=0; i<Nnz_; ++i)
598 rowindex[i]=mat.rowindex[i];
599 }
600 return *this;
601 }
602
603 template<class Mat, class I>
605 ::setMatrix(const Matrix& mat)
606 {
607 N_=MatrixDimension<Mat>::rowdim(mat);
608 M_=MatrixDimension<Mat>::coldim(mat);
609 ColCompMatrixInitializer<Mat, I> initializer(*this);
610
611 copyToColCompMatrix(initializer, MatrixRowSet<Matrix>(mat));
612 }
613
614 template<class Mat, class I>
616 ::setMatrix(const Matrix& mat, const std::set<std::size_t>& mrs)
617 {
618 if(N_+M_+Nnz_!=0)
619 free();
620
621 N_=mrs.size()*MatrixDimension<Mat>::rowdim(mat) / mat.N();
622 M_=mrs.size()*MatrixDimension<Mat>::coldim(mat) / mat.M();
623 ColCompMatrixInitializer<Mat, I> initializer(*this);
624
625 copyToColCompMatrix(initializer, MatrixRowSubset<Mat,std::set<std::size_t> >(mat,mrs));
626 }
627
628 template<class Mat, class I>
630 {
631 if(N_+M_+Nnz_!=0)
632 free();
633 }
634
635 template<class Mat, class I>
637 {
638 delete[] values;
639 delete[] rowindex;
640 delete[] colstart;
641 N_ = 0;
642 M_ = 0;
643 Nnz_ = 0;
644 }
645
646#endif // DOXYGEN
647
648}
649#endif
Implementation of the BCRSMatrix class.
This file implements a vector space as a tensor product of a given vector space. The number of compon...
Inititializer for the ColCompMatrix as needed by OverlappingSchwarz.
Definition: colcompmatrix.hh:255
ColCompMatrixInitializer(ColCompMatrix &lum, typename std::enable_if_t< Dune::IsNumber< Block >::value > *sfinae=nullptr)
Constructor for scalar-valued matrices.
Definition: colcompmatrix.hh:329
ColCompMatrixInitializer(ColCompMatrix &lum, typename std::enable_if_t<!Dune::IsNumber< Block >::value > *sfinae=nullptr)
Constructor for dense matrix-valued matrices.
Definition: colcompmatrix.hh:340
Utility class for converting an ISTL Matrix into a column-compressed matrix.
Definition: colcompmatrix.hh:162
virtual ~ColCompMatrix()
Destructor.
virtual void setMatrix(const Matrix &mat, const std::set< std::size_t > &mrs)
Initialize data from a given set of matrix rows and columns.
ColCompMatrix(const Matrix &mat)
Constructor that initializes the data.
Mat Matrix
The type of the matrix to convert.
Definition: colcompmatrix.hh:169
virtual void free()
free allocated space.
size_type N() const
Get the number of rows.
Definition: colcompmatrix.hh:192
size_type M() const
Get the number of columns.
Definition: colcompmatrix.hh:211
virtual void setMatrix(const Matrix &mat)
Initialize data from given matrix.
Base class for stl conformant forward iterators.
Definition: iteratorfacades.hh:139
ConstIterator class for sequential access.
Definition: matrix.hh:401
Provides access to an iterator over all matrix rows.
Definition: colcompmatrix.hh:23
Matrix::ConstRowIterator const_iterator
The matrix row iterator type.
Definition: colcompmatrix.hh:28
const_iterator begin() const
Get the row iterator at the first row.
Definition: colcompmatrix.hh:39
M Matrix
The type of the matrix.
Definition: colcompmatrix.hh:26
MatrixRowSet(const Matrix &m)
Construct an row set over all matrix rows.
Definition: colcompmatrix.hh:34
const_iterator end() const
Get the row iterator at the end of all rows.
Definition: colcompmatrix.hh:44
The matrix row iterator type.
Definition: colcompmatrix.hh:90
Provides access to an iterator over an arbitrary subset of matrix rows.
Definition: colcompmatrix.hh:61
S RowIndexSet
the type of the set of valid row indices.
Definition: colcompmatrix.hh:66
const_iterator begin() const
Get the row iterator at the first row.
Definition: colcompmatrix.hh:123
M Matrix
the type of the matrix class.
Definition: colcompmatrix.hh:64
MatrixRowSubset(const Matrix &m, const RowIndexSet &s)
Construct an row set over all matrix rows.
Definition: colcompmatrix.hh:73
const_iterator end() const
Get the row iterator at the end of all rows.
Definition: colcompmatrix.hh:128
A generic dynamic dense matrix.
Definition: matrix.hh:558
A::size_type size_type
Type for indices and sizes.
Definition: matrix.hh:574
size_type M() const
Return the number of columns.
Definition: matrix.hh:696
T block_type
Export the type representing the components.
Definition: matrix.hh:565
MatrixImp::DenseMatrixBase< T, A >::window_type row_type
The type implementing a matrix row.
Definition: matrix.hh:571
size_type N() const
Return the number of rows.
Definition: matrix.hh:691
Initializer for SuperLU Matrices representing the subdomains.
Definition: overlappingschwarz.hh:43
Implements a matrix constructed from a given type representing a field and compile-time given number ...
Implements a vector constructed from a given type representing a field and a compile-time given size.
#define DUNE_UNUSED_PARAMETER(parm)
A macro to mark intentionally unused function parameters with.
Definition: unused.hh:25
auto max(ADLTag< 0 >, const V &v1, const V &v2)
implements binary Simd::max()
Definition: defaults.hh:79
Dune namespace.
Definition: alignedallocator.hh:14
Implements a scalar matrix view wrapper around an existing scalar.
Whether this type acts as a scalar in the context of (hierarchically blocked) containers.
Definition: typetraits.hh:163
Traits for type conversions and type information.
Definition of the DUNE_UNUSED macro for the case that config.h is not available.
Creative Commons License   |  Legal Statements / Impressum  |  Hosted by TU Dresden  |  generated with Hugo v0.111.3 (Jul 15, 22:36, 2024)