46 #ifndef MUELU_STRUCTUREDAGGREGATIONFACTORY_DEF_HPP_ 47 #define MUELU_STRUCTUREDAGGREGATIONFACTORY_DEF_HPP_ 49 #include <Xpetra_Map.hpp> 50 #include <Xpetra_CrsGraph.hpp> 52 #include "MueLu_AggregationStructuredAlgorithm.hpp" 55 #include "MueLu_Aggregates.hpp" 58 #include "MueLu_Utilities.hpp" 59 #include "MueLu_UncoupledIndexManager.hpp" 60 #include "MueLu_LocalLexicographicIndexManager.hpp" 61 #include "MueLu_GlobalLexicographicIndexManager.hpp" 67 template <
class Scalar,
class LocalOrdinal,
class GlobalOrdinal,
class Node>
72 template <
class Scalar,
class LocalOrdinal,
class GlobalOrdinal,
class Node>
75 RCP<ParameterList> validParamList = rcp(
new ParameterList());
77 #define SET_VALID_ENTRY(name) validParamList->setEntry(name, MasterList::getEntry(name)) 80 SET_VALID_ENTRY(
"aggregation: error on nodes with no on-rank neighbors");
89 #undef SET_VALID_ENTRY 90 validParamList->set<RCP<const FactoryBase> >(
"Graph", Teuchos::null,
91 "Graph of the matrix after amalgamation but without dropping.");
92 validParamList->set<RCP<const FactoryBase> >(
"numDimensions", Teuchos::null,
93 "Number of spatial dimension provided by CoordinatesTransferFactory.");
94 validParamList->set<RCP<const FactoryBase> >(
"gNodesPerDim", Teuchos::null,
95 "Global number of nodes per spatial dimension provided by CoordinatesTransferFactory.");
96 validParamList->set<RCP<const FactoryBase> >(
"lNodesPerDim", Teuchos::null,
97 "Local number of nodes per spatial dimension provided by CoordinatesTransferFactory.");
98 validParamList->set<RCP<const FactoryBase> >(
"DofsPerNode", Teuchos::null,
99 "Generating factory for variable \'DofsPerNode\', usually the same as the \'Graph\' factory");
100 validParamList->set<
const bool>(
"aggregation: single coarse point",
false,
101 "Allows the aggreagtion process to reduce spacial dimensions to a single layer");
103 return validParamList;
106 template <
class Scalar,
class LocalOrdinal,
class GlobalOrdinal,
class Node>
109 Input(currentLevel,
"Graph");
110 Input(currentLevel,
"DofsPerNode");
112 ParameterList pL = GetParameterList();
113 std::string coupling = pL.get<std::string>(
"aggregation: mode");
114 const bool coupled = (coupling ==
"coupled" ? true :
false);
123 "gNodesPerDim was not provided by the user on level0!");
126 Input(currentLevel,
"gNodesPerDim");
137 "numDimensions was not provided by the user on level0!");
144 "lNodesPerDim was not provided by the user on level0!");
147 Input(currentLevel,
"numDimensions");
148 Input(currentLevel,
"lNodesPerDim");
152 template <
class Scalar,
class LocalOrdinal,
class GlobalOrdinal,
class Node>
157 RCP<Teuchos::FancyOStream> out;
158 if(
const char* dbg = std::getenv(
"MUELU_STRUCTUREDAGGREGATION_DEBUG")) {
159 out = Teuchos::fancyOStream(Teuchos::rcpFromRef(std::cout));
160 out->setShowAllFrontMatter(
false).setShowProcRank(
true);
162 out = Teuchos::getFancyOStream(rcp(
new Teuchos::oblackholestream()));
165 *out <<
"Entering structured aggregation" << std::endl;
167 ParameterList pL = GetParameterList();
168 bDefinitionPhase_ =
false;
171 RCP<const GraphBase> graph = Get< RCP<GraphBase> >(currentLevel,
"Graph");
172 RCP<const Map> fineMap = graph->GetDomainMap();
173 const int myRank = fineMap->getComm()->getRank();
174 const int numRanks = fineMap->getComm()->getSize();
175 const GO minGlobalIndex = fineMap->getMinGlobalIndex();
176 const LO dofsPerNode = Get<LO>(currentLevel,
"DofsPerNode");
180 const int interpolationOrder = pL.get<
int>(
"aggregation: coarsening order");
181 std::string meshLayout = pL.get<std::string>(
"aggregation: mesh layout");
182 std::string coupling = pL.get<std::string>(
"aggregation: mode");
183 const bool coupled = (coupling ==
"coupled" ? true :
false);
184 std::string outputType = pL.get<std::string>(
"aggregation: output type");
185 const bool outputAggregates = (outputType ==
"Aggregates" ? true :
false);
186 const bool singleCoarsePoint = pL.get<
bool>(
"aggregation: single coarse point");
188 Array<GO> gFineNodesPerDir(3);
189 Array<LO> lFineNodesPerDir(3);
190 if(currentLevel.GetLevelID() == 0) {
192 numDimensions = currentLevel.Get<
int>(
"numDimensions",
NoFactory::get());
193 lFineNodesPerDir = currentLevel.Get<Array<LO> >(
"lNodesPerDim",
NoFactory::get());
195 gFineNodesPerDir = currentLevel.Get<Array<GO> >(
"gNodesPerDim",
NoFactory::get());
199 numDimensions = Get<int>(currentLevel,
"numDimensions");
200 lFineNodesPerDir = Get<Array<LO> >(currentLevel,
"lNodesPerDim");
202 gFineNodesPerDir = Get<Array<GO> >(currentLevel,
"gNodesPerDim");
208 for(
int dim = 0; dim < 3; ++dim) {
209 if(dim >= numDimensions) {
210 gFineNodesPerDir[dim] = 1;
211 lFineNodesPerDir[dim] = 1;
216 std::string coarseningRate = pL.get<std::string>(
"aggregation: coarsening rate");
217 Teuchos::Array<LO> coarseRate;
219 coarseRate = Teuchos::fromStringToArray<LO>(coarseningRate);
220 }
catch(
const Teuchos::InvalidArrayStringRepresentation& e) {
221 GetOStream(
Errors,-1) <<
" *** \"aggregation: coarsening rate\" must be a string convertible into an array! *** " 225 TEUCHOS_TEST_FOR_EXCEPTION((coarseRate.size() > 1) && (coarseRate.size() < numDimensions),
227 "\"aggregation: coarsening rate\" must have at least as many" 228 " components as the number of spatial dimensions in the problem.");
231 RCP<IndexManager > geoData;
243 }
else if(meshLayout ==
"Local Lexicographic") {
245 if(currentLevel.GetLevelID() == 0) {
247 meshData = currentLevel.Get<Array<GO> >(
"aggregation: mesh data",
NoFactory::get());
249 "The meshData array is empty, somehow the input for structured" 250 " aggregation are not captured correctly.");
253 meshData = Get<Array<GO> >(currentLevel,
"aggregation: mesh data");
269 }
else if(meshLayout ==
"Global Lexicographic") {
285 *out <<
"The index manager has now been built" << std::endl;
286 *out <<
"graph num nodes: " << fineMap->getNodeNumElements()
287 <<
", structured aggregation num nodes: " << geoData->getNumLocalFineNodes() << std::endl;
288 TEUCHOS_TEST_FOR_EXCEPTION(fineMap->getNodeNumElements()
289 !=
static_cast<size_t>(geoData->getNumLocalFineNodes()),
291 "The local number of elements in the graph's map is not equal to " 292 "the number of nodes given by: lNodesPerDim!");
294 TEUCHOS_TEST_FOR_EXCEPTION(fineMap->getGlobalNumElements()
295 !=
static_cast<size_t>(geoData->getNumGlobalFineNodes()),
297 "The global number of elements in the graph's map is not equal to " 298 "the number of nodes given by: gNodesPerDim!");
301 *out <<
"Compute coarse mesh data" << std::endl;
302 std::vector<std::vector<GO> > coarseMeshData = geoData->getCoarseMeshData();
306 RCP<const FactoryBase> graphFact = GetFactory(
"Graph");
307 RCP<const Map> coarseCoordinatesFineMap, coarseCoordinatesMap;
308 RCP<MueLu::AggregationStructuredAlgorithm<LocalOrdinal, GlobalOrdinal, Node> >
311 if(interpolationOrder == 0 && outputAggregates){
313 *out <<
"Compute Aggregates" << std::endl;
314 RCP<Aggregates> aggregates = rcp(
new Aggregates(graph->GetDomainMap()));
315 aggregates->setObjectLabel(
"ST");
316 aggregates->SetIndexManager(geoData);
317 aggregates->AggregatesCrossProcessors(coupled);
318 aggregates->SetNumAggregates(geoData->getNumLocalCoarseNodes());
319 std::vector<unsigned> aggStat(geoData->getNumLocalFineNodes(),
READY);
320 LO numNonAggregatedNodes = geoData->getNumLocalFineNodes();
322 myStructuredAlgorithm->BuildAggregates(pL, *graph, *aggregates, aggStat,
323 numNonAggregatedNodes);
326 "MueLu::StructuredAggregationFactory::Build: Leftover nodes found! Error!");
327 aggregates->ComputeAggregateSizes(
true);
328 GetOStream(
Statistics1) << aggregates->description() << std::endl;
329 Set(currentLevel,
"Aggregates", aggregates);
333 *out <<
"Compute CrsGraph" << std::endl;
334 RCP<CrsGraph> myGraph;
335 myStructuredAlgorithm->BuildGraph(*graph, geoData, dofsPerNode, myGraph,
336 coarseCoordinatesFineMap, coarseCoordinatesMap);
337 Set(currentLevel,
"prolongatorGraph", myGraph);
341 Set(currentLevel,
"gCoarseNodesPerDim", geoData->getGlobalCoarseNodesPerDir());
343 Set(currentLevel,
"lCoarseNodesPerDim", geoData->getLocalCoarseNodesPerDir());
344 Set(currentLevel,
"coarseCoordinatesFineMap", coarseCoordinatesFineMap);
345 Set(currentLevel,
"coarseCoordinatesMap", coarseCoordinatesMap);
346 Set(currentLevel,
"structuredInterpolationOrder", interpolationOrder);
347 Set(currentLevel,
"numDimensions", numDimensions);
void Build(Level ¤tLevel) const
Build aggregates.
Container class for aggregation information.
Timer to be used in factories. Similar to Monitor but with additional timers.
Algorithm for coarsening a graph with structured aggregation.
void DeclareInput(Level ¤tLevel) const
Input.
Namespace for MueLu classes and methods.
StructuredAggregationFactory()
Constructor.
static const NoFactory * get()
int GetLevelID() const
Return level number.
RCP< const ParameterList > GetValidParameterList() const
Return a const parameter list of valid parameters that setParameterList() will accept.
Class that holds all level-specific information.
bool IsAvailable(const std::string &ename, const FactoryBase *factory=NoFactory::get()) const
Test whether a need's value has been saved.
Exception throws to report errors in the internal logical of the program.
void DeclareInput(const std::string &ename, const FactoryBase *factory, const FactoryBase *requestedBy=NoFactory::get())
Callback from FactoryBase::CallDeclareInput() and FactoryBase::DeclareInput()
#define SET_VALID_ENTRY(name)