All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
Xpetra_StridedMap_def.hpp
Go to the documentation of this file.
1 // @HEADER
2 //
3 // ***********************************************************************
4 //
5 // Xpetra: A linear algebra interface package
6 // Copyright 2012 Sandia Corporation
7 //
8 // Under the terms of Contract DE-AC04-94AL85000 with Sandia Corporation,
9 // the U.S. Government retains certain rights in this software.
10 //
11 // Redistribution and use in source and binary forms, with or without
12 // modification, are permitted provided that the following conditions are
13 // met:
14 //
15 // 1. Redistributions of source code must retain the above copyright
16 // notice, this list of conditions and the following disclaimer.
17 //
18 // 2. Redistributions in binary form must reproduce the above copyright
19 // notice, this list of conditions and the following disclaimer in the
20 // documentation and/or other materials provided with the distribution.
21 //
22 // 3. Neither the name of the Corporation nor the names of the
23 // contributors may be used to endorse or promote products derived from
24 // this software without specific prior written permission.
25 //
26 // THIS SOFTWARE IS PROVIDED BY SANDIA CORPORATION "AS IS" AND ANY
27 // EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
28 // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
29 // PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL SANDIA CORPORATION OR THE
30 // CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
31 // EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
32 // PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
33 // PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
34 // LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
35 // NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
36 // SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
37 //
38 // Questions? Contact
39 // Jonathan Hu (jhu@sandia.gov)
40 // Andrey Prokopenko (aprokop@sandia.gov)
41 // Ray Tuminaro (rstumin@sandia.gov)
42 //
43 // ***********************************************************************
44 //
45 // @HEADER
46 
47 // WARNING: This code is experimental. Backwards compatibility should not be expected.
48 
49 #ifndef XPETRA_STRIDEDMAP_DEF_HPP
50 #define XPETRA_STRIDEDMAP_DEF_HPP
51 
53 
55 
56 #include "Xpetra_Exceptions.hpp"
57 #include "Xpetra_MapFactory.hpp"
58 
59 namespace Xpetra {
60 
61 
62 
63 #ifdef TPETRA_ENABLE_DEPRECATED_CODE
64 template<class LocalOrdinal, class GlobalOrdinal, class Node>
65 TPETRA_DEPRECATED
68  global_size_t numGlobalElements,
69  GlobalOrdinal indexBase,
70  std::vector<size_t>& stridingInfo,
71  const Teuchos::RCP<const Teuchos::Comm<int>>& comm,
72  LocalOrdinal stridedBlockId, // FIXME (mfh 03 Sep 2014) This breaks for unsigned LocalOrdinal
73  GlobalOrdinal offset,
74  LocalGlobal lg,
75  const Teuchos::RCP<Node>& /* node */)
76  : StridedMap(xlib, numGlobalElements, indexBase, stridingInfo, comm, stridedBlockId, offset, lg)
77 {
78 }
79 #endif // #ifdef TPETRA_ENABLE_DEPRECATED_CODE
80 
81 
82 template<class LocalOrdinal, class GlobalOrdinal, class Node>
83 StridedMap<LocalOrdinal, GlobalOrdinal, Node>::
84 StridedMap(UnderlyingLib xlib,
85  global_size_t numGlobalElements,
86  GlobalOrdinal indexBase,
87  std::vector<size_t>& stridingInfo,
88  const Teuchos::RCP<const Teuchos::Comm<int>>& comm,
89  LocalOrdinal stridedBlockId, // FIXME (mfh 03 Sep 2014) This breaks for unsigned LocalOrdinal
90  GlobalOrdinal offset,
91  LocalGlobal lg)
92  : stridingInfo_(stridingInfo), stridedBlockId_(stridedBlockId), offset_(offset), indexBase_(indexBase)
93 {
95 
96  size_t blkSize = getFixedBlockSize();
97 
98  TEUCHOS_TEST_FOR_EXCEPTION(stridingInfo.size() == 0,
100  "StridedMap::StridedMap: stridingInfo not valid: stridingInfo.size() = 0?");
101 
103  std::invalid_argument,
104  "StridedMap::StridedMap: numGlobalElements is invalid");
105 
106  TEUCHOS_TEST_FOR_EXCEPTION(numGlobalElements % blkSize != 0,
108  "StridedMap::StridedMap: stridingInfo not valid: getFixedBlockSize "
109  "is not an integer multiple of numGlobalElements.");
110 
111  if(stridedBlockId != -1)
112  {
113  TEUCHOS_TEST_FOR_EXCEPTION(stridingInfo.size() < static_cast<size_t>(stridedBlockId),
115  "StridedTpetraMap::StridedTpetraMap: "
116  "stridedBlockId > stridingInfo.size()");
117  }
118 
119  // Try to create a shortcut
120  if(blkSize != 1 || offset_ != 0)
121  {
122  // check input data and reorganize map
123  global_size_t numGlobalNodes = numGlobalElements / blkSize;
124 
125  // build an equally distributed node map
126  RCP<Map> nodeMap = MapFactory_t::Build(xlib, numGlobalNodes, indexBase, comm, lg);
127  global_size_t numLocalNodes = nodeMap->getNodeNumElements();
128 
129  // translate local node ids to local dofs
130  size_t nStridedOffset = 0;
131  size_t nDofsPerNode = blkSize; // dofs per node for local striding block
132  if(stridedBlockId > -1)
133  {
134  for(int j = 0; j < stridedBlockId; j++)
135  {
136  nStridedOffset += stridingInfo_[ j ];
137  }
138 
139  nDofsPerNode = stridingInfo_[ stridedBlockId ];
140  numGlobalElements = numGlobalNodes * Teuchos::as<global_size_t>(nDofsPerNode);
141  }
142  size_t numLocalElements = numLocalNodes * Teuchos::as<size_t>(nDofsPerNode);
143 
144  std::vector<GlobalOrdinal> dofgids(numLocalElements);
145  for(LocalOrdinal i = 0; i < Teuchos::as<LocalOrdinal>(numLocalNodes); i++)
146  {
147  GlobalOrdinal nodeGID = nodeMap->getGlobalElement(i);
148 
149  for(size_t j = 0; j < nDofsPerNode; j++)
150  {
151  dofgids[ i * nDofsPerNode + j ] = indexBase_ + offset_
152  + (nodeGID - indexBase_) * Teuchos::as<GlobalOrdinal>(blkSize)
153  + Teuchos::as<GlobalOrdinal>(nStridedOffset + j);
154  }
155  }
156 
157  map_ = MapFactory_t::Build(xlib, numGlobalElements, dofgids, indexBase, comm);
158 
159  if(stridedBlockId == -1)
160  {
161  TEUCHOS_TEST_FOR_EXCEPTION(getNodeNumElements() != Teuchos::as<size_t>(nodeMap->getNodeNumElements() * nDofsPerNode),
163  "StridedTpetraMap::StridedTpetraMap: wrong distribution of dofs among processors.");
164 
165  TEUCHOS_TEST_FOR_EXCEPTION(getGlobalNumElements()
166  != Teuchos::as<size_t>(nodeMap->getGlobalNumElements() * nDofsPerNode),
168  "StridedTpetraMap::StridedTpetraMap: wrong distribution of dofs among processors.");
169  }
170  else
171  {
172  size_t nDofsInStridedBlock = stridingInfo[ stridedBlockId ];
173  TEUCHOS_TEST_FOR_EXCEPTION(getNodeNumElements()
174  != Teuchos::as<size_t>(nodeMap->getNodeNumElements() * nDofsInStridedBlock),
176  "StridedTpetraMap::StridedTpetraMap: wrong distribution of dofs among processors.");
177 
178  TEUCHOS_TEST_FOR_EXCEPTION(getGlobalNumElements()
179  != Teuchos::as<size_t>(nodeMap->getGlobalNumElements() * nDofsInStridedBlock),
181  "StridedTpetraMap::StridedTpetraMap: wrong distribution of dofs among processors.");
182  }
183  }
184  else
185  {
186  map_ = MapFactory_t::Build(xlib, numGlobalElements, indexBase, comm, lg);
187  }
188 
189  TEUCHOS_TEST_FOR_EXCEPTION(CheckConsistency() == false, Exceptions::RuntimeError, "StridedTpetraMap::StridedTpetraMap: CheckConsistency() == false");
190 }
191 
192 
193 #ifdef TPETRA_ENABLE_DEPRECATED_CODE
194 template<class LocalOrdinal, class GlobalOrdinal, class Node>
195 TPETRA_DEPRECATED
198  global_size_t numGlobalElements,
199  size_t numLocalElements,
200  GlobalOrdinal indexBase,
201  std::vector<size_t>& stridingInfo,
202  const Teuchos::RCP<const Teuchos::Comm<int>>& comm,
203  LocalOrdinal stridedBlockId,
204  GlobalOrdinal offset,
205  const Teuchos::RCP<Node>& /* node */)
206  : StridedMap(xlib, numGlobalElements, numLocalElements, indexBase, stridingInfo, comm, stridedBlockId, offset)
207 {
208 }
209 #endif // TPETRA_ENABLE_DEPRECATED_CODE
210 
211 
212 template<class LocalOrdinal, class GlobalOrdinal, class Node>
215  global_size_t numGlobalElements,
216  size_t numLocalElements,
217  GlobalOrdinal indexBase,
218  std::vector<size_t>& stridingInfo,
219  const Teuchos::RCP<const Teuchos::Comm<int>>& comm,
220  LocalOrdinal stridedBlockId,
221  GlobalOrdinal offset)
222  : stridingInfo_(stridingInfo), stridedBlockId_(stridedBlockId), offset_(offset), indexBase_(indexBase)
223 {
225 
226  size_t blkSize = getFixedBlockSize();
227  TEUCHOS_TEST_FOR_EXCEPTION(stridingInfo.size() == 0,
229  "StridedMap::StridedMap: stridingInfo not valid: stridingInfo.size() = 0?");
230  if(numGlobalElements != Teuchos::OrdinalTraits<global_size_t>::invalid())
231  {
232  TEUCHOS_TEST_FOR_EXCEPTION(numGlobalElements % blkSize != 0,
234  "StridedMap::StridedMap: stridingInfo not valid: getFixedBlockSize is not an integer "
235  "multiple of numGlobalElements.");
236 #ifdef HAVE_XPETRA_DEBUG
237  // We have to do this check ourselves, as we don't necessarily construct the full Tpetra map
238  global_size_t sumLocalElements;
239  Teuchos::reduceAll(*comm, Teuchos::REDUCE_SUM, Teuchos::as<global_size_t>(numLocalElements), Teuchos::outArg(sumLocalElements));
240 
241  TEUCHOS_TEST_FOR_EXCEPTION(sumLocalElements != numGlobalElements,
242  std::invalid_argument,
243  "StridedMap::StridedMap: sum of numbers of local elements is different from the provided "
244  "number of global elements.");
245 #endif
246  }
247 
249  numLocalElements % blkSize != 0,
251  "StridedMap::StridedMap: stridingInfo not valid: getFixedBlockSize is not an integer multiple of numLocalElements.");
252 
253  if(stridedBlockId != -1)
254  {
255  TEUCHOS_TEST_FOR_EXCEPTION(stridingInfo.size() < Teuchos::as<size_t>(stridedBlockId),
257  "StridedTpetraMap::StridedTpetraMap: stridedBlockId > stridingInfo.size()");
258  }
259 
260  // Try to create a shortcut
261  if(blkSize != 1 || offset_ != 0)
262  {
263  // check input data and reorganize map
265  if(numGlobalElements != Teuchos::OrdinalTraits<global_size_t>::invalid())
266  {
267  numGlobalNodes = numGlobalElements / blkSize;
268  }
269  global_size_t numLocalNodes = numLocalElements / blkSize;
270 
271  // build an equally distributed node map
272  RCP<Map> nodeMap = MapFactory_t::Build(xlib, numGlobalNodes, numLocalNodes, indexBase, comm);
273 
274  // translate local node ids to local dofs
275  size_t nStridedOffset = 0;
276  size_t nDofsPerNode = blkSize; // dofs per node for local striding block
277  if(stridedBlockId > -1)
278  {
279  for(int j = 0; j < stridedBlockId; j++)
280  {
281  nStridedOffset += stridingInfo_[ j ];
282  }
283 
284  nDofsPerNode = stridingInfo_[ stridedBlockId ];
285  numGlobalElements = nodeMap->getGlobalNumElements() * Teuchos::as<global_size_t>(nDofsPerNode);
286  }
287  numLocalElements = numLocalNodes * Teuchos::as<size_t>(nDofsPerNode);
288 
289  std::vector<GlobalOrdinal> dofgids(numLocalElements);
290  for(LocalOrdinal i = 0; i < Teuchos::as<LocalOrdinal>(numLocalNodes); i++)
291  {
292  GlobalOrdinal nodeGID = nodeMap->getGlobalElement(i);
293 
294  for(size_t j = 0; j < nDofsPerNode; j++)
295  {
296  dofgids[ i * nDofsPerNode + j ] = indexBase_ + offset_
297  + (nodeGID - indexBase_) * Teuchos::as<GlobalOrdinal>(blkSize)
298  + Teuchos::as<GlobalOrdinal>(nStridedOffset + j);
299  }
300  }
301 
302  map_ = MapFactory_t::Build(xlib, numGlobalElements, dofgids, indexBase, comm);
303 
304  if(stridedBlockId == -1)
305  {
306  TEUCHOS_TEST_FOR_EXCEPTION(getNodeNumElements() != Teuchos::as<size_t>(nodeMap->getNodeNumElements() * nDofsPerNode),
308  "StridedTpetraMap::StridedTpetraMap: wrong distribution of dofs among processors.");
309 
311  != Teuchos::as<size_t>(nodeMap->getGlobalNumElements() * nDofsPerNode),
313  "StridedTpetraMap::StridedTpetraMap: wrong distribution of dofs among processors.");
314  }
315  else
316  {
317  int nDofsInStridedBlock = stridingInfo[ stridedBlockId ];
318 
320  != Teuchos::as<size_t>(nodeMap->getNodeNumElements() * nDofsInStridedBlock),
322  "StridedTpetraMap::StridedTpetraMap: wrong distribution of dofs among processors.");
323 
325  != Teuchos::as<size_t>(nodeMap->getGlobalNumElements() * nDofsInStridedBlock),
327  "StridedTpetraMap::StridedTpetraMap: wrong distribution of dofs among processors.");
328  }
329  }
330  else
331  {
332  map_ = MapFactory_t::Build(xlib, numGlobalElements, numLocalElements, indexBase, comm);
333  }
334 
335  TEUCHOS_TEST_FOR_EXCEPTION(CheckConsistency() == false, Exceptions::RuntimeError, "StridedTpetraMap::StridedTpetraMap: CheckConsistency() == false");
336 }
337 
338 
339 #ifdef TPETRA_ENABLE_DEPRECATED_CODE
340 template<class LocalOrdinal, class GlobalOrdinal, class Node>
341 TPETRA_DEPRECATED
344  global_size_t numGlobalElements,
345  const Teuchos::ArrayView<const GlobalOrdinal>& elementList,
346  GlobalOrdinal indexBase,
347  std::vector<size_t>& stridingInfo,
348  const Teuchos::RCP<const Teuchos::Comm<int>>& comm,
349  LocalOrdinal stridedBlockId,
350  const Teuchos::RCP<Node>& /* node */)
351  : StridedMap(xlib, numGlobalElements, elementList, indexBase, stridingInfo, comm, stridedBlockId)
352 {
353 }
354 #endif // TPETRA_ENABLE_DEPRECATED_CODE
355 
356 
357 template<class LocalOrdinal, class GlobalOrdinal, class Node>
360  global_size_t numGlobalElements,
361  const Teuchos::ArrayView<const GlobalOrdinal>& elementList,
362  GlobalOrdinal indexBase,
363  std::vector<size_t>& stridingInfo,
364  const Teuchos::RCP<const Teuchos::Comm<int>>& comm,
365  LocalOrdinal stridedBlockId)
366  : stridingInfo_(stridingInfo), stridedBlockId_(stridedBlockId), indexBase_(indexBase)
367 {
369 
370  size_t blkSize = getFixedBlockSize();
371 
372  TEUCHOS_TEST_FOR_EXCEPTION(stridingInfo.size() == 0,
374  "StridedMap::StridedMap: stridingInfo not valid: stridingInfo.size() = 0?");
375  if(stridedBlockId != -1)
376  TEUCHOS_TEST_FOR_EXCEPTION(stridingInfo.size() < Teuchos::as<size_t>(stridedBlockId),
378  "StridedTpetraMap::StridedTpetraMap: stridedBlockId > stridingInfo.size()");
379  if(numGlobalElements != Teuchos::OrdinalTraits<global_size_t>::invalid())
380  {
381  TEUCHOS_TEST_FOR_EXCEPTION(numGlobalElements % blkSize != 0,
383  "StridedMap::StridedMap: stridingInfo not valid: getFixedBlockSize is not an integer "
384  "multiple of numGlobalElements.");
385 #ifdef HAVE_XPETRA_DEBUG
386  // We have to do this check ourselves, as we don't necessarily construct the full Tpetra map
387  global_size_t sumLocalElements, numLocalElements = elementList.size();
388  Teuchos::reduceAll(*comm, Teuchos::REDUCE_SUM, numLocalElements, Teuchos::outArg(sumLocalElements));
389  TEUCHOS_TEST_FOR_EXCEPTION(sumLocalElements != numGlobalElements,
390  std::invalid_argument,
391  "StridedMap::StridedMap: sum of numbers of local elements is different from the provided "
392  "number of global elements.");
393 #endif
394  }
395 
396  if(stridedBlockId == -1)
397  {
398  // numGlobalElements can be -1! FIXME
399  // TEUCHOS_TEST_FOR_EXCEPTION(numGlobalElements % blkSize != 0, Exceptions::RuntimeError,
400  // "StridedMap::StridedMap: stridingInfo not valid: getFixedBlockSize is not an integer multiple of
401  // numGlobalElements.");
402  TEUCHOS_TEST_FOR_EXCEPTION(elementList.size() % blkSize != 0,
404  "StridedMap::StridedMap: stridingInfo not valid: getFixedBlockSize is not an integer "
405  "multiple of elementList.size().");
406  }
407  else
408  {
409  // numGlobalElements can be -1! FIXME
410  // TEUCHOS_TEST_FOR_EXCEPTION(numGlobalElements % stridingInfo[stridedBlockId] != 0, Exceptions::RuntimeError,
411  // "StridedMap::StridedMap: stridingInfo not valid: stridingBlockInfo[stridedBlockId] is not an integer multiple of
412  // numGlobalElements.");
413  TEUCHOS_TEST_FOR_EXCEPTION(elementList.size() % stridingInfo[ stridedBlockId ] != 0,
415  "StridedMap::StridedMap: stridingInfo not valid: stridingBlockInfo[stridedBlockId] is not "
416  "an integer multiple of elementList.size().");
417  }
418 
419  map_ = MapFactory_t::Build(xlib, numGlobalElements, elementList, indexBase, comm);
420 
421  // calculate offset_
422 
423  // find minimum GID over all procs
424  GlobalOrdinal minGidOnCurProc = Teuchos::OrdinalTraits<GlobalOrdinal>::max();
425  for(Teuchos_Ordinal k = 0; k < elementList.size(); k++) // TODO fix occurence of Teuchos_Ordinal
426  {
427  if(elementList[ k ] < minGidOnCurProc)
428  {
429  minGidOnCurProc = elementList[ k ];
430  }
431  }
432 
433  Teuchos::reduceAll(*comm, Teuchos::REDUCE_MIN, minGidOnCurProc, Teuchos::outArg(offset_));
434 
435  // calculate striding index
436  size_t nStridedOffset = 0;
437  for(int j = 0; j < stridedBlockId; j++)
438  {
439  nStridedOffset += stridingInfo[ j ];
440  }
441  const GlobalOrdinal goStridedOffset = Teuchos::as<GlobalOrdinal>(nStridedOffset);
442 
443  // adapt offset_
444  offset_ -= goStridedOffset + indexBase_;
445 
446  TEUCHOS_TEST_FOR_EXCEPTION(CheckConsistency() == false, Exceptions::RuntimeError, "StridedTpetraMap::StridedTpetraMap: CheckConsistency() == false");
447 }
448 
449 
450 template<class LocalOrdinal, class GlobalOrdinal, class Node>
453  std::vector<size_t>& stridingInfo,
454  GlobalOrdinal /* indexBase */,
455  LocalOrdinal stridedBlockId,
456  GlobalOrdinal offset)
457  : stridingInfo_(stridingInfo),
458  stridedBlockId_(stridedBlockId),
459  offset_(offset),
460  indexBase_(map->getIndexBase())
461 {
462  // TAW: 11/24/15
463  // A strided map never can be built from a strided map. getMap always returns the underlying
464  // Xpetra::Map object which contains the data (either in a Xpetra::EpetraMapT or Xpetra::TpetraMap
465  // object)
466  if(Teuchos::rcp_dynamic_cast<const StridedMap>(map) == Teuchos::null)
467  {
468  map_ = map; // if map is not a strided map, just store it (standard case)
469  }
470  else
471  {
472  map_ = map->getMap(); // if map is also a strided map, store the underlying plain Epetra/Tpetra Xpetra map object
473  }
474 }
475 
476 
477 template<class LocalOrdinal, class GlobalOrdinal, class Node>
480 {
481 }
482 
483 
484 template<class LocalOrdinal, class GlobalOrdinal, class Node>
485 std::vector<size_t>
488 {
489  return stridingInfo_;
490 }
491 
492 
493 template<class LocalOrdinal, class GlobalOrdinal, class Node>
494 void
496 setStridingData(std::vector<size_t> stridingInfo)
497 {
498  stridingInfo_ = stridingInfo;
499 }
500 
501 
502 template<class LocalOrdinal, class GlobalOrdinal, class Node>
503 size_t
506 {
507  size_t blkSize = 0;
508  for(std::vector<size_t>::const_iterator it = stridingInfo_.begin(); it != stridingInfo_.end(); ++it)
509  {
510  blkSize += *it;
511  }
512  return blkSize;
513 }
514 
515 
516 template<class LocalOrdinal, class GlobalOrdinal, class Node>
517 LocalOrdinal
520 {
521  return stridedBlockId_;
522 }
523 
524 
525 template<class LocalOrdinal, class GlobalOrdinal, class Node>
526 bool
528 isStrided() const
529 {
530  return stridingInfo_.size() > 1 ? true : false;
531 }
532 
533 
534 template<class LocalOrdinal, class GlobalOrdinal, class Node>
535 bool
537 isBlocked() const
538 {
539  return getFixedBlockSize() > 1 ? true : false;
540 }
541 
542 
543 template<class LocalOrdinal, class GlobalOrdinal, class Node>
544 GlobalOrdinal
546 getOffset() const
547 {
548  return offset_;
549 }
550 
551 
552 template<class LocalOrdinal, class GlobalOrdinal, class Node>
553 void
555 setOffset(GlobalOrdinal offset)
556 {
557  offset_ = offset;
558 }
559 
560 
561 template<class LocalOrdinal, class GlobalOrdinal, class Node>
562 size_t
564 GID2StridingBlockId(GlobalOrdinal gid) const
565 {
566  GlobalOrdinal tgid = gid - offset_ - indexBase_;
567  tgid = tgid % getFixedBlockSize();
568 
569  size_t nStridedOffset = 0;
570  size_t stridedBlockId = 0;
571  for(size_t j = 0; j < stridingInfo_.size(); j++)
572  {
573  nStridedOffset += stridingInfo_[ j ];
574  if(Teuchos::as<size_t>(tgid) < nStridedOffset)
575  {
576  stridedBlockId = j;
577  break;
578  }
579  }
580  return stridedBlockId;
581 }
582 
583 
584 template<class LocalOrdinal, class GlobalOrdinal, class Node>
587 getMap() const
588 {
589  return map_;
590 }
591 
592 
593 template<class LocalOrdinal, class GlobalOrdinal, class Node>
594 bool
597 {
598 #ifndef HAVE_XPETRA_DEBUG
599  return true;
600 #else
601  if(getStridedBlockId() == -1)
602  {
603  // Strided map contains the full map
604  if(getNodeNumElements() % getFixedBlockSize() != 0 || // number of local elements is not a multiple of block size
605  getGlobalNumElements() % getFixedBlockSize() != 0) // number of global -//-
606  return false;
607  }
608  else
609  {
610  // Strided map contains only the partial map
611  Teuchos::ArrayView<const GlobalOrdinal> dofGids = getNodeElementList();
612  // std::sort(dofGids.begin(), dofGids.end());
613 
614  if(dofGids.size() == 0) // special treatment for empty processors
615  {
616  return true;
617  }
618 
619  if(dofGids.size() % stridingInfo_[ stridedBlockId_ ] != 0)
620  {
621  return false;
622  }
623 
624 
625  // Calculate nStridedOffset
626  size_t nStridedOffset = 0;
627  for(int j = 0; j < stridedBlockId_; j++)
628  {
629  nStridedOffset += stridingInfo_[ j ];
630  }
631 
632  const GlobalOrdinal goStridedOffset = Teuchos::as<GlobalOrdinal>(nStridedOffset);
633  const GlobalOrdinal goZeroOffset = (dofGids[ 0 ] - nStridedOffset - offset_ - indexBase_) / Teuchos::as<GlobalOrdinal>(getFixedBlockSize());
634 
635  GlobalOrdinal cnt = 0;
636  for(size_t i = 0;
637  i < Teuchos::as<size_t>(dofGids.size()) / stridingInfo_[ stridedBlockId_ ];
638  i += stridingInfo_[ stridedBlockId_ ])
639  {
640  const GlobalOrdinal first_gid = dofGids[ i ];
641 
642  // We expect this to be the same for all DOFs of the same node
643  cnt = (first_gid - goStridedOffset - offset_ - indexBase_) / Teuchos::as<GlobalOrdinal>(getFixedBlockSize()) - goZeroOffset;
644 
645  // Loop over all DOFs that belong to current node
646  for(size_t j = 0; j < stridingInfo_[ stridedBlockId_ ]; j++)
647  {
648  const GlobalOrdinal gid = dofGids[ i + j ];
649  const GlobalOrdinal r = (gid - Teuchos::as<GlobalOrdinal>(j) - goStridedOffset - offset_ - indexBase_)
650  / Teuchos::as<GlobalOrdinal>(getFixedBlockSize())
651  - goZeroOffset - cnt;
652  // TAW 1/18/2016: We cannot use Teuchos::OrdinalTraits<GlobalOrdinal>::zero() ) here,
653  // If, e.g., GO=long long is disabled, OrdinalTraits<long long> is not available.
654  // But we instantiate stubs on GO=long long which might contain StridedMaps.
655  // These lead to compilation errors, then.
656  if(0 != r)
657  {
658  std::cout << "goZeroOffset : " << goZeroOffset << std::endl
659  << "dofGids[0] : " << dofGids[ 0 ] << std::endl
660  << "stridedOffset : " << nStridedOffset << std::endl
661  << "offset_ : " << offset_ << std::endl
662  << "goStridedOffset: " << goStridedOffset << std::endl
663  << "getFixedBlkSize: " << getFixedBlockSize() << std::endl
664  << "gid: " << gid << " GID: " << r << std::endl;
665 
666  return false;
667  }
668  }
669  }
670  }
671 
672  return true;
673 #endif
674 }
675 
676 
677 template<class LocalOrdinal, class GlobalOrdinal, class Node>
681 {
682  return map_->getGlobalNumElements();
683 }
684 
685 
686 template<class LocalOrdinal, class GlobalOrdinal, class Node>
687 size_t
690 {
691  return map_->getNodeNumElements();
692 }
693 
694 
695 template<class LocalOrdinal, class GlobalOrdinal, class Node>
696 GlobalOrdinal
699 {
700  return map_->getIndexBase();
701 }
702 
703 
704 template<class LocalOrdinal, class GlobalOrdinal, class Node>
705 LocalOrdinal
708 {
709  return map_->getMinLocalIndex();
710 }
711 
712 
713 template<class LocalOrdinal, class GlobalOrdinal, class Node>
714 LocalOrdinal
717 {
718  return map_->getMaxLocalIndex();
719 }
720 
721 
722 template<class LocalOrdinal, class GlobalOrdinal, class Node>
723 GlobalOrdinal
726 {
727  return map_->getMinGlobalIndex();
728 }
729 
730 
731 template<class LocalOrdinal, class GlobalOrdinal, class Node>
732 GlobalOrdinal
735 {
736  return map_->getMaxGlobalIndex();
737 }
738 
739 
740 template<class LocalOrdinal, class GlobalOrdinal, class Node>
741 GlobalOrdinal
744 {
745  return map_->getMinAllGlobalIndex();
746 }
747 
748 
749 template<class LocalOrdinal, class GlobalOrdinal, class Node>
750 GlobalOrdinal
753 {
754  return map_->getMaxAllGlobalIndex();
755 }
756 
757 
758 template<class LocalOrdinal, class GlobalOrdinal, class Node>
759 LocalOrdinal
761 getLocalElement(GlobalOrdinal globalIndex) const
762 {
763  return map_->getLocalElement(globalIndex);
764 }
765 
766 
767 template<class LocalOrdinal, class GlobalOrdinal, class Node>
768 GlobalOrdinal
770 getGlobalElement(LocalOrdinal localIndex) const
771 {
772  return map_->getGlobalElement(localIndex);
773 }
774 
775 
776 template<class LocalOrdinal, class GlobalOrdinal, class Node>
780  const Teuchos::ArrayView<int>& nodeIDList,
781  const Teuchos::ArrayView<LocalOrdinal>& LIDList) const
782 {
783  return map_->getRemoteIndexList(GIDList, nodeIDList, LIDList);
784 }
785 
786 
787 template<class LocalOrdinal, class GlobalOrdinal, class Node>
791  const Teuchos::ArrayView<int>& nodeIDList) const
792 {
793  return map_->getRemoteIndexList(GIDList, nodeIDList);
794 }
795 
796 
797 template<class LocalOrdinal, class GlobalOrdinal, class Node>
801 {
802  return map_->getNodeElementList();
803 }
804 
805 
806 template<class LocalOrdinal, class GlobalOrdinal, class Node>
807 bool
809 isNodeLocalElement(LocalOrdinal localIndex) const
810 {
811  return map_->isNodeLocalElement(localIndex);
812 }
813 
814 
815 template<class LocalOrdinal, class GlobalOrdinal, class Node>
816 bool
818 isNodeGlobalElement(GlobalOrdinal globalIndex) const
819 {
820  return map_->isNodeGlobalElement(globalIndex);
821 }
822 
823 
824 template<class LocalOrdinal, class GlobalOrdinal, class Node>
825 bool
828 {
829  return map_->isContiguous();
830 }
831 
832 
833 template<class LocalOrdinal, class GlobalOrdinal, class Node>
834 bool
837 {
838  return map_->isDistributed();
839 }
840 
841 
842 template<class LocalOrdinal, class GlobalOrdinal, class Node>
843 bool
845 isCompatible(const Map& map) const
846 {
847  return map_->isCompatible(map);
848 }
849 
850 
851 template<class LocalOrdinal, class GlobalOrdinal, class Node>
852 bool
854 isSameAs(const Map& map) const
855 {
856  return map_->isSameAs(map);
857 }
858 
859 
860 template<class LocalOrdinal, class GlobalOrdinal, class Node>
863 getComm() const
864 {
865  return map_->getComm();
866 }
867 
868 
869 #ifdef TPETRA_ENABLE_DEPRECATED_CODE
870 template<class LocalOrdinal, class GlobalOrdinal, class Node>
873 getNode() const
874 {
875  return map_->getNode();
876 }
877 #endif // TPETRA_ENABLE_DEPRECATED_CODE
878 
879 
880 template<class LocalOrdinal, class GlobalOrdinal, class Node>
881 RCP<const Xpetra::Map<LocalOrdinal,GlobalOrdinal,Node>>
884 {
885  return map_->removeEmptyProcesses();
886 }
887 
888 
889 template<class LocalOrdinal, class GlobalOrdinal, class Node>
893 {
894  return map_->replaceCommWithSubset(newComm);
895 }
896 
897 
898 template<class LocalOrdinal, class GlobalOrdinal, class Node>
899 std::string
901 description() const
902 {
903  return map_->description();
904 }
905 
906 
907 template<class LocalOrdinal, class GlobalOrdinal, class Node>
908 void
911 {
912  map_->describe(out, verbLevel);
913 }
914 
915 
916 template<class LocalOrdinal, class GlobalOrdinal, class Node>
919 lib() const
920 {
921  return map_->lib();
922 }
923 
924 
925 
926 } // namespace Xpetra
927 
928 
929 
930 #endif // XPETRA_STRIDEDMAP_DEF_HPP
931 
932 
LookupStatus getRemoteIndexList(const Teuchos::ArrayView< const GlobalOrdinal > &GIDList, const Teuchos::ArrayView< int > &nodeIDList, const Teuchos::ArrayView< LocalOrdinal > &LIDList) const
Returns the node IDs and corresponding local indices for a given list of global indices.
LocalOrdinal getStridedBlockId() const
GlobalOrdinal getMaxGlobalIndex() const
Returns maximum global index owned by this node.
GlobalOrdinal getGlobalElement(LocalOrdinal localIndex) const
Return the global index for a given local index.
size_t GID2StridingBlockId(GlobalOrdinal gid) const
bool isContiguous() const
Returns true if this Map is distributed contiguously; returns false otherwise.
void setStridingData(std::vector< size_t > stridingInfo)
#define TEUCHOS_TEST_FOR_EXCEPTION(throw_exception_test, Exception, msg)
Teuchos::ArrayView< const GlobalOrdinal > getNodeElementList() const
Return a list of the global indices owned by this node.
GlobalOrdinal indexBase_
index base for the strided map (default = 0)
size_type size() const
GlobalOrdinal getOffset() const
Exception throws to report errors in the internal logical of the program.
LocalOrdinal getMaxLocalIndex() const
Returns maximum local index.
Teuchos::RCP< const Teuchos::Comm< int > > getComm() const
Get the Comm object for this Map.
bool isCompatible(const Map &map) const
Returns true if map is compatible with this Map.
std::string description() const
Return a simple one-line description of this object.
GlobalOrdinal getMaxAllGlobalIndex() const
Return the maximum global index over all nodes.
bool isNodeGlobalElement(GlobalOrdinal globalIndex) const
Returns true if the global index is found in this Map on this node; returns false if it isn&#39;t...
bool isNodeLocalElement(LocalOrdinal localIndex) const
Returns true if the local index is valid for this Map on this node; returns false if it isn&#39;t...
bool isStrided() const
returns true, if this is a strided map (i.e. more than 1 strided blocks)
bool isSameAs(const Map &map) const
Returns true if map is identical to this Map.
std::vector< size_t > stridingInfo_
vector with size of strided blocks (dofs)
RCP< const Map > removeEmptyProcesses() const
Return a new Map with processes with zero elements removed.
RCP< const Map > replaceCommWithSubset(const Teuchos::RCP< const Teuchos::Comm< int >> &newComm) const
bool isDistributed() const
Returns true if this Map is distributed across more than one node; returns false otherwise.
size_t getFixedBlockSize() const
GlobalOrdinal offset_
offset for gids in map (default = 0)
TEUCHOS_DEPRECATED void reduceAll(const Comm< Ordinal > &comm, const EReductionType reductType, const Packet &send, Packet *globalReduct)
GlobalOrdinal getMinGlobalIndex() const
Returns minimum global index owned by this node.
size_t getNodeNumElements() const
Returns the number of elements belonging to the calling node.
size_t global_size_t
Global size_t object.
GlobalOrdinal getIndexBase() const
Returns the index base for this Map.
RCP< const Xpetra::Map< LocalOrdinal, GlobalOrdinal, Node > > getMap() const
global_size_t getGlobalNumElements() const
Returns the number of elements in this Map.
std::vector< size_t > getStridingData() const
LocalOrdinal getLocalElement(GlobalOrdinal globalIndex) const
Return the local index for a given global index.
StridedMap(UnderlyingLib xlib, global_size_t numGlobalElements, GlobalOrdinal indexBase, std::vector< size_t > &stridingInfo, const Teuchos::RCP< const Teuchos::Comm< int >> &comm, LocalOrdinal stridedBlockId=-1, GlobalOrdinal offset=0, LocalGlobal lg=GloballyDistributed)
Map constructor with contiguous uniform distribution.
LocalOrdinal getMinLocalIndex() const
Returns minimum local index.
UnderlyingLib lib() const
Get the library used by this object (Tpetra or Epetra?)
GlobalOrdinal getMinAllGlobalIndex() const
Return the minimum global index over all nodes.
Create an Xpetra::Map instance.
void describe(Teuchos::FancyOStream &out, const Teuchos::EVerbosityLevel verbLevel=Teuchos::Describable::verbLevel_default) const
Print the object with some verbosity level to a FancyOStream object.
virtual ~StridedMap()
Destructor.
Class that stores a strided map.
void setOffset(GlobalOrdinal offset)
RCP< const Xpetra::Map< LocalOrdinal, GlobalOrdinal, Node > > map_