Panzer Version of the Day
Loading...
Searching...
No Matches
Panzer_BlockedDOFManager.cpp
Go to the documentation of this file.
1// @HEADER
2// ***********************************************************************
3//
4// Panzer: A partial differential equation assembly
5// engine for strongly coupled complex multiphysics systems
6// Copyright (2011) 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 Roger P. Pawlowski (rppawlo@sandia.gov) and
39// Eric C. Cyr (eccyr@sandia.gov)
40// ***********************************************************************
41// @HEADER
42
43#ifndef PANZER_BLOCKED_DOF_MANAGER_IMPL_HPP
44#define PANZER_BLOCKED_DOF_MANAGER_IMPL_HPP
45
46#include <map>
47#include <numeric>
48
52#include "Teuchos_DefaultMpiComm.hpp"
53
54namespace panzer {
55
56using Teuchos::RCP;
57
58// ************************************************************
59// class BlockedDOFManager
60// ************************************************************
61
63 : fieldsRegistered_(false), maxSubFieldNum_(-1), requireOrientations_(false), useDOFManagerFEI_(true), useTieBreak_(false)
64{ }
65
66BlockedDOFManager::BlockedDOFManager(const Teuchos::RCP<ConnManager> & connMngr,MPI_Comm mpiComm)
67 : fieldsRegistered_(false), maxSubFieldNum_(-1), requireOrientations_(false), useDOFManagerFEI_(true), useTieBreak_(false)
68{
69 setConnManager(connMngr,mpiComm);
70}
71
74
75int BlockedDOFManager::getFieldNum(const std::string & str) const
76{
77 std::map<std::string,int>::const_iterator itr = fieldStrToNum_.find(str);
78
79 // return based on what was found
80 if(itr==fieldStrToNum_.end()) {
81 // incorrect field name
82 TEUCHOS_TEST_FOR_EXCEPTION(true,std::logic_error,
83 "BlockedDOFManager::getFieldNum No field with the name \"" + str + "\" has been added");
84 }
85 else {
86 return itr->second;
87 }
88}
89
90const std::string & BlockedDOFManager::getFieldString(int number) const
91{
92 std::map<int,std::string>::const_iterator itr = fieldNumToStr_.find(number);
93
94 // return based on what was found
95 if(itr==fieldNumToStr_.end()) {
96 std::stringstream ss; ss << number; // itoa() in c-language
97 // incorrect field name
98 TEUCHOS_TEST_FOR_EXCEPTION(true,std::logic_error,
99 "BlockedDOFManager::getFieldString No field with number \"" + ss.str() + "\" has been added");
100 }
101 else {
102 return itr->second;
103 }
104}
105
106bool BlockedDOFManager::fieldInBlock(const std::string & field,const std::string & block) const
107{
108 // try to find element block
109 std::map<std::string,std::set<std::string> >::const_iterator fieldsItr = blockIdToFieldStrings_.find(block);
110 TEUCHOS_TEST_FOR_EXCEPTION(fieldsItr==blockIdToFieldStrings_.end(),std::logic_error,
111 "BlockedDOFManager::fieldInBlock could not find the element block \""+block+"\"");
112
113 // find field in element block
114 const std::set<std::string> & fields = fieldsItr->second;
115 std::set<std::string>::const_iterator itr = fields.find(field);
116 return itr!=fields.end();
117}
118
121const std::vector<int> & BlockedDOFManager::getBlockFieldNumbers(const std::string & block) const
122{
123 // try to find element block
124 std::map<std::string,std::vector<int> >::const_iterator fieldsItr = blockIdToFieldNumbers_.find(block);
125 if(fieldsItr!=blockIdToFieldNumbers_.end())
126 return fieldsItr->second;
127
128 // nothing to return
129 static std::vector<int> empty;
130 return empty;
131}
132
133void BlockedDOFManager::getElementGIDs(panzer::LocalOrdinal localElmtId,std::vector<GlobalOrdinal> & gids,const std::string & blockIdHint) const
134{
135 // WARNING: there is an assumed ordering being used here it
136 // corresponds directly to the blockGIDOffset_ map and (as
137 // a result) the getBlockGIDOffset function. However for
138 // the sake of speed this conversion is implicit.
139 //
140 // Any changes to the order should be reflected in the
141 // blockGIDOffset_ map.
142
143 gids.resize(0);
144
145 // loop over field block manager and grab indices
146 for(std::size_t fbm=0;fbm<fieldBlockManagers_.size();fbm++) {
147 std::vector<panzer::GlobalOrdinal> fieldBlockOwned;
148
149 fieldBlockManagers_[fbm]->getElementGIDs(localElmtId,fieldBlockOwned,blockIdHint);
150
151 TEUCHOS_TEST_FOR_EXCEPTION(true,std::runtime_error,"getElementGIDs() not supported for BlockedDOFManager!")
152 // for(std::size_t i=0;i<fieldBlockOwned.size();i++)
153 // gids.push_back(std::make_pair(fbm,fieldBlockOwned[i]));
154 }
155}
156
157 void BlockedDOFManager::getElementGIDsPair(panzer::LocalOrdinal localElmtId,std::vector<std::pair<int,GlobalOrdinal>> & gids,const std::string & blockIdHint) const
158{
159 // WARNING: there is an assumed ordering being used here it
160 // corresponds directly to the blockGIDOffset_ map and (as
161 // a result) the getBlockGIDOffset function. However for
162 // the sake of speed this conversion is implicit.
163 //
164 // Any changes to the order should be reflected in the
165 // blockGIDOffset_ map.
166
167 gids.resize(0);
168
169 // loop over field block manager and grab indices
170 for(std::size_t fbm=0;fbm<fieldBlockManagers_.size();fbm++) {
171 std::vector<panzer::GlobalOrdinal> fieldBlockOwned;
172
173 fieldBlockManagers_[fbm]->getElementGIDs(localElmtId,fieldBlockOwned,blockIdHint);
174
175 for(std::size_t i=0;i<fieldBlockOwned.size();i++)
176 gids.push_back(std::make_pair(fbm,fieldBlockOwned[i]));
177 }
178}
179
180void BlockedDOFManager::getElementOrientation(panzer::LocalOrdinal localElmtId,std::vector<double> & gidsOrientation) const
181{
182 // WARNING: there is an assumed ordering being used here it
183 // corresponds directly to the blockGIDOffset_ map and (as
184 // a result) the getBlockGIDOffset function. However for
185 // the sake of speed this conversion is implicit.
186 //
187 // Any changes to the order should be reflected in the
188 // blockGIDOffset_ map.
189
190 gidsOrientation.resize(0);
191
192 // loop over field block manager and grab indices
193 for(std::size_t fbm=0;fbm<fieldBlockManagers_.size();fbm++) {
194 std::vector<double> blkOrientation;
195
196 fieldBlockManagers_[fbm]->getElementOrientation(localElmtId,blkOrientation);
197
198 for(std::size_t i=0;i<blkOrientation.size();i++)
199 gidsOrientation.push_back(blkOrientation[i]);
200 }
201}
202
203const std::vector<int> & BlockedDOFManager::getGIDFieldOffsets(const std::string & blockId,int fieldNum) const
204{
205 typedef std::map<std::string,std::map<int,std::vector<int> > > FieldOffsetsMap;
206
207 FieldOffsetsMap::iterator blockItr = gidFieldOffsets_.find(blockId);
208 if(blockItr!=gidFieldOffsets_.end()) {
209 std::map<int,std::vector<int> > & fieldToVectorMap = blockItr->second;
210 std::map<int,std::vector<int> >::const_iterator itr = fieldToVectorMap.find(fieldNum);
211
212 // we have found the vector, return the precomputed one
213 if(itr!=fieldToVectorMap.end())
214 return itr->second;
215 }
216 else {
217 std::vector<std::string> elementBlocks;
218 getElementBlockIds(elementBlocks);
219 TEUCHOS_TEST_FOR_EXCEPTION(std::find(elementBlocks.begin(),elementBlocks.end(),blockId)==elementBlocks.end(),std::logic_error,
220 "BlockedDOFManager::getGIDFieldOffsets: Block ID \""+blockId+"\" does not exist");
221
222 gidFieldOffsets_[blockId] = std::map<int,std::vector<int> >();
223 blockItr = gidFieldOffsets_.find(blockId);
224 }
225
226 // grab relevant map from iterator
227 std::map<int,std::vector<int> > & fieldToVectorMap = blockItr->second;
228
229 // we have not found the vector, now we need to build one
231
232 // first grab all pieces that are needed for extracting GIDs from sub system
233 int fieldBlock = getFieldBlock(fieldNum);
234 Teuchos::RCP<const GlobalIndexer> dofManager = fieldBlockManagers_[fieldBlock];
235
236 // grab offsets for sub dof manager. Notice you must convert to field number used by sub manager!
237 const std::vector<int> & subGIDOffsets
238 = dofManager->getGIDFieldOffsets(blockId,dofManager->getFieldNum(getFieldString(fieldNum)));
239
240 // increment offsets to correspond with blocked system
241 int gidOffset = getBlockGIDOffset(blockId,fieldBlock);
242 std::vector<int> & finalFieldOffsets = fieldToVectorMap[fieldNum];
243 finalFieldOffsets.resize(subGIDOffsets.size());
244 for(std::size_t i=0;i<finalFieldOffsets.size();i++)
245 finalFieldOffsets[i] = gidOffset+subGIDOffsets[i];
246
247 return finalFieldOffsets;
248}
249
250bool BlockedDOFManager::LessThan
251::operator()(const Teuchos::Tuple<int,3> & a,const Teuchos::Tuple<int,3> & b) const
252{
253 if(a[0] < b[0]) return true;
254 if(a[0] > b[0]) return false;
255
256 // a[0]==b[0]
257 if(a[1] < b[1]) return true;
258 if(a[1] > b[1]) return false;
259
260 // a[1]==b[1] && a[0]==b[0]
261 if(a[2] < b[2]) return true;
262 if(a[2] > b[2]) return false;
263
264 // a[2]==b[2] && a[1]==b[1] && a[0]==b[0]
265 return false; // these are equal to, but not less than!
266}
267
268const std::pair<std::vector<int>,std::vector<int> > &
269BlockedDOFManager::getGIDFieldOffsets_closure(const std::string & blockId,int fieldNum,int subcellDim,int subcellId) const
270{
271 typename std::map<std::string,TupleToVectorPairMap>::iterator blockItr = gidFieldOffsets_closure_.find(blockId);
272 if(blockItr!=gidFieldOffsets_closure_.end()) {
273 TupleToVectorPairMap & fieldToTupleMap = blockItr->second;
274 typename TupleToVectorPairMap::const_iterator itr =
275 fieldToTupleMap.find(Teuchos::tuple(fieldNum,subcellDim,subcellId));
276
277 // we have found the vector, return the precomputed one
278 if(itr!=fieldToTupleMap.end())
279 return itr->second;
280 }
281 else {
282 std::vector<std::string> elementBlocks;
283 getElementBlockIds(elementBlocks);
284 TEUCHOS_TEST_FOR_EXCEPTION(std::find(elementBlocks.begin(),elementBlocks.end(),blockId)==elementBlocks.end(),std::logic_error,
285 "BlockedDOFManager::getGIDFieldOffsets: Block ID \""+blockId+"\" does not exist");
286
288 blockItr = gidFieldOffsets_closure_.find(blockId);
289 }
290
291 // grab relevant map from iterator
292 TupleToVectorPairMap & fieldToTupleMap = blockItr->second;
293
294 // we have not found the vector, now we need to build one
296
297 // first grab all pieces that are needed for extracting GIDs from sub system
298 int fieldBlock = getFieldBlock(fieldNum);
299 Teuchos::RCP<const GlobalIndexer> dofManager = fieldBlockManagers_[fieldBlock];
300
301 // grab offsets for sub dof manager. Notice you must convert to field number used by sub manager!
302 const std::pair<std::vector<int>,std::vector<int> > & subGIDOffsets_closure
303 = dofManager->getGIDFieldOffsets_closure(blockId,dofManager->getFieldNum(getFieldString(fieldNum)),subcellDim,subcellId);
304
305 // increment offsets to correspond with blocked system
306 int gidOffset = getBlockGIDOffset(blockId,fieldBlock);
307 std::pair<std::vector<int>,std::vector<int> > & finalFieldOffsets = fieldToTupleMap[Teuchos::tuple(fieldNum,subcellDim,subcellId)];
308 finalFieldOffsets.first.resize(subGIDOffsets_closure.first.size());
309 finalFieldOffsets.second = subGIDOffsets_closure.second;
310 for(std::size_t i=0;i<finalFieldOffsets.first.size();i++)
311 finalFieldOffsets.first[i] = gidOffset+subGIDOffsets_closure.first[i];
312
313 return finalFieldOffsets;
314}
315
317//
318// getOwnedIndices()
319//
321void BlockedDOFManager::getOwnedIndices(std::vector<GlobalOrdinal>& indices) const
322{
323 using std::make_pair;
324 using std::size_t;
325 using std::vector;
326 for (size_t fbm(0); fbm < fieldBlockManagers_.size(); ++fbm)
327 {
328 vector<panzer::GlobalOrdinal> fieldBlockOwned;
329 fieldBlockManagers_[fbm]->getOwnedIndices(fieldBlockOwned);
330 TEUCHOS_TEST_FOR_EXCEPTION(true,std::runtime_error,"getOwnedIndices() not supported for BlockedDOFManager!")
331 // for (size_t i(0); i < fieldBlockOwned.size(); ++i)
332 // indices.push_back(make_pair(fbm, fieldBlockOwned[i]));
333 }
334}
335
337//
338// getGhostedIndices()
339//
341void BlockedDOFManager::getGhostedIndices(std::vector<GlobalOrdinal>& indices) const
342{
343 using std::make_pair;
344 using std::size_t;
345 using std::vector;
346 for (size_t fbm(0); fbm < fieldBlockManagers_.size(); ++fbm)
347 {
348 vector<panzer::GlobalOrdinal> fieldBlockGhosted;
349 fieldBlockManagers_[fbm]->getGhostedIndices(fieldBlockGhosted);
350 TEUCHOS_TEST_FOR_EXCEPTION(true,std::runtime_error,"getGhostedIndices() not supported for BlockedDOFManager!")
351 // for (size_t i(0); i < fieldBlockGhosted.size(); ++i)
352 // indices.push_back(make_pair(fbm, fieldBlockGhosted[i]));
353 }
354}
355
357//
358// getOwnedAndGhostedIndices()
359//
361void BlockedDOFManager::getOwnedAndGhostedIndices(std::vector<GlobalOrdinal>& indices) const
362{
363 using std::make_pair;
364 using std::size_t;
365 using std::vector;
366 for (size_t fbm(0); fbm < fieldBlockManagers_.size(); ++fbm)
367 {
368 vector<panzer::GlobalOrdinal> fieldBlockOwnedAndGhosted;
369 fieldBlockManagers_[fbm]->getOwnedAndGhostedIndices(
370 fieldBlockOwnedAndGhosted);
371 TEUCHOS_TEST_FOR_EXCEPTION(true,std::runtime_error,"getOwnedAndGhostedIndices() not supported for BlockedDOFManager!")
372 // for (size_t i(0); i < fieldBlockOwnedAndGhosted.size(); ++i)
373 // indices.push_back(make_pair(fbm, fieldBlockOwnedAndGhosted[i]));
374 }
375}
376
378void BlockedDOFManager::getElementGIDsAsInt(panzer::LocalOrdinal localElmtId,std::vector<int> & gids,const std::string & blockIdHint) const
379{
380 // WARNING: there is an assumed ordering being used here it
381 // corresponds directly to the blockGIDOffset_ map and (as
382 // a result) the getBlockGIDOffset function. However for
383 // the sake of speed this conversion is implicit.
384 //
385 // Any changes to the order should be reflected in the
386 // blockGIDOffset_ map.
387
388 gids.resize(0);
389
390 // loop over field block manager and grab indices
391 for(std::size_t fbm=0;fbm<fieldBlockManagers_.size();fbm++) {
392 std::vector<int> fieldBlockOwned;
393
394 fieldBlockManagers_[fbm]->getElementGIDsAsInt(localElmtId,fieldBlockOwned,blockIdHint);
395
396 TEUCHOS_TEST_FOR_EXCEPTION(true,std::runtime_error,"getElementGIDsAsInt() not supported for BlockedDOFManager!")
397 // for(std::size_t i=0;i<fieldBlockOwned.size();i++)
398 // gids.push_back(std::make_pair(fbm,fieldBlockOwned[i]));
399 }
400}
401
403void BlockedDOFManager::getOwnedIndicesAsInt(std::vector<int>& indices) const
404{
405 using std::make_pair;
406 using std::size_t;
407 using std::vector;
408 for (size_t fbm(0); fbm < fieldBlockManagers_.size(); ++fbm)
409 {
410 vector<int> fieldBlockOwned;
411 fieldBlockManagers_[fbm]->getOwnedIndicesAsInt(fieldBlockOwned);
412 TEUCHOS_TEST_FOR_EXCEPTION(true,std::runtime_error,"getOwnedIndicesAsInt() not supported for BlockedDOFManager!")
413 // for (size_t i(0); i < fieldBlockOwned.size(); ++i)
414 // indices.push_back(make_pair(fbm, fieldBlockOwned[i]));
415 }
416}
417
419void BlockedDOFManager::getGhostedIndicesAsInt(std::vector<int>& indices) const
420{
421 using std::make_pair;
422 using std::size_t;
423 using std::vector;
424 for (size_t fbm(0); fbm < fieldBlockManagers_.size(); ++fbm)
425 {
426 vector<int> fieldBlockGhosted;
427 fieldBlockManagers_[fbm]->getGhostedIndicesAsInt(fieldBlockGhosted);
428 TEUCHOS_TEST_FOR_EXCEPTION(true,std::runtime_error,"getGhostedIndicesAsInt() not supported for BlockedDOFManager!")
429 // for (size_t i(0); i < fieldBlockGhosted.size(); ++i)
430 // indices.push_back(make_pair(fbm, fieldBlockGhosted[i]));
431 }
432}
433
435void BlockedDOFManager::getOwnedAndGhostedIndicesAsInt(std::vector<int>& indices) const
436{
437 using std::make_pair;
438 using std::size_t;
439 using std::vector;
440 for (size_t fbm(0); fbm < fieldBlockManagers_.size(); ++fbm)
441 {
442 vector<int> fieldBlockOwnedAndGhosted;
443 fieldBlockManagers_[fbm]->getOwnedAndGhostedIndicesAsInt(
444 fieldBlockOwnedAndGhosted);
445 TEUCHOS_TEST_FOR_EXCEPTION(true,std::runtime_error,"getOwnedAndGhostedIndicesAsInt() not supported for BlockedDOFManager!")
446 // for (size_t i(0); i < fieldBlockOwnedAndGhosted.size(); ++i)
447 // indices.push_back(make_pair(fbm, fieldBlockOwnedAndGhosted[i]));
448 }
449}
450
452//
453// getNumOwned()
454//
457{
458 using std::size_t;
459 int result(0);
460 for (size_t fbm(0); fbm < fieldBlockManagers_.size(); ++fbm)
462 return result;
463}
464
466//
467// getNumGhosted()
468//
471{
472 using std::size_t;
473 int result(0);
474 for (size_t fbm(0); fbm < fieldBlockManagers_.size(); ++fbm)
476 return result;
477}
478
480//
481// getNumOwnedAndGhosted()
482//
485{
486 using std::size_t;
487 int result(0);
488 for (size_t fbm(0); fbm < fieldBlockManagers_.size(); ++fbm)
490 return result;
491}
492
493void BlockedDOFManager::ownedIndices(const std::vector<GlobalOrdinal> & indices,std::vector<bool> & isOwned) const
494{
495 isOwned.resize(0);
496
497 std::vector<std::vector<panzer::GlobalOrdinal> > blockIndices(fieldBlockManagers_.size());
498 TEUCHOS_TEST_FOR_EXCEPTION(true,std::runtime_error,"ownedIndices() not supported for BlockedDOFManager!")
499 // for(std::size_t i=0;i<indices.size();i++)
500 // blockIndices[indices[i].first].push_back(indices[i].second);
501
502 // build bool vector stating if each sub block is owned
503 std::vector<std::vector<bool> > blockIsOwned(fieldBlockManagers_.size());
504 std::vector<std::vector<bool>::const_iterator> blockItrs;
505 for(std::size_t fbm=0;fbm<fieldBlockManagers_.size();fbm++) {
506 fieldBlockManagers_[fbm]->ownedIndices(blockIndices[fbm],blockIsOwned[fbm]);
507
508 // setup iterators to boolean vectors
509 blockItrs.push_back(blockIsOwned[fbm].begin());
510 }
511
512 // loop over indices, consider their block and look it up
513 // in iterator vector
514 TEUCHOS_TEST_FOR_EXCEPTION(true,std::runtime_error,"ownedIndices() not supported for BlockedDOFManager!")
515/*
516 for(std::size_t i=0;i<indices.size();i++) {
517 int block = indices[i].first;
518
519 // set owned status from iterator of block
520 bool owned = *blockItrs[block];
521 isOwned.push_back(owned);
522
523 // increment block iterator
524 blockItrs[block]++;
525 }
526
527 // quick error sanity check
528 TEUCHOS_ASSERT(isOwned.size()==indices.size());
529 for(std::size_t fbm=0;fbm<fieldBlockManagers_.size();fbm++) {
530 TEUCHOS_TEST_FOR_EXCEPTION(blockItrs[fbm]!=blockIsOwned[fbm].end(),std::logic_error,
531 "BlockedDOFManager::ownedIndices: Did not consume all sub block boolean entries as expected.");
532 }
533*/
534}
535
536
539
540
552void BlockedDOFManager::setConnManager(const Teuchos::RCP<ConnManager> & connMngr,MPI_Comm mpiComm)
553{
554 communicator_ = Teuchos::rcp(new Teuchos::MpiComm<int>(Teuchos::opaqueWrapper(mpiComm)));
555
556 // this kills any old connection manager
557 resetIndices();
558
559 connMngr_ = connMngr;
560
561 mpiComm_ = *communicator_->getRawMpiComm();
562}
563
572Teuchos::RCP<ConnManager> BlockedDOFManager::resetIndices()
573{
574 Teuchos::RCP<ConnManager> connMngr = connMngr_;
575
576 connMngr_ = Teuchos::null;
577 //ownedGIDHashTable_.clear();
578 blockGIDOffset_.clear();
579
580 return connMngr;
581}
582
583void BlockedDOFManager::addField(const std::string & str,
584 const Teuchos::RCP<const FieldPattern> & pattern)
585{
586 std::vector<std::string> elementBlockIds;
587 connMngr_->getElementBlockIds(elementBlockIds);
588
589 // loop over blocks adding field pattern to each
590 for(std::size_t i=0;i<elementBlockIds.size();i++)
591 addField(elementBlockIds[i],str,pattern);
592}
593
594void BlockedDOFManager::addField(const std::string & blockId,const std::string & str,
595 const Teuchos::RCP<const FieldPattern> & pattern)
596{
597 TEUCHOS_TEST_FOR_EXCEPTION(fieldsRegistered(),std::logic_error,
598 "BlockedDOFManager::addField: addField cannot be called after registerFields or"
599 "buildGlobalUnknowns has been called");
600
601 fieldStringToPattern_[std::make_pair(blockId,str)] = pattern;
602 blockIdToFieldStrings_[blockId].insert(str);
603}
604
605void BlockedDOFManager::registerFields(bool buildSubUGIs)
606{
607 if(buildSubUGIs)
608 fieldBlockManagers_.clear();
609 fieldStrToNum_.clear();
610 fieldNumToStr_.clear();
611 fieldNumToFieldBlk_.clear();
612 maxSubFieldNum_ = -1;
613
614 fieldsRegistered_ = false;
615
616 // test validity of the field order, build default if none is provided
617 {
618 // build a unique set of fields, so we can compare validate the ordered list
619 std::set<std::string> fields;
620 for(std::map<std::pair<std::string,std::string>,Teuchos::RCP<const FieldPattern> >::const_iterator
621 fieldItr=fieldStringToPattern_.begin(); fieldItr!=fieldStringToPattern_.end();++fieldItr) {
622 std::string fieldName = fieldItr->first.second;
623 fields.insert(fieldName);
624 }
625
626 // construct default field order if neccessary
627 if(fieldOrder_.size()==0) {
628 std::set<std::string>::const_iterator itr;
629 for(itr=fields.begin();itr!=fields.end();itr++) {
630 std::vector<std::string> block;
631 block.push_back(*itr);
632 fieldOrder_.push_back(block);
633 }
634 }
635
636 // check validity of field order: no repeats, and everything is accounted for
637 bool validOrder = validFieldOrder(fieldOrder_,fields);
638 if(!validOrder) {
639 // for outputing
640 std::stringstream ss;
641
642 ss << "BlockedDOFManager::registerFields - Field order is invalid!\n";
643
644 ss << " fields = [ ";
645 for(std::set<std::string>::const_iterator itr=fields.begin();
646 itr!=fields.end();++itr)
647 ss << "\"" << *itr << "\" ";
648 ss << " ]\n";
649
650 ss << " fieldOrder = [ ";
651 for(std::vector<std::vector<std::string> >::const_iterator bitr=fieldOrder_.begin();
652 bitr!=fieldOrder_.end();++bitr) {
653 ss << "[ ";
654 for(std::vector<std::string>::const_iterator itr=bitr->begin();
655 itr!=bitr->end();++itr) {
656 ss << "\"" << *itr << "\" ";
657 }
658 ss << " ], ";
659 }
660 ss << " ]\n";
661
662 TEUCHOS_TEST_FOR_EXCEPTION(!validOrder,std::logic_error,ss.str());
663 }
664 }
665
666 // build sub DOFManagers for each field block
667 if(buildSubUGIs) {
668 for(std::size_t fldBlk=0;fldBlk<fieldOrder_.size();fldBlk++) {
669 Teuchos::RCP<panzer::GlobalIndexer> dofManager = buildNewIndexer(getConnManager(),mpiComm_);
670
671 // add in these fields to the new manager
672 this->addFieldsToFieldBlockManager(fieldOrder_[fldBlk],*dofManager);
673
674 fieldBlockManagers_.push_back(dofManager);
675 }
676 }
677
679 // build field numbers: two stage algorithm
680
681 // 1st Stage: Extract field numbers used by each sub DOFManager.
682 // determine largest of these
683 //
684 // - note at this point since "validFieldOrder" has
685 // been called we are gurranteed to not have repeated fields
686 maxSubFieldNum_ = -1;
687 std::map<std::string,int> tempStrToNum;
688 for(std::size_t fldBlk=0;fldBlk<fieldBlockManagers_.size();fldBlk++) {
689 Teuchos::RCP<const panzer::GlobalIndexer> dofManager =
690 fieldBlockManagers_[fldBlk];
691 const std::vector<std::string> & activeFields = fieldOrder_[fldBlk];
692
693 int fieldNum = 0;
694 for(std::size_t f=0;f<activeFields.size();f++) {
695 fieldNum = dofManager->getFieldNum(activeFields[f]);
696 tempStrToNum[activeFields[f]] = fieldNum;
697
698 maxSubFieldNum_ = (fieldNum>maxSubFieldNum_) ? fieldNum : maxSubFieldNum_;
699 }
700 }
701
702 // 2nd Stage: Using field block index, field number and largest field number
703 // build a up fieldStrToNum_ map and fieldNumToFieldBlk_
704 int numOffset = 0;
705 for(std::size_t fldBlk=0;fldBlk<fieldBlockManagers_.size();fldBlk++) {
706 const std::vector<std::string> & activeFields = fieldOrder_[fldBlk];
707
708 for(std::size_t f=0;f<activeFields.size();f++) {
709 // compute offset field number
710 int fieldNum = tempStrToNum[activeFields[f]]+numOffset;
711
712 // build up map data
713 fieldStrToNum_[activeFields[f]] = fieldNum;
714 fieldNumToStr_[fieldNum] = activeFields[f];
715 fieldNumToFieldBlk_[fieldNum] = fldBlk;
716 }
717
718 // increament field number offset based on largest sub field number
719 numOffset += (maxSubFieldNum_+1);
720 }
721
722 // end build field numbers
724
725 // build block to field numbers: this requires field numbers have been built
726 // and that "getFieldNum" behaves correctly
727 for(std::map<std::string,std::set<std::string> >::const_iterator itr=blockIdToFieldStrings_.begin();
728 itr!=blockIdToFieldStrings_.end();++itr) {
729 const std::set<std::string> & fields = itr->second;
730
731 std::vector<int> & fieldNums = blockIdToFieldNumbers_[itr->first];
732 for(std::set<std::string>::const_iterator fldItr=fields.begin();
733 fldItr!=fields.end();++fldItr) {
734 fieldNums.push_back(getFieldNum(*fldItr));
735 }
736 }
737
738 // everything completed, mark as fields registered
739 fieldsRegistered_ = true;
740}
741
742Teuchos::RCP<GlobalIndexer>
743BlockedDOFManager::buildNewIndexer(const Teuchos::RCP<ConnManager> & connManager,MPI_Comm mpiComm) const
744{
745 Teuchos::RCP<panzer::DOFManager> dofManager = Teuchos::rcp(new panzer::DOFManager);
746 dofManager->enableTieBreak(useTieBreak_);
747 dofManager->setConnManager(connManager,mpiComm);
748 return dofManager;
749}
750
751void BlockedDOFManager::setOrientationsRequired(const Teuchos::RCP<GlobalIndexer> & indexer,bool required) const
752{
753 using Teuchos::RCP;
754 using Teuchos::rcp_dynamic_cast;
755
756 // standard version
757 {
758 RCP<DOFManager> dofManager = rcp_dynamic_cast<DOFManager>(indexer);
759
760 if(dofManager!=Teuchos::null) {
761 dofManager->setOrientationsRequired(required);
762 return;
763 }
764 }
765
766 // you should never get here!
767 TEUCHOS_ASSERT(false);
768}
769
771buildGlobalUnknowns(const Teuchos::RCP<GlobalIndexer> & indexer,const Teuchos::RCP<const FieldPattern> & geomPattern) const
772{
773 using Teuchos::RCP;
774 using Teuchos::rcp_dynamic_cast;
775
776 // standard version
777 {
778 RCP<DOFManager> dofManager = rcp_dynamic_cast<DOFManager>(indexer);
779
780 if(dofManager!=Teuchos::null) {
781 dofManager->buildGlobalUnknowns(geomPattern);
782 return;
783 }
784 }
785
786 // you should never get here!
787 TEUCHOS_ASSERT(false);
788}
789
790void BlockedDOFManager::printFieldInformation(const Teuchos::RCP<GlobalIndexer> & indexer,
791 std::ostream & os) const
792{
793 using Teuchos::RCP;
794 using Teuchos::rcp_dynamic_cast;
795
796 // standard version
797 {
798 RCP<DOFManager> dofManager = rcp_dynamic_cast<DOFManager>(indexer);
799
800 if(dofManager!=Teuchos::null) {
801 dofManager->printFieldInformation(os);
802 return;
803 }
804 }
805
806 // you should never get here!
807 TEUCHOS_ASSERT(false);
808}
809
810int BlockedDOFManager::getElementBlockGIDCount(const Teuchos::RCP<GlobalIndexer> & indexer,
811 const std::string & elementBlock) const
812{
813 using Teuchos::RCP;
814 using Teuchos::rcp_dynamic_cast;
815
816 TEUCHOS_ASSERT(indexer!=Teuchos::null);
817
818 return indexer->getElementBlockGIDCount(elementBlock);
819}
820
821int BlockedDOFManager::getElementBlockGIDCount(const Teuchos::RCP<GlobalIndexer> & indexer,
822 const std::size_t & elementBlock) const
823{
824 using Teuchos::RCP;
825 using Teuchos::rcp_dynamic_cast;
826
827 TEUCHOS_ASSERT(indexer!=Teuchos::null);
828
829 return indexer->getElementBlockGIDCount(elementBlock);
830}
831
832int BlockedDOFManager::getElementBlockGIDCount(const std::string & elementBlock) const
833{
834 int gidCount = 0;
835 for(std::size_t i=0;i<fieldBlockManagers_.size();i++)
836 gidCount += fieldBlockManagers_[i]->getElementBlockGIDCount(elementBlock);
837
838 return gidCount;
839}
840
841int BlockedDOFManager::getElementBlockGIDCount(const std::size_t & elementBlock) const
842{
843 int gidCount = 0;
844 for(std::size_t i=0;i<fieldBlockManagers_.size();i++)
845 gidCount += fieldBlockManagers_[i]->getElementBlockGIDCount(elementBlock);
846
847 return gidCount;
848}
849
850void BlockedDOFManager::addFieldsToFieldBlockManager(const std::vector<std::string> & activeFields,
851 GlobalIndexer & fieldBlockManager) const
852{
853 using Teuchos::Ptr;
854 using Teuchos::ptrFromRef;
855 using Teuchos::ptr_dynamic_cast;
856
857 Ptr<GlobalIndexer> ugi_ptr = ptrFromRef(fieldBlockManager);
858
859 // standard version
860 {
861 Ptr<DOFManager> dofManager_ptr = ptr_dynamic_cast<DOFManager>(ugi_ptr);
862
863 if(dofManager_ptr!=Teuchos::null) {
864 addFieldsToFieldBlockManager(activeFields,*dofManager_ptr);
865 return;
866 }
867 }
868
869 // you should never get here!
870 TEUCHOS_ASSERT(false);
871}
872
874addFieldsToFieldBlockManager(const std::vector<std::string> & activeFields,
875 DOFManager & fieldBlockManager) const
876{
877 std::vector<std::size_t> correctnessCheck(activeFields.size(),0);
878 std::vector<std::string> elementBlocks;
879 this->getElementBlockIds(elementBlocks);
880
881 // loop over element blocks adding each field in this element block and this field block
882 for(std::size_t eb=0;eb<elementBlocks.size();eb++) {
883 std::string elementBlock = elementBlocks[eb];
884
885 // loop over active fields extracting those that are associated with this element block
886 for(std::size_t f=0;f<activeFields.size();f++) {
887 std::string fieldName = activeFields[f];
888 Teuchos::RCP<const FieldPattern> fp = this->getFieldPattern(elementBlock,fieldName);
889
890 if(fp!=Teuchos::null) {
891 fieldBlockManager.addField(elementBlock,fieldName,fp);
892 correctnessCheck[f] = 1; // all active fields should be placed in DOFManager
893 }
894 }
895 }
896
897 // verify correctness check
898 std::size_t correctFlag = std::accumulate(correctnessCheck.begin(),correctnessCheck.end(),0);
899 TEUCHOS_TEST_FOR_EXCEPTION(correctFlag!=activeFields.size(),std::logic_error,
900 "BlockedDOFManager::addFieldsToFieldBlockManager detected inconsistincies in the active fields.");
901
902 // set field order
903 fieldBlockManager.setFieldOrder(activeFields);
904}
905
906void BlockedDOFManager::setFieldOrder(const std::vector<std::vector<std::string> > & fieldOrder)
907{
908 fieldOrder_ = fieldOrder;
909}
910
913void BlockedDOFManager::getFieldOrder(std::vector<std::vector<std::string> > & fieldOrder) const
914{
915 fieldOrder = fieldOrder_;
916}
917
919{
920 if(fieldsRegistered())
921 return fieldStrToNum_.size();
922
923 // more work needs to be done if the fields have not yet been registered
924 // pull it from the (block id x field name) ==> pattern map
925 std::set<std::string> fields;
926 std::map<std::pair<std::string,std::string>,Teuchos::RCP<const FieldPattern> >::const_iterator itr;
927 for(itr=fieldStringToPattern_.begin();itr!=fieldStringToPattern_.end();++itr)
928 fields.insert(itr->first.second);
929
930 return fields.size();
931}
932
933// build the global unknown numberings
934// 1. this builds the pattens
935// 2. initializes the connectivity
936// 3. calls initComplete
938buildGlobalUnknowns(const std::vector<Teuchos::RCP<GlobalIndexer>> & fieldBlockManagers)
939{
940 using Teuchos::RCP;
941 using Teuchos::rcp_dynamic_cast;
942
943 RCP<const FieldPattern> refGeomPattern;
944 RCP<ConnManager> refConnManager = getConnManager();
945
946 // verify the pre-conditions:
947 // 1. all the UGIs are of type DOFManager
948 // 2. the geometric patterns are all the same
949 // 3. the connection managers are all the same
951 {
952 TEUCHOS_ASSERT(fieldBlockManagers.size()>0); // the minimum requirement!
953
954 // get reference values from the initial DOFManager
955 RCP<const DOFManager> refDofManager = rcp_dynamic_cast<const DOFManager>(fieldBlockManagers[0]);
956
957 TEUCHOS_TEST_FOR_EXCEPTION(refDofManager==Teuchos::null,std::runtime_error,
958 "panzer::BlockedDOFManager::buildGlobalUnknowns: UGI at index " << 0 <<
959 " is not of DOFManager type!");
960
961 RCP<const ConnManager> connManager = refDofManager->getConnManager();
962 TEUCHOS_TEST_FOR_EXCEPTION(refConnManager!=connManager,std::runtime_error,
963 "panzer::BlockedDOFManager::buildGlobalUnknowns: connection manager for UGI " << 0 <<
964 " does not match the reference connection manager");
965
966 refGeomPattern = refDofManager->getGeometricFieldPattern();
967
968 for(std::size_t i=1;i<fieldBlockManagers.size();i++) {
969 RCP<const DOFManager> dofManager = rcp_dynamic_cast<const DOFManager>(fieldBlockManagers[i]);
970
971 TEUCHOS_TEST_FOR_EXCEPTION(refDofManager==Teuchos::null,std::runtime_error,
972 "panzer::BlockedDOFManager::buildGlobalUnknowns: UGI at index " << i <<
973 " is not of DOFManager type!");
974
975 RCP<const FieldPattern> geomPattern = dofManager->getGeometricFieldPattern();
976 RCP<const ConnManager> testConnManager = dofManager->getConnManager();
977
978 TEUCHOS_TEST_FOR_EXCEPTION(!refGeomPattern->equals(*geomPattern),std::runtime_error,
979 "panzer::BlockedDOFManager::buildGlobalUnknowns: geometric pattern for UGI " << i <<
980 " does not match the reference pattern (from UGI 0)");
981 TEUCHOS_TEST_FOR_EXCEPTION(refConnManager!=testConnManager,std::runtime_error,
982 "panzer::BlockedDOFManager::buildGlobalUnknowns: connection manager for UGI " << i <<
983 " does not match the reference connection manager (from UGI 0)");
984 }
985 }
986
987 // add all the fields to the blocked dof manager
989 {
990 std::vector<std::string> eblocks;
991 this->getElementBlockIds(eblocks);
992
993 for(std::size_t i=0;i<fieldBlockManagers.size();i++) {
994 RCP<const DOFManager> dofManager
995 = rcp_dynamic_cast<const DOFManager>(fieldBlockManagers[i]);
996
997 for(std::size_t e=0;e<eblocks.size();e++) {
998 const std::vector<int> & fieldIds = dofManager->getBlockFieldNumbers(eblocks[e]);
999
1000 // insert the fields into the block dof manager
1001 for(std::size_t f=0;f<fieldIds.size();f++) {
1002 // get the field name and pattern
1003 std::string fieldName = dofManager->getFieldString(fieldIds[f]);
1004 Teuchos::RCP<const panzer::FieldPattern> fieldPattern
1005 = dofManager->getFieldPattern(eblocks[e],fieldName);
1006
1007 // add in the field
1008 this->addField(eblocks[e],fieldName,fieldPattern);
1009 }
1010 }
1011 }
1012 }
1013
1014 // save and set some of the data
1015 fieldBlockManagers_ = fieldBlockManagers;
1016
1017 registerFields(false);
1018
1019 geomPattern_ = refGeomPattern;
1020
1021 // build field block offsets: this helps fast construction
1022 // of GID offset vectors. GIDs are ordering by field block.
1024 {
1025 std::vector<std::string> elementBlocks;
1026 getElementBlockIds(elementBlocks);
1027 for(std::size_t eb=0;eb<elementBlocks.size();eb++) {
1028 int offset = 0;
1029 for(std::size_t fb=0;fb<fieldBlockManagers_.size();fb++) {
1030 int cnt = getElementBlockGIDCount(fieldBlockManagers_[fb],elementBlocks[eb]);
1031 blockGIDOffset_[std::make_pair(elementBlocks[eb],fb)] = offset;
1032 offset += cnt;
1033 }
1034 }
1035 }
1036}
1037
1038// build the global unknown numberings
1039// 1. this builds the pattens
1040// 2. initializes the connectivity
1041// 3. calls initComplete
1042void BlockedDOFManager::buildGlobalUnknowns(const Teuchos::RCP<const FieldPattern> & geomPattern)
1043{
1044 if(!fieldsRegistered()) {
1045 registerFields(true);
1046 }
1047
1048 // save the geometry pattern
1049 geomPattern_ = geomPattern;
1050
1051 // build global unknowns for each field block
1052 for(std::size_t fb=0;fb<fieldBlockManagers_.size();fb++) {
1055 }
1056
1057 // build field block offsets: this helps fast construction
1058 // of GID offset vectors. GIDs are ordering by field block.
1059 std::vector<std::string> elementBlocks;
1060 getElementBlockIds(elementBlocks);
1061 for(std::size_t eb=0;eb<elementBlocks.size();eb++) {
1062 int offset = 0;
1063 for(std::size_t fb=0;fb<fieldBlockManagers_.size();fb++) {
1064 // int cnt = fieldBlockManagers_[fb]->getElementBlockGIDCount(elementBlocks[eb]);
1065 int cnt = getElementBlockGIDCount(fieldBlockManagers_[fb],elementBlocks[eb]);
1066 blockGIDOffset_[std::make_pair(elementBlocks[eb],fb)] = offset;
1067 offset += cnt;
1068 }
1069 }
1070}
1071
1072// build the global unknown numberings
1073// 1. this builds the pattens
1074// 2. initializes the connectivity
1075// 3. calls initComplete
1077{
1078 if(!fieldsRegistered())
1079 registerFields(true);
1080
1081 // build the pattern for the ID layout on the mesh
1082 // NOTE: hard coded to CG-only for now since this class is deprecated
1083 std::vector<std::pair<FieldType,RCP<const FieldPattern>>> patVector;
1084 std::map<std::pair<std::string,std::string>,Teuchos::RCP<const FieldPattern> >::iterator f2p_itr;
1085 for(f2p_itr=fieldStringToPattern_.begin();f2p_itr!=fieldStringToPattern_.end();f2p_itr++)
1086 patVector.push_back(std::make_pair(FieldType::CG,f2p_itr->second));
1087
1088 // if orientations are required, add the nodal field pattern to make it possible to compute them
1090 patVector.push_back(std::make_pair(FieldType::CG,Teuchos::rcp(new NodalFieldPattern(patVector[0].second->getCellTopology()))));
1091
1092 RCP<GeometricAggFieldPattern> aggFieldPattern = Teuchos::rcp(new GeometricAggFieldPattern);
1093 aggFieldPattern->buildPattern(patVector);
1094
1095 // setup connectivity mesh
1096 connMngr_->buildConnectivity(*aggFieldPattern);
1097
1098 // using new geometric pattern, build global unknowns
1099 buildGlobalUnknowns(aggFieldPattern);
1100}
1101
1102void BlockedDOFManager::printFieldInformation(std::ostream & os) const
1103{
1104 os << "BlockedDOFManager Field Information: " << std::endl;
1105
1106 if(fieldsRegistered()) {
1107 // Print field block DOF managers
1108 for(std::size_t fbm=0;fbm<fieldBlockManagers_.size();fbm++) {
1109 os << "*************************************************\n";
1110 os << "Field Block Index = " << fbm << std::endl;
1112
1113 // print out mapping between sub field IDs and blocked field IDs
1114 os << " Field String to Field Id (blocked/sub):\n";
1115 for(std::size_t i=0;i<fieldOrder_[fbm].size();i++) {
1116 std::string fieldString = fieldOrder_[fbm][i];
1117 int fieldNum = getFieldNum(fieldString);
1118 os << " \"" << fieldString << "\" is field ID " << fieldNum
1119 << "/" << fieldBlockManagers_[fbm]->getFieldNum(fieldString) << std::endl;
1120 }
1121 os << std::endl;
1122 }
1123 }
1124 else {
1125 // fields are not registered
1126 os << "Fields not yet registered! Unknowns not built (call registerFields or buildGlobalUnknowns)" << std::endl;
1127 }
1128}
1129
1130Teuchos::RCP<const FieldPattern>
1131BlockedDOFManager::getFieldPattern(const std::string & blockId, const std::string & fieldName) const
1132{
1133 std::map<std::pair<std::string,std::string>,Teuchos::RCP<const FieldPattern> >::const_iterator itr;
1134 itr = fieldStringToPattern_.find(std::make_pair(blockId,fieldName));
1135
1136 if(itr==fieldStringToPattern_.end()) // not found
1137 return Teuchos::null;
1138 else // found
1139 return itr->second;
1140}
1141
1150bool BlockedDOFManager::validFieldOrder(const std::vector<std::vector<std::string> > & fieldOrder_ut,
1151 const std::set<std::string> & fields) const
1152{
1153 std::set<std::string> orderedFields;
1154 std::size_t numberInOrder = 0;
1155
1156 for(std::size_t b=0;b<fieldOrder_ut.size();b++) {
1157 numberInOrder += fieldOrder_ut[b].size();
1158 orderedFields.insert(fieldOrder_ut[b].begin(),
1159 fieldOrder_ut[b].end());
1160 }
1161
1162 bool correctCount = (numberInOrder==fields.size());
1163 bool sameFields = (orderedFields==fields);
1164
1165 return correctCount && sameFields;
1166}
1167
1169{
1170 if(fieldOrder_.size()==0)
1171 return 1; // only one field block
1172 return fieldOrder_.size();
1173}
1174
1176
1177}
1178
1179#endif
PHX::MDField< ScalarT, panzer::Cell, panzer::IP > result
A field that will be used to build up the result of the integral we're performing.
PHX::MDField< ScalarT, panzer::Cell, panzer::BASIS > field
A field to which we'll contribute, or in which we'll store, the result of computing this integral.
void setFieldOrder(const std::vector< std::vector< std::string > > &fieldOrder)
virtual void getGhostedIndicesAsInt(std::vector< int > &indices) const
Get the set of indices ghosted for this processor.
Teuchos::RCP< ConnManager > connMngr_
int getFieldBlock(int fieldNum) const
void addFieldsToFieldBlockManager(const std::vector< std::string > &activeFields, GlobalIndexer &fieldBlockManager) const
virtual int getNumGhosted() const
Get the number of indices ghosted for this processor.
bool validFieldOrder(const std::vector< std::vector< std::string > > &fieldOrder_ut, const std::set< std::string > &fields) const
virtual void getOwnedIndicesAsInt(std::vector< int > &indices) const
Get the set of indices owned by this processor.
virtual void getGhostedIndices(std::vector< GlobalOrdinal > &indices) const
Get the set of indices ghosted for this processor.
void registerFields(bool buildSubUGIs)
virtual const std::vector< int > & getBlockFieldNumbers(const std::string &block) const
Teuchos::RCP< Teuchos::MpiComm< int > > communicator_
std::map< std::string, TupleToVectorPairMap > gidFieldOffsets_closure_
std::map< int, std::string > fieldNumToStr_
field number ==> field string
void getElementGIDsAsInt(panzer::LocalOrdinal localElmtId, std::vector< int > &gids, const std::string &blockIdHint="") const
Get the global IDs for a particular element. This function overwrites the gids variable.
std::map< std::pair< std::string, int >, int > blockGIDOffset_
(element block,field block) ==> gid offset
void getElementGIDsPair(panzer::LocalOrdinal localElmtId, std::vector< std::pair< int, GlobalOrdinal > > &gids, const std::string &blockIdHint="") const
Get the global IDs for a particular element. This function overwrites the gids variable.
virtual int getNumOwnedAndGhosted() const
Get the number of owned and ghosted indices for this processor.
int getBlockGIDOffset(const std::string &elementBlock, int fieldBlock) const
void getElementGIDs(panzer::LocalOrdinal localElmtId, std::vector< GlobalOrdinal > &gids, const std::string &blockIdHint="") const
Get the global IDs for a particular element. This function overwrites the gids variable.
virtual void getElementOrientation(panzer::LocalOrdinal localElmtId, std::vector< double > &gidsOrientation) const
Get a vector containg the orientation of the GIDs relative to the neighbors.
virtual bool fieldInBlock(const std::string &field, const std::string &block) const
void addField(const std::string &str, const Teuchos::RCP< const FieldPattern > &pattern)
Add a field to the DOF manager.
void setConnManager(const Teuchos::RCP< ConnManager > &connMngr, MPI_Comm mpiComm)
Set the connection manager and MPI_Comm objects.
int getNumFields() const
How many fields are handled by this manager.
virtual const std::vector< int > & getGIDFieldOffsets(const std::string &blockId, int fieldNum) const
Use the field pattern so that you can find a particular field in the GIDs array.
std::vector< std::vector< std::string > > fieldOrder_
virtual void getOwnedAndGhostedIndicesAsInt(std::vector< int > &indices) const
Get the set of owned and ghosted indices for this processor.
std::map< std::pair< std::string, std::string >, Teuchos::RCP< const FieldPattern > > fieldStringToPattern_
(block ID x field string) ==> pattern
const std::string & getFieldString(int num) const
Get the string name associated with a field number.
Teuchos::RCP< const FieldPattern > geomPattern_
virtual void getElementBlockIds(std::vector< std::string > &elementBlockIds) const
virtual void getOwnedAndGhostedIndices(std::vector< GlobalOrdinal > &indices) const
Get the set of owned and ghosted indices for this processor.
virtual void getOwnedIndices(std::vector< GlobalOrdinal > &indices) const
Get the set of indices owned by this processor.
std::map< Teuchos::Tuple< int, 3 >, std::pair< std::vector< int >, std::vector< int > >, LessThan > TupleToVectorPairMap
virtual const std::pair< std::vector< int >, std::vector< int > > & getGIDFieldOffsets_closure(const std::string &blockId, int fieldNum, int subcellDim, int subcellId) const
Use the field pattern so that you can find a particular field in the GIDs array. This version lets yo...
int getFieldNum(const std::string &str) const
Get the number used for access to this field.
Teuchos::RCP< ConnManager > resetIndices()
Reset the indicies for this DOF manager.
Teuchos::RCP< const FieldPattern > getFieldPattern(const std::string &blockId, const std::string &fieldName) const
Find a field pattern stored for a particular block and field number. This will retrive the pattern ad...
virtual int getNumOwned() const
Get the number of indices owned by this processor.
std::vector< Teuchos::RCP< GlobalIndexer > > fieldBlockManagers_
Teuchos::RCP< GlobalIndexer > buildNewIndexer(const Teuchos::RCP< ConnManager > &connManager, MPI_Comm mpiComm) const
void getFieldOrder(std::vector< std::vector< std::string > > &fieldOrder) const
virtual void ownedIndices(const std::vector< GlobalOrdinal > &indices, std::vector< bool > &isOwned) const
std::map< int, int > fieldNumToFieldBlk_
field number ==> field block
std::map< std::string, int > fieldStrToNum_
field string ==> field number
Teuchos::RCP< const ConnManager > getConnManager() const
std::map< std::string, std::map< int, std::vector< int > > > gidFieldOffsets_
std::map< std::string, std::set< std::string > > blockIdToFieldStrings_
block ID ==> field strings
std::map< std::string, std::vector< int > > blockIdToFieldNumbers_
block ID ==> field numbers
virtual int getElementBlockGIDCount(const std::string &blockId) const
How any GIDs are associate with a particular element block.
void printFieldInformation(std::ostream &os) const
void setFieldOrder(const std::vector< std::string > &fieldOrder)
int addField(const std::string &str, const Teuchos::RCP< const FieldPattern > &pattern, const panzer::FieldType &type=panzer::FieldType::CG)
Add a field to the DOF manager.