21 #ifndef AMESOS2_EPETRACRSMATRIX_MATRIXADAPTER_DECL_HPP
22 #define AMESOS2_EPETRACRSMATRIX_MATRIXADAPTER_DECL_HPP
24 #include "Amesos2_config.h"
26 #include <Epetra_CrsMatrix.h>
27 #ifdef HAVE_AMESOS2_EPETRAEXT
28 #include <EpetraExt_Reindex_CrsMatrix.h>
30 #include <Epetra_Comm.h>
31 #include <Epetra_SerialComm.h>
33 # include <Epetra_MpiComm.h>
37 #include "Amesos2_MatrixAdapter_decl.hpp"
56 class ConcreteMatrixAdapter< Epetra_CrsMatrix >
63 typedef Epetra_CrsMatrix matrix_t;
69 typedef super_t::scalar_t scalar_t;
70 typedef super_t::local_ordinal_t local_ordinal_t;
71 typedef super_t::global_ordinal_t global_ordinal_t;
72 typedef super_t::node_t node_t;
73 typedef super_t::global_size_t global_size_t;
75 typedef Tpetra::Map<local_ordinal_t,global_ordinal_t,node_t> map_t;
76 typedef ConcreteMatrixAdapter<matrix_t> type;
78 ConcreteMatrixAdapter(RCP<matrix_t> m);
81 RCP<const MatrixAdapter<matrix_t> > get_impl(
const Teuchos::Ptr<const map_t> map,
EDistribution distribution = ROOTED)
const;
82 RCP<const MatrixAdapter<matrix_t> > reindex_impl(Teuchos::RCP<const map_t> &contigRowMap,
83 Teuchos::RCP<const map_t> &contigColMap,
84 const EPhase current_phase)
const;
87 template<
typename KV_S,
typename KV_GO,
typename KV_GS,
typename host_ordinal_type_array,
typename host_scalar_type_array>
88 local_ordinal_t gather_impl(KV_S& nzvals, KV_GO& indices, KV_GS& pointers,
89 host_ordinal_type_array &perm_g2l,
90 host_ordinal_type_array &recvCountRows, host_ordinal_type_array &recvDisplRows,
91 host_ordinal_type_array &recvCounts, host_ordinal_type_array &recvDispls,
92 host_ordinal_type_array &transpose_map, host_scalar_type_array &nzvals_t,
93 bool column_major,
EPhase current_phase)
const
95 local_ordinal_t ret = -1;
97 auto rowMap = this->getRowMap();
98 auto colMap = this->getColMap();
100 auto comm = rowMap->getComm();
101 auto nRanks = comm->getSize();
102 auto myRank = comm->getRank();
104 RCP<Teuchos::Comm<int>> comm = Teuchos::createSerialComm<int>();
109 int *lclRowptr =
nullptr;
110 int *lclColind =
nullptr;
111 double *lclNzvals =
nullptr;
112 this->mat_->ExtractCrsDataPointers(lclRowptr, lclColind, lclNzvals);
114 int nRows = this->mat_->NumGlobalRows();
115 int myNRows = this->mat_->NumMyRows();
116 int myNnz = this->mat_->NumMyNonzeros();
117 if(current_phase == PREORDERING || current_phase == SYMBFACT) {
119 Kokkos::resize(recvCounts, nRanks);
120 Kokkos::resize(recvDispls, nRanks+1);
123 global_ordinal_t rowIndexBase = rowMap->getIndexBase();
124 global_ordinal_t colIndexBase = colMap->getIndexBase();
126 host_ordinal_type_array perm_l2g;
130 bool need_to_perm =
false;
132 #ifdef HAVE_AMESOS2_TIMERS
133 Teuchos::RCP< Teuchos::Time > gatherTime = Teuchos::TimeMonitor::getNewCounter (
"Amesos2::gather(rowptr)");
134 Teuchos::TimeMonitor GatherTimer(*gatherTime);
136 Teuchos::gather<int, int> (&myNRows, 1, recvCounts.data(), 1, 0, *comm);
138 Kokkos::resize(recvDispls, nRanks+1);
140 for (
int p = 1; p <= nRanks; p++) {
141 recvDispls(p) = recvDispls(p-1) + recvCounts(p-1);
143 if (recvDispls(nRanks) != nRows) {
144 TEUCHOS_TEST_FOR_EXCEPTION(
true, std::runtime_error,
"Amesos2_TpetraCrsMatrix_MatrixAdapter::gather_impl : mismatch between gathered(local nrows) and global nrows.");
147 for (
int p = 0; p < nRanks; p++) {
151 recvDispls(nRanks) = 0;
155 host_ordinal_type_array lclMap;
156 Kokkos::resize(lclMap, myNRows);
158 Kokkos::resize(perm_g2l, nRows);
159 Kokkos::resize(perm_l2g, nRows);
161 Kokkos::resize(perm_g2l, 1);
163 for (
int i=0; i < myNRows; i++) {
164 lclMap(i) = rowMap->getGlobalElement(i);
166 Teuchos::gatherv<int, local_ordinal_t> (lclMap.data(), myNRows, perm_g2l.data(),
167 recvCounts.data(), recvDispls.data(),
170 for (
int i=0; i < nRows; i++) {
171 perm_g2l(i) -= rowIndexBase;
172 perm_l2g(perm_g2l(i)) = i;
173 if (i != perm_g2l(i)) need_to_perm =
true;
177 if (myRank == 0 && (column_major || need_to_perm)) {
178 Kokkos::resize(pointers_t, nRows+1);
179 }
else if (myRank != 0) {
180 Kokkos::resize(pointers_t, 2);
182 local_ordinal_t sendIdx = (myNRows > 0 ? 1 : 0);
183 local_ordinal_t *pointers_ = ((myRank != 0 || (column_major || need_to_perm)) ? pointers_t.data() : pointers.data());
184 Teuchos::gatherv<int, local_ordinal_t> (&lclRowptr[sendIdx], myNRows, &pointers_[1],
185 recvCounts.data(), recvDispls.data(),
188 Kokkos::resize(recvCountRows, nRanks);
189 Kokkos::resize(recvDisplRows, nRanks+1);
190 Kokkos::deep_copy(recvCountRows, recvCounts);
191 Kokkos::deep_copy(recvDisplRows, recvDispls);
195 recvCounts(0) = pointers_[recvDispls(1)];
196 local_ordinal_t displs = recvCounts(0);
197 for (
int p = 1; p < nRanks; p++) {
200 if (recvDispls(p+1) > recvDispls(p)) {
202 recvCounts(p) = pointers_[recvDispls(p+1)];
204 for (
int i = 1+recvDispls(p); i <= recvDispls(p+1); i++) {
205 pointers_[i] += displs;
207 displs += recvCounts(p);
210 ret = pointers_[nRows];
214 #ifdef HAVE_AMESOS2_TIMERS
215 Teuchos::RCP< Teuchos::Time > gatherTime = Teuchos::TimeMonitor::getNewCounter (
"Amesos2::gather(colind)");
216 Teuchos::TimeMonitor GatherTimer(*gatherTime);
221 for (
int p = 0; p < nRanks; p++) {
222 recvDispls(p+1) = recvDispls(p) + recvCounts(p);
226 KV_GO lclColind_ (
"localColind_", myNnz);
227 for (
int i = 0; i < int(myNnz); i++) lclColind_(i) = (colMap->getGlobalElement((lclColind[i])) - colIndexBase);
228 if (column_major || need_to_perm) {
229 Kokkos::resize(indices_t, indices.extent(0));
230 Teuchos::gatherv<int, local_ordinal_t> (lclColind_.data(), myNnz, indices_t.data(),
231 recvCounts.data(), recvDispls.data(),
234 Teuchos::gatherv<int, local_ordinal_t> (lclColind_.data(), myNnz, indices.data(),
235 recvCounts.data(), recvDispls.data(),
240 #ifdef HAVE_AMESOS2_TIMERS
241 Teuchos::RCP< Teuchos::Time > gatherTime = Teuchos::TimeMonitor::getNewCounter (
"Amesos2::gather(transpose index)");
242 Teuchos::TimeMonitor GatherTimer(*gatherTime);
246 Kokkos::resize(transpose_map, ret);
248 for (
int i=0; i<=nRows; i++) {
251 for (
int k=0; k<ret; k++) {
252 int col = indices_t(k);
257 for (
int i=1; i < nRows; i++) {
258 pointers(i+1) += pointers(i);
261 for (
int row=0; row<nRows; row++) {
262 int i = perm_g2l(row);
263 for (
int k=pointers_t(i); k<pointers_t(i+1); k++) {
264 int col = indices_t(k);
265 transpose_map(k) = pointers(1+col);
266 indices(pointers(1+col)) = row;
270 }
else if (need_to_perm) {
272 Kokkos::resize(transpose_map, ret);
273 for (
int i=0; i<nRows; i++) {
274 int row = perm_g2l(i);
275 pointers(row+2) = pointers_t(i+1)-pointers_t(i);
277 for (
int i=1; i < nRows; i++) {
278 pointers(i+1) += pointers(i);
280 for (
int i=0; i<nRows; i++) {
281 int row = perm_g2l(i);
282 for (
int k=pointers_t(i); k<pointers_t(i+1); k++) {
283 int col = indices_t(k);
284 transpose_map(k) = pointers(1+row);
285 indices(pointers(1+row)) = col;
290 Kokkos::resize(transpose_map, 0);
297 #ifdef HAVE_AMESOS2_TIMERS
298 Teuchos::RCP< Teuchos::Time > gatherTime = Teuchos::TimeMonitor::getNewCounter (
"Amesos2::gather(nzvals)");
299 Teuchos::TimeMonitor GatherTimer(*gatherTime);
302 if (transpose_map.extent(0) > 0) {
303 Kokkos::resize(nzvals_t, nzvals.extent(0));
304 Teuchos::gatherv<int, scalar_t> (lclNzvals, myNnz, nzvals_t.data(),
305 recvCounts.data(), recvDispls.data(),
308 Teuchos::gatherv<int, scalar_t> (lclNzvals, myNnz, nzvals.data(),
309 recvCounts.data(), recvDispls.data(),
315 ret = pointers(nRows);
316 if (transpose_map.extent(0) > 0) {
317 for (
int k=0; k<ret; k++) {
318 nzvals(transpose_map(k)) = nzvals_t(k);
324 Teuchos::broadcast<int, local_ordinal_t>(*comm, 0, 1, &ret);
331 describe (Teuchos::FancyOStream& os,
332 const Teuchos::EVerbosityLevel verbLevel =
333 Teuchos::Describable::verbLevel_default)
const;
334 #ifdef HAVE_AMESOS2_EPETRAEXT
336 mutable RCP<EpetraExt::CrsMatrix_Reindex> StdIndex_;
337 mutable RCP<Epetra_CrsMatrix> ContigMat_;
343 #endif // AMESOS2_EPETRACRSMATRIX_MATRIXADAPTER_DECL_HPP
EPhase
Used to indicate a phase in the direct solution.
Definition: Amesos2_TypeDecl.hpp:31
A Matrix adapter interface for Amesos2.
Definition: Amesos2_MatrixAdapter_decl.hpp:42
Provides the Epetra_RowMatrix abstraction for the concrete Epetra row matric adapters.
Definition: Amesos2_AbstractConcreteMatrixAdapter.hpp:55
EDistribution
Definition: Amesos2_TypeDecl.hpp:89