48 #ifndef PACKAGES_XPETRA_SUP_UTILS_XPETRA_MATRIXMATRIX_HPP_ 49 #define PACKAGES_XPETRA_SUP_UTILS_XPETRA_MATRIXMATRIX_HPP_ 62 #ifdef HAVE_XPETRA_EPETRA 66 #ifdef HAVE_XPETRA_EPETRAEXT 67 #include <EpetraExt_MatrixMatrix.h> 68 #include <EpetraExt_RowMatrixOut.h> 69 #include <Epetra_RowMatrixTransposer.h> 70 #endif // HAVE_XPETRA_EPETRAEXT 72 #ifdef HAVE_XPETRA_TPETRA 73 #include <TpetraExt_MatrixMatrix.hpp> 74 #include <MatrixMarket_Tpetra.hpp> 78 #endif // HAVE_XPETRA_TPETRA 88 template <
class Scalar,
89 class LocalOrdinal = int,
90 class GlobalOrdinal = LocalOrdinal,
97 #ifdef HAVE_XPETRA_EPETRA 102 "Cast from Xpetra::Matrix to Xpetra::CrsMatrixWrap failed");
107 "Cast from Xpetra::CrsMatrix to Xpetra::EpetraCrsMatrix failed");
109 return tmp_ECrsMtx->getEpetra_CrsMatrix();
117 "Cast from Xpetra::Matrix to Xpetra::CrsMatrixWrap failed");
121 TEUCHOS_TEST_FOR_EXCEPTION(tmp_ECrsMtx == Teuchos::null,
Exceptions::BadCast,
"Cast from Xpetra::CrsMatrix to Xpetra::EpetraCrsMatrix failed");
123 return tmp_ECrsMtx->getEpetra_CrsMatrixNonConst();
133 "Cast from Xpetra::CrsMatrix to Xpetra::EpetraCrsMatrix failed");
135 return *tmp_ECrsMtx->getEpetra_CrsMatrix();
151 return *Teuchos::rcp_const_cast<Epetra_CrsMatrix>(tmp_ECrsMtx->getEpetra_CrsMatrix());
157 #endif // HAVE_XPETRA_EPETRA 159 #ifdef HAVE_XPETRA_TPETRA 167 TEUCHOS_TEST_FOR_EXCEPTION(tmp_ECrsMtx == Teuchos::null,
Xpetra::Exceptions::BadCast,
"Cast from Xpetra::CrsMatrix to Xpetra::TpetraCrsMatrix failed");
169 return tmp_ECrsMtx->getTpetra_CrsMatrix();
178 TEUCHOS_TEST_FOR_EXCEPTION(tmp_ECrsMtx == Teuchos::null,
Xpetra::Exceptions::BadCast,
"Cast from Xpetra::CrsMatrix to Xpetra::TpetraCrsMatrix failed");
180 return tmp_ECrsMtx->getTpetra_CrsMatrixNonConst();
191 return *tmp_TCrsMtx->getTpetra_CrsMatrix();
206 return *Teuchos::rcp_const_cast<Tpetra::CrsMatrix<Scalar, LocalOrdinal, GlobalOrdinal, Node> >(tmp_TCrsMtx->getTpetra_CrsMatrix());
212 #endif // HAVE_XPETRA_TPETRA 216 template <
class Scalar,
218 class GlobalOrdinal ,
221 #undef XPETRA_MATRIXMATRIX_SHORT 251 const Matrix& B,
bool transposeB,
253 bool call_FillComplete_on_result =
true,
254 bool doOptimizeStorage =
true,
255 const std::string & label = std::string(),
266 bool haveMultiplyDoFillComplete = call_FillComplete_on_result && doOptimizeStorage;
269 #if defined(HAVE_XPETRA_EPETRA) && defined(HAVE_XPETRA_EPETRAEXT) 270 throw(
Xpetra::Exceptions::RuntimeError(
"Xpetra::MatrixMatrix::Multiply only available for GO=int or GO=long long with EpetraNode (Serial or OpenMP depending on configuration)"));
276 #ifdef HAVE_XPETRA_TPETRA 283 Tpetra::MatrixMatrix::Multiply(tpA, transposeA, tpB, transposeB, tpC, haveMultiplyDoFillComplete, label, params);
289 if (call_FillComplete_on_result && !haveMultiplyDoFillComplete) {
291 fillParams->
set(
"Optimize Storage", doOptimizeStorage);
300 C.
CreateView(
"stridedMaps", rcpA, transposeA, rcpB, transposeB);
327 bool doFillComplete =
true,
328 bool doOptimizeStorage =
true,
329 const std::string & label = std::string(),
338 if (C == Teuchos::null) {
339 double nnzPerRow = Teuchos::as<double>(0);
348 nnzPerRow *= nnzPerRow;
351 if (totalNnz < minNnz)
355 fos <<
"Matrix product nnz per row estimate = " << Teuchos::as<LO>(nnzPerRow) << std::endl;
363 fos <<
"Reuse C pattern" << std::endl;
366 Multiply(A, transposeA, B, transposeB, *C, doFillComplete, doOptimizeStorage, label, params);
382 bool callFillCompleteOnResult =
true,
bool doOptimizeStorage =
true,
const std::string& label = std::string(),
384 return Multiply(A, transposeA, B, transposeB, Teuchos::null, fos, callFillCompleteOnResult, doOptimizeStorage, label, params);
387 #ifdef HAVE_XPETRA_EPETRAEXT 390 const Epetra_CrsMatrix& epB,
392 throw(
Xpetra::Exceptions::RuntimeError(
"MLTwoMatrixMultiply only available for GO=int or GO=long long with EpetraNode (Serial or OpenMP depending on configuration)"));
393 return Teuchos::null;
395 #endif //ifdef HAVE_XPETRA_EPETRAEXT 410 bool doFillComplete =
true,
411 bool doOptimizeStorage =
true) {
413 "TwoMatrixMultiply for BlockedCrsMatrix not implemented for transposeA==true or transposeB==true");
424 for (
size_t i = 0; i < A.
Rows(); ++i) {
425 for (
size_t j = 0; j < B.
Cols(); ++j) {
428 for (
size_t l = 0; l < B.
Rows(); ++l) {
434 if (crmat1->getGlobalNumEntries() == 0 || crmat2->getGlobalNumEntries() == 0)
444 if(crop1 != Teuchos::null && crop2 != Teuchos::null)
445 temp = Multiply (*crop1,
false, *crop2,
false, fos);
450 TEUCHOS_TEST_FOR_EXCEPTION(bop2.is_null()==
true,
Xpetra::Exceptions::BadCast,
"B is not a BlockedCrsMatrix. (TwoMatrixMultiplyBlock)");
451 TEUCHOS_TEST_FOR_EXCEPTION(bop1->Cols()!=bop2->Rows(),
Xpetra::Exceptions::RuntimeError,
"A has " << bop1->Cols() <<
" columns and B has " << bop2->Rows() <<
" rows. Matrices are not compatible! (TwoMatrixMultiplyBlock)");
452 TEUCHOS_TEST_FOR_EXCEPTION(bop1->getDomainMap()->isSameAs(*(bop2->getRangeMap()))==
false,
Xpetra::Exceptions::RuntimeError,
"Domain map of A is not the same as range map of B. Matrices are not compatible! (TwoMatrixMultiplyBlock)");
455 temp = TwoMatrixMultiplyBlock(*bop1, transposeA, *bop2, transposeB, fos, doFillComplete, doOptimizeStorage);
458 TEUCHOS_TEST_FOR_EXCEPTION(btemp->Rows()!=bop1->Rows(),
Xpetra::Exceptions::RuntimeError,
"Number of block rows of local blocked operator is " << btemp->Rows() <<
" but should be " << bop1->Rows() <<
". (TwoMatrixMultiplyBlock)");
459 TEUCHOS_TEST_FOR_EXCEPTION(btemp->Cols()!=bop2->Cols(),
Xpetra::Exceptions::RuntimeError,
"Number of block cols of local blocked operator is " << btemp->Cols() <<
" but should be " << bop2->Cols() <<
". (TwoMatrixMultiplyBlock)");
460 TEUCHOS_TEST_FOR_EXCEPTION(btemp->getRangeMapExtractor()->getFullMap()->isSameAs(*(bop1->getRangeMapExtractor()->getFullMap())) ==
false,
Xpetra::Exceptions::RuntimeError,
"Range map of local blocked operator should be same as first operator. (TwoMatrixMultiplyBlock)");
461 TEUCHOS_TEST_FOR_EXCEPTION(btemp->getDomainMapExtractor()->getFullMap()->isSameAs(*(bop2->getDomainMapExtractor()->getFullMap())) ==
false,
Xpetra::Exceptions::RuntimeError,
"Domain map of local blocked operator should be same as second operator. (TwoMatrixMultiplyBlock)");
462 TEUCHOS_TEST_FOR_EXCEPTION(btemp->getRangeMapExtractor()->getThyraMode() != bop1->getRangeMapExtractor()->getThyraMode(),
Xpetra::Exceptions::RuntimeError,
"Thyra mode of local range map extractor incompatible with range map extractor of A (TwoMatrixMultiplyBlock)");
463 TEUCHOS_TEST_FOR_EXCEPTION(btemp->getDomainMapExtractor()->getThyraMode() != bop2->getDomainMapExtractor()->getThyraMode(),
Xpetra::Exceptions::RuntimeError,
"Thyra mode of local domain map extractor incompatible with domain map extractor of B (TwoMatrixMultiplyBlock)");
478 if (Cij->isFillComplete())
481 C->setMatrix(i, j, Cij);
483 C->setMatrix(i, j, Teuchos::null);
511 throw Exceptions::RuntimeError(
"TwoMatrixAdd for Epetra matrices needs <double,int,int> for Scalar, LocalOrdinal and GlobalOrdinal.");
513 #ifdef HAVE_XPETRA_TPETRA 517 Tpetra::MatrixMatrix::Add(tpA, transposeA, alpha, tpB, beta);
538 const Matrix& B,
bool transposeB,
const SC& beta,
550 if(rcpBopA == Teuchos::null && rcpBopB == Teuchos::null) {
556 if (C == Teuchos::null) {
559 size_t numLocalRows = 0;
565 if (maxNzInA == 1 || maxNzInB == 1 || AHasFixedNnzPerRow) {
570 if ((maxNzInA == 1 && maxNzInB > 1) || AHasFixedNnzPerRow) {
571 for (
size_t i = 0; i < numLocalRows; ++i)
575 for (
size_t i = 0; i < numLocalRows; ++i)
579 fos <<
"MatrixMatrix::TwoMatrixAdd : special case detected (one matrix has a fixed nnz per row)" 580 <<
", using static profiling" << std::endl;
586 LO nnzToAllocate = Teuchos::as<LO>( (nnzPerRowInA + nnzPerRowInB) * 1.5) + Teuchos::as<LO>(1);
593 fos <<
"nnzPerRowInA = " << nnzPerRowInA <<
", nnzPerRowInB = " << nnzPerRowInB << std::endl;
594 fos <<
"MatrixMatrix::TwoMatrixAdd : space allocated per row = " << nnzToAllocate
595 <<
", max possible nnz per row in sum = " << maxPossible
601 fos <<
"MatrixMatrix::TwoMatrixAdd : ** WARNING ** estimate could be badly wrong because second summand is transposed" << std::endl;
607 #ifdef HAVE_XPETRA_TPETRA 612 Tpetra::MatrixMatrix::Add(tpA, transposeA, alpha, tpB, transposeB, beta, tpC);
618 if (A.
IsView(
"stridedMaps")) C->CreateView(
"stridedMaps", rcpFromRef(A));
619 if (B.
IsView(
"stridedMaps")) C->CreateView(
"stridedMaps", rcpFromRef(B));
623 else if(rcpBopA == Teuchos::null && rcpBopB != Teuchos::null) {
631 for (
size_t j = 0; j < rcpBopB->Cols(); ++j) {
633 if(rcpA != Teuchos::null &&
634 rcpBopB->getMatrix(i,j)!=Teuchos::null) {
636 TwoMatrixAdd(*rcpA, transposeA, alpha,
637 *(rcpBopB->getMatrix(i,j)), transposeB, beta,
638 Cij, fos, AHasFixedNnzPerRow);
639 }
else if (rcpA == Teuchos::null &&
640 rcpBopB->getMatrix(i,j)!=Teuchos::null) {
641 Cij = rcpBopB->getMatrix(i,j);
642 }
else if (rcpA != Teuchos::null &&
643 rcpBopB->getMatrix(i,j)==Teuchos::null) {
644 Cij = Teuchos::rcp_const_cast<
Matrix>(rcpA);
650 if (Cij->isFillComplete())
653 bC->setMatrix(i, j, Cij);
655 bC->setMatrix(i, j, Teuchos::null);
660 else if(rcpBopA != Teuchos::null && rcpBopB == Teuchos::null) {
667 for (
size_t i = 0; i < rcpBopA->Rows(); ++i) {
669 if(rcpBopA->getMatrix(i,j)!=Teuchos::null &&
670 rcpB!=Teuchos::null) {
672 TwoMatrixAdd(*(rcpBopA->getMatrix(i,j)), transposeA, alpha,
673 *rcpB, transposeB, beta,
674 Cij, fos, AHasFixedNnzPerRow);
675 }
else if (rcpBopA->getMatrix(i,j) == Teuchos::null &&
676 rcpB!=Teuchos::null) {
677 Cij = Teuchos::rcp_const_cast<
Matrix>(rcpB);
678 }
else if (rcpBopA->getMatrix(i,j) != Teuchos::null &&
679 rcpB==Teuchos::null) {
680 Cij = rcpBopA->getMatrix(i,j);
686 if (Cij->isFillComplete())
689 bC->setMatrix(i, j, Cij);
691 bC->setMatrix(i, j, Teuchos::null);
713 for (
size_t i = 0; i < rcpBopA->Rows(); ++i) {
714 for (
size_t j = 0; j < rcpBopB->Cols(); ++j) {
717 if(rcpBopA->getMatrix(i,j)!=Teuchos::null &&
718 rcpBopB->getMatrix(i,j)!=Teuchos::null) {
720 TwoMatrixAdd(*(rcpBopA->getMatrix(i,j)), transposeA, alpha,
721 *(rcpBopB->getMatrix(i,j)), transposeB, beta,
722 Cij, fos, AHasFixedNnzPerRow);
723 }
else if (rcpBopA->getMatrix(i,j) == Teuchos::null &&
724 rcpBopB->getMatrix(i,j)!=Teuchos::null) {
725 Cij = rcpBopB->getMatrix(i,j);
726 }
else if (rcpBopA->getMatrix(i,j) != Teuchos::null &&
727 rcpBopB->getMatrix(i,j)==Teuchos::null) {
728 Cij = rcpBopA->getMatrix(i,j);
734 if (Cij->isFillComplete())
737 bC->setMatrix(i, j, Cij);
739 bC->setMatrix(i, j, Teuchos::null);
751 #ifdef HAVE_XPETRA_EPETRA 788 const Matrix& B,
bool transposeB,
790 bool call_FillComplete_on_result =
true,
791 bool doOptimizeStorage =
true,
792 const std::string & label = std::string(),
802 bool haveMultiplyDoFillComplete = call_FillComplete_on_result && doOptimizeStorage;
805 #if defined(HAVE_XPETRA_EPETRA) && defined(HAVE_XPETRA_EPETRAEXT) 810 int i = EpetraExt::MatrixMatrix::Multiply(epA, transposeA, epB, transposeB, epC, haveMultiplyDoFillComplete);
811 if (haveMultiplyDoFillComplete) {
822 std::ostringstream buf;
824 std::string msg =
"EpetraExt::MatrixMatrix::Multiply return value of " + buf.str();
832 #ifdef HAVE_XPETRA_TPETRA 833 # if ((defined(EPETRA_HAVE_OMP) && (!defined(HAVE_TPETRA_INST_OPENMP) || !defined(HAVE_TPETRA_INST_INT_INT))) || \ 834 (!defined(EPETRA_HAVE_OMP) && (!defined(HAVE_TPETRA_INST_SERIAL) || !defined(HAVE_TPETRA_INST_INT_INT)))) 843 Tpetra::MatrixMatrix::Multiply(tpA, transposeA, tpB, transposeB, tpC, haveMultiplyDoFillComplete, label, params);
850 if (call_FillComplete_on_result && !haveMultiplyDoFillComplete) {
852 fillParams->
set(
"Optimize Storage",doOptimizeStorage);
861 C.
CreateView(
"stridedMaps", rcpA, transposeA, rcpB, transposeB);
887 const Matrix& B,
bool transposeB,
890 bool doFillComplete =
true,
891 bool doOptimizeStorage =
true,
892 const std::string & label = std::string(),
900 #if defined(HAVE_XPETRA_EPETRA) && defined(HAVE_XPETRA_EPETRAEXT) && defined(HAVE_XPETRA_ML_MMM) 906 RCP<Matrix> C = Convert_Epetra_CrsMatrix_ToXpetra_CrsMatrixWrap<SC,LO,GO,NO> (epC);
907 if (doFillComplete) {
909 fillParams->
set(
"Optimize Storage", doOptimizeStorage);
916 C->CreateView(
"stridedMaps", rcpFromRef(A), transposeA, rcpFromRef(B), transposeB);
920 #endif // EPETRA + EPETRAEXT + ML 925 if (C == Teuchos::null) {
926 double nnzPerRow = Teuchos::as<double>(0);
935 nnzPerRow *= nnzPerRow;
938 if (totalNnz < minNnz)
942 fos <<
"Matrix product nnz per row estimate = " << Teuchos::as<LO>(nnzPerRow) << std::endl;
951 fos <<
"Reuse C pattern" << std::endl;
954 Multiply(A, transposeA, B, transposeB, *C, doFillComplete, doOptimizeStorage, label, params);
970 const Matrix& B,
bool transposeB,
972 bool callFillCompleteOnResult =
true,
973 bool doOptimizeStorage =
true,
974 const std::string & label = std::string(),
976 return Multiply(A, transposeA, B, transposeB, Teuchos::null, fos, callFillCompleteOnResult, doOptimizeStorage, label, params);
979 #if defined(HAVE_XPETRA_EPETRA) && defined(HAVE_XPETRA_EPETRAEXT) 982 const Epetra_CrsMatrix& epB,
984 #if defined(HAVE_XPETRA_ML_MMM) // Note: this is currently not supported 986 ML_Comm_Create(&comm);
987 fos <<
"****** USING ML's MATRIX MATRIX MULTIPLY ******" << std::endl;
990 const Epetra_MpiComm * Mcomm =
dynamic_cast<const Epetra_MpiComm*
>(&(epA.Comm()));
992 ML_Comm_Set_UsrComm(comm,Mcomm->GetMpiComm());
995 EpetraExt::CrsMatrix_SolverMap Atransform;
996 EpetraExt::CrsMatrix_SolverMap Btransform;
997 const Epetra_CrsMatrix& A = Atransform(const_cast<Epetra_CrsMatrix&>(epA));
998 const Epetra_CrsMatrix& B = Btransform(const_cast<Epetra_CrsMatrix&>(epB));
1004 ML_Operator* ml_As = ML_Operator_Create(comm);
1005 ML_Operator* ml_Bs = ML_Operator_Create(comm);
1006 ML_Operator_WrapEpetraCrsMatrix(const_cast<Epetra_CrsMatrix*>(&A),ml_As);
1007 ML_Operator_WrapEpetraCrsMatrix(const_cast<Epetra_CrsMatrix*>(&B),ml_Bs);
1008 ML_Operator* ml_AtimesB = ML_Operator_Create(comm);
1011 ML_2matmult(ml_As,ml_Bs,ml_AtimesB,ML_CSR_MATRIX);
1013 ML_Operator_Destroy(&ml_As);
1014 ML_Operator_Destroy(&ml_Bs);
1019 int N_local = ml_AtimesB->invec_leng;
1020 ML_CommInfoOP* getrow_comm = ml_AtimesB->getrow->pre_comm;
1022 ML_Comm* comm_AB = ml_AtimesB->comm;
1023 if (N_local != B.DomainMap().NumMyElements())
1028 for (
int i = 0; i < getrow_comm->N_neighbors; i++) {
1029 N_rcvd += (getrow_comm->neighbors)[i].N_rcv;
1030 N_send += (getrow_comm->neighbors)[i].N_send;
1031 if ( ((getrow_comm->neighbors)[i].N_rcv != 0) &&
1032 ((getrow_comm->neighbors)[i].rcv_list != NULL) ) flag = 1;
1036 std::vector<double> dtemp(N_local + N_rcvd + 1);
1037 std::vector<int> cmap (N_local + N_rcvd + 1);
1038 for (
int i = 0; i < N_local; ++i) {
1039 cmap[i] = B.DomainMap().GID(i);
1040 dtemp[i] = (double) cmap[i];
1042 ML_cheap_exchange_bdry(&dtemp[0],getrow_comm,N_local,N_send,comm_AB);
1044 int count = N_local;
1045 const int neighbors = getrow_comm->N_neighbors;
1046 for (
int i = 0; i < neighbors; i++) {
1047 const int nrcv = getrow_comm->neighbors[i].N_rcv;
1048 for (
int j = 0; j < nrcv; j++)
1049 cmap[getrow_comm->neighbors[i].rcv_list[j]] = (
int) dtemp[count++];
1052 for (
int i = 0; i < N_local+N_rcvd; ++i)
1053 cmap[i] = (
int)dtemp[i];
1058 Epetra_Map gcmap(-1, N_local+N_rcvd, &cmap[0], B.ColMap().IndexBase(), A.Comm());
1065 const int myrowlength = A.RowMap().NumMyElements();
1066 const Epetra_Map& rowmap = A.RowMap();
1071 int educatedguess = 0;
1072 for (
int i = 0; i < myrowlength; ++i) {
1074 ML_get_matrix_row(ml_AtimesB, 1, &i, &allocated, &bindx, &val, &rowlength, 0);
1075 if (rowlength>educatedguess)
1076 educatedguess = rowlength;
1082 std::vector<int> gcid(educatedguess);
1083 for (
int i = 0; i < myrowlength; ++i) {
1084 const int grid = rowmap.GID(i);
1086 ML_get_matrix_row(ml_AtimesB, 1, &i, &allocated, &bindx, &val, &rowlength, 0);
1087 if (!rowlength)
continue;
1088 if ((
int)gcid.size() < rowlength) gcid.resize(rowlength);
1089 for (
int j = 0; j < rowlength; ++j) {
1090 gcid[j] = gcmap.GID(bindx[j]);
1094 int err = result->InsertGlobalValues(grid, rowlength, val, &gcid[0]);
1095 if (err != 0 && err != 1) {
1096 std::ostringstream errStr;
1097 errStr <<
"Epetra_CrsMatrix::InsertGlobalValues returned err=" << err;
1102 if (bindx) ML_free(bindx);
1103 if (val) ML_free(val);
1104 ML_Operator_Destroy(&ml_AtimesB);
1105 ML_Comm_Destroy(&comm);
1108 #else // no MUELU_ML 1110 "No ML multiplication available. This feature is currently not supported by Xpetra.");
1111 return Teuchos::null;
1114 #endif //ifdef HAVE_XPETRA_EPETRAEXT 1129 bool doFillComplete =
true,
1130 bool doOptimizeStorage =
true) {
1132 "TwoMatrixMultiply for BlockedCrsMatrix not implemented for transposeA==true or transposeB==true");
1143 for (
size_t i = 0; i < A.
Rows(); ++i) {
1144 for (
size_t j = 0; j < B.
Cols(); ++j) {
1147 for (
size_t l = 0; l < B.
Rows(); ++l) {
1153 if (crmat1->getGlobalNumEntries() == 0 || crmat2->getGlobalNumEntries() == 0)
1163 if(crop1 != Teuchos::null && crop2 != Teuchos::null)
1164 temp = Multiply (*crop1,
false, *crop2,
false, fos);
1169 TEUCHOS_TEST_FOR_EXCEPTION(bop2.is_null()==
true,
Xpetra::Exceptions::BadCast,
"B is not a BlockedCrsMatrix. (TwoMatrixMultiplyBlock)");
1170 TEUCHOS_TEST_FOR_EXCEPTION(bop1->Cols()!=bop2->Rows(),
Xpetra::Exceptions::RuntimeError,
"A has " << bop1->Cols() <<
" columns and B has " << bop2->Rows() <<
" rows. Matrices are not compatible! (TwoMatrixMultiplyBlock)");
1171 TEUCHOS_TEST_FOR_EXCEPTION(bop1->getDomainMap()->isSameAs(*(bop2->getRangeMap()))==
false,
Xpetra::Exceptions::RuntimeError,
"Domain map of A is not the same as range map of B. Matrices are not compatible! (TwoMatrixMultiplyBlock)");
1174 temp = TwoMatrixMultiplyBlock(*bop1, transposeA, *bop2, transposeB, fos, doFillComplete, doOptimizeStorage);
1177 TEUCHOS_TEST_FOR_EXCEPTION(btemp->Rows()!=bop1->Rows(),
Xpetra::Exceptions::RuntimeError,
"Number of block rows of local blocked operator is " << btemp->Rows() <<
" but should be " << bop1->Rows() <<
". (TwoMatrixMultiplyBlock)");
1178 TEUCHOS_TEST_FOR_EXCEPTION(btemp->Cols()!=bop2->Cols(),
Xpetra::Exceptions::RuntimeError,
"Number of block cols of local blocked operator is " << btemp->Cols() <<
" but should be " << bop2->Cols() <<
". (TwoMatrixMultiplyBlock)");
1179 TEUCHOS_TEST_FOR_EXCEPTION(btemp->getRangeMapExtractor()->getFullMap()->isSameAs(*(bop1->getRangeMapExtractor()->getFullMap())) ==
false,
Xpetra::Exceptions::RuntimeError,
"Range map of local blocked operator should be same as first operator. (TwoMatrixMultiplyBlock)");
1180 TEUCHOS_TEST_FOR_EXCEPTION(btemp->getDomainMapExtractor()->getFullMap()->isSameAs(*(bop2->getDomainMapExtractor()->getFullMap())) ==
false,
Xpetra::Exceptions::RuntimeError,
"Domain map of local blocked operator should be same as second operator. (TwoMatrixMultiplyBlock)");
1181 TEUCHOS_TEST_FOR_EXCEPTION(btemp->getRangeMapExtractor()->getThyraMode() != bop1->getRangeMapExtractor()->getThyraMode(),
Xpetra::Exceptions::RuntimeError,
"Thyra mode of local range map extractor incompatible with range map extractor of A (TwoMatrixMultiplyBlock)");
1182 TEUCHOS_TEST_FOR_EXCEPTION(btemp->getDomainMapExtractor()->getThyraMode() != bop2->getDomainMapExtractor()->getThyraMode(),
Xpetra::Exceptions::RuntimeError,
"Thyra mode of local domain map extractor incompatible with domain map extractor of B (TwoMatrixMultiplyBlock)");
1197 if (Cij->isFillComplete())
1200 C->setMatrix(i, j, Cij);
1202 C->setMatrix(i, j, Teuchos::null);
1227 "TwoMatrixAdd: matrix row maps are not the same.");
1230 #if defined(HAVE_XPETRA_EPETRA) && defined(HAVE_XPETRA_EPETRAEXT) 1235 int rv = EpetraExt::MatrixMatrix::Add(epA, transposeA, alpha, epB, beta);
1239 std::ostringstream buf;
1244 #ifdef HAVE_XPETRA_TPETRA 1245 # if ((defined(EPETRA_HAVE_OMP) && (!defined(HAVE_TPETRA_INST_OPENMP) || !defined(HAVE_TPETRA_INST_INT_INT))) || \ 1246 (!defined(EPETRA_HAVE_OMP) && (!defined(HAVE_TPETRA_INST_SERIAL) || !defined(HAVE_TPETRA_INST_INT_INT)))) 1252 Tpetra::MatrixMatrix::Add(tpA, transposeA, alpha, tpB, beta);
1274 const Matrix& B,
bool transposeB,
const SC& beta,
1281 if(rcpBopA == Teuchos::null && rcpBopB == Teuchos::null) {
1287 if (C == Teuchos::null) {
1288 size_t maxNzInA = 0;
1289 size_t maxNzInB = 0;
1290 size_t numLocalRows = 0;
1298 if (maxNzInA == 1 || maxNzInB == 1 || AHasFixedNnzPerRow) {
1303 if ((maxNzInA == 1 && maxNzInB > 1) || AHasFixedNnzPerRow) {
1304 for (
size_t i = 0; i < numLocalRows; ++i)
1308 for (
size_t i = 0; i < numLocalRows; ++i)
1312 fos <<
"MatrixMatrix::TwoMatrixAdd : special case detected (one matrix has a fixed nnz per row)" 1313 <<
", using static profiling" << std::endl;
1320 LO nnzToAllocate = Teuchos::as<LO>( (nnzPerRowInA + nnzPerRowInB) * 1.5) + Teuchos::as<LO>(1);
1327 fos <<
"nnzPerRowInA = " << nnzPerRowInA <<
", nnzPerRowInB = " << nnzPerRowInB << std::endl;
1328 fos <<
"MatrixMatrix::TwoMatrixAdd : space allocated per row = " << nnzToAllocate
1329 <<
", max possible nnz per row in sum = " << maxPossible
1335 fos <<
"MatrixMatrix::TwoMatrixAdd : ** WARNING ** estimate could be badly wrong because second summand is transposed" << std::endl;
1339 #if defined(HAVE_XPETRA_EPETRA) && defined(HAVE_XPETRA_EPETRAEXT) 1343 Epetra_CrsMatrix* ref2epC = &*epC;
1346 int rv = EpetraExt::MatrixMatrix::Add(epA, transposeA, alpha, epB, transposeB, beta, ref2epC);
1354 #ifdef HAVE_XPETRA_TPETRA 1355 # if ((defined(EPETRA_HAVE_OMP) && (!defined(HAVE_TPETRA_INST_OPENMP) || !defined(HAVE_TPETRA_INST_INT_INT))) || \ 1356 (!defined(EPETRA_HAVE_OMP) && (!defined(HAVE_TPETRA_INST_SERIAL) || !defined(HAVE_TPETRA_INST_INT_INT)))) 1363 Tpetra::MatrixMatrix::Add(tpA, transposeA, alpha, tpB, transposeB, beta, tpC);
1371 if (A.
IsView(
"stridedMaps")) C->CreateView(
"stridedMaps", rcpFromRef(A));
1372 if (B.
IsView(
"stridedMaps")) C->CreateView(
"stridedMaps", rcpFromRef(B));
1376 else if(rcpBopA == Teuchos::null && rcpBopB != Teuchos::null) {
1384 for (
size_t j = 0; j < rcpBopB->Cols(); ++j) {
1386 if(rcpA != Teuchos::null &&
1387 rcpBopB->getMatrix(i,j)!=Teuchos::null) {
1389 TwoMatrixAdd(*rcpA, transposeA, alpha,
1390 *(rcpBopB->getMatrix(i,j)), transposeB, beta,
1391 Cij, fos, AHasFixedNnzPerRow);
1392 }
else if (rcpA == Teuchos::null &&
1393 rcpBopB->getMatrix(i,j)!=Teuchos::null) {
1394 Cij = rcpBopB->getMatrix(i,j);
1395 }
else if (rcpA != Teuchos::null &&
1396 rcpBopB->getMatrix(i,j)==Teuchos::null) {
1397 Cij = Teuchos::rcp_const_cast<
Matrix>(rcpA);
1399 Cij = Teuchos::null;
1403 if (Cij->isFillComplete())
1405 Cij->fillComplete();
1406 bC->setMatrix(i, j, Cij);
1408 bC->setMatrix(i, j, Teuchos::null);
1413 else if(rcpBopA != Teuchos::null && rcpBopB == Teuchos::null) {
1421 for (
size_t i = 0; i < rcpBopA->Rows(); ++i) {
1423 if(rcpBopA->getMatrix(i,j)!=Teuchos::null &&
1424 rcpB!=Teuchos::null) {
1426 TwoMatrixAdd(*(rcpBopA->getMatrix(i,j)), transposeA, alpha,
1427 *rcpB, transposeB, beta,
1428 Cij, fos, AHasFixedNnzPerRow);
1429 }
else if (rcpBopA->getMatrix(i,j) == Teuchos::null &&
1430 rcpB!=Teuchos::null) {
1431 Cij = Teuchos::rcp_const_cast<
Matrix>(rcpB);
1432 }
else if (rcpBopA->getMatrix(i,j) != Teuchos::null &&
1433 rcpB==Teuchos::null) {
1434 Cij = rcpBopA->getMatrix(i,j);
1436 Cij = Teuchos::null;
1440 if (Cij->isFillComplete())
1442 Cij->fillComplete();
1443 bC->setMatrix(i, j, Cij);
1445 bC->setMatrix(i, j, Teuchos::null);
1468 for (
size_t i = 0; i < rcpBopA->Rows(); ++i) {
1469 for (
size_t j = 0; j < rcpBopB->Cols(); ++j) {
1472 if(rcpBopA->getMatrix(i,j)!=Teuchos::null &&
1473 rcpBopB->getMatrix(i,j)!=Teuchos::null) {
1476 TwoMatrixAdd(*(rcpBopA->getMatrix(i,j)), transposeA, alpha,
1477 *(rcpBopB->getMatrix(i,j)), transposeB, beta,
1478 Cij, fos, AHasFixedNnzPerRow);
1479 }
else if (rcpBopA->getMatrix(i,j) == Teuchos::null &&
1480 rcpBopB->getMatrix(i,j)!=Teuchos::null) {
1481 Cij = rcpBopB->getMatrix(i,j);
1482 }
else if (rcpBopA->getMatrix(i,j) != Teuchos::null &&
1483 rcpBopB->getMatrix(i,j)==Teuchos::null) {
1484 Cij = rcpBopA->getMatrix(i,j);
1486 Cij = Teuchos::null;
1490 if (Cij->isFillComplete())
1493 Cij->fillComplete();
1494 bC->setMatrix(i, j, Cij);
1496 bC->setMatrix(i, j, Teuchos::null);
1541 const Matrix& B,
bool transposeB,
1543 bool call_FillComplete_on_result =
true,
1544 bool doOptimizeStorage =
true,
1545 const std::string & label = std::string(),
1556 bool haveMultiplyDoFillComplete = call_FillComplete_on_result && doOptimizeStorage;
1559 #if defined(HAVE_XPETRA_EPETRA) && defined(HAVE_XPETRA_EPETRAEXT) 1564 int i = EpetraExt::MatrixMatrix::Multiply(epA, transposeA, epB, transposeB, epC, haveMultiplyDoFillComplete);
1565 if (haveMultiplyDoFillComplete) {
1576 std::ostringstream buf;
1578 std::string msg =
"EpetraExt::MatrixMatrix::Multiply return value of " + buf.str();
1586 #ifdef HAVE_XPETRA_TPETRA 1587 # if ((defined(EPETRA_HAVE_OMP) && (!defined(HAVE_TPETRA_INST_OPENMP) || !defined(HAVE_TPETRA_INST_INT_LONG_LONG))) || \ 1588 (!defined(EPETRA_HAVE_OMP) && (!defined(HAVE_TPETRA_INST_SERIAL) || !defined(HAVE_TPETRA_INST_INT_LONG_LONG)))) 1597 Tpetra::MatrixMatrix::Multiply(tpA, transposeA, tpB, transposeB, tpC, haveMultiplyDoFillComplete, label, params);
1604 if(call_FillComplete_on_result && !haveMultiplyDoFillComplete) {
1606 fillParams->
set(
"Optimize Storage",doOptimizeStorage);
1615 C.
CreateView(
"stridedMaps", rcpA, transposeA, rcpB, transposeB);
1641 const Matrix& B,
bool transposeB,
1644 bool doFillComplete =
true,
1645 bool doOptimizeStorage =
true,
1646 const std::string & label = std::string(),
1655 if (C == Teuchos::null) {
1656 double nnzPerRow = Teuchos::as<double>(0);
1665 nnzPerRow *= nnzPerRow;
1668 if (totalNnz < minNnz)
1672 fos <<
"Matrix product nnz per row estimate = " << Teuchos::as<LO>(nnzPerRow) << std::endl;
1680 fos <<
"Reuse C pattern" << std::endl;
1683 Multiply(A, transposeA, B, transposeB, *C, doFillComplete, doOptimizeStorage, label, params);
1699 const Matrix& B,
bool transposeB,
1701 bool callFillCompleteOnResult =
true,
1702 bool doOptimizeStorage =
true,
1703 const std::string & label = std::string(),
1705 return Multiply(A, transposeA, B, transposeB, Teuchos::null, fos, callFillCompleteOnResult, doOptimizeStorage, label, params);
1708 #if defined(HAVE_XPETRA_EPETRA) && defined(HAVE_XPETRA_EPETRAEXT) 1711 const Epetra_CrsMatrix& epB,
1714 "No ML multiplication available. This feature is currently not supported by Xpetra.");
1715 return Teuchos::null;
1717 #endif //ifdef HAVE_XPETRA_EPETRAEXT 1732 bool doFillComplete =
true,
1733 bool doOptimizeStorage =
true) {
1735 "TwoMatrixMultiply for BlockedCrsMatrix not implemented for transposeA==true or transposeB==true");
1746 for (
size_t i = 0; i < A.
Rows(); ++i) {
1747 for (
size_t j = 0; j < B.
Cols(); ++j) {
1750 for (
size_t l = 0; l < B.
Rows(); ++l) {
1756 if (crmat1->getGlobalNumEntries() == 0 || crmat2->getGlobalNumEntries() == 0)
1766 if(crop1 != Teuchos::null && crop2 != Teuchos::null)
1767 temp = Multiply (*crop1,
false, *crop2,
false, fos);
1772 TEUCHOS_TEST_FOR_EXCEPTION(bop2.is_null()==
true,
Xpetra::Exceptions::BadCast,
"B is not a BlockedCrsMatrix. (TwoMatrixMultiplyBlock)");
1773 TEUCHOS_TEST_FOR_EXCEPTION(bop1->Cols()!=bop2->Rows(),
Xpetra::Exceptions::RuntimeError,
"A has " << bop1->Cols() <<
" columns and B has " << bop2->Rows() <<
" rows. Matrices are not compatible! (TwoMatrixMultiplyBlock)");
1774 TEUCHOS_TEST_FOR_EXCEPTION(bop1->getDomainMap()->isSameAs(*(bop2->getRangeMap()))==
false,
Xpetra::Exceptions::RuntimeError,
"Domain map of A is not the same as range map of B. Matrices are not compatible! (TwoMatrixMultiplyBlock)");
1777 temp = TwoMatrixMultiplyBlock(*bop1, transposeA, *bop2, transposeB, fos, doFillComplete, doOptimizeStorage);
1780 TEUCHOS_TEST_FOR_EXCEPTION(btemp->Rows()!=bop1->Rows(),
Xpetra::Exceptions::RuntimeError,
"Number of block rows of local blocked operator is " << btemp->Rows() <<
" but should be " << bop1->Rows() <<
". (TwoMatrixMultiplyBlock)");
1781 TEUCHOS_TEST_FOR_EXCEPTION(btemp->Cols()!=bop2->Cols(),
Xpetra::Exceptions::RuntimeError,
"Number of block cols of local blocked operator is " << btemp->Cols() <<
" but should be " << bop2->Cols() <<
". (TwoMatrixMultiplyBlock)");
1782 TEUCHOS_TEST_FOR_EXCEPTION(btemp->getRangeMapExtractor()->getFullMap()->isSameAs(*(bop1->getRangeMapExtractor()->getFullMap())) ==
false,
Xpetra::Exceptions::RuntimeError,
"Range map of local blocked operator should be same as first operator. (TwoMatrixMultiplyBlock)");
1783 TEUCHOS_TEST_FOR_EXCEPTION(btemp->getDomainMapExtractor()->getFullMap()->isSameAs(*(bop2->getDomainMapExtractor()->getFullMap())) ==
false,
Xpetra::Exceptions::RuntimeError,
"Domain map of local blocked operator should be same as second operator. (TwoMatrixMultiplyBlock)");
1784 TEUCHOS_TEST_FOR_EXCEPTION(btemp->getRangeMapExtractor()->getThyraMode() != bop1->getRangeMapExtractor()->getThyraMode(),
Xpetra::Exceptions::RuntimeError,
"Thyra mode of local range map extractor incompatible with range map extractor of A (TwoMatrixMultiplyBlock)");
1785 TEUCHOS_TEST_FOR_EXCEPTION(btemp->getDomainMapExtractor()->getThyraMode() != bop2->getDomainMapExtractor()->getThyraMode(),
Xpetra::Exceptions::RuntimeError,
"Thyra mode of local domain map extractor incompatible with domain map extractor of B (TwoMatrixMultiplyBlock)");
1800 if (Cij->isFillComplete())
1803 C->setMatrix(i, j, Cij);
1805 C->setMatrix(i, j, Teuchos::null);
1830 "TwoMatrixAdd: matrix row maps are not the same.");
1833 #if defined(HAVE_XPETRA_EPETRA) && defined(HAVE_XPETRA_EPETRAEXT) 1838 int rv = EpetraExt::MatrixMatrix::Add(epA, transposeA, alpha, epB, beta);
1842 std::ostringstream buf;
1847 #ifdef HAVE_XPETRA_TPETRA 1848 # if ((defined(EPETRA_HAVE_OMP) && (!defined(HAVE_TPETRA_INST_OPENMP) || !defined(HAVE_TPETRA_INST_INT_LONG_LONG))) || \ 1849 (!defined(EPETRA_HAVE_OMP) && (!defined(HAVE_TPETRA_INST_SERIAL) || !defined(HAVE_TPETRA_INST_INT_LONG_LONG)))) 1855 Tpetra::MatrixMatrix::Add(tpA, transposeA, alpha, tpB, beta);
1877 const Matrix& B,
bool transposeB,
const SC& beta,
1884 if(rcpBopA == Teuchos::null && rcpBopB == Teuchos::null) {
1886 "TwoMatrixAdd: matrix row maps are not the same.");
1888 if (C == Teuchos::null) {
1889 size_t maxNzInA = 0;
1890 size_t maxNzInB = 0;
1891 size_t numLocalRows = 0;
1898 if (maxNzInA == 1 || maxNzInB == 1 || AHasFixedNnzPerRow) {
1903 if ((maxNzInA == 1 && maxNzInB > 1) || AHasFixedNnzPerRow) {
1904 for (
size_t i = 0; i < numLocalRows; ++i)
1908 for (
size_t i = 0; i < numLocalRows; ++i)
1912 fos <<
"MatrixMatrix::TwoMatrixAdd : special case detected (one matrix has a fixed nnz per row)" 1913 <<
", using static profiling" << std::endl;
1920 LO nnzToAllocate = Teuchos::as<LO>( (nnzPerRowInA + nnzPerRowInB) * 1.5) + Teuchos::as<LO>(1);
1927 fos <<
"nnzPerRowInA = " << nnzPerRowInA <<
", nnzPerRowInB = " << nnzPerRowInB << std::endl;
1928 fos <<
"MatrixMatrix::TwoMatrixAdd : space allocated per row = " << nnzToAllocate
1929 <<
", max possible nnz per row in sum = " << maxPossible
1935 fos <<
"MatrixMatrix::TwoMatrixAdd : ** WARNING ** estimate could be badly wrong because second summand is transposed" << std::endl;
1939 #if defined(HAVE_XPETRA_EPETRA) && defined(HAVE_XPETRA_EPETRAEXT) 1943 Epetra_CrsMatrix* ref2epC = &*epC;
1946 int rv = EpetraExt::MatrixMatrix::Add(epA, transposeA, alpha, epB, transposeB, beta, ref2epC);
1954 #ifdef HAVE_XPETRA_TPETRA 1955 # if ((defined(EPETRA_HAVE_OMP) && (!defined(HAVE_TPETRA_INST_OPENMP) || !defined(HAVE_TPETRA_INST_INT_LONG_LONG))) || \ 1956 (!defined(EPETRA_HAVE_OMP) && (!defined(HAVE_TPETRA_INST_SERIAL) || !defined(HAVE_TPETRA_INST_INT_LONG_LONG)))) 1963 Tpetra::MatrixMatrix::Add(tpA, transposeA, alpha, tpB, transposeB, beta, tpC);
1971 if (A.
IsView(
"stridedMaps")) C->CreateView(
"stridedMaps", rcpFromRef(A));
1972 if (B.
IsView(
"stridedMaps")) C->CreateView(
"stridedMaps", rcpFromRef(B));
1976 else if(rcpBopA == Teuchos::null && rcpBopB != Teuchos::null) {
1984 for (
size_t j = 0; j < rcpBopB->Cols(); ++j) {
1986 if(rcpA != Teuchos::null &&
1987 rcpBopB->getMatrix(i,j)!=Teuchos::null) {
1989 TwoMatrixAdd(*rcpA, transposeA, alpha,
1990 *(rcpBopB->getMatrix(i,j)), transposeB, beta,
1991 Cij, fos, AHasFixedNnzPerRow);
1992 }
else if (rcpA == Teuchos::null &&
1993 rcpBopB->getMatrix(i,j)!=Teuchos::null) {
1994 Cij = rcpBopB->getMatrix(i,j);
1995 }
else if (rcpA != Teuchos::null &&
1996 rcpBopB->getMatrix(i,j)==Teuchos::null) {
1997 Cij = Teuchos::rcp_const_cast<
Matrix>(rcpA);
1999 Cij = Teuchos::null;
2003 if (Cij->isFillComplete())
2005 Cij->fillComplete();
2006 bC->setMatrix(i, j, Cij);
2008 bC->setMatrix(i, j, Teuchos::null);
2013 else if(rcpBopA != Teuchos::null && rcpBopB == Teuchos::null) {
2021 for (
size_t i = 0; i < rcpBopA->Rows(); ++i) {
2023 if(rcpBopA->getMatrix(i,j)!=Teuchos::null &&
2024 rcpB!=Teuchos::null) {
2026 TwoMatrixAdd(*(rcpBopA->getMatrix(i,j)), transposeA, alpha,
2027 *rcpB, transposeB, beta,
2028 Cij, fos, AHasFixedNnzPerRow);
2029 }
else if (rcpBopA->getMatrix(i,j) == Teuchos::null &&
2030 rcpB!=Teuchos::null) {
2031 Cij = Teuchos::rcp_const_cast<
Matrix>(rcpB);
2032 }
else if (rcpBopA->getMatrix(i,j) != Teuchos::null &&
2033 rcpB==Teuchos::null) {
2034 Cij = rcpBopA->getMatrix(i,j);
2036 Cij = Teuchos::null;
2040 if (Cij->isFillComplete())
2042 Cij->fillComplete();
2043 bC->setMatrix(i, j, Cij);
2045 bC->setMatrix(i, j, Teuchos::null);
2068 for (
size_t i = 0; i < rcpBopA->Rows(); ++i) {
2069 for (
size_t j = 0; j < rcpBopB->Cols(); ++j) {
2072 if(rcpBopA->getMatrix(i,j)!=Teuchos::null &&
2073 rcpBopB->getMatrix(i,j)!=Teuchos::null) {
2076 TwoMatrixAdd(*(rcpBopA->getMatrix(i,j)), transposeA, alpha,
2077 *(rcpBopB->getMatrix(i,j)), transposeB, beta,
2078 Cij, fos, AHasFixedNnzPerRow);
2079 }
else if (rcpBopA->getMatrix(i,j) == Teuchos::null &&
2080 rcpBopB->getMatrix(i,j)!=Teuchos::null) {
2081 Cij = rcpBopB->getMatrix(i,j);
2082 }
else if (rcpBopA->getMatrix(i,j) != Teuchos::null &&
2083 rcpBopB->getMatrix(i,j)==Teuchos::null) {
2084 Cij = rcpBopA->getMatrix(i,j);
2086 Cij = Teuchos::null;
2090 if (Cij->isFillComplete())
2093 Cij->fillComplete();
2094 bC->setMatrix(i, j, Cij);
2096 bC->setMatrix(i, j, Teuchos::null);
2105 #endif // HAVE_XPETRA_EPETRA 2109 #define XPETRA_MATRIXMATRIX_SHORT virtual size_t getNodeMaxNumRowEntries() const =0
Returns the maximum number of entries across all rows/columns on this node.
virtual size_t getNodeNumRows() const =0
Returns the number of matrix rows owned on the calling node.
static void TwoMatrixAdd(const Matrix &A, bool transposeA, const SC &alpha, const Matrix &B, bool transposeB, const SC &beta, RCP< Matrix > &C, Teuchos::FancyOStream &fos, bool AHasFixedNnzPerRow=false)
Helper function to calculate C = alpha*A + beta*B.
virtual size_t getNodeNumEntries() const =0
Returns the local number of entries in this matrix.
static void TwoMatrixAdd(const Matrix &A, bool transposeA, const SC &alpha, const Matrix &B, bool transposeB, const SC &beta, RCP< Matrix > &C, Teuchos::FancyOStream &fos, bool AHasFixedNnzPerRow=false)
Helper function to calculate C = alpha*A + beta*B.
virtual global_size_t getGlobalNumRows() const =0
Returns the number of global rows in this matrix.
virtual const RCP< const Map > & getRowMap() const
Returns the Map that describes the row distribution in this matrix.
bool isFillComplete() const
Returns true if fillComplete() has been called and the matrix is in compute mode. ...
static RCP< Matrix > Multiply(const Matrix &A, bool transposeA, const Matrix &B, bool transposeB, RCP< Matrix > C_in, Teuchos::FancyOStream &fos, bool doFillComplete=true, bool doOptimizeStorage=true, const std::string &label=std::string(), const RCP< ParameterList > ¶ms=null)
Helper function to do matrix-matrix multiply.
ParameterList & set(std::string const &name, T const &value, std::string const &docString="", RCP< const ParameterEntryValidator > const &validator=null)
static Epetra_CrsMatrix & Op2NonConstEpetraCrs(const Matrix &Op)
#define TEUCHOS_TEST_FOR_EXCEPTION(throw_exception_test, Exception, msg)
Xpetra utility class containing transformation routines between Xpetra::Matrix and Epetra/Tpetra obje...
Exception throws to report errors in the internal logical of the program.
static RCP< BlockedCrsMatrix > TwoMatrixMultiplyBlock(const BlockedCrsMatrix &A, bool transposeA, const BlockedCrsMatrix &B, bool transposeB, Teuchos::FancyOStream &fos, bool doFillComplete=true, bool doOptimizeStorage=true)
Helper function to do matrix-matrix multiply "in-place".
static const Epetra_CrsMatrix & Op2EpetraCrs(const Matrix &Op)
static RCP< Time > getNewTimer(const std::string &name)
RCP< const MapExtractor > getRangeMapExtractor() const
Returns map extractor class for range map.
Exception indicating invalid cast attempted.
virtual void fillComplete(const RCP< const Map > &domainMap, const RCP< const Map > &rangeMap, const RCP< ParameterList > ¶ms=null)=0
Signal that data entry is complete, specifying domain and range maps.
static void TwoMatrixAdd(const Matrix &A, bool transposeA, const SC &alpha, const Matrix &B, bool transposeB, const SC &beta, RCP< Matrix > &C, Teuchos::FancyOStream &fos, bool AHasFixedNnzPerRow=false)
Helper function to calculate C = alpha*A + beta*B.
TEUCHOS_DEPRECATED RCP< T > rcp(T *p, Dealloc_T dealloc, bool owns_mem)
static RCP< Matrix > Multiply(const Matrix &A, bool transposeA, const Matrix &B, bool transposeB, Teuchos::FancyOStream &fos, bool callFillCompleteOnResult=true, bool doOptimizeStorage=true, const std::string &label=std::string(), const RCP< ParameterList > ¶ms=null)
Helper function to do matrix-matrix multiply.
virtual bool isFillComplete() const =0
Returns true if fillComplete() has been called and the matrix is in compute mode. ...
void CreateView(viewLabel_t viewLabel, const RCP< const Map > &rowMap, const RCP< const Map > &colMap)
static void Multiply(const Matrix &A, bool transposeA, const Matrix &B, bool transposeB, Matrix &C, bool call_FillComplete_on_result=true, bool doOptimizeStorage=true, const std::string &label=std::string(), const RCP< ParameterList > ¶ms=null)
RCP< CrsMatrix > getCrsMatrix() const
static RCP< Matrix > Multiply(const Matrix &A, bool transposeA, const Matrix &B, bool transposeB, RCP< Matrix > C_in, Teuchos::FancyOStream &fos, bool doFillComplete=true, bool doOptimizeStorage=true, const std::string &label=std::string(), const RCP< ParameterList > ¶ms=null)
Helper function to do matrix-matrix multiply.
static Tpetra::CrsMatrix< SC, LO, GO, NO > & Op2NonConstTpetraCrs(const Matrix &Op)
static RCP< Matrix > Multiply(const Matrix &A, bool transposeA, const Matrix &B, bool transposeB, RCP< Matrix > C_in, Teuchos::FancyOStream &fos, bool doFillComplete=true, bool doOptimizeStorage=true, const std::string &label=std::string(), const RCP< ParameterList > ¶ms=null)
Helper function to do matrix-matrix multiply.
virtual size_t getNumEntriesInLocalRow(LocalOrdinal localRow) const =0
Returns the current number of entries on this node in the specified local row.
static void Multiply(const Matrix &A, bool transposeA, const Matrix &B, bool transposeB, Matrix &C, bool call_FillComplete_on_result=true, bool doOptimizeStorage=true, const std::string &label=std::string(), const RCP< ParameterList > ¶ms=null)
static RCP< BlockedCrsMatrix > TwoMatrixMultiplyBlock(const BlockedCrsMatrix &A, bool transposeA, const BlockedCrsMatrix &B, bool transposeB, Teuchos::FancyOStream &fos, bool doFillComplete=true, bool doOptimizeStorage=true)
Helper function to do matrix-matrix multiply "in-place".
static void TwoMatrixAdd(const Matrix &A, bool transposeA, SC alpha, Matrix &B, SC beta)
Helper function to calculate B = alpha*A + beta*B.
static RCP< const Epetra_CrsMatrix > Op2EpetraCrs(RCP< Matrix > Op)
static void Multiply(const Matrix &A, bool transposeA, const Matrix &B, bool transposeB, Matrix &C, bool call_FillComplete_on_result=true, bool doOptimizeStorage=true, const std::string &label=std::string(), const RCP< ParameterList > ¶ms=null)
static RCP< Epetra_CrsMatrix > Op2NonConstEpetraCrs(RCP< Matrix > Op)
Exception throws to report incompatible objects (like maps).
static void TwoMatrixAdd(const Matrix &A, bool transposeA, SC alpha, Matrix &B, SC beta)
Helper function to calculate B = alpha*A + beta*B.
RCP< const Map > getRangeMap() const
Returns the Map associated with the range of this operator.
virtual global_size_t getGlobalNumEntries() const =0
Returns the global number of entries in this matrix.
Concrete implementation of Xpetra::Matrix.
Teuchos::RCP< Matrix > getMatrix(size_t r, size_t c) const
return block (r,c)
virtual Teuchos::RCP< const Map > getRangeMap() const =0
The Map associated with the range of this operator, which must be compatible with Y...
bool IsView(const viewLabel_t viewLabel) const
static RCP< Epetra_CrsMatrix > MLTwoMatrixMultiply(const Epetra_CrsMatrix &epA, const Epetra_CrsMatrix &epB, Teuchos::FancyOStream &fos)
RCP< const MapExtractor > getDomainMapExtractor() const
Returns map extractor for domain map.
static RCP< Matrix > Build(const RCP< const Map > &rowMap, size_t maxNumEntriesPerRow, Xpetra::ProfileType pftype=Xpetra::DynamicProfile)
Constructor specifying the number of non-zeros for all rows.
static RCP< BlockedCrsMatrix > TwoMatrixMultiplyBlock(const BlockedCrsMatrix &A, bool transposeA, const BlockedCrsMatrix &B, bool transposeB, Teuchos::FancyOStream &fos, bool doFillComplete=true, bool doOptimizeStorage=true)
Helper function to do matrix-matrix multiply "in-place".
virtual size_t Rows() const
number of row blocks
static RCP< Tpetra::CrsMatrix< SC, LO, GO, NO > > Op2NonConstTpetraCrs(RCP< Matrix > Op)
virtual size_t Cols() const
number of column blocks
static RCP< Matrix > Multiply(const Matrix &A, bool transposeA, const Matrix &B, bool transposeB, Teuchos::FancyOStream &fos, bool callFillCompleteOnResult=true, bool doOptimizeStorage=true, const std::string &label=std::string(), const RCP< ParameterList > ¶ms=null)
Helper function to do matrix-matrix multiply.
RCP< const Map > getDomainMap() const
Returns the Map associated with the domain of this operator.
static RCP< Epetra_CrsMatrix > MLTwoMatrixMultiply(const Epetra_CrsMatrix &epA, const Epetra_CrsMatrix &epB, Teuchos::FancyOStream &fos)
static RCP< Epetra_CrsMatrix > MLTwoMatrixMultiply(const Epetra_CrsMatrix &epA, const Epetra_CrsMatrix &epB, Teuchos::FancyOStream &fos)
static void TwoMatrixAdd(const Matrix &A, bool transposeA, SC alpha, Matrix &B, SC beta)
Helper function to calculate B = alpha*A + beta*B.
static const Tpetra::CrsMatrix< SC, LO, GO, NO > & Op2TpetraCrs(const Matrix &Op)
virtual Teuchos::RCP< const Map > getDomainMap() const =0
The Map associated with the domain of this operator, which must be compatible with X...
Xpetra-specific matrix class.
static RCP< const Tpetra::CrsMatrix< SC, LO, GO, NO > > Op2TpetraCrs(RCP< Matrix > Op)
std::string toString(const T &t)
static RCP< Matrix > Multiply(const Matrix &A, bool transposeA, const Matrix &B, bool transposeB, Teuchos::FancyOStream &fos, bool callFillCompleteOnResult=true, bool doOptimizeStorage=true, const std::string &label=std::string(), const RCP< ParameterList > ¶ms=null)
Helper function to do matrix-matrix multiply.