46 #ifndef MUELU_UNCOUPLEDAGGREGATIONFACTORY_DEF_HPP_
47 #define MUELU_UNCOUPLEDAGGREGATIONFACTORY_DEF_HPP_
58 #include "MueLu_InterfaceAggregationAlgorithm.hpp"
59 #include "MueLu_OnePtAggregationAlgorithm.hpp"
60 #include "MueLu_PreserveDirichletAggregationAlgorithm.hpp"
61 #include "MueLu_IsolatedNodeAggregationAlgorithm.hpp"
63 #include "MueLu_AggregationPhase1Algorithm.hpp"
64 #include "MueLu_AggregationPhase2aAlgorithm.hpp"
65 #include "MueLu_AggregationPhase2bAlgorithm.hpp"
66 #include "MueLu_AggregationPhase3Algorithm.hpp"
70 #include "MueLu_Aggregates.hpp"
73 #include "MueLu_AmalgamationInfo.hpp"
74 #include "MueLu_Utilities.hpp"
78 template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
80 : bDefinitionPhase_(true)
83 template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
91 #define SET_VALID_ENTRY(name) validParamList->setEntry(name, MasterList::getEntry(name))
97 rcp(
new validatorType(Teuchos::tuple<std::string>(
"natural",
"graph",
"random"),
"aggregation: ordering")));
105 SET_VALID_ENTRY(
"aggregation: error on nodes with no on-rank neighbors");
107 #undef SET_VALID_ENTRY
111 validParamList->
set<
RCP<const FactoryBase> >(
"DofsPerNode", null,
"Generating factory for variable \'DofsPerNode\', usually the same as for \'Graph\'");
114 validParamList->
set< std::string > (
"OnePt aggregate map name",
"",
"Name of input map for single node aggregates. (default='')");
115 validParamList->
set< std::string > (
"OnePt aggregate map factory",
"",
"Generating factory of (DOF) map for single node aggregates.");
120 validParamList->
set< std::string > (
"Interface aggregate map name",
"",
"Name of input map for interface aggregates. (default='')");
121 validParamList->
set< std::string > (
"Interface aggregate map factory",
"",
"Generating factory of (DOF) map for interface aggregates.");
122 validParamList->
set<
RCP<const FactoryBase> > (
"nodeOnInterface", Teuchos::null,
"Array specifying whether or not a node is on the interface (1 or 0).");
124 return validParamList;
127 template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
129 Input(currentLevel,
"Graph");
130 Input(currentLevel,
"DofsPerNode");
135 std::string mapOnePtName = pL.
get<std::string>(
"OnePt aggregate map name");
136 if (mapOnePtName.length() > 0) {
137 std::string mapOnePtFactName = pL.
get<std::string>(
"OnePt aggregate map factory");
138 if (mapOnePtFactName ==
"" || mapOnePtFactName ==
"NoFactory") {
147 if (pL.
get<
bool>(
"aggregation: use interface aggregation") ==
true){
154 "nodeOnInterface was not provided by the user on level0!");
157 Input(currentLevel,
"nodeOnInterface");
162 template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
167 bDefinitionPhase_ =
false;
169 if (pL.
get<
int>(
"aggregation: max agg size") == -1)
170 pL.
set(
"aggregation: max agg size", INT_MAX);
191 std::string mapOnePtName = pL.
get<std::string>(
"OnePt aggregate map name");
193 if (mapOnePtName.length()) {
194 std::string mapOnePtFactName = pL.
get<std::string>(
"OnePt aggregate map factory");
195 if (mapOnePtFactName ==
"" || mapOnePtFactName ==
"NoFactory") {
199 OnePtMap = currentLevel.
Get<
RCP<Map> >(mapOnePtName, mapOnePtFact.
get());
204 std::string mapInterfaceName = pL.
get<std::string>(
"Interface aggregate map name");
205 RCP<Map> InterfaceMap = Teuchos::null;
211 aggregates->setObjectLabel(
"UC");
216 std::vector<unsigned> aggStat(numRows,
READY);
219 if (pL.
get<
bool>(
"aggregation: use interface aggregation") ==
true){
221 for (
LO i = 0; i < numRows; i++) {
222 if (nodeOnInterface[i])
228 if (dirichletBoundaryMap != Teuchos::null)
229 for (
LO i = 0; i < numRows; i++)
230 if (dirichletBoundaryMap[i] ==
true)
233 LO nDofsPerNode = Get<LO>(currentLevel,
"DofsPerNode");
235 if (OnePtMap != Teuchos::null) {
236 for (
LO i = 0; i < numRows; i++) {
238 GO grid = (graph->
GetDomainMap()->getGlobalElement(i)-indexBase) * nDofsPerNode + indexBase;
240 for (
LO kr = 0; kr < nDofsPerNode; kr++)
241 if (OnePtMap->isNodeGlobalElement(grid + kr))
249 GO numGlobalRows = 0;
253 LO numNonAggregatedNodes = numRows;
254 GO numGlobalAggregatedPrev = 0, numGlobalAggsPrev = 0;
255 for (
size_t a = 0; a < algos_.size(); a++) {
256 std::string phase = algos_[a]->description();
259 int oldRank = algos_[a]->SetProcRankVerbose(this->GetProcRankVerbose());
260 algos_[a]->BuildAggregates(pL, *graph, *aggregates, aggStat, numNonAggregatedNodes);
261 algos_[a]->SetProcRankVerbose(oldRank);
264 GO numLocalAggregated = numRows - numNonAggregatedNodes, numGlobalAggregated = 0;
265 GO numLocalAggs = aggregates->GetNumAggregates(), numGlobalAggs = 0;
266 MueLu_sumAll(comm, numLocalAggregated, numGlobalAggregated);
269 double aggPercent = 100*as<double>(numGlobalAggregated)/as<double>(numGlobalRows);
270 if (aggPercent > 99.99 && aggPercent < 100.00) {
277 GetOStream(
Statistics1) <<
" aggregated : " << (numGlobalAggregated - numGlobalAggregatedPrev) <<
" (phase), " << std::fixed
278 << std::setprecision(2) << numGlobalAggregated <<
"/" << numGlobalRows <<
" [" << aggPercent <<
"%] (total)\n"
279 <<
" remaining : " << numGlobalRows - numGlobalAggregated <<
"\n"
280 <<
" aggregates : " << numGlobalAggs-numGlobalAggsPrev <<
" (phase), " << numGlobalAggs <<
" (total)" << std::endl;
281 numGlobalAggregatedPrev = numGlobalAggregated;
282 numGlobalAggsPrev = numGlobalAggs;
288 aggregates->AggregatesCrossProcessors(
false);
289 aggregates->ComputeAggregateSizes(
true);
291 Set(currentLevel,
"Aggregates", aggregates);
293 GetOStream(
Statistics1) << aggregates->description() << std::endl;
Algorithm for coarsening a graph with uncoupled aggregation. keep special marked nodes as singleton n...
#define MueLu_sumAll(rcpComm, in, out)
T & Get(const std::string &ename, const FactoryBase *factory=NoFactory::get())
Get data without decrementing associated storage counter (i.e., read-only access). Usage: Level->Get< RCP<Matrix> >("A", factory) if factory == NULL => use default factory.
Container class for aggregation information.
void setValidator(RCP< const ParameterEntryValidator > const &validator)
T & get(const std::string &name, T def_value)
virtual size_t GetNodeNumVertices() const =0
Return number of vertices owned by the calling node.
ParameterList & set(std::string const &name, T const &value, std::string const &docString="", RCP< const ParameterEntryValidator > const &validator=null)
Timer to be used in factories. Similar to Monitor but with additional timers.
virtual const ArrayRCP< const bool > GetBoundaryNodeMap() const =0
#define TEUCHOS_TEST_FOR_EXCEPTION(throw_exception_test, Exception, msg)
virtual const RCP< const Map > GetDomainMap() const =0
void DeclareInput(Level ¤tLevel) const
Input.
static const NoFactory * get()
Algorithm for coarsening a graph with uncoupled aggregation. creates aggregates along an interface us...
Builds one-to-one aggregates for all Dirichlet boundary nodes. For some applications this might be ne...
TEUCHOS_DEPRECATED RCP< T > rcp(T *p, Dealloc_T dealloc, bool owns_mem)
Class that holds all level-specific information.
Timer to be used in factories. Similar to SubMonitor but adds a timer level by level.
RCP< const ParameterList > GetValidParameterList() const
Return a const parameter list of valid parameters that setParameterList() will accept.
virtual const RCP< const Teuchos::Comm< int > > GetComm() const =0
#define SET_VALID_ENTRY(name)
UncoupledAggregationFactory()
Constructor.
Among unaggregated points, see if we can make a reasonable size aggregate out of it.IdeaAmong unaggregated points, see if we can make a reasonable size aggregate out of it. We do this by looking at neighbors and seeing how many are unaggregated and on my processor. Loosely, base the number of new aggregates created on the percentage of unaggregated nodes.
void Build(Level ¤tLevel) const
Build aggregates.
Add leftovers to existing aggregatesIdeaIn phase 2b non-aggregated nodes are added to existing aggreg...
Algorithm for coarsening a graph with uncoupled aggregation.
int GetLevelID() const
Return level number.
Exception throws to report errors in the internal logical of the program.
Handle leftover nodes. Try to avoid singleton nodesIdeaIn phase 3 we try to stick unaggregated nodes ...
ParameterEntry & getEntry(const std::string &name)
void DeclareInput(const std::string &ename, const FactoryBase *factory, const FactoryBase *requestedBy=NoFactory::get())
Callback from FactoryBase::CallDeclareInput() and FactoryBase::DeclareInput()
bool IsAvailable(const std::string &ename, const FactoryBase *factory=NoFactory::get()) const
Test whether a need's value has been saved.