10#ifndef IFPACK2_REORDERFILTER_DEF_HPP
11#define IFPACK2_REORDERFILTER_DEF_HPP
12#include "Ifpack2_ReorderFilter_decl.hpp"
15#include "Tpetra_ConfigDefs.hpp"
16#include "Tpetra_RowMatrix.hpp"
17#include "Tpetra_Map.hpp"
18#include "Tpetra_MultiVector.hpp"
19#include "Tpetra_Vector.hpp"
23template<
class MatrixType>
26 const Teuchos::ArrayRCP<local_ordinal_type>& perm,
27 const Teuchos::ArrayRCP<local_ordinal_type>& reverseperm)
30 reverseperm_ (reverseperm)
32 TEUCHOS_TEST_FOR_EXCEPTION(
33 A_.is_null (), std::invalid_argument,
34 "Ifpack2::ReorderFilter: The input matrix is null.");
37 TEUCHOS_TEST_FOR_EXCEPTION(
38 A_->getComm()->getSize() != 1, std::invalid_argument,
39 "Ifpack2::ReorderFilter: This class may only be used if the input matrix's "
40 "communicator has one process. This class is an implementation detail of "
41 "Ifpack2::AdditiveSchwarz, and it is not meant to be used otherwise.");
43 TEUCHOS_TEST_FOR_EXCEPTION(
44 A_->getLocalNumRows () != A_->getGlobalNumRows (),
45 std::invalid_argument,
46 "Ifpack2::ReorderFilter: The input matrix is not square.");
49 Kokkos::resize(Indices_,A_->getLocalMaxNumRowEntries ());
50 Kokkos::resize(Values_,A_->getLocalMaxNumRowEntries ());
54template<
class MatrixType>
58template<
class MatrixType>
67template<
class MatrixType>
68Teuchos::RCP<const typename ReorderFilter<MatrixType>::map_type>
71 TEUCHOS_TEST_FOR_EXCEPTION(
72 A_.is_null (), std::runtime_error,
"Ifpack2::ReorderFilter::"
73 "getRowMap: The matrix A is null, so there is no row Map.");
75 return A_->getRowMap ();
79template<
class MatrixType>
80Teuchos::RCP<const typename ReorderFilter<MatrixType>::map_type>
83 TEUCHOS_TEST_FOR_EXCEPTION(
84 A_.is_null (), std::runtime_error,
"Ifpack2::ReorderFilter::"
85 "getColMap: The matrix A is null, so there is no column Map.");
87 return A_->getColMap();
91template<
class MatrixType>
92Teuchos::RCP<const typename ReorderFilter<MatrixType>::map_type>
95 TEUCHOS_TEST_FOR_EXCEPTION(
96 A_.is_null (), std::runtime_error,
"Ifpack2::ReorderFilter::"
97 "getDomainMap: The matrix A is null, so there is no domain Map.");
99 return A_->getDomainMap();
103template<
class MatrixType>
104Teuchos::RCP<const typename ReorderFilter<MatrixType>::map_type>
107 TEUCHOS_TEST_FOR_EXCEPTION(
108 A_.is_null (), std::runtime_error,
"Ifpack2::ReorderFilter::"
109 "getRangeMap: The matrix A is null, so there is no range Map.");
111 return A_->getRangeMap();
115template<
class MatrixType>
116Teuchos::RCP<
const Tpetra::RowGraph<
typename MatrixType::local_ordinal_type,
117 typename MatrixType::global_ordinal_type,
118 typename MatrixType::node_type> >
121 throw std::runtime_error(
"Ifpack2::ReorderFilter: does not support getGraph.");
125template<
class MatrixType>
128 return A_->getGlobalNumRows();
132template<
class MatrixType>
135 return A_->getGlobalNumCols();
139template<
class MatrixType>
142 return A_->getLocalNumRows();
146template<
class MatrixType>
149 return A_->getLocalNumCols();
153template<
class MatrixType>
156 return A_->getIndexBase();
160template<
class MatrixType>
163 return A_->getGlobalNumEntries();
167template<
class MatrixType>
170 return A_->getLocalNumEntries();
173template<
class MatrixType>
176 return A_->getBlockSize();
179template<
class MatrixType>
183 if (A_.is_null () || A_->getRowMap ().is_null ()) {
184 return Teuchos::OrdinalTraits<size_t>::invalid ();
187 const local_ordinal_type lclRow =
188 A_->getRowMap ()->getLocalElement (globalRow);
189 if (lclRow == Teuchos::OrdinalTraits<local_ordinal_type>::invalid ()) {
191 return static_cast<size_t> (0);
193 const local_ordinal_type origLclRow = reverseperm_[lclRow];
194 return A_->getNumEntriesInLocalRow (origLclRow);
199template<
class MatrixType>
205 if (A_->getRowMap ()->isNodeLocalElement (localRow)) {
207 const local_ordinal_type localReorderedRow = reverseperm_[localRow];
208 return A_->getNumEntriesInLocalRow (localReorderedRow);
211 return static_cast<size_t> (0);
216template<
class MatrixType>
219 return A_->getGlobalMaxNumRowEntries();
223template<
class MatrixType>
226 return A_->getLocalMaxNumRowEntries();
230template<
class MatrixType>
237template<
class MatrixType>
240 return A_->isLocallyIndexed();
244template<
class MatrixType>
247 return A_->isGloballyIndexed();
251template<
class MatrixType>
254 return A_->isFillComplete();
258template<
class MatrixType>
261 nonconst_global_inds_host_view_type &globalInd,
262 nonconst_values_host_view_type &val,
263 size_t& numEntries)
const
265 using Teuchos::Array;
266 using Teuchos::ArrayView;
267 using Teuchos::av_reinterpret_cast;
268 typedef local_ordinal_type LO;
269 typedef Teuchos::OrdinalTraits<LO> OTLO;
271 const map_type& rowMap = * (A_->getRowMap ());
272 const local_ordinal_type localRow = rowMap.getLocalElement (globalRow);
273 TEUCHOS_TEST_FOR_EXCEPTION(
274 localRow == OTLO::invalid (), std::invalid_argument,
"Ifpack2::Reorder"
275 "Filter::getGlobalRowCopy: The given global row index " << globalRow
276 <<
" is not owned by the calling process with rank "
277 << rowMap.getComm ()->getRank () <<
".");
284 for (
size_t k = 0; k < numEntries; ++k) {
285 globalInd[k] = rowMap.getGlobalElement (Indices_[k]);
290template<
class MatrixType>
293 nonconst_local_inds_host_view_type &Indices,
294 nonconst_values_host_view_type &Values,
295 size_t& NumEntries)
const
298 TEUCHOS_TEST_FOR_EXCEPTION(
299 ! A_->getRowMap ()->isNodeLocalElement (LocalRow),
300 std::invalid_argument,
301 "Ifpack2::ReorderFilter::getLocalRowCopy: The given local row index "
302 << LocalRow <<
" is not a valid local row index on the calling process "
303 "with rank " << A_->getRowMap ()->getComm ()->getRank () <<
".");
307 const local_ordinal_type origLclRow = reverseperm_[LocalRow];
308 const size_t numEntries = A_->getNumEntriesInLocalRow (origLclRow);
310 TEUCHOS_TEST_FOR_EXCEPTION(
311 static_cast<size_t> (Indices.size ()) < numEntries ||
312 static_cast<size_t> (Values.size ()) < numEntries,
313 std::invalid_argument,
314 "Ifpack2::ReorderFilter::getLocalRowCopy: The given array views are not "
315 "long enough to store all the data in the given row " << LocalRow
316 <<
". Indices.size() = " << Indices.size () <<
", Values.size() = "
317 << Values.size () <<
", but the (original) row has " << numEntries
320 A_->getLocalRowCopy (origLclRow, Indices, Values, NumEntries);
325 for (
size_t i = 0; i < NumEntries; ++i) {
326 Indices[i] = perm_[Indices[i]];
331template<
class MatrixType>
333 global_inds_host_view_type &,
334 values_host_view_type &)
const
336 throw std::runtime_error(
"Ifpack2::ReorderFilter: does not support getGlobalRowView.");
341template<
class MatrixType>
343 local_inds_host_view_type & ,
344 values_host_view_type & )
const
346 throw std::runtime_error(
"Ifpack2::ReorderFilter: does not support getLocalRowView.");
351template<
class MatrixType>
353getLocalDiagCopy (Tpetra::Vector<scalar_type,local_ordinal_type,global_ordinal_type,node_type> &diag)
const
356 return A_->getLocalDiagCopy(diag);
360template<
class MatrixType>
363 throw std::runtime_error(
"Ifpack2::ReorderFilter does not support leftScale.");
367template<
class MatrixType>
370 throw std::runtime_error(
"Ifpack2::ReorderFilter does not support rightScale.");
374template<
class MatrixType>
376apply (
const Tpetra::MultiVector<scalar_type,local_ordinal_type,global_ordinal_type,node_type> &X,
377 Tpetra::MultiVector<scalar_type,local_ordinal_type,global_ordinal_type,node_type> &Y,
378 Teuchos::ETransp mode,
380 scalar_type beta)
const
382 typedef Teuchos::ScalarTraits<scalar_type> STS;
384 TEUCHOS_TEST_FOR_EXCEPTION(
385 alpha != STS::one () || beta != STS::zero (), std::logic_error,
386 "Ifpack2::ReorderFilter::apply is only implemented for alpha = 1 and "
387 "beta = 0. You set alpha = " << alpha <<
" and beta = " << beta <<
".");
391 TEUCHOS_TEST_FOR_EXCEPTION(
392 X.getNumVectors() != Y.getNumVectors(), std::runtime_error,
393 "Ifpack2::ReorderFilter::apply: X.getNumVectors() != Y.getNumVectors().");
395 const scalar_type zero = STS::zero ();
396 Teuchos::ArrayRCP<Teuchos::ArrayRCP<const scalar_type> > x_ptr = X.get2dView();
397 Teuchos::ArrayRCP<Teuchos::ArrayRCP<scalar_type> > y_ptr = Y.get2dViewNonConst();
400 const size_t NumVectors = Y.getNumVectors ();
402 for (
size_t i = 0; i < A_->getLocalNumRows (); ++i) {
406 scalar_type* Values =
reinterpret_cast<scalar_type*
>(Values_.data());
407 if (mode == Teuchos::NO_TRANS) {
408 for (
size_t j = 0; j < Nnz; ++j) {
409 for (
size_t k = 0; k < NumVectors; ++k) {
410 y_ptr[k][i] += Values[j] * x_ptr[k][Indices_[j]];
414 else if (mode == Teuchos::TRANS) {
415 for (
size_t j = 0; j < Nnz; ++j) {
416 for (
size_t k = 0; k < NumVectors; ++k) {
417 y_ptr[k][Indices_[j]] += Values[j] * x_ptr[k][i];
422 for (
size_t j = 0; j < Nnz; ++j) {
423 for (
size_t k = 0; k < NumVectors; ++k) {
424 y_ptr[k][Indices_[j]] += STS::conjugate(Values[j]) * x_ptr[k][i];
432template<
class MatrixType>
439template<
class MatrixType>
446template<
class MatrixType>
450 return A_->getFrobeniusNorm ();
454template<
class MatrixType>
456permuteOriginalToReordered (
const Tpetra::MultiVector<scalar_type,local_ordinal_type,global_ordinal_type,node_type> &originalX,
457 Tpetra::MultiVector<scalar_type,local_ordinal_type,global_ordinal_type,node_type> &reorderedY)
const
459 this->
template permuteOriginalToReorderedTempl<scalar_type,scalar_type>(originalX, reorderedY);
463template<
class MatrixType>
464template<
class DomainScalar,
class RangeScalar>
465void ReorderFilter<MatrixType>::permuteOriginalToReorderedTempl(
const Tpetra::MultiVector<DomainScalar,local_ordinal_type,global_ordinal_type,node_type> &originalX,
466 Tpetra::MultiVector<RangeScalar,local_ordinal_type,global_ordinal_type,node_type> &reorderedY)
const
468 TEUCHOS_TEST_FOR_EXCEPTION(originalX.getNumVectors() != reorderedY.getNumVectors(), std::runtime_error,
469 "Ifpack2::ReorderFilter::permuteOriginalToReordered ERROR: X.getNumVectors() != Y.getNumVectors().");
471 Teuchos::ArrayRCP<Teuchos::ArrayRCP<const DomainScalar> > x_ptr = originalX.get2dView();
472 Teuchos::ArrayRCP<Teuchos::ArrayRCP<RangeScalar> > y_ptr = reorderedY.get2dViewNonConst();
476 for(
size_t k=0; k < originalX.getNumVectors(); k++)
479 y_ptr[k][perm_[i]*blockSize + j] = (RangeScalar)x_ptr[k][i*blockSize + j];
483template<
class MatrixType>
485 Tpetra::MultiVector<scalar_type,local_ordinal_type,global_ordinal_type,node_type> &originalY)
const
487 this->
template permuteReorderedToOriginalTempl<scalar_type,scalar_type>(reorderedX, originalY);
491template<
class MatrixType>
492template<
class DomainScalar,
class RangeScalar>
495 Tpetra::MultiVector<RangeScalar,local_ordinal_type,global_ordinal_type,node_type> &originalY)
const
497 TEUCHOS_TEST_FOR_EXCEPTION(
498 reorderedX.getNumVectors() != originalY.getNumVectors(),
500 "Ifpack2::ReorderFilter::permuteReorderedToOriginal: "
501 "X.getNumVectors() != Y.getNumVectors().");
503#ifdef HAVE_IFPACK2_DEBUG
505 typedef Teuchos::ScalarTraits<magnitude_type> STM;
506 Teuchos::Array<magnitude_type> norms (reorderedX.getNumVectors ());
507 reorderedX.norm2 (norms ());
510 j < reorderedX.getNumVectors (); ++j) {
511 if (STM::isnaninf (norms[j])) {
516 TEUCHOS_TEST_FOR_EXCEPTION(
517 ! good, std::runtime_error,
"Ifpack2::ReorderFilter::"
518 "permuteReorderedToOriginalTempl: The 2-norm of the input reorderedX is "
523 Teuchos::ArrayRCP<Teuchos::ArrayRCP<const DomainScalar> > x_ptr = reorderedX.get2dView();
524 Teuchos::ArrayRCP<Teuchos::ArrayRCP<RangeScalar> > y_ptr = originalY.get2dViewNonConst();
528 for (
size_t k = 0; k < reorderedX.getNumVectors (); ++k) {
531 y_ptr[k][reverseperm_[i]*blockSize + j] = (RangeScalar) x_ptr[k][i*blockSize + j];
536#ifdef HAVE_IFPACK2_DEBUG
538 typedef Teuchos::ScalarTraits<magnitude_type> STM;
539 Teuchos::Array<magnitude_type> norms (originalY.getNumVectors ());
540 originalY.norm2 (norms ());
543 j < originalY.getNumVectors (); ++j) {
544 if (STM::isnaninf (norms[j])) {
549 TEUCHOS_TEST_FOR_EXCEPTION(
550 ! good, std::runtime_error,
"Ifpack2::ReorderFilter::"
551 "permuteReorderedToOriginalTempl: The 2-norm of the output originalY is "
559#define IFPACK2_REORDERFILTER_INSTANT(S,LO,GO,N) \
560 template class Ifpack2::ReorderFilter< Tpetra::RowMatrix<S, LO, GO, N> >;
Wraps a Tpetra::RowMatrix in a filter that reorders local rows and columns.
Definition Ifpack2_ReorderFilter_decl.hpp:37
virtual local_ordinal_type getBlockSize() const
The number of degrees of freedom per mesh point.
Definition Ifpack2_ReorderFilter_def.hpp:174
virtual size_t getLocalNumCols() const
Returns the number of columns needed to apply the forward operator on this node, i....
Definition Ifpack2_ReorderFilter_def.hpp:147
virtual size_t getNumEntriesInGlobalRow(global_ordinal_type globalRow) const
The current number of entries in this matrix, stored on the calling process, in the row whose global ...
Definition Ifpack2_ReorderFilter_def.hpp:181
virtual mag_type getFrobeniusNorm() const
Returns the Frobenius norm of the matrix.
Definition Ifpack2_ReorderFilter_def.hpp:447
virtual size_t getGlobalMaxNumRowEntries() const
Returns the maximum number of entries across all rows/columns on all nodes.
Definition Ifpack2_ReorderFilter_def.hpp:217
virtual Teuchos::RCP< const map_type > getColMap() const
Returns the Map that describes the column distribution in this matrix.
Definition Ifpack2_ReorderFilter_def.hpp:81
virtual void rightScale(const Tpetra::Vector< scalar_type, local_ordinal_type, global_ordinal_type, node_type > &x)
Scales the RowMatrix on the right with the Vector x.
Definition Ifpack2_ReorderFilter_def.hpp:368
virtual bool hasColMap() const
Indicates whether this matrix has a well-defined column map.
Definition Ifpack2_ReorderFilter_def.hpp:231
virtual size_t getLocalMaxNumRowEntries() const
Returns the maximum number of entries across all rows/columns on this node.
Definition Ifpack2_ReorderFilter_def.hpp:224
virtual void permuteReorderedToOriginal(const Tpetra::MultiVector< scalar_type, local_ordinal_type, global_ordinal_type, node_type > &reorderedX, Tpetra::MultiVector< scalar_type, local_ordinal_type, global_ordinal_type, node_type > &originalY) const
Permute multivector: reordered-to-original.
Definition Ifpack2_ReorderFilter_def.hpp:484
virtual void permuteOriginalToReordered(const Tpetra::MultiVector< scalar_type, local_ordinal_type, global_ordinal_type, node_type > &originalX, Tpetra::MultiVector< scalar_type, local_ordinal_type, global_ordinal_type, node_type > &reorderedY) const
Permute multivector: original-to-reordered.
Definition Ifpack2_ReorderFilter_def.hpp:456
virtual Teuchos::RCP< const map_type > getDomainMap() const
Returns the Map that describes the domain distribution in this matrix.
Definition Ifpack2_ReorderFilter_def.hpp:93
virtual bool supportsRowViews() const
Returns true if RowViews are supported.
Definition Ifpack2_ReorderFilter_def.hpp:440
virtual global_ordinal_type getIndexBase() const
Returns the index base for global indices for this matrix.
Definition Ifpack2_ReorderFilter_def.hpp:154
virtual void getLocalDiagCopy(Tpetra::Vector< scalar_type, local_ordinal_type, global_ordinal_type, node_type > &diag) const
Get a copy of the diagonal entries owned by this node, with local row indices.
Definition Ifpack2_ReorderFilter_def.hpp:353
virtual bool isGloballyIndexed() const
If matrix indices are in the global range, this function returns true. Otherwise, this function retur...
Definition Ifpack2_ReorderFilter_def.hpp:245
virtual Teuchos::RCP< const map_type > getRowMap() const
Returns the Map that describes the row distribution in this matrix.
Definition Ifpack2_ReorderFilter_def.hpp:69
virtual size_t getLocalNumRows() const
Returns the number of rows owned on the calling node.
Definition Ifpack2_ReorderFilter_def.hpp:140
virtual Teuchos::RCP< const map_type > getRangeMap() const
Returns the Map that describes the range distribution in this matrix.
Definition Ifpack2_ReorderFilter_def.hpp:105
virtual Teuchos::RCP< const Teuchos::Comm< int > > getComm() const
The matrix's communicator.
Definition Ifpack2_ReorderFilter_def.hpp:59
ReorderFilter(const Teuchos::RCP< const row_matrix_type > &A, const Teuchos::ArrayRCP< local_ordinal_type > &perm, const Teuchos::ArrayRCP< local_ordinal_type > &reverseperm)
Constructor.
Definition Ifpack2_ReorderFilter_def.hpp:25
virtual bool isFillComplete() const
Returns true if fillComplete() has been called.
Definition Ifpack2_ReorderFilter_def.hpp:252
virtual bool isLocallyIndexed() const
If matrix indices are in the local range, this function returns true. Otherwise, this function return...
Definition Ifpack2_ReorderFilter_def.hpp:238
virtual size_t getLocalNumEntries() const
Returns the local number of entries in this matrix.
Definition Ifpack2_ReorderFilter_def.hpp:168
virtual ~ReorderFilter()
Destructor.
Definition Ifpack2_ReorderFilter_def.hpp:55
virtual void getGlobalRowCopy(global_ordinal_type GlobalRow, nonconst_global_inds_host_view_type &Indices, nonconst_values_host_view_type &Values, size_t &NumEntries) const
Extract a list of entries in a specified global row of this matrix. Put into pre-allocated storage.
Definition Ifpack2_ReorderFilter_def.hpp:260
virtual void getLocalRowView(local_ordinal_type LocalRow, local_inds_host_view_type &indices, values_host_view_type &values) const
Extract a const, non-persisting view of local indices in a specified row of the matrix.
Definition Ifpack2_ReorderFilter_def.hpp:342
virtual size_t getNumEntriesInLocalRow(local_ordinal_type localRow) const
The current number of entries in this matrix, stored on the calling process, in the row whose local i...
Definition Ifpack2_ReorderFilter_def.hpp:201
virtual void getLocalRowCopy(local_ordinal_type LocalRow, nonconst_local_inds_host_view_type &Indices, nonconst_values_host_view_type &Values, size_t &NumEntries) const
Extract a list of entries in a specified local row of the graph. Put into storage allocated by callin...
Definition Ifpack2_ReorderFilter_def.hpp:292
virtual Teuchos::RCP< const Tpetra::RowGraph< local_ordinal_type, global_ordinal_type, node_type > > getGraph() const
Returns the RowGraph associated with this matrix.
Definition Ifpack2_ReorderFilter_def.hpp:119
virtual void apply(const Tpetra::MultiVector< scalar_type, local_ordinal_type, global_ordinal_type, node_type > &X, Tpetra::MultiVector< scalar_type, local_ordinal_type, global_ordinal_type, node_type > &Y, Teuchos::ETransp mode=Teuchos::NO_TRANS, scalar_type alpha=Teuchos::ScalarTraits< scalar_type >::one(), scalar_type beta=Teuchos::ScalarTraits< scalar_type >::zero()) const
, where Op(A) is either A, , or .
Definition Ifpack2_ReorderFilter_def.hpp:376
virtual global_size_t getGlobalNumRows() const
Returns the number of global rows in this matrix.
Definition Ifpack2_ReorderFilter_def.hpp:126
virtual bool hasTransposeApply() const
Whether apply() can apply the transpose or conjugate transpose.
Definition Ifpack2_ReorderFilter_def.hpp:433
virtual global_size_t getGlobalNumCols() const
Returns the number of global columns in this matrix.
Definition Ifpack2_ReorderFilter_def.hpp:133
virtual global_size_t getGlobalNumEntries() const
Returns the global number of entries in this matrix.
Definition Ifpack2_ReorderFilter_def.hpp:161
virtual void leftScale(const Tpetra::Vector< scalar_type, local_ordinal_type, global_ordinal_type, node_type > &x)
Scales the RowMatrix on the left with the Vector x.
Definition Ifpack2_ReorderFilter_def.hpp:361
virtual void getGlobalRowView(global_ordinal_type GlobalRow, global_inds_host_view_type &indices, values_host_view_type &values) const
Extract a const, non-persisting view of global indices in a specified row of the matrix.
Definition Ifpack2_ReorderFilter_def.hpp:332
Preconditioners and smoothers for Tpetra sparse matrices.
Definition Ifpack2_AdditiveSchwarz_decl.hpp:41