46 #ifndef MUELU_AGGREGATIONPHASE1ALGORITHM_KOKKOS_DEF_HPP 47 #define MUELU_AGGREGATIONPHASE1ALGORITHM_KOKKOS_DEF_HPP 49 #ifdef HAVE_MUELU_KOKKOS_REFACTOR 53 #include <Teuchos_Comm.hpp> 54 #include <Teuchos_CommHelpers.hpp> 56 #include <Xpetra_Vector.hpp> 60 #include "MueLu_Aggregates_kokkos.hpp" 62 #include "MueLu_LWGraph_kokkos.hpp" 67 template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
68 void AggregationPhase1Algorithm_kokkos<LocalOrdinal, GlobalOrdinal, Node>::
69 BuildAggregates(
const ParameterList& params,
const LWGraph_kokkos& graph, Aggregates_kokkos& aggregates, std::vector<unsigned>& aggStat,
70 LO& numNonAggregatedNodes)
const {
71 Monitor m(*
this,
"BuildAggregates");
73 std::string ordering = params.get<std::string>(
"aggregation: ordering");
74 int maxNeighAlreadySelected = params.get<
int> (
"aggregation: max selected neighbors");
75 int minNodesPerAggregate = params.get<
int> (
"aggregation: min agg size");
76 int maxNodesPerAggregate = params.get<
int> (
"aggregation: max agg size");
79 "MueLu::UncoupledAggregationAlgorithm::BuildAggregates: minNodesPerAggregate must be smaller or equal to MaxNodePerAggregate!");
81 const LO numRows = graph.GetNodeNumVertices();
82 const int myRank = graph.GetComm()->getRank();
84 ArrayRCP<LO> vertex2AggId = aggregates.GetVertex2AggId()->getDataNonConst(0);
85 ArrayRCP<LO> procWinner = aggregates.GetProcWinner() ->getDataNonConst(0);
87 LO numLocalAggregates = aggregates.GetNumAggregates();
89 ArrayRCP<LO> randomVector;
90 if (ordering ==
"random") {
91 randomVector = arcp<LO>(numRows);
92 for (LO i = 0; i < numRows; i++)
94 RandomReorder(randomVector);
99 std::vector<int> aggList(graph.getNodeMaxNumRowEntries());
101 std::queue<LO> graphOrderQueue;
104 for (LO i = 0; i < numRows; i++) {
106 LO rootCandidate = 0;
107 if (ordering ==
"natural") rootCandidate = i;
108 else if (ordering ==
"random") rootCandidate = randomVector[i];
109 else if (ordering ==
"graph") {
111 if (graphOrderQueue.size() == 0) {
113 for (LO jnode = 0; jnode < numRows; jnode++)
114 if (aggStat[jnode] ==
READY) {
115 graphOrderQueue.push(jnode);
119 if (graphOrderQueue.size() == 0) {
123 rootCandidate = graphOrderQueue.front();
124 graphOrderQueue.pop();
127 if (aggStat[rootCandidate] !=
READY)
132 aggList[aggSize++] = rootCandidate;
134 typename LWGraph_kokkos::row_type neighOfINode = graph.getNeighborVertices(rootCandidate);
140 if ((ordering ==
"natural" || ordering ==
"random") &&
141 neighOfINode.size() < minNodesPerAggregate) {
145 LO numAggregatedNeighbours = 0;
147 for (
int j = 0; j < neighOfINode.size(); j++) {
148 LO neigh = neighOfINode(j);
150 if (neigh != rootCandidate && graph.isLocalNeighborVertex(neigh)) {
152 if (aggStat[neigh] ==
READY || aggStat[neigh] ==
NOTSEL) {
161 if (aggSize < as<size_t>(maxNodesPerAggregate))
162 aggList[aggSize++] = neigh;
165 numAggregatedNeighbours++;
171 if ((numAggregatedNeighbours <= maxNeighAlreadySelected) &&
172 (aggSize >= as<size_t>(minNodesPerAggregate))) {
175 aggregates.SetIsRoot(rootCandidate);
176 aggIndex = numLocalAggregates++;
178 for (
size_t k = 0; k < aggSize; k++) {
180 vertex2AggId[aggList[k]] = aggIndex;
181 procWinner [aggList[k]] = myRank;
184 numNonAggregatedNodes -= aggSize;
188 aggStat[rootCandidate] =
NOTSEL;
195 if (ordering ==
"graph") {
200 for (
size_t k = 0; k < aggSize; k++) {
201 typename LWGraph_kokkos::row_type neighOfJNode = graph.getNeighborVertices(aggList[k]);
203 for (
int j = 0; j < neighOfJNode.size(); j++) {
204 LO neigh = neighOfJNode(j);
206 if (graph.isLocalNeighborVertex(neigh) && aggStat[neigh] ==
READY)
207 graphOrderQueue.push(neigh);
215 for (LO i = 0; i < numRows; i++)
220 aggregates.SetNumAggregates(numLocalAggregates);
223 template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
224 void AggregationPhase1Algorithm_kokkos<LocalOrdinal, GlobalOrdinal, Node>::RandomReorder(ArrayRCP<LO> list)
const {
227 for(
int i = 0; i < n-1; i++)
228 std::swap(list[i], list[RandomOrdinal(i,n-1)]);
231 template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
232 int AggregationPhase1Algorithm_kokkos<LocalOrdinal, GlobalOrdinal, Node>::RandomOrdinal(
int min,
int max)
const {
233 return min + as<int>((max-min+1) * (static_cast<double>(std::rand()) / (RAND_MAX + 1.0)));
238 #endif // HAVE_MUELU_KOKKOS_REFACTOR 239 #endif // MUELU_AGGREGATIONPHASE1ALGORITHM_KOKKOS_DEF_HPP
#define TEUCHOS_TEST_FOR_EXCEPTION(throw_exception_test, Exception, msg)
Namespace for MueLu classes and methods.