15#ifndef TPETRA_MAP_DEF_HPP
16#define TPETRA_MAP_DEF_HPP
23#include "Teuchos_as.hpp"
24#include "Teuchos_TypeNameTraits.hpp"
25#include "Teuchos_CommHelpers.hpp"
27#include "Kokkos_Sort.hpp"
29#include "Tpetra_Directory.hpp"
32#include "Tpetra_Details_FixedHashTable.hpp"
38#include "Tpetra_Details_mpiIsInitialized.hpp"
46inline void checkMapInputArray(
const char ctorName[],
47 const void* indexList,
48 const size_t indexListSize,
49 const Teuchos::Comm<int>*
const comm) {
52 const bool debug = Behavior::debug(
"Map");
55 using Teuchos::outArg;
56 using Teuchos::REDUCE_MIN;
57 using Teuchos::reduceAll;
59 const int myRank = comm ==
nullptr ? 0 : comm->getRank();
60 const bool verbose = Behavior::verbose(
"Map");
61 std::ostringstream lclErrStrm;
64 if (indexListSize != 0 && indexList ==
nullptr) {
67 lclErrStrm <<
"Proc " << myRank <<
": indexList is null, "
69 << indexListSize <<
" != 0." << endl;
73 reduceAll(*comm, REDUCE_MIN, lclSuccess, outArg(gblSuccess));
74 if (gblSuccess != 1) {
75 std::ostringstream gblErrStrm;
76 gblErrStrm <<
"Tpetra::Map constructor " << ctorName <<
" detected a problem with the input array "
77 "(raw array, Teuchos::ArrayView, or Kokkos::View) "
81 using ::Tpetra::Details::gathervPrint;
84 TEUCHOS_TEST_FOR_EXCEPTION(
true, std::invalid_argument, gblErrStrm.str());
89template <
class LocalOrdinal,
class GlobalOrdinal,
class ViewType>
90void computeConstantsOnDevice(
const ViewType& entryList, GlobalOrdinal& minMyGID, GlobalOrdinal& maxMyGID, GlobalOrdinal& firstContiguousGID, GlobalOrdinal& lastContiguousGID_val, LocalOrdinal& lastContiguousGID_loc) {
91 using LO = LocalOrdinal;
92 using GO = GlobalOrdinal;
93 using exec_space =
typename ViewType::device_type::execution_space;
94 using range_policy = Kokkos::RangePolicy<exec_space, Kokkos::IndexType<LO>>;
95 const LO numLocalElements = entryList.extent(0);
99 typedef typename Kokkos::MinLoc<LO, GO>::value_type minloc_type;
100 minloc_type myMinLoc;
105 Kokkos::parallel_reduce(
106 range_policy(0, numLocalElements), KOKKOS_LAMBDA(
const LO& i, GO& l_myMin, GO& l_myMax, GO& l_firstCont, minloc_type& l_lastCont) {
107 GO entry_0 = entryList[0];
108 GO entry_i = entryList[i];
111 l_myMin = (l_myMin < entry_i) ? l_myMin : entry_i;
112 l_myMax = (l_myMax > entry_i) ? l_myMax : entry_i;
113 l_firstCont = entry_0;
115 if (entry_i - entry_0 != i && l_lastCont.val >= i) {
117 l_lastCont.val = i - 1;
118 l_lastCont.loc = entryList[i - 1];
119 }
else if (i == numLocalElements - 1 && i < l_lastCont.val) {
122 l_lastCont.loc = entry_i;
125 Kokkos::Min<GO>(minMyGID), Kokkos::Max<GO>(maxMyGID), Kokkos::Min<GO>(firstContiguousGID), Kokkos::MinLoc<LO, GO>(myMinLoc));
128 lastContiguousGID_val = myMinLoc.loc;
129 lastContiguousGID_loc = myMinLoc.val;
134template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
139 , numGlobalElements_(0)
140 , numLocalElements_(0)
150 , distributed_(
false)
151 , haveGlobalConstants_(
true)
158template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
162 const Teuchos::RCP<
const Teuchos::Comm<int>>& comm,
169 using Teuchos::broadcast;
170 using Teuchos::outArg;
171 using Teuchos::REDUCE_MAX;
172 using Teuchos::REDUCE_MIN;
173 using Teuchos::reduceAll;
174 using Teuchos::typeName;
177 const GST GSTI = Tpetra::Details::OrdinalTraits<GST>::invalid();
178 const char funcName[] =
"Map(gblNumInds,indexBase,comm,LG)";
180 "Tpetra::Map::Map(gblNumInds,indexBase,comm,LG): ";
184 std::unique_ptr<std::string>
prefix;
187 comm_.getRawPtr(),
"Map",
funcName);
188 std::ostringstream
os;
190 std::cerr <<
os.str();
208 std::invalid_argument,
exPfx <<
"All processes must "
209 "provide the same number of global elements. Process 0 set "
213 << comm->getRank() <<
" set "
216 "and max values over all processes are "
226 std::invalid_argument,
exPfx <<
"All processes must "
227 "provide the same indexBase argument. Process 0 set "
251 std::invalid_argument,
exPfx <<
"numGlobalElements (= " <<
numGlobalElements <<
") must be nonnegative.");
254 "Tpetra::global_size_t>::invalid(). This version of the "
255 "constructor requires a valid value of numGlobalElements. "
256 "You probably mistook this constructor for the \"contiguous "
257 "nonuniform\" constructor, which can compute the global "
258 "number of elements for you if you set numGlobalElements to "
259 "Teuchos::OrdinalTraits<Tpetra::global_size_t>::invalid().");
262 if (
lOrG == GloballyDistributed) {
278 const GST myRank =
static_cast<GST>(comm_->getRank());
303 distributed_ =
false;
306 minAllGID_ = indexBase;
307 maxAllGID_ = indexBase + numGlobalElements - 1;
308 indexBase_ = indexBase;
309 numGlobalElements_ = numGlobalElements;
310 numLocalElements_ = numLocalElements;
311 firstContiguousGID_ = minMyGID_;
312 lastContiguousGID_ = maxMyGID_;
314 haveGlobalConstants_ =
true;
320 std::ostringstream os;
321 os << *prefix <<
"Done" << endl;
322 std::cerr << os.str();
326template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
331 const Teuchos::RCP<
const Teuchos::Comm<int>>& comm)
337 using Teuchos::broadcast;
338 using Teuchos::outArg;
339 using Teuchos::REDUCE_MAX;
340 using Teuchos::REDUCE_MIN;
341 using Teuchos::REDUCE_SUM;
342 using Teuchos::reduceAll;
346 const GST GSTI = Tpetra::Details::OrdinalTraits<GST>::invalid();
348 "Map(gblNumInds,lclNumInds,indexBase,comm)";
350 "Tpetra::Map::Map(gblNumInds,lclNumInds,indexBase,comm): ";
352 ". Please report this bug to the Tpetra developers.";
356 std::unique_ptr<std::string>
prefix;
359 comm_.getRawPtr(),
"Map",
funcName);
360 std::ostringstream
os;
362 std::cerr <<
os.str();
397 const int numProcs = comm->getSize();
402 numGlobalElements_ = globalSum;
406 TEUCHOS_TEST_FOR_EXCEPTION(globalSum != debugGlobalSum, std::logic_error, exPfx <<
"globalSum = " << globalSum <<
" != debugGlobalSum = " << debugGlobalSum << suffix);
409 numLocalElements_ = numLocalElements;
410 indexBase_ = indexBase;
411 minAllGID_ = (numGlobalElements_ == 0) ? std::numeric_limits<GO>::max() : indexBase;
412 maxAllGID_ = (numGlobalElements_ == 0) ? std::numeric_limits<GO>::lowest() : indexBase + GO(numGlobalElements_) - GO(1);
413 minMyGID_ = (numLocalElements_ == 0) ? std::numeric_limits<GO>::max() : indexBase + GO(myOffset);
414 maxMyGID_ = (numLocalElements_ == 0) ? std::numeric_limits<GO>::lowest() : indexBase + myOffset + GO(numLocalElements) - GO(1);
415 firstContiguousGID_ = minMyGID_;
416 lastContiguousGID_ = maxMyGID_;
418 distributed_ = (comm->getSize() > 1);
419 haveGlobalConstants_ =
true;
425 std::ostringstream os;
426 os << *prefix <<
"Done" << endl;
427 std::cerr << os.str();
431template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
433Map<LocalOrdinal, GlobalOrdinal, Node>::
434 initialNonuniformDebugCheck(
435 const char errorMessagePrefix[],
437 const size_t numLocalElements,
438 const global_ordinal_type indexBase,
439 const Teuchos::RCP<
const Teuchos::Comm<int>>& comm)
const {
445 using Teuchos::broadcast;
446 using Teuchos::outArg;
448 using Teuchos::REDUCE_MAX;
449 using Teuchos::REDUCE_MIN;
450 using Teuchos::REDUCE_SUM;
451 using Teuchos::reduceAll;
452 using GO = global_ordinal_type;
454 const GST GSTI = Tpetra::Details::OrdinalTraits<GST>::invalid();
481 "must provide the same number of global elements, even if "
483 "Teuchos::OrdinalTraits<Tpetra::global_size_t>::invalid() "
484 "(which signals that the Map should compute the global "
485 "number of elements). Process 0 set numGlobalElements"
498 std::invalid_argument,
errorMessagePrefix <<
"All processes must provide the same indexBase argument. "
499 "Process 0 set indexBase = "
502 << comm->getRank() <<
" set indexBase=" <<
indexBase <<
". The min and max values over all "
510 std::invalid_argument,
512 "indices over all processes, "
515 "would like this constructor to compute numGlobalElements "
516 "for you, you may set numGlobalElements="
517 "Teuchos::OrdinalTraits<Tpetra::global_size_t>::invalid() "
518 "on input. Please note that this is NOT necessarily -1.");
523template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
524void Map<LocalOrdinal, GlobalOrdinal, Node>::
525 initWithNonownedHostIndexList(
526 const char errorMessagePrefix[],
528 const Kokkos::View<
const global_ordinal_type*,
531 Kokkos::MemoryUnmanaged>& entryList_host,
532 const global_ordinal_type indexBase,
533 const Teuchos::RCP<
const Teuchos::Comm<int>>& comm,
534 const Teuchos::RCP<Teuchos::ParameterList>& params) {
537 using Kokkos::LayoutLeft;
538 using Kokkos::subview;
540 using Kokkos::view_alloc;
541 using Kokkos::WithoutInitializing;
543 using Teuchos::broadcast;
544 using Teuchos::outArg;
546 using Teuchos::REDUCE_MAX;
547 using Teuchos::REDUCE_MIN;
548 using Teuchos::REDUCE_SUM;
549 using Teuchos::reduceAll;
553 const GST GSTI = Tpetra::Details::OrdinalTraits<GST>::invalid();
557 << Teuchos::TypeNameTraits<execution_space>::name()
558 <<
" has not been initialized. "
559 "Please initialize it before creating a Map.")
618 numLocalElements_ = numLocalElements;
619 indexBase_ = indexBase;
621 minMyGID_ = indexBase_;
622 maxMyGID_ = indexBase_;
632 if (numLocalElements_ > 0) {
637 typename decltype(lgMap_)::non_const_type lgMap(view_alloc(
"lgMap", WithoutInitializing), numLocalElements_);
639 Kokkos::create_mirror_view(Kokkos::HostSpace(), lgMap);
647 firstContiguousGID_ = entryList_host[0];
648 lastContiguousGID_ = firstContiguousGID_ + 1;
656 lgMap_host[0] = firstContiguousGID_;
658 for (;
i < numLocalElements_; ++
i) {
662 if (lastContiguousGID_ !=
curGid)
break;
669 ++lastContiguousGID_;
671 --lastContiguousGID_;
677 minMyGID_ = firstContiguousGID_;
678 maxMyGID_ = lastContiguousGID_;
689 "Tpetra::Map noncontiguous constructor: "
690 "nonContigGids_host.extent(0) = "
692 <<
" != entryList_host.extent(0) - i = "
695 <<
". Please report this bug to the Tpetra developers.");
705 Kokkos::fence(
"Map::initWithNonownedHostIndexList");
718 for (;
i < numLocalElements_; ++
i) {
720 const LO
curLid =
static_cast<LO
>(
i);
728 if (curGid > maxMyGID_) {
735 Kokkos::deep_copy(execution_space(), lgMap, lgMap_host);
743 minMyGID_ = std::numeric_limits<GlobalOrdinal>::max();
744 maxMyGID_ = std::numeric_limits<GlobalOrdinal>::lowest();
748 firstContiguousGID_ = indexBase_ + 1;
749 lastContiguousGID_ = indexBase_;
755 if (req) req->wait();
757 const bool callComputeGlobalConstants = (params.get() ==
nullptr) ||
758 params->get(
"compute global constants",
true) ||
759 (comm->getSize() == 1);
761 if (callComputeGlobalConstants)
762 computeGlobalConstants();
764 distributed_ = params->get(
"distributed",
true);
771template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
777 const Teuchos::RCP<
const Teuchos::Comm<int>>& comm,
778 const Teuchos::RCP<Teuchos::ParameterList>&
params)
784 "Map(gblNumInds,indexList,indexListSize,indexBase,comm)";
787 std::unique_ptr<std::string>
prefix;
790 comm_.getRawPtr(),
"Map",
funcName);
791 std::ostringstream
os;
793 std::cerr <<
os.str();
798 Impl::checkMapInputArray(
"(GST, const GO[], LO, GO, comm)",
808 Kokkos::MemoryUnmanaged>
813 std::ostringstream
os;
815 std::cerr <<
os.str();
819template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
822 const Teuchos::ArrayView<const GlobalOrdinal>&
entryList,
824 const Teuchos::RCP<
const Teuchos::Comm<int>>& comm,
825 const Teuchos::RCP<Teuchos::ParameterList>&
params)
830 const char*
funcName =
"Map(gblNumInds,entryList(Teuchos::ArrayView),indexBase,comm)";
832 const bool verbose = Details::Behavior::verbose(
"Map");
833 std::unique_ptr<std::string>
prefix;
835 prefix = Details::createPrefix(
836 comm_.getRawPtr(),
"Map",
funcName);
837 std::ostringstream
os;
839 std::cerr <<
os.str();
845 Impl::checkMapInputArray(
"(GST, ArrayView, GO, comm)",
856 Kokkos::MemoryUnmanaged>
861 std::ostringstream
os;
863 std::cerr <<
os.str();
867template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
870 const Kokkos::View<const GlobalOrdinal*, device_type>&
entryList,
872 const Teuchos::RCP<
const Teuchos::Comm<int>>& comm,
873 const Teuchos::RCP<Teuchos::ParameterList>&
params)
877 using Kokkos::LayoutLeft;
878 using Kokkos::subview;
880 using Kokkos::view_alloc;
881 using Kokkos::WithoutInitializing;
884 using Teuchos::ArrayView;
886 using Teuchos::broadcast;
887 using Teuchos::outArg;
889 using Teuchos::REDUCE_MAX;
890 using Teuchos::REDUCE_MIN;
891 using Teuchos::REDUCE_SUM;
892 using Teuchos::reduceAll;
893 using Teuchos::typeName;
896 const GST GSTI = Tpetra::Details::OrdinalTraits<GST>::invalid();
898 "Map(gblNumInds,entryList(Kokkos::View),indexBase,comm)";
901 std::unique_ptr<std::string>
prefix;
904 comm_.getRawPtr(),
"Map",
funcName);
905 std::ostringstream
os;
907 std::cerr <<
os.str();
912 Impl::checkMapInputArray(
"(GST, Kokkos::View, GO, comm)",
914 static_cast<size_t>(
entryList.extent(0)),
941 std::shared_ptr<Details::CommRequest>
req;
977 minMyGID_ = indexBase_;
978 maxMyGID_ = indexBase_;
988 if (numLocalElements_ > 0) {
996 Kokkos::deep_copy(
typename device_type::execution_space(),
lgMap,
entryList);
1010 minMyGID_ = std::numeric_limits<GlobalOrdinal>::max();
1011 maxMyGID_ = std::numeric_limits<GlobalOrdinal>::lowest();
1015 firstContiguousGID_ = indexBase_ + 1;
1016 lastContiguousGID_ = indexBase_;
1020 if (req) req->wait();
1022 const bool callComputeGlobalConstants = (params.get() ==
nullptr) ||
1023 params->get(
"compute global constants",
true) ||
1024 (comm->getSize() == 1);
1026 if (callComputeGlobalConstants)
1029 distributed_ = params->get(
"distributed",
true);
1032 contiguous_ =
false;
1038 std::ostringstream
os;
1040 std::cerr <<
os.str();
1044template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
1049 if (haveGlobalConstants_)
1052 if (comm_->getSize() == 1) {
1053 minAllGID_ = minMyGID_;
1054 maxAllGID_ = maxMyGID_;
1055 distributed_ =
false;
1056 haveGlobalConstants_ =
true;
1083 Kokkos::View<GO*, Kokkos::HostSpace>
minMaxInput(Kokkos::ViewAllocateWithoutInitializing(
"minMaxInput"), 3);
1084 Kokkos::View<GO*, Kokkos::HostSpace>
minMaxOutput(Kokkos::ViewAllocateWithoutInitializing(
"minMaxOutput"), 3);
1086 minMaxInput[0] = std::numeric_limits<GO>::max() - minMyGID_;
1088 minMaxInput[2] = std::numeric_limits<GO>::max() -
static_cast<GO
>(numLocalElements_);
1092 minAllGID_ = std::numeric_limits<GO>::max() -
minMaxOutput[0];
1098 haveGlobalConstants_ =
true;
1101 minAllGID_ < indexBase_,
1102 std::invalid_argument,
1103 "Tpetra::Map constructor (noncontiguous): "
1104 "Minimum global ID = "
1105 << minAllGID_ <<
" over all process(es) is "
1106 "less than the given indexBase = "
1107 << indexBase_ <<
".");
1110template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
1114 minAllGID_ =
map.getMinAllGlobalIndex();
1115 maxAllGID_ =
map.getMaxAllGlobalIndex();
1116 haveGlobalConstants_ =
true;
1117 distributed_ = (getComm()->getSize() > 1) &&
map.distributed_;
1120template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
1122 if (!Kokkos::is_initialized()) {
1123 std::ostringstream
os;
1124 os <<
"WARNING: Tpetra::Map destructor (~Map()) is being called after "
1125 "Kokkos::finalize() has been called. This is user error! There are "
1126 "two likely causes: "
1128 <<
" 1. You have a static Tpetra::Map (or RCP or shared_ptr of a Map)"
1130 <<
" 2. You declare and construct a Tpetra::Map (or RCP or shared_ptr "
1131 "of a Tpetra::Map) at the same scope in main() as Kokkos::finalize() "
1132 "or Tpetra::finalize()."
1135 <<
"Don't do either of these! Please refer to GitHib Issue #2372."
1138 this->getComm().getRawPtr());
1140 using ::Tpetra::Details::mpiIsFinalized;
1141 using ::Tpetra::Details::mpiIsInitialized;
1142 using ::Tpetra::Details::teuchosCommIsAnMpiComm;
1144 Teuchos::RCP<const Teuchos::Comm<int>> comm = this->getComm();
1145 if (!comm.is_null() && teuchosCommIsAnMpiComm(*comm) &&
1146 mpiIsInitialized() && mpiIsFinalized()) {
1152 std::ostringstream
os;
1153 os <<
"WARNING: Tpetra::Map destructor (~Map()) is being called after "
1154 "MPI_Finalize() has been called. This is user error! There are "
1155 "two likely causes: "
1157 <<
" 1. You have a static Tpetra::Map (or RCP or shared_ptr of a Map)"
1159 <<
" 2. You declare and construct a Tpetra::Map (or RCP or shared_ptr "
1160 "of a Tpetra::Map) at the same scope in main() as MPI_finalize() or "
1161 "Tpetra::finalize()."
1164 <<
"Don't do either of these! Please refer to GitHib Issue #2372."
1174template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
1177 getComm().
is_null(), std::logic_error,
1178 "Tpetra::Map::isOneToOne: "
1179 "getComm() returns null. Please report this bug to the Tpetra "
1184 return directory_->isOneToOne(*
this);
1187template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
1191 if (isContiguous()) {
1194 return Tpetra::Details::OrdinalTraits<LocalOrdinal>::invalid();
1209template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
1214 return Tpetra::Details::OrdinalTraits<GlobalOrdinal>::invalid();
1216 if (isContiguous()) {
1228template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
1229bool Map<LocalOrdinal, GlobalOrdinal, Node>::getGlobalElements(
1230 const local_ordinal_type localIndices[],
size_t numEntries, global_ordinal_type globalIndices[])
const {
1231 auto const minGI = getMinGlobalIndex();
1232 auto const minLI = getMinLocalIndex();
1233 auto const maxLI = getMaxLocalIndex();
1234 if (isContiguous()) {
1235 for (
size_t i = 0; i < numEntries; i++) {
1236 auto lclInd = localIndices[i];
1237 if (lclInd < minLI || lclInd > maxLI) {
1240 globalIndices[i] = minGI + lclInd;
1248 for (
size_t i = 0; i < numEntries; i++) {
1249 auto lclInd = localIndices[i];
1250 if (lclInd < minLI || lclInd > maxLI) {
1253 globalIndices[i] = lgMapHost_[lclInd];
1259template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
1269template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
1273 Tpetra::Details::OrdinalTraits<LocalOrdinal>::invalid();
1276template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
1281template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
1286template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
1291 getMinGlobalIndex(), getMaxGlobalIndex(),
1292 firstContiguousGID_, lastContiguousGID_,
1293 getLocalNumElements(), isContiguous());
1296template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
1299 using Teuchos::outArg;
1300 using Teuchos::REDUCE_MIN;
1301 using Teuchos::reduceAll;
1310 }
else if (getComm()->getSize() !=
map.getComm()->getSize()) {
1315 }
else if (getGlobalNumElements() !=
map.getGlobalNumElements()) {
1319 }
else if (isContiguous() && isUniform() &&
1320 map.isContiguous() &&
map.isUniform()) {
1325 }
else if (!isContiguous() && !
map.isContiguous() &&
1326 lgMap_.extent(0) != 0 &&
map.lgMap_.extent(0) != 0 &&
1327 lgMap_.data() ==
map.lgMap_.data()) {
1342 getGlobalNumElements() !=
map.getGlobalNumElements(), std::logic_error,
1343 "Tpetra::Map::isCompatible: There's a bug in this method. We've already "
1344 "checked that this condition is true above, but it's false here. "
1345 "Please report this bug to the Tpetra developers.");
1349 (getLocalNumElements() ==
map.getLocalNumElements()) ? 1 : 0;
1356template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
1359 using Teuchos::ArrayView;
1375 }
else if (getLocalNumElements() !=
map.getLocalNumElements()) {
1377 }
else if (getMinGlobalIndex() !=
map.getMinGlobalIndex() ||
1378 getMaxGlobalIndex() !=
map.getMaxGlobalIndex()) {
1381 if (isContiguous()) {
1382 if (
map.isContiguous()) {
1386 !this->isContiguous() ||
map.isContiguous(), std::logic_error,
1387 "Tpetra::Map::locallySameAs: BUG");
1389 const GO
minLhsGid = this->getMinGlobalIndex();
1399 }
else if (
map.isContiguous()) {
1401 this->isContiguous() || !
map.isContiguous(), std::logic_error,
1402 "Tpetra::Map::locallySameAs: BUG");
1413 }
else if (this->lgMap_.data() ==
map.lgMap_.data()) {
1416 return this->getLocalNumElements() ==
map.getLocalNumElements();
1418 if (this->getLocalNumElements() !=
map.getLocalNumElements()) {
1421 using range_type = Kokkos::RangePolicy<LocalOrdinal, typename node_type::execution_space>;
1427 Kokkos::parallel_reduce(
1428 "Tpetra::Map::locallySameAs",
1429 range_type(0, this->getLocalNumElements()),
1442template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
1453 auto lmap2 = this->getLocalMap();
1463 if (
lmap1.isContiguous() &&
lmap2.isContiguous()) {
1465 return ((
lmap1.getMinGlobalIndex() ==
lmap2.getMinGlobalIndex()) &&
1466 (
lmap1.getMaxGlobalIndex() <=
lmap2.getMaxGlobalIndex()));
1469 if (
lmap1.getMinGlobalIndex() <
lmap2.getMinGlobalIndex() ||
1470 lmap1.getMaxGlobalIndex() >
lmap2.getMaxGlobalIndex()) {
1478 Kokkos::RangePolicy<LO, typename node_type::execution_space>;
1482 Kokkos::parallel_reduce(
1493template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
1496 using Teuchos::outArg;
1497 using Teuchos::REDUCE_MIN;
1498 using Teuchos::reduceAll;
1507 }
else if (getComm()->getSize() !=
map.getComm()->getSize()) {
1512 }
else if (getGlobalNumElements() !=
map.getGlobalNumElements()) {
1516 }
else if (haveGlobalConstants() &&
map.haveGlobalConstants() && (getMinAllGlobalIndex() !=
map.getMinAllGlobalIndex() || getMaxAllGlobalIndex() !=
map.getMaxAllGlobalIndex() || getIndexBase() !=
map.getIndexBase())) {
1520 }
else if (haveGlobalConstants() &&
map.haveGlobalConstants() && (isDistributed() !=
map.isDistributed())) {
1524 }
else if (isContiguous() && isUniform() &&
1525 map.isContiguous() &&
map.isUniform()) {
1554template <
class LO,
class GO,
class DT>
1557 FillLgMap(
const Kokkos::View<GO*, DT>&
lgMap,
1561 Kokkos::RangePolicy<LO, typename DT::execution_space>
1562 range(
static_cast<LO
>(0),
static_cast<LO
>(
lgMap.size()));
1563 Kokkos::parallel_for(
range, *
this);
1566 KOKKOS_INLINE_FUNCTION
void operator()(
const LO& lid)
const {
1567 lgMap_(lid) = startGid_ +
static_cast<GO
>(lid);
1571 const Kokkos::View<GO*, DT> lgMap_;
1577template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
1578typename Map<LocalOrdinal, GlobalOrdinal, Node>::global_indices_array_type
1584 using lg_view_type =
typename const_lg_view_type::non_const_type;
1588 std::unique_ptr<std::string>
prefix;
1591 comm_.getRawPtr(),
"Map",
"getMyGlobalIndices");
1592 std::ostringstream
os;
1594 std::cerr <<
os.str();
1601 lgMap_.extent(0) == 0 && numLocalElements_ > 0;
1605 std::ostringstream
os;
1607 std::cerr <<
os.str();
1613 "Tpetra::Map::getMyGlobalIndices: The local-to-global "
1614 "mapping (lgMap_) should have been set up already for a "
1615 "noncontiguous Map. Please report this bug to the Tpetra "
1618 const LO
numElts =
static_cast<LO
>(getLocalNumElements());
1620 using Kokkos::view_alloc;
1621 using Kokkos::WithoutInitializing;
1624 std::ostringstream
os;
1626 std::cerr <<
os.str();
1631 std::ostringstream
os;
1633 std::cerr <<
os.str();
1636 auto lgMapHost = Kokkos::create_mirror_view(Kokkos::HostSpace(),
lgMap);
1653 std::ostringstream
os;
1655 std::cerr <<
os.str();
1660template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
1661typename Map<LocalOrdinal, GlobalOrdinal, Node>::global_indices_array_device_type
1667 using lg_view_type =
typename const_lg_view_type::non_const_type;
1671 std::unique_ptr<std::string>
prefix;
1674 comm_.getRawPtr(),
"Map",
"getMyGlobalIndicesDevice");
1675 std::ostringstream
os;
1677 std::cerr <<
os.str();
1684 lgMap_.extent(0) == 0 && numLocalElements_ > 0;
1688 std::ostringstream
os;
1690 std::cerr <<
os.str();
1696 "Tpetra::Map::getMyGlobalIndices: The local-to-global "
1697 "mapping (lgMap_) should have been set up already for a "
1698 "noncontiguous Map. Please report this bug to the Tpetra "
1701 const LO
numElts =
static_cast<LO
>(getLocalNumElements());
1703 using Kokkos::view_alloc;
1704 using Kokkos::WithoutInitializing;
1707 std::ostringstream
os;
1709 std::cerr <<
os.str();
1718 std::ostringstream
os;
1720 std::cerr <<
os.str();
1725template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
1726Teuchos::ArrayView<const GlobalOrdinal>
1733 (
void)this->getMyGlobalIndices();
1741 return Teuchos::ArrayView<const GO>(
1743 lgMapHost_.extent(0),
1744 Teuchos::RCP_DISABLE_NODE_LOOKUP);
1747template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
1749 return distributed_;
1752template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
1754 using Teuchos::TypeNameTraits;
1755 std::ostringstream
os;
1757 os <<
"Tpetra::Map: {"
1764 os <<
", Global number of entries: " << getGlobalNumElements()
1765 <<
", Number of processes: " << getComm()->getSize()
1766 <<
", Uniform: " << (isUniform() ?
"true" :
"false")
1767 <<
", Contiguous: " << (isContiguous() ?
"true" :
"false")
1768 <<
", Distributed: " << (isDistributed() ?
"true" :
"false")
1777template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
1781 using LO = local_ordinal_type;
1785 if (
vl < Teuchos::VERB_HIGH) {
1786 return std::string();
1788 auto outStringP = Teuchos::rcp(
new std::ostringstream());
1789 Teuchos::RCP<Teuchos::FancyOStream> outp =
1790 Teuchos::getFancyOStream(outStringP);
1791 Teuchos::FancyOStream& out = *outp;
1793 auto comm = this->getComm();
1794 const int myRank = comm->getRank();
1795 const int numProcs = comm->getSize();
1796 out <<
"Process " << myRank <<
" of " << numProcs <<
":" << endl;
1797 Teuchos::OSTab tab1(out);
1799 const LO numEnt =
static_cast<LO
>(this->getLocalNumElements());
1800 out <<
"My number of entries: " << numEnt << endl
1801 <<
"My minimum global index: " << this->getMinGlobalIndex() << endl
1802 <<
"My maximum global index: " << this->getMaxGlobalIndex() << endl;
1804 if (vl == Teuchos::VERB_EXTREME) {
1805 out <<
"My global indices: [";
1806 const LO minLclInd = this->getMinLocalIndex();
1807 for (LO k = 0; k < numEnt; ++k) {
1808 out << minLclInd + this->getGlobalElement(k);
1809 if (k + 1 < numEnt) {
1817 return outStringP->str();
1820template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
1823 const Teuchos::EVerbosityLevel
verbLevel)
const {
1825 using Teuchos::TypeNameTraits;
1826 using Teuchos::VERB_DEFAULT;
1827 using Teuchos::VERB_HIGH;
1828 using Teuchos::VERB_LOW;
1829 using Teuchos::VERB_NONE;
1832 const Teuchos::EVerbosityLevel
vl =
1842 auto comm = this->getComm();
1843 if (comm.is_null()) {
1846 const int myRank = comm->getRank();
1847 const int numProcs = comm->getSize();
1856 Teuchos::RCP<Teuchos::OSTab>
tab0,
tab1;
1862 tab0 = Teuchos::rcp(
new Teuchos::OSTab(
out));
1863 out <<
"\"Tpetra::Map\":" <<
endl;
1864 tab1 = Teuchos::rcp(
new Teuchos::OSTab(
out));
1866 out <<
"Template parameters:" <<
endl;
1874 out <<
"Label: \"" << label <<
"\"" <<
endl;
1876 out <<
"Global number of entries: " << getGlobalNumElements() <<
endl
1877 <<
"Minimum global index: " << getMinAllGlobalIndex() <<
endl
1878 <<
"Maximum global index: " << getMaxAllGlobalIndex() <<
endl
1879 <<
"Index base: " << getIndexBase() <<
endl
1881 <<
"Uniform: " << (isUniform() ?
"true" :
"false") <<
endl
1882 <<
"Contiguous: " << (isContiguous() ?
"true" :
"false") <<
endl
1883 <<
"Distributed: " << (isDistributed() ?
"true" :
"false") <<
endl;
1888 const std::string
lclStr = this->localDescribeToString(
vl);
1893template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
1894Teuchos::RCP<const Map<LocalOrdinal, GlobalOrdinal, Node>>
1912 return Teuchos::null;
1913 }
else if (
newComm->getSize() == 1) {
1926 newMap->indexBase_ = this->indexBase_;
1927 newMap->numGlobalElements_ = this->numLocalElements_;
1928 newMap->numLocalElements_ = this->numLocalElements_;
1929 newMap->minMyGID_ = this->minMyGID_;
1930 newMap->maxMyGID_ = this->maxMyGID_;
1931 newMap->minAllGID_ = this->minMyGID_;
1932 newMap->maxAllGID_ = this->maxMyGID_;
1933 newMap->firstContiguousGID_ = this->firstContiguousGID_;
1934 newMap->lastContiguousGID_ = this->lastContiguousGID_;
1935 newMap->haveGlobalConstants_ = this->haveGlobalConstants_;
1938 newMap->uniform_ = this->uniform_;
1939 newMap->contiguous_ = this->contiguous_;
1942 newMap->distributed_ =
false;
1943 newMap->lgMap_ = this->lgMap_;
1944 newMap->lgMapHost_ = this->lgMapHost_;
1945 newMap->glMap_ = this->glMap_;
1946 newMap->glMapHost_ = this->glMapHost_;
1966 const GST RECOMPUTE = Tpetra::Details::OrdinalTraits<GST>::invalid();
1982 auto lgMap = this->getMyGlobalIndices();
1984 typename std::decay<
decltype(
lgMap.extent(0))>::type;
1986 static_cast<size_type
>(this->getLocalNumElements());
1987 using Teuchos::TypeNameTraits;
1989 "Tpetra::Map::replaceCommWithSubset: Result of getMyGlobalIndices() "
1993 <<
this->getLocalNumElements() <<
". The latter, upon being "
1994 "cast to size_type = "
1997 <<
lclNumInds <<
". Please report this bug to the Tpetra "
2000 Teuchos::ArrayView<const GO>
lgMap = this->getLocalElementList();
2003 const GO
indexBase = this->getIndexBase();
2010template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
2011Teuchos::RCP<const Map<LocalOrdinal, GlobalOrdinal, Node>>
2015 using Teuchos::Comm;
2016 using Teuchos::null;
2017 using Teuchos::outArg;
2020 using Teuchos::REDUCE_MIN;
2021 using Teuchos::reduceAll;
2028 const int color = (numLocalElements_ == 0) ? 0 : 1;
2045 map->indexBase_ = indexBase_;
2046 map->numGlobalElements_ = numGlobalElements_;
2047 map->numLocalElements_ = numLocalElements_;
2048 map->minMyGID_ = minMyGID_;
2049 map->maxMyGID_ = maxMyGID_;
2050 map->minAllGID_ = minAllGID_;
2051 map->maxAllGID_ = maxAllGID_;
2052 map->firstContiguousGID_ = firstContiguousGID_;
2053 map->lastContiguousGID_ = lastContiguousGID_;
2054 map->haveGlobalConstants_ = haveGlobalConstants_;
2058 map->uniform_ = uniform_;
2059 map->contiguous_ = contiguous_;
2074 if (!distributed_ ||
newComm->getSize() == 1) {
2075 map->distributed_ =
false;
2076 if (
newComm->getSize() == 1) {
2077 map->minAllGID_ =
map->minMyGID_;
2078 map->maxAllGID_ =
map->maxMyGID_;
2079 map->haveGlobalConstants_ =
true;
2082 const int iOwnAllGids = (numLocalElements_ == numGlobalElements_) ? 1 : 0;
2088 map->lgMap_ = lgMap_;
2089 map->lgMapHost_ = lgMapHost_;
2090 map->glMap_ = glMap_;
2091 map->glMapHost_ = glMapHost_;
2108template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
2111 directory_.is_null(), std::logic_error,
2112 "Tpetra::Map::setupDirectory: "
2113 "The Directory is null. "
2114 "Please report this bug to the Tpetra developers.");
2118 if (!directory_->initialized()) {
2120 if (isDistributed() && !isUniform() && !isContiguous())
2121 computeGlobalConstants();
2122 directory_->initialize(*
this);
2126template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
2130 const Teuchos::ArrayView<int>&
PIDs,
2131 const Teuchos::ArrayView<LocalOrdinal>&
LIDs)
const {
2134 using Tpetra::Details::OrdinalTraits;
2135 using size_type = Teuchos::ArrayView<int>::size_type;
2139 std::unique_ptr<std::string>
prefix;
2142 "Map",
"getRemoteIndexList(GIDs,PIDs,LIDs)");
2143 std::ostringstream
os;
2147 std::cerr <<
os.str();
2156 if (getGlobalNumElements() == 0) {
2157 if (
GIDs.size() == 0) {
2159 std::ostringstream
os;
2160 os << *
prefix <<
"Done; both Map & input are empty" <<
endl;
2161 std::cerr <<
os.str();
2166 std::ostringstream
os;
2167 os << *
prefix <<
"Done: Map is empty on all processes, "
2168 "so all output PIDs & LIDs are invalid (-1)."
2170 std::cerr <<
os.str();
2172 for (size_type
k = 0;
k <
PIDs.size(); ++
k) {
2175 for (size_type
k = 0;
k <
LIDs.size(); ++
k) {
2187 std::ostringstream
os;
2189 std::cerr <<
os.str();
2193 std::ostringstream
os;
2194 os << *
prefix <<
"Call directory_->getDirectoryEntries" <<
endl;
2195 std::cerr <<
os.str();
2198 directory_->getDirectoryEntries(*
this,
GIDs,
PIDs,
LIDs);
2200 std::ostringstream
os;
2201 os << *
prefix <<
"Done; getDirectoryEntries returned "
2208 std::cerr <<
os.str();
2213template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
2217 const Teuchos::ArrayView<int>&
PIDs)
const {
2223 std::unique_ptr<std::string>
prefix;
2226 "Map",
"getRemoteIndexList(GIDs,PIDs)");
2227 std::ostringstream
os;
2231 std::cerr <<
os.str();
2234 if (getGlobalNumElements() == 0) {
2235 if (
GIDs.size() == 0) {
2237 std::ostringstream
os;
2238 os << *
prefix <<
"Done; both Map & input are empty" <<
endl;
2239 std::cerr <<
os.str();
2244 std::ostringstream
os;
2245 os << *
prefix <<
"Done: Map is empty on all processes, "
2246 "so all output PIDs are invalid (-1)."
2248 std::cerr <<
os.str();
2250 for (Teuchos::ArrayView<int>::size_type
k = 0;
k <
PIDs.size(); ++
k) {
2251 PIDs[
k] = Tpetra::Details::OrdinalTraits<int>::invalid();
2262 std::ostringstream
os;
2264 std::cerr <<
os.str();
2268 std::ostringstream
os;
2269 os << *
prefix <<
"Call directory_->getDirectoryEntries" <<
endl;
2270 std::cerr <<
os.str();
2273 directory_->getDirectoryEntries(*
this,
GIDs,
PIDs);
2275 std::ostringstream
os;
2276 os << *
prefix <<
"Done; getDirectoryEntries returned "
2281 std::cerr <<
os.str();
2286template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
2288 using exec_space =
typename Node::device_type::execution_space;
2289 if (lgMap_.extent(0) != lgMapHost_.extent(0)) {
2295 auto lgMap_host = Kokkos::create_mirror(Kokkos::HostSpace(), lgMap_);
2308template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
2309Teuchos::RCP<const Teuchos::Comm<int>>
2314template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
2319 using Teuchos::outArg;
2320 using Teuchos::REDUCE_MIN;
2321 using Teuchos::reduceAll;
2324 std::unique_ptr<std::string>
prefix;
2327 comm_.getRawPtr(),
"Map",
"checkIsDist");
2328 std::ostringstream
os;
2330 std::cerr <<
os.str();
2333 bool global =
false;
2334 if (comm_->getSize() > 1) {
2338 if (numGlobalElements_ == as<global_size_t>(numLocalElements_)) {
2351 reduceAll<int, int>(*comm_, REDUCE_MIN, localRep, outArg(allLocalRep));
2352 if (allLocalRep != 1) {
2362 std::ostringstream os;
2363 os << *prefix <<
"Done; global=" << (global ?
"true" :
"false")
2365 std::cerr << os.str();
2372template <
class LocalOrdinal,
class GlobalOrdinal>
2373Teuchos::RCP<const Tpetra::Map<LocalOrdinal, GlobalOrdinal>>
2375 const Teuchos::RCP<
const Teuchos::Comm<int>>& comm) {
2376 typedef LocalOrdinal LO;
2377 typedef GlobalOrdinal GO;
2378 using NT = typename ::Tpetra::Map<LO, GO>::node_type;
2379 return createLocalMapWithNode<LO, GO, NT>(numElements, comm);
2382template <
class LocalOrdinal,
class GlobalOrdinal>
2383Teuchos::RCP<const Tpetra::Map<LocalOrdinal, GlobalOrdinal>>
2385 const Teuchos::RCP<
const Teuchos::Comm<int>>& comm) {
2386 typedef LocalOrdinal LO;
2387 typedef GlobalOrdinal GO;
2388 using NT = typename ::Tpetra::Map<LO, GO>::node_type;
2389 return createUniformContigMapWithNode<LO, GO, NT>(numElements, comm);
2392template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
2393Teuchos::RCP<const Tpetra::Map<LocalOrdinal, GlobalOrdinal, Node>>
2395 const Teuchos::RCP<
const Teuchos::Comm<int>>& comm) {
2398 const GlobalOrdinal indexBase =
static_cast<GlobalOrdinal
>(0);
2400 return rcp(
new map_type(numElements, indexBase, comm, GloballyDistributed));
2403template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
2404Teuchos::RCP<const Tpetra::Map<LocalOrdinal, GlobalOrdinal, Node>>
2406 const Teuchos::RCP<
const Teuchos::Comm<int>>& comm) {
2410 const GlobalOrdinal indexBase = 0;
2413 return rcp(
new map_type(globalNumElts, indexBase, comm, LocallyReplicated));
2416template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
2417Teuchos::RCP<const Tpetra::Map<LocalOrdinal, GlobalOrdinal, Node>>
2419 const size_t localNumElements,
2420 const Teuchos::RCP<
const Teuchos::Comm<int>>& comm) {
2423 const GlobalOrdinal indexBase = 0;
2425 return rcp(
new map_type(numElements, localNumElements, indexBase, comm));
2428template <
class LocalOrdinal,
class GlobalOrdinal>
2429Teuchos::RCP<const Tpetra::Map<LocalOrdinal, GlobalOrdinal>>
2431 const size_t localNumElements,
2432 const Teuchos::RCP<
const Teuchos::Comm<int>>& comm) {
2433 typedef LocalOrdinal LO;
2434 typedef GlobalOrdinal GO;
2440template <
class LocalOrdinal,
class GlobalOrdinal>
2441Teuchos::RCP<const Tpetra::Map<LocalOrdinal, GlobalOrdinal>>
2443 const Teuchos::RCP<
const Teuchos::Comm<int>>& comm) {
2444 typedef LocalOrdinal LO;
2445 typedef GlobalOrdinal GO;
2451template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
2452Teuchos::RCP<const Tpetra::Map<LocalOrdinal, GlobalOrdinal, Node>>
2454 const Teuchos::RCP<
const Teuchos::Comm<int>>& comm) {
2458 const GST INV = Tpetra::Details::OrdinalTraits<GST>::invalid();
2462 const GlobalOrdinal indexBase = 0;
2464 return rcp(
new map_type(INV, elementList, indexBase, comm));
2467template <
class LO,
class GO,
class NT>
2468Teuchos::RCP<const Tpetra::Map<LO, GO, NT>>
2470 using Details::verbosePrintArray;
2473 using Teuchos::Array;
2474 using Teuchos::ArrayView;
2480 const bool verbose = Details::Behavior::verbose(
"Map");
2481 std::unique_ptr<std::string> prefix;
2483 auto comm = M.is_null() ? Teuchos::null : M->getComm();
2484 prefix = Details::createPrefix(
2485 comm.getRawPtr(),
"createOneToOne(Map)");
2486 std::ostringstream os;
2487 os << *prefix <<
"Start" << endl;
2490 const size_t maxNumToPrint = verbose ? Details::Behavior::verbosePrintCountThreshold() : size_t(0);
2491 const GST GINV = Tpetra::Details::OrdinalTraits<GST>::invalid();
2492 const int myRank = M->getComm()->getRank();
2498 if (!M->isDistributed()) {
2505 const GST numGlobalEntries = M->getGlobalNumElements();
2506 if (M->isContiguous()) {
2507 const size_t numLocalEntries =
2508 (myRank == 0) ? as<size_t>(numGlobalEntries) : size_t(0);
2510 std::ostringstream os;
2511 os << *prefix <<
"Input is locally replicated & contiguous; "
2513 << numLocalEntries << endl;
2517 rcp(
new map_type(numGlobalEntries, numLocalEntries,
2518 M->getIndexBase(), M->getComm()));
2520 std::ostringstream os;
2521 os << *prefix <<
"Done" << endl;
2527 std::ostringstream os;
2528 os << *prefix <<
"Input is locally replicated & noncontiguous"
2532 ArrayView<const GO> myGids =
2533 (myRank == 0) ? M->getLocalElementList() : Teuchos::null;
2535 rcp(
new map_type(GINV, myGids(), M->getIndexBase(),
2538 std::ostringstream os;
2539 os << *prefix <<
"Done" << endl;
2544 }
else if (M->isContiguous()) {
2546 std::ostringstream os;
2547 os << *prefix <<
"Input is distributed & contiguous" << endl;
2555 std::ostringstream os;
2556 os << *prefix <<
"Input is distributed & noncontiguous" << endl;
2560 const size_t numMyElems = M->getLocalNumElements();
2561 ArrayView<const GO> myElems = M->getLocalElementList();
2562 Array<int> owner_procs_vec(numMyElems);
2565 std::ostringstream os;
2566 os << *prefix <<
"Call Directory::getDirectoryEntries: ";
2571 directory.getDirectoryEntries(*M, myElems, owner_procs_vec());
2573 std::ostringstream os;
2574 os << *prefix <<
"getDirectoryEntries result: ";
2580 Array<GO> myOwned_vec(numMyElems);
2581 size_t numMyOwnedElems = 0;
2582 for (
size_t i = 0; i < numMyElems; ++i) {
2583 const GO GID = myElems[i];
2584 const int owner = owner_procs_vec[i];
2586 if (myRank == owner) {
2587 myOwned_vec[numMyOwnedElems++] = GID;
2590 myOwned_vec.resize(numMyOwnedElems);
2593 std::ostringstream os;
2594 os << *prefix <<
"Create Map: ";
2599 auto retMap = rcp(
new map_type(GINV, myOwned_vec(),
2600 M->getIndexBase(), M->getComm()));
2602 std::ostringstream os;
2603 os << *prefix <<
"Done" << endl;
2610template <
class LocalOrdinal,
class GlobalOrdinal,
class Node>
2611Teuchos::RCP<const Tpetra::Map<LocalOrdinal, GlobalOrdinal, Node>>
2614 using Details::Behavior;
2615 using Details::verbosePrintArray;
2618 using Teuchos::Array;
2619 using Teuchos::ArrayView;
2622 using Teuchos::toString;
2623 using LO = LocalOrdinal;
2624 using GO = GlobalOrdinal;
2627 const bool verbose = Behavior::verbose(
"Map");
2628 std::unique_ptr<std::string> prefix;
2630 auto comm = M.is_null() ? Teuchos::null : M->getComm();
2631 prefix = Details::createPrefix(
2632 comm.getRawPtr(),
"createOneToOne(Map,TieBreak)");
2633 std::ostringstream os;
2634 os << *prefix <<
"Start" << endl;
2637 const size_t maxNumToPrint = verbose ? Behavior::verbosePrintCountThreshold() : size_t(0);
2644 std::ostringstream os;
2645 os << *prefix <<
"Initialize Directory" << endl;
2648 directory.initialize(*M, tie_break);
2650 std::ostringstream os;
2651 os << *prefix <<
"Done initializing Directory" << endl;
2654 size_t numMyElems = M->getLocalNumElements();
2655 ArrayView<const GO> myElems = M->getLocalElementList();
2656 Array<int> owner_procs_vec(numMyElems);
2658 std::ostringstream os;
2659 os << *prefix <<
"Call Directory::getDirectoryEntries: ";
2664 directory.getDirectoryEntries(*M, myElems, owner_procs_vec());
2666 std::ostringstream os;
2667 os << *prefix <<
"getDirectoryEntries result: ";
2673 const int myRank = M->getComm()->getRank();
2674 Array<GO> myOwned_vec(numMyElems);
2675 size_t numMyOwnedElems = 0;
2676 for (
size_t i = 0; i < numMyElems; ++i) {
2677 const GO GID = myElems[i];
2678 const int owner = owner_procs_vec[i];
2679 if (myRank == owner) {
2680 myOwned_vec[numMyOwnedElems++] = GID;
2683 myOwned_vec.resize(numMyOwnedElems);
2688 Tpetra::Details::OrdinalTraits<global_size_t>::invalid();
2690 std::ostringstream os;
2691 os << *prefix <<
"Create Map: ";
2696 RCP<const map_type> retMap(
new map_type(GINV, myOwned_vec(), M->getIndexBase(),
2699 std::ostringstream os;
2700 os << *prefix <<
"Done" << endl;
2708template <
class p
ids_view_type>
2711 pids_view_type pids;
2713 SortToFit(
int _myRank, pids_view_type _pids)
2718 bool operator()(
size_t i,
size_t j)
const {
2719 if (pids(i) == myRank) {
2720 if (pids(j) == myRank)
2725 if (pids(j) == myRank)
2735template <
class LO,
class GO,
class NT>
2736Teuchos::RCP<const Tpetra::Map<LO, GO, NT>>
2738 Teuchos::RCP<const Tpetra::Map<LO, GO, NT>>
constM =
M;
2748 const pid_type myRank =
M->getComm()->getRank();
2749 const size_t numMyElems =
M->getLocalNumElements();
2751 Kokkos::View<pid_type*, typename NT::memory_space> pids(
"pids",
numMyElems);
2753 auto gids_vec =
M->getLocalElementList();
2756 Kokkos::View<pid_type*, Kokkos::HostSpace, Kokkos::MemoryTraits<Kokkos::Unmanaged>>
pids_h(
pids_vec.data(),
pids_vec.size());
2757 Kokkos::deep_copy(pids,
pids_h);
2760 auto gids =
M->getMyGlobalIndicesDevice();
2762 auto policy = Kokkos::RangePolicy<size_t, typename NT::execution_space>(0,
numMyElems);
2764 Kokkos::View<size_t*, typename NT::memory_space> idx(Kokkos::ViewAllocateWithoutInitializing(
"idx"),
numMyElems);
2765 Kokkos::parallel_for(
2768 Tpetra::Details::SortToFit
cmp(myRank, pids);
2769 Kokkos::sort(
typename NT::execution_space(), idx,
cmp);
2771 Kokkos::View<GO*, typename NT::memory_space>
new_gids(Kokkos::ViewAllocateWithoutInitializing(
"new_gids"),
numMyElems);
2772 Kokkos::parallel_for(
2794#define TPETRA_MAP_INSTANT(LO, GO, NODE) \
2796 template class Map<LO, GO, NODE>; \
2798 template Teuchos::RCP<const Map<LO, GO, NODE>> \
2799 createLocalMapWithNode<LO, GO, NODE>(const size_t numElements, \
2800 const Teuchos::RCP<const Teuchos::Comm<int>>& comm); \
2802 template Teuchos::RCP<const Map<LO, GO, NODE>> \
2803 createContigMapWithNode<LO, GO, NODE>(const global_size_t numElements, \
2804 const size_t localNumElements, \
2805 const Teuchos::RCP<const Teuchos::Comm<int>>& comm); \
2807 template Teuchos::RCP<const Map<LO, GO, NODE>> \
2808 createNonContigMapWithNode(const Teuchos::ArrayView<const GO>& elementList, \
2809 const Teuchos::RCP<const Teuchos::Comm<int>>& comm); \
2811 template Teuchos::RCP<const Map<LO, GO, NODE>> \
2812 createUniformContigMapWithNode<LO, GO, NODE>(const global_size_t numElements, \
2813 const Teuchos::RCP<const Teuchos::Comm<int>>& comm); \
2815 template Teuchos::RCP<const Map<LO, GO, NODE>> \
2816 createOneToOne(const Teuchos::RCP<const Map<LO, GO, NODE>>& M); \
2818 template Teuchos::RCP<const Map<LO, GO, NODE>> \
2819 createOneToOne(const Teuchos::RCP<const Map<LO, GO, NODE>>& M, \
2820 const Tpetra::Details::TieBreak<LO, GO>& tie_break); \
2822 template Teuchos::RCP<const Map<LO, GO, NODE>> \
2823 createOneToOneAndMakeOverlappingMapFitted(Teuchos::RCP<const Map<LO, GO, NODE>>& M);
2826#define TPETRA_MAP_INSTANT_DEFAULTNODE(LO, GO) \
2827 template Teuchos::RCP<const Map<LO, GO>> \
2828 createLocalMap<LO, GO>(const size_t, const Teuchos::RCP<const Teuchos::Comm<int>>&); \
2830 template Teuchos::RCP<const Map<LO, GO>> \
2831 createContigMap<LO, GO>(global_size_t, size_t, \
2832 const Teuchos::RCP<const Teuchos::Comm<int>>&); \
2834 template Teuchos::RCP<const Map<LO, GO>> \
2835 createNonContigMap(const Teuchos::ArrayView<const GO>&, \
2836 const Teuchos::RCP<const Teuchos::Comm<int>>&); \
2838 template Teuchos::RCP<const Map<LO, GO>> \
2839 createUniformContigMap<LO, GO>(const global_size_t, \
2840 const Teuchos::RCP<const Teuchos::Comm<int>>&);
Functions for initializing and finalizing Tpetra.
Declaration of Tpetra::Details::Behavior, a class that describes Tpetra's behavior.
Declaration of Tpetra::Details::Profiling, a scope guard for Kokkos Profiling.
Declaration of a function that prints strings from each process.
Declaration of Tpetra::Details::iallreduce.
Declaration of Tpetra::Details::initializeKokkos.
Declaration of Tpetra::Details::printOnce.
Declaration of the Tpetra::Map class and related nonmember constructors.
Stand-alone utility functions and macros.
Struct that holds views of the contents of a CrsMatrix.
Description of Tpetra's behavior.
static void reject_unrecognized_env_vars()
Search the environment for TPETRA_ variables and reject unrecognized ones.
static bool debug()
Whether Tpetra is in debug mode.
static bool verbose()
Whether Tpetra is in verbose mode.
static size_t verbosePrintCountThreshold()
Number of entries below which arrays, lists, etc. will be printed in debug mode.
"Local" part of Map suitable for Kokkos kernels.
Interface for breaking ties in ownership.
Implement mapping from global ID to process ID and local ID.
A parallel distribution of indices over processes.
bool isDistributed() const
Whether this Map is globally distributed or locally replicated.
bool isOneToOne() const
Whether the Map is one to one.
std::string description() const
Implementation of Teuchos::Describable.
Teuchos::ArrayView< const global_ordinal_type > getLocalElementList() const
Return a NONOWNING view of the global indices owned by this process.
::Tpetra::Details::FixedHashTable< global_ordinal_type, local_ordinal_type, device_type > global_to_local_table_type
Type of a mapping from global IDs to local IDs.
global_ordinal_type getGlobalElement(local_ordinal_type localIndex) const
The global index corresponding to the given local index.
Node node_type
Legacy typedef that will go away at some point.
Kokkos::View< const global_ordinal_type *, Kokkos::LayoutLeft, device_type > lgMap_
A mapping from local IDs to global IDs.
Map()
Default constructor (that does nothing).
GlobalOrdinal global_ordinal_type
The type of global indices.
LookupStatus getRemoteIndexList(const Teuchos::ArrayView< const global_ordinal_type > &GIDList, const Teuchos::ArrayView< int > &nodeIDList, const Teuchos::ArrayView< local_ordinal_type > &LIDList) const
Return the process ranks and corresponding local indices for the given global indices.
bool isNodeLocalElement(local_ordinal_type localIndex) const
Whether the given local index is valid for this Map on the calling process.
bool isUniform() const
Whether the range of global indices is uniform.
Teuchos::RCP< const Teuchos::Comm< int > > getComm() const
Accessors for the Teuchos::Comm and Kokkos Node objects.
typename device_type::execution_space execution_space
The Kokkos execution space.
LO local_ordinal_type
The type of local indices.
Teuchos::RCP< const Map< local_ordinal_type, global_ordinal_type, Node > > removeEmptyProcesses() const
Advanced methods.
void lazyPushToHost() const
Push the device data to host, if needed.
void copyGlobalConstants(const Map< local_ordinal_type, global_ordinal_type, Node > &map)
Copy global constants from a different map.
bool isCompatible(const Map< local_ordinal_type, global_ordinal_type, Node > &map) const
True if and only if map is compatible with this Map.
bool locallySameAs(const Map< local_ordinal_type, global_ordinal_type, node_type > &map) const
Is this Map locally the same as the input Map?
bool isLocallyFitted(const Map< local_ordinal_type, global_ordinal_type, Node > &map) const
True if and only if map is locally fitted to this Map.
virtual ~Map()
Destructor (virtual for memory safety of derived classes).
global_indices_array_device_type getMyGlobalIndicesDevice() const
Return a view of the global indices owned by this process on the Map's device.
local_ordinal_type getLocalElement(global_ordinal_type globalIndex) const
The local index corresponding to the given global index.
Teuchos::RCP< const Map< local_ordinal_type, global_ordinal_type, Node > > replaceCommWithSubset(const Teuchos::RCP< const Teuchos::Comm< int > > &newComm) const
Replace this Map's communicator with a subset communicator.
bool isContiguous() const
True if this Map is distributed contiguously, else false.
void describe(Teuchos::FancyOStream &out, const Teuchos::EVerbosityLevel verbLevel=Teuchos::Describable::verbLevel_default) const
Describe this object in a human-readable way to the given output stream.
bool isNodeGlobalElement(global_ordinal_type globalIndex) const
Whether the given global index is owned by this Map on the calling process.
bool isSameAs(const Map< local_ordinal_type, global_ordinal_type, Node > &map) const
True if and only if map is identical to this Map.
global_to_local_table_type glMap_
A mapping from global IDs to local IDs.
local_map_type getLocalMap() const
Get the LocalMap for Kokkos-Kernels.
global_indices_array_type getMyGlobalIndices() const
Return a view of the global indices owned by this process.
void computeGlobalConstants() const
Compute global constants for the map. This method needs to be called collectively over all processes ...
typename Node::device_type device_type
This class' Kokkos::Device specialization.
Implementation details of Tpetra.
Nonmember function that computes a residual Computes R = B - A * X.
void verbosePrintArray(std::ostream &out, const ArrayType &x, const char name[], const size_t maxNumToPrint)
Print min(x.size(), maxNumToPrint) entries of x.
void printOnce(std::ostream &out, const std::string &s, const Teuchos::Comm< int > *comm)
Print on one process of the given communicator, or at least try to do so (if MPI is not initialized).
std::unique_ptr< std::string > createPrefix(const int myRank, const char prefix[])
Create string prefix for each line of verbose output.
bool congruent(const Teuchos::Comm< int > &comm1, const Teuchos::Comm< int > &comm2)
Whether the two communicators are congruent.
void initializeKokkos(int *argc, char ***argv, int myRank)
Initialize Kokkos, using command-line arguments (if any) given to Teuchos::GlobalMPISession.
void gathervPrint(std::ostream &out, const std::string &s, const Teuchos::Comm< int > &comm)
On Process 0 in the given communicator, print strings from each process in that communicator,...
Namespace Tpetra contains the class and methods constituting the Tpetra library.
Teuchos::RCP< const Map< LocalOrdinal, GlobalOrdinal > > createLocalMap(const size_t numElements, const Teuchos::RCP< const Teuchos::Comm< int > > &comm)
Nonmember constructor for a locally replicated Map with the default Kokkos Node.
Teuchos::RCP< const Map< LocalOrdinal, GlobalOrdinal > > createUniformContigMap(const global_size_t numElements, const Teuchos::RCP< const Teuchos::Comm< int > > &comm)
Non-member constructor for a uniformly distributed, contiguous Map with the default Kokkos Node.
Teuchos::RCP< const Map< LocalOrdinal, GlobalOrdinal > > createNonContigMap(const Teuchos::ArrayView< const GlobalOrdinal > &elementList, const Teuchos::RCP< const Teuchos::Comm< int > > &comm)
Nonmember constructor for a non-contiguous Map using the default Kokkos::Device type.
Teuchos::RCP< const Map< LocalOrdinal, GlobalOrdinal, Node > > createUniformContigMapWithNode(const global_size_t numElements, const Teuchos::RCP< const Teuchos::Comm< int > > &comm)
Non-member constructor for a uniformly distributed, contiguous Map with a user-specified Kokkos Node.
Teuchos::RCP< const Tpetra::Map< LO, GO, NT > > createOneToOneAndMakeOverlappingMapFitted(Teuchos::RCP< const Tpetra::Map< LO, GO, NT > > &M)
Creates a one-to-one version of the given Map where each GID lives on only one process....
LookupStatus
Return status of Map remote index lookup (getRemoteIndexList()).
Teuchos::RCP< const Map< LocalOrdinal, GlobalOrdinal > > createContigMap(const global_size_t numElements, const size_t localNumElements, const Teuchos::RCP< const Teuchos::Comm< int > > &comm)
Non-member constructor for a (potentially) non-uniformly distributed, contiguous Map using the defaul...
size_t global_size_t
Global size_t object.
Teuchos::RCP< const Map< LocalOrdinal, GlobalOrdinal, Node > > createOneToOne(const Teuchos::RCP< const Map< LocalOrdinal, GlobalOrdinal, Node > > &M)
Nonmember constructor for a contiguous Map with user-defined weights and a user-specified,...
Teuchos::RCP< const Map< LocalOrdinal, GlobalOrdinal, Node > > createLocalMapWithNode(const size_t numElements, const Teuchos::RCP< const Teuchos::Comm< int > > &comm)
Nonmember constructor for a locally replicated Map with a specified Kokkos Node.
Teuchos::RCP< const Map< LocalOrdinal, GlobalOrdinal, Node > > createNonContigMapWithNode(const Teuchos::ArrayView< const GlobalOrdinal > &elementList, const Teuchos::RCP< const Teuchos::Comm< int > > &comm)
Nonmember constructor for a noncontiguous Map with a user-specified, possibly nondefault Kokkos Node ...
LocalGlobal
Enum for local versus global allocation of Map entries.
Teuchos::RCP< const Map< LocalOrdinal, GlobalOrdinal, Node > > createContigMapWithNode(const global_size_t numElements, const size_t localNumElements, const Teuchos::RCP< const Teuchos::Comm< int > > &comm)
Nonmember constructor for a (potentially) nonuniformly distributed, contiguous Map for a user-specifi...