17 #ifndef MUELU_LOCALPERMUTATIONSTRATEGY_DEF_HPP_
18 #define MUELU_LOCALPERMUTATIONSTRATEGY_DEF_HPP_
28 #include <Xpetra_CrsMatrixWrap.hpp>
30 #include "MueLu_Utilities.hpp"
35 template <
class Scalar,
class LocalOrdinal,
class GlobalOrdinal,
class Node>
37 permWidth_ = nDofsPerNode;
39 result_permvecs_.clear();
43 for (
size_t t = 0; t < nDofsPerNode; t++)
45 std::string cs = ss.str();
50 std::vector<int> newPerm(cs.length(), -1);
51 for (
size_t len = 0; len < cs.length(); len++) {
52 newPerm[len] = Teuchos::as<int>(cs[len] -
'0');
54 result_permvecs_.push_back(newPerm);
56 }
while (std::next_permutation(cs.begin(), cs.end()));
59 template <
class Scalar,
class LocalOrdinal,
class GlobalOrdinal,
class Node>
63 size_t nDofsPerNode = 1;
64 if (A->IsView(
"stridedMaps")) {
66 nDofsPerNode = Teuchos::rcp_dynamic_cast<
const StridedMap>(permRowMapStrided)->getFixedBlockSize();
72 std::vector<std::pair<GlobalOrdinal, GlobalOrdinal> > RowColPairs;
75 if (permWidth_ != nDofsPerNode)
76 BuildPermutations(nDofsPerNode);
79 LocalOrdinal lonDofsPerNode = Teuchos::as<LocalOrdinal>(nDofsPerNode);
83 std::vector<GlobalOrdinal> growIds(nDofsPerNode);
87 LocalOrdinal numLocalNodes = A->getRowMap()->getLocalNumElements() / nDofsPerNode;
88 for (
LocalOrdinal node = 0; node < numLocalNodes; ++node) {
95 for (
LocalOrdinal lrdof = 0; lrdof < lonDofsPerNode; ++lrdof) {
97 growIds[lrdof] = grow;
100 A->getLocalRowView(A->getRowMap()->getLocalElement(grow), indices, vals);
105 for (
size_t j = 0; j < Teuchos::as<size_t>(indices.size()); j++) {
113 for (
size_t j = 0; j < Teuchos::as<size_t>(indices.size()); j++) {
114 GlobalOrdinal gcol = A->getColMap()->getGlobalElement(indices[j]);
116 if (grnodeid == gcnodeid) {
118 subBlockMatrix(lrdof, gcol % nDofsPerNode) = vals[j] / maxVal;
120 subBlockMatrix(lrdof, gcol % nDofsPerNode) = vals[j];
121 std::cout <<
"maxVal never should be zero!!!!" << std::endl;
140 std::vector<Scalar> performance_vector = std::vector<Scalar>(result_permvecs_.size());
141 for (
size_t t = 0; t < result_permvecs_.size(); t++) {
142 std::vector<int> vv = result_permvecs_[t];
144 for (
size_t j = 0; j < vv.size(); j++) {
145 value = value * subBlockMatrix(j, vv[j]);
147 performance_vector[t] = value;
162 size_t maxPerformancePermutationIdx = 0;
163 for (
size_t j = 0; j < Teuchos::as<size_t>(performance_vector.size()); j++) {
166 maxPerformancePermutationIdx = j;
171 std::vector<int> bestPerformancePermutation = result_permvecs_[maxPerformancePermutationIdx];
172 for (
size_t t = 0; t < nDofsPerNode; t++) {
173 RowColPairs.push_back(std::make_pair(growIds[t], growIds[bestPerformancePermutation[t]]));
182 Pperm->putScalar(SC_ZERO);
183 Qperm->putScalar(SC_ZERO);
188 typename std::vector<std::pair<GlobalOrdinal, GlobalOrdinal> >::iterator p = RowColPairs.
begin();
189 while (p != RowColPairs.end()) {
194 LocalOrdinal ljk = A->getDomainMap()->getLocalElement(jk);
196 Pperm->replaceLocalValue(lik, ik);
197 Qperm->replaceLocalValue(ljk, ik);
199 p = RowColPairs.erase(p);
202 if (RowColPairs.size() > 0) GetOStream(
Warnings0) <<
"MueLu::LocalPermutationStrategy: There are Row/col pairs left!" << std::endl;
211 for (
size_t row = 0; row < A->getLocalNumRows(); row++) {
215 permPTmatrix->insertGlobalValues(A->getRowMap()->getGlobalElement(row), indoutP.
view(0, indoutP.
size()), valout.
view(0, valout.
size()));
216 permQTmatrix->insertGlobalValues(A->getRowMap()->getGlobalElement(row), indoutQ.
view(0, indoutQ.
size()), valout.
view(0, valout.
size()));
219 permPTmatrix->fillComplete();
220 permQTmatrix->fillComplete();
248 LO lCntZeroDiagonals = 0;
249 permPApermQt->getLocalDiagCopy(*diagVec);
251 for (
size_t i = 0; i < diagVec->getMap()->getLocalNumElements(); ++i) {
252 if (diagVecData[i] != SC_ZERO)
262 GO gCntZeroDiagonals = 0;
263 GO glCntZeroDiagonals = Teuchos::as<GlobalOrdinal>(lCntZeroDiagonals);
264 MueLu_sumAll(comm,glCntZeroDiagonals,gCntZeroDiagonals);
265 GetOStream(
Statistics0) <<
"MueLu::LocalPermutationStrategy: found " << gCntZeroDiagonals <<
" zeros on diagonal" << std::endl;
270 for (
size_t row = 0; row < A->getLocalNumRows(); row++) {
273 diagScalingOp->insertGlobalValues(A->getRowMap()->getGlobalElement(row), indout.view(0, indout.size()), valout.
view(0, valout.
size()));
275 diagScalingOp->fillComplete();
278 currentLevel.
Set(
"A", Teuchos::rcp_dynamic_cast<Matrix>(scaledA), genFactory);
280 currentLevel.
Set(
"permA", Teuchos::rcp_dynamic_cast<Matrix>(permPApermQt), genFactory);
281 currentLevel.
Set(
"permP", Teuchos::rcp_dynamic_cast<Matrix>(permPmatrix), genFactory);
282 currentLevel.
Set(
"permQT", Teuchos::rcp_dynamic_cast<Matrix>(permQTmatrix), genFactory);
283 currentLevel.
Set(
"permScaling", Teuchos::rcp_dynamic_cast<Matrix>(diagScalingOp), genFactory);
288 permPmatrix->getLocalDiagCopy(*diagPVec);
292 for (
size_t i = 0; i < diagPVec->getMap()->getLocalNumElements(); ++i) {
293 if (diagPVecData[i] == SC_ZERO) {
294 lNumRowPermutations++;
299 MueLu_sumAll(diagPVec->getMap()->getComm(), lNumRowPermutations, gNumRowPermutations);
304 permQTmatrix->getLocalDiagCopy(*diagQTVec);
308 for (
size_t i = 0; i < diagQTVec->getMap()->getLocalNumElements(); ++i) {
309 if (diagQTVecData[i] == SC_ZERO) {
310 lNumColPermutations++;
315 MueLu_sumAll(diagQTVec->getMap()->getComm(), lNumColPermutations, gNumColPermutations);
317 currentLevel.
Set(
"#RowPermutations", gNumRowPermutations, genFactory );
318 currentLevel.
Set(
"#ColPermutations", gNumColPermutations, genFactory );
319 currentLevel.
Set(
"#WideRangeRowPermutations", 0, genFactory );
320 currentLevel.
Set(
"#WideRangeColPermutations", 0, genFactory );
322 GetOStream(
Statistics0) <<
"#Row permutations/max possible permutations: " << gNumRowPermutations <<
"/" << diagPVec->getMap()->getGlobalNumElements() << std::endl;
323 GetOStream(
Statistics0) <<
"#Column permutations/max possible permutations: " << gNumColPermutations <<
"/" << diagQTVec->getMap()->getGlobalNumElements() << std::endl;
326 template <
class Scalar,
class LocalOrdinal,
class GlobalOrdinal,
class Node>
328 size_t nDofsPerNode = 1;
329 if (A->IsView(
"stridedMaps")) {
331 nDofsPerNode = Teuchos::rcp_dynamic_cast<
const StridedMap>(permRowMapStrided)->getFixedBlockSize();
334 LocalOrdinal localDofId = localNodeId * nDofsPerNode + localDof;
336 return A->getRowMap()->getGlobalElement(localDofId);
339 template <
class Scalar,
class LocalOrdinal,
class GlobalOrdinal,
class Node>
341 size_t nDofsPerNode = 1;
342 if (A->IsView(
"stridedMaps")) {
344 nDofsPerNode = Teuchos::rcp_dynamic_cast<
const StridedMap>(permRowMapStrided)->getFixedBlockSize();
Important warning messages (one line)
#define MueLu_sumAll(rcpComm, in, out)
MueLu::DefaultLocalOrdinal LocalOrdinal
void BuildPermutation(const Teuchos::RCP< Matrix > &A, const Teuchos::RCP< const Map > permRowMap, Level ¤tLevel, const FactoryBase *genFactory) const
build permutation operators
Print even more statistics.
GlobalOrdinal getGlobalDofId(const Teuchos::RCP< Matrix > &A, LocalOrdinal localNodeId, LocalOrdinal localDof) const
Base class for factories (e.g., R, P, and A_coarse).
Print statistics that do not involve significant additional computation.
TEUCHOS_DEPRECATED RCP< T > rcp(T *p, Dealloc_T dealloc, bool owns_mem)
MueLu::DefaultScalar Scalar
MueLu::DefaultGlobalOrdinal GlobalOrdinal
Class that holds all level-specific information.
void BuildPermutations(size_t nDofsPerNode) const
int putScalar(const ScalarType value=Teuchos::ScalarTraits< ScalarType >::zero())
GlobalOrdinal globalDofId2globalNodeId(const Teuchos::RCP< Matrix > &A, GlobalOrdinal grid) const
static RCP< Xpetra::Matrix< Scalar, LocalOrdinal, GlobalOrdinal, Node > > Transpose(Xpetra::Matrix< Scalar, LocalOrdinal, GlobalOrdinal, Node > &Op, bool optimizeTranspose=false, const std::string &label=std::string(), const Teuchos::RCP< Teuchos::ParameterList > ¶ms=Teuchos::null)
void Set(const std::string &ename, const T &entry, const FactoryBase *factory=NoFactory::get())
static magnitudeType magnitude(T a)
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)
ArrayView< T > view(size_type lowerOffset, size_type size) const