Xpetra Version of the Day
Loading...
Searching...
No Matches
Xpetra_TripleMatrixMultiply_def.hpp
Go to the documentation of this file.
1// @HEADER
2// *****************************************************************************
3// Xpetra: A linear algebra interface package
4//
5// Copyright 2012 NTESS and the Xpetra contributors.
6// SPDX-License-Identifier: BSD-3-Clause
7// *****************************************************************************
8// @HEADER
9
10#ifndef PACKAGES_XPETRA_SUP_UTILS_XPETRA_TRIPLEMATRIXMULTIPLY_DEF_HPP_
11#define PACKAGES_XPETRA_SUP_UTILS_XPETRA_TRIPLEMATRIXMULTIPLY_DEF_HPP_
12
14
15namespace Xpetra {
16
17template <class Scalar, class LocalOrdinal, class GlobalOrdinal, class Node>
19 const Matrix& A, bool transposeA,
20 const Matrix& P, bool transposeP,
21 Matrix& Ac,
22 bool call_FillComplete_on_result,
23 bool doOptimizeStorage,
24 const std::string& label,
25 const RCP<ParameterList>& params) {
26 TEUCHOS_TEST_FOR_EXCEPTION(transposeR == false && Ac.getRowMap()->isSameAs(*R.getRowMap()) == false,
27 Exceptions::RuntimeError, "XpetraExt::TripleMatrixMultiply::MultiplyRAP: row map of Ac is not same as row map of R");
28 TEUCHOS_TEST_FOR_EXCEPTION(transposeR == true && Ac.getRowMap()->isSameAs(*R.getDomainMap()) == false,
29 Exceptions::RuntimeError, "XpetraExt::TripleMatrixMultiply::MultiplyRAP: row map of Ac is not same as domain map of R");
30
34
35 bool haveMultiplyDoFillComplete = call_FillComplete_on_result && doOptimizeStorage;
36
37 if (Ac.getRowMap()->lib() == Xpetra::UseEpetra) {
38 throw(Xpetra::Exceptions::RuntimeError("Xpetra::TripleMatrixMultiply::MultiplyRAP is only implemented for Tpetra"));
39 } else if (Ac.getRowMap()->lib() == Xpetra::UseTpetra) {
40#ifdef HAVE_XPETRA_TPETRA
41 using helpers = Xpetra::Helpers<SC, LO, GO, NO>;
42 if (helpers::isTpetraCrs(R) && helpers::isTpetraCrs(A) && helpers::isTpetraCrs(P)) {
43 // All matrices are Crs
44 const Tpetra::CrsMatrix<SC, LO, GO, NO>& tpR = Xpetra::Helpers<SC, LO, GO, NO>::Op2TpetraCrs(R);
45 const Tpetra::CrsMatrix<SC, LO, GO, NO>& tpA = Xpetra::Helpers<SC, LO, GO, NO>::Op2TpetraCrs(A);
46 const Tpetra::CrsMatrix<SC, LO, GO, NO>& tpP = Xpetra::Helpers<SC, LO, GO, NO>::Op2TpetraCrs(P);
47 Tpetra::CrsMatrix<SC, LO, GO, NO>& tpAc = Xpetra::Helpers<SC, LO, GO, NO>::Op2NonConstTpetraCrs(Ac);
48
49 // 18Feb2013 JJH I'm reenabling the code that allows the matrix matrix multiply to do the fillComplete.
50 // Previously, Tpetra's matrix matrix multiply did not support fillComplete.
51 Tpetra::TripleMatrixMultiply::MultiplyRAP(tpR, transposeR, tpA, transposeA, tpP, transposeP, tpAc, haveMultiplyDoFillComplete, label, params);
52 } else if (helpers::isTpetraBlockCrs(R) && helpers::isTpetraBlockCrs(A) && helpers::isTpetraBlockCrs(P)) {
53 // All matrices are BlockCrs (except maybe Ac)
54 // FIXME: For the moment we're just going to clobber the innards of Ac, so no reuse. Once we have a reuse kernel,
55 // we'll need to think about refactoring BlockCrs so we can do something smarter here.
56
57 if (!A.getRowMap()->getComm()->getRank())
58 std::cout << "WARNING: Using inefficient BlockCrs Multiply Placeholder" << std::endl;
59
60 const Tpetra::BlockCrsMatrix<SC, LO, GO, NO>& tpR = Xpetra::Helpers<SC, LO, GO, NO>::Op2TpetraBlockCrs(R);
61 const Tpetra::BlockCrsMatrix<SC, LO, GO, NO>& tpA = Xpetra::Helpers<SC, LO, GO, NO>::Op2TpetraBlockCrs(A);
62 const Tpetra::BlockCrsMatrix<SC, LO, GO, NO>& tpP = Xpetra::Helpers<SC, LO, GO, NO>::Op2TpetraBlockCrs(P);
63 // Tpetra::BlockCrsMatrix<SC,LO,GO,NO> & tpAc = Xpetra::Helpers<SC,LO,GO,NO>::Op2NonConstTpetraBlockCrs(Ac);
64
65 using CRS = Tpetra::CrsMatrix<SC, LO, GO, NO>;
66 RCP<const CRS> Rcrs = Tpetra::convertToCrsMatrix(tpR);
67 RCP<const CRS> Acrs = Tpetra::convertToCrsMatrix(tpA);
68 RCP<const CRS> Pcrs = Tpetra::convertToCrsMatrix(tpP);
69 // RCP<CRS> Accrs = Tpetra::convertToCrsMatrix(tpAc);
70
71 // FIXME: The lines below only works because we're assuming Ac is Point
72 RCP<CRS> Accrs = Teuchos::rcp(new CRS(Rcrs->getRowMap(), 0));
73 const bool do_fill_complete = true;
74 Tpetra::TripleMatrixMultiply::MultiplyRAP(*Rcrs, transposeR, *Acrs, transposeA, *Pcrs, transposeP, *Accrs, do_fill_complete, label, params);
75
76 // Temporary output matrix
77 RCP<Tpetra::BlockCrsMatrix<SC, LO, GO, NO> > Ac_t = Tpetra::convertToBlockCrsMatrix(*Accrs, A.GetStorageBlockSize());
80
81 // We can now cheat and replace the innards of Ac
82 RCP<Xpetra::CrsMatrixWrap<SC, LO, GO, NO> > Ac_w = Teuchos::rcp_dynamic_cast<Xpetra::CrsMatrixWrap<SC, LO, GO, NO> >(Teuchos::rcpFromRef(Ac));
83 Ac_w->replaceCrsMatrix(Ac_p);
84 } else {
85 // Mix and match
86 TEUCHOS_TEST_FOR_EXCEPTION(1, Exceptions::RuntimeError, "Mix-and-match Crs/BlockCrs Multiply not currently supported");
87 }
88#else
89 throw(Xpetra::Exceptions::RuntimeError("Xpetra must be compiled with Tpetra."));
90#endif
91 }
92
93 if (call_FillComplete_on_result && !haveMultiplyDoFillComplete) {
95 fillParams->set("Optimize Storage", doOptimizeStorage);
96 Ac.fillComplete((transposeP) ? P.getRangeMap() : P.getDomainMap(),
97 (transposeR) ? R.getDomainMap() : R.getRangeMap(),
98 fillParams);
99 }
100
101 // transfer striding information
102 RCP<const Map> domainMap = Teuchos::null;
103 RCP<const Map> rangeMap = Teuchos::null;
104
105 const std::string stridedViewLabel("stridedMaps");
106 const size_t blkSize = 1;
107 std::vector<size_t> stridingInfo(1, blkSize);
108 LocalOrdinal stridedBlockId = -1;
109
110 if (R.IsView(stridedViewLabel)) {
111 rangeMap = transposeR ? R.getColMap(stridedViewLabel) : R.getRowMap(stridedViewLabel);
112 } else {
113 rangeMap = transposeR ? R.getDomainMap() : R.getRangeMap();
114 rangeMap = StridedMapFactory::Build(rangeMap, stridingInfo, stridedBlockId);
115 }
116
117 if (P.IsView(stridedViewLabel)) {
118 domainMap = transposeP ? P.getRowMap(stridedViewLabel) : P.getColMap(stridedViewLabel);
119 } else {
120 domainMap = transposeP ? P.getRangeMap() : P.getDomainMap();
121 domainMap = StridedMapFactory::Build(domainMap, stridingInfo, stridedBlockId);
122 }
123 Ac.CreateView(stridedViewLabel, rangeMap, domainMap);
124
125} // end Multiply
126
127} // end namespace Xpetra
128
129#define XPETRA_TRIPLEMATRIXMULTIPLY_SHORT
130
131#endif /* PACKAGES_XPETRA_SUP_UTILS_XPETRA_TRIPLEMATRIXMULTIPLY_DEF_HPP_ */
Exception throws to report errors in the internal logical of the program.
static RCP< Tpetra::CrsMatrix< SC, LO, GO, NO > > Op2NonConstTpetraCrs(RCP< Matrix > Op)
static RCP< const Tpetra::BlockCrsMatrix< SC, LO, GO, NO > > Op2TpetraBlockCrs(RCP< Matrix > Op)
static RCP< const Tpetra::CrsMatrix< SC, LO, GO, NO > > Op2TpetraCrs(RCP< Matrix > Op)
Xpetra-specific matrix class.
void CreateView(viewLabel_t viewLabel, const RCP< const Map > &rowMap, const RCP< const Map > &colMap)
virtual const RCP< const Map > & getRowMap() const
Returns the Map that describes the row distribution in this matrix.
virtual bool isFillComplete() const =0
Returns true if fillComplete() has been called and the matrix is in compute mode.
virtual const RCP< const Map > & getColMap() const
Returns the Map that describes the column distribution in this matrix. This might be null until fillC...
virtual void fillComplete(const RCP< const Map > &domainMap, const RCP< const Map > &rangeMap, const RCP< ParameterList > &params=null)=0
Signal that data entry is complete, specifying domain and range maps.
bool IsView(const viewLabel_t viewLabel) const
virtual LocalOrdinal GetStorageBlockSize() const =0
Returns the block size of the storage mechanism, which is usually 1, except for Tpetra::BlockCrsMatri...
virtual const Teuchos::RCP< const map_type > getDomainMap() const =0
The Map associated with the domain of this operator, which must be compatible with X....
virtual const Teuchos::RCP< const map_type > getRangeMap() const =0
The Map associated with the range of this operator, which must be compatible with Y....
static RCP< Xpetra::StridedMap< LocalOrdinal, GlobalOrdinal, Node > > Build(UnderlyingLib lib, global_size_t numGlobalElements, GlobalOrdinal indexBase, std::vector< size_t > &stridingInfo, const Teuchos::RCP< const Teuchos::Comm< int > > &comm, LocalOrdinal stridedBlockId=-1, GlobalOrdinal offset=0, LocalGlobal lg=Xpetra::GloballyDistributed)
Map constructor with Xpetra-defined contiguous uniform distribution.
static void MultiplyRAP(const Matrix &R, bool transposeR, const Matrix &A, bool transposeA, const Matrix &P, bool transposeP, Matrix &Ac, bool call_FillComplete_on_result=true, bool doOptimizeStorage=true, const std::string &label=std::string(), const RCP< ParameterList > &params=null)
#define TEUCHOS_TEST_FOR_EXCEPTION(throw_exception_test, Exception, msg)
TEUCHOS_DEPRECATED RCP< T > rcp(T *p, Dealloc_T dealloc, bool owns_mem)