14 {
15
16const FiniteElement *
17Core::get_finite_element_structure(const std::string &name,
19 auto miit = finiteElements.get<FiniteElement_name_mi_tag>().find(name);
20 if (miit == finiteElements.get<FiniteElement_name_mi_tag>().end()) {
22 throw MoFEMException(
24 std::string("finite element < " + name +
25 " > not in database (top tip: check spelling)")
26 .c_str());
27 } else {
28 return nullptr;
29 }
30 }
31 return miit->get();
32}
33
34bool Core::check_finite_element(const std::string &name) const {
35 auto miit = finiteElements.get<FiniteElement_name_mi_tag>().find(name);
36 if (miit == finiteElements.get<FiniteElement_name_mi_tag>().end())
37 return false;
38 else
39 return true;
40}
41
45 *buildMoFEM &= 1 << 0;
46 if (verb == -1) {
47 verb = verbose;
48 }
49
50
51
52
53 auto add_meshset_to_partition = [&](auto meshset) {
55 const void *tag_vals[] = {&rAnk};
56 ParallelComm *pcomm = ParallelComm::get_pcomm(
57 &get_moab(), get_basic_entity_data_ptr()->pcommID);
58 Tag part_tag = pcomm->part_tag();
60 CHKERR get_moab().get_entities_by_type_and_tag(0, MBENTITYSET, &part_tag,
61 tag_vals, 1, tagged_sets,
62 moab::Interface::UNION);
63 for (auto s : tagged_sets)
64 CHKERR get_moab().add_entities(s, &meshset, 1);
66 };
67
68 auto &finite_element_name_set =
69 finiteElements.get<FiniteElement_name_mi_tag>();
70 auto it_fe = finite_element_name_set.find(fe_name);
71
73 if (it_fe != finite_element_name_set.end()) {
75 fe_name.c_str());
76 }
77
78 } else {
79 if (it_fe != finite_element_name_set.end())
81 }
83 CHKERR get_moab().create_meshset(MESHSET_SET, meshset);
84 CHKERR add_meshset_to_partition(meshset);
85
86
87 int fe_shift = 0;
88 for (; finiteElements.get<BitFEId_mi_tag>().find(
BitFEId().
set(fe_shift)) !=
89 finiteElements.get<BitFEId_mi_tag>().end();
90 ++fe_shift) {
91 }
92
93 auto id =
BitFEId().set(fe_shift);
94 CHKERR get_moab().tag_set_data(th_FEId, &meshset, 1, &
id);
95
96
97 void const *tag_data[] = {fe_name.c_str()};
98 int tag_sizes[1];
99 tag_sizes[0] = fe_name.size();
100 CHKERR get_moab().tag_set_by_ptr(th_FEName, &meshset, 1, tag_data, tag_sizes);
101
102
103 auto p = finiteElements.insert(
104 boost::shared_ptr<FiniteElement>(new FiniteElement(moab, meshset)));
105 if (!p.second)
107 "FiniteElement not inserted");
108
110 MOFEM_LOG(
"WORLD", Sev::inform) <<
"Add finite element " << fe_name;
111
113}
114
116Core::modify_finite_element_adjacency_table(const std::string &fe_name,
117 const EntityType type,
118 ElementAdjacencyFunct function) {
120 *buildMoFEM &= 1 << 0;
121 typedef FiniteElement_multiIndex::index<FiniteElement_name_mi_tag>::type
122 FiniteElements_by_name;
123 FiniteElements_by_name &finite_element_name_set =
124 finiteElements.get<FiniteElement_name_mi_tag>();
125 FiniteElements_by_name::iterator it_fe =
126 finite_element_name_set.find(fe_name);
127 if (it_fe == finite_element_name_set.end())
129 "This finite element is not defined (advise: check spelling)");
130 boost::shared_ptr<FiniteElement> fe;
131 fe = *it_fe;
132 fe->elementAdjacencyTable[
type] =
function;
134}
135
137Core::modify_finite_element_add_field_data(const std::string &fe_name,
138 const std::string name_data) {
140 *buildMoFEM &= 1 << 0;
141 typedef FiniteElement_multiIndex::index<FiniteElement_name_mi_tag>::type
142 FiniteElements_by_name;
143 FiniteElements_by_name &finite_element_name_set =
144 finiteElements.get<FiniteElement_name_mi_tag>();
145 FiniteElements_by_name::iterator it_fe =
146 finite_element_name_set.find(fe_name);
147 if (it_fe == finite_element_name_set.end())
149 "This finite element is not defined (advise: check spelling)");
150 bool success = finite_element_name_set.modify(
151 it_fe, FiniteElement_change_bit_add(get_field_id(name_data)));
152 if (!success)
154 "modification unsuccessful");
156}
157
159Core::modify_finite_element_add_field_row(const std::string &fe_name,
160 const std::string name_row) {
162 *buildMoFEM &= 1 << 0;
163 typedef FiniteElement_multiIndex::index<FiniteElement_name_mi_tag>::type
164 FiniteElements_by_name;
165 FiniteElements_by_name &finite_element_name_set =
166 finiteElements.get<FiniteElement_name_mi_tag>();
167 FiniteElements_by_name::iterator it_fe =
168 finite_element_name_set.find(fe_name);
169 if (it_fe == finite_element_name_set.end())
171 fe_name.c_str());
172 bool success = finite_element_name_set.modify(
173 it_fe, FiniteElement_row_change_bit_add(get_field_id(name_row)));
174 if (!success)
176 "modification unsuccessful");
178}
179
181Core::modify_finite_element_add_field_col(const std::string &fe_name,
182 const std::string name_col) {
184 *buildMoFEM &= 1 << 0;
185 auto &finite_element_name_set =
186 finiteElements.get<FiniteElement_name_mi_tag>();
187 auto it_fe = finite_element_name_set.find(fe_name);
188 if (it_fe == finite_element_name_set.end())
190 "this FiniteElement is there");
191 bool success = finite_element_name_set.modify(
192 it_fe, FiniteElement_col_change_bit_add(get_field_id(name_col)));
193 if (!success)
195 "modification unsuccessful");
197}
198
200Core::modify_finite_element_off_field_data(const std::string &fe_name,
201 const std::string name_data) {
203 *buildMoFEM &= 1 << 0;
204 auto &finite_element_name_set =
205 finiteElements.get<FiniteElement_name_mi_tag>();
206 auto it_fe = finite_element_name_set.find(fe_name);
207 if (it_fe == finite_element_name_set.end())
209 bool success = finite_element_name_set.modify(
210 it_fe, FiniteElement_change_bit_off(get_field_id(name_data)));
211 if (!success)
213 "modification unsuccessful");
215}
216
218Core::modify_finite_element_off_field_row(const std::string &fe_name,
219 const std::string name_row) {
221 *buildMoFEM &= 1 << 0;
222 auto &finite_element_name_set =
223 finiteElements.get<FiniteElement_name_mi_tag>();
224 auto it_fe = finite_element_name_set.find(fe_name);
225 if (it_fe == finite_element_name_set.end())
227 fe_name.c_str());
228 bool success = finite_element_name_set.modify(
229 it_fe, FiniteElement_row_change_bit_off(get_field_id(name_row)));
230 if (!success)
232 "modification unsuccessful");
234}
235
237Core::modify_finite_element_off_field_col(const std::string &fe_name,
238 const std::string name_col) {
240 *buildMoFEM &= 1 << 0;
241 auto &finite_element_name_set =
242 finiteElements.get<FiniteElement_name_mi_tag>();
243 auto it_fe = finite_element_name_set.find(fe_name);
244 if (it_fe == finite_element_name_set.end())
246 bool success = finite_element_name_set.modify(
247 it_fe, FiniteElement_col_change_bit_off(get_field_id(name_col)));
248 if (!success)
250 "modification unsuccessful");
252}
253
254BitFEId Core::getBitFEId(
const std::string &fe_name)
const {
255 auto &fe_by_id = finiteElements.get<FiniteElement_name_mi_tag>();
256 auto miit = fe_by_id.find(fe_name);
257 if (miit == fe_by_id.end())
259 ("finite element < " + fe_name + " > not found (top tip: check spelling)")
260 .c_str());
261 return (*miit)->getId();
262}
263
264std::string Core::getBitFEIdName(const BitFEId id) const {
265 auto &fe_by_id = finiteElements.get<BitFEId_mi_tag>();
266 auto miit = fe_by_id.find(id);
267 if (miit == fe_by_id.end())
269 return (*miit)->getName();
270}
271
272EntityHandle Core::get_finite_element_meshset(
const BitFEId
id)
const {
273 auto &fe_by_id = finiteElements.get<BitFEId_mi_tag>();
274 auto miit = fe_by_id.find(id);
275 if (miit == fe_by_id.end())
277 return (*miit)->meshset;
278}
279
280EntityHandle Core::get_finite_element_meshset(
const std::string name)
const {
281 return get_finite_element_meshset(getBitFEId(name));
282}
283
285Core::get_finite_element_entities_by_dimension(const std::string name, int dim,
287
289
290 EntityHandle meshset = get_finite_element_meshset(name);
291 CHKERR get_moab().get_entities_by_dimension(meshset, dim, ents,
true);
293}
294
295MoFEMErrorCode Core::get_finite_element_entities_by_type(
const std::string name,
296 EntityType type,
298
300
301 EntityHandle meshset = get_finite_element_meshset(name);
302 CHKERR get_moab().get_entities_by_type(meshset, type, ents,
true);
303
305}
306
308Core::get_finite_element_entities_by_handle(const std::string name,
310
312
313 EntityHandle meshset = get_finite_element_meshset(name);
314 CHKERR get_moab().get_entities_by_handle(meshset, ents,
true);
315
317}
318
321 for (auto &fe : finiteElements.get<FiniteElement_name_mi_tag>())
323
326}
327
329 const EntityHandle meshset,
const EntityType type,
const std::string name,
330 const bool recursive) {
331 *buildMoFEM &= 1 << 0;
334
335 idm = get_finite_element_meshset(getBitFEId(name));
337 CHKERR get_moab().get_entities_by_type(meshset, type, ents, recursive);
338 CHKERR getInterface<BitRefManager>()->setElementsBitRefLevel(ents);
339 CHKERR get_moab().add_entities(idm, ents);
340
342}
343
345Core::add_ents_to_finite_element_by_dim(
const EntityHandle meshset,
346 const int dim, const std::string name,
347 const bool recursive) {
349 *buildMoFEM &= 1 << 0;
351 idm = get_finite_element_meshset(getBitFEId(name));
353 CHKERR get_moab().get_entities_by_dimension(meshset, dim, ents, recursive);
354 CHKERR getInterface<BitRefManager>()->setElementsBitRefLevel(ents);
355 CHKERR get_moab().add_entities(idm, ents);
357}
358
360 const Range ents,
const EntityType type,
const std::string name) {
362 *buildMoFEM &= 1 << 0;
364 idm = get_finite_element_meshset(getBitFEId(name));
365 CHKERR getInterface<BitRefManager>()->setElementsBitRefLevel(
366 ents.subset_by_type(type));
367 CHKERR get_moab().add_entities(idm, ents.subset_by_type(type));
369}
370
372Core::add_ents_to_finite_element_by_dim(
const Range ents,
const int dim,
373 const std::string name) {
375 *buildMoFEM &= 1 << 0;
377 idm = get_finite_element_meshset(getBitFEId(name));
378 CHKERR getInterface<BitRefManager>()->setElementsBitRefLevel(
379 ents.subset_by_dimension(dim));
380 CHKERR get_moab().add_entities(idm, ents.subset_by_dimension(dim));
382}
383
385Core::add_ents_to_finite_element_EntType_by_bit_ref(
const BitRefLevel &
bit,
386 const std::string &name,
387 EntityType type, int verb) {
390 type, verb);
391
393}
394
395MoFEMErrorCode Core::add_ents_to_finite_element_EntType_by_bit_ref(
396 const BitRefLevel &
bit,
const BitRefLevel &mask,
const std::string &name,
397 EntityType type, int verb) {
399 CHKERR add_ents_to_finite_element_by_bit_ref(
bit, mask, name, type, verb);
400
402}
403
405 const BitRefLevel
bit,
const BitRefLevel mask,
const std::string name,
406 EntityType type, int verb) {
408
409 if (verb == -1)
410 verb = verbose;
411 *buildMoFEM &= 1 << 0;
412 const BitFEId id = getBitFEId(name);
413 const EntityHandle idm = get_finite_element_meshset(
id);
414
415 auto &ref_MoFEMFiniteElement = refinedFiniteElements.get<Ent_mi_tag>();
418
419 int nb_add_fes = 0;
420 for (; miit != hi_miit; miit++) {
421 const auto &bit2 = miit->get()->getBitRefLevel();
422 if ((bit2 & mask) != bit2)
423 continue;
424 if ((bit2 &
bit).any()) {
426 CHKERR get_moab().add_entities(idm, &ent, 1);
427 nb_add_fes++;
428 }
429 }
430
432 << "Finite element " << name << " added. Nb. of elements added "
433 << nb_add_fes << " out of " << std::distance(miit, hi_miit);
434
436
438}
439
441 const EntityHandle meshset,
const std::string &name,
const bool recursive) {
443 *buildMoFEM &= 1 << 0;
444 const BitFEId id = getBitFEId(name);
445 const EntityHandle idm = get_finite_element_meshset(
id);
446 if (recursive == false) {
447 CHKERR get_moab().add_entities(idm, &meshset, 1);
448 } else {
450 CHKERR get_moab().get_entities_by_type(meshset, MBENTITYSET, meshsets,
451 false);
452 CHKERR get_moab().add_entities(idm, meshsets);
453 }
455}
456
458Core::buildFiniteElements(const boost::shared_ptr<FiniteElement> &fe,
459 const Range *ents_ptr,
int verb) {
462 verb = verbose;
463
466 << "Build Finite Elements " << fe->getName();
467
468 auto &fields_by_id = fIelds.get<BitFieldId_mi_tag>();
469
470
472 std::array<BitFieldId, LAST> fe_fields = {fe.get()->getBitFieldIdRow(),
473 fe.get()->getBitFieldIdCol(),
474 fe.get()->getBitFieldIdData()};
475
476
477 EntityHandle meshset = get_finite_element_meshset(fe.get()->getId());
478
479
481 CHKERR get_moab().get_entities_by_handle(meshset, fe_ents,
false);
482
483 if (ents_ptr)
484 fe_ents = intersect(fe_ents, *ents_ptr);
485
486
487 typedef std::vector<boost::weak_ptr<EntFiniteElement>> VecOfWeakFEPtrs;
488 VecOfWeakFEPtrs processed_fes;
489 processed_fes.reserve(fe_ents.size());
490
491 int last_data_field_ents_view_size = 0;
492 int last_row_field_ents_view_size = 0;
493 int last_col_field_ents_view_size = 0;
494
495
496 std::vector<EntityHandle> adj_ents;
497
498
499 for (Range::const_pair_iterator peit = fe_ents.const_pair_begin();
500 peit != fe_ents.const_pair_end(); peit++) {
501
502 const auto first = peit->first;
503 const auto second = peit->second;
504
505
506
507
508 auto ref_fe_miit =
509 refinedFiniteElements.get<Ent_mi_tag>().lower_bound(first);
510 auto hi_ref_fe_miit =
511 refinedFiniteElements.get<Ent_mi_tag>().upper_bound(second);
512 if (std::distance(ref_fe_miit, hi_ref_fe_miit) != (second - first + 1)) {
513 MOFEM_LOG(
"SELF", Sev::noisy) <<
"Finite element " << fe->getName()
514 << " not defined on all entities in "
515 "the meshset, missing entities";
517 << "Missing entities: " << first << " - " << second;
518 }
519
520 EntFiniteElement_multiIndex::iterator hint_p = entsFiniteElements.end();
521 for (; ref_fe_miit != hi_ref_fe_miit; ref_fe_miit++) {
522
523
524 hint_p = entsFiniteElements.emplace_hint(
525 hint_p, boost::make_shared<EntFiniteElement>(*ref_fe_miit, fe));
526 processed_fes.emplace_back(*hint_p);
527 auto fe_raw_ptr = hint_p->get();
528
529
530 bool row_as_data = false, col_as_row = false;
531 if (fe_fields[
DATA] == fe_fields[
ROW])
532 row_as_data = true;
533 if (fe_fields[
ROW] == fe_fields[
COL])
534 col_as_row = true;
535
536 fe_raw_ptr->getDataFieldEntsPtr()->reserve(
537 last_data_field_ents_view_size);
538
539 if (row_as_data) {
540 fe_raw_ptr->getRowFieldEntsPtr() = fe_raw_ptr->getDataFieldEntsPtr();
541 } else {
542
543 if (fe_raw_ptr->getRowFieldEntsPtr() ==
544 fe_raw_ptr->getDataFieldEntsPtr())
545 fe_raw_ptr->getRowFieldEntsPtr() =
546 boost::make_shared<FieldEntity_vector_view>();
547 fe_raw_ptr->getRowFieldEntsPtr()->reserve(
548 last_row_field_ents_view_size);
549 }
550
551 if (row_as_data && col_as_row) {
552 fe_raw_ptr->getColFieldEntsPtr() = fe_raw_ptr->getDataFieldEntsPtr();
553 } else if (col_as_row) {
554 fe_raw_ptr->getColFieldEntsPtr() = fe_raw_ptr->getRowFieldEntsPtr();
555 } else {
556 if (
557
558 fe_raw_ptr->getColFieldEntsPtr() ==
559 fe_raw_ptr->getRowFieldEntsPtr() ||
560 fe_raw_ptr->getColFieldEntsPtr() ==
561 fe_raw_ptr->getDataFieldEntsPtr()
562
563 )
564 fe_raw_ptr->getColFieldEntsPtr() =
565 boost::make_shared<FieldEntity_vector_view>();
566 fe_raw_ptr->getColFieldEntsPtr()->reserve(
567 last_col_field_ents_view_size);
568 }
569
570
571 for (
unsigned int ii = 0; ii !=
BitFieldId().size(); ++ii) {
572
573
575
576 for (int ss = 0; ss < LAST; ss++) {
577 id_common |= fe_fields[ss] &
BitFieldId().set(ii);
578 }
579 if (id_common.none())
580 continue;
581
582
584 auto miit = fields_by_id.find(field_id);
585 if (miit == fields_by_id.end())
587 auto field_bit_number = (*miit)->getBitNumber();
588
589
590
591 const std::string
field_name = miit->get()->getName();
592 const bool add_to_data = (field_id & fe_fields[
DATA]).any();
593 const bool add_to_row = (field_id & fe_fields[
ROW]).any();
594 const bool add_to_col = (field_id & fe_fields[
COL]).any();
595
596
597
598 adj_ents.clear();
599 CHKERR fe_raw_ptr->getElementAdjacency(*miit, adj_ents);
600
601 for (auto ent : adj_ents) {
602
603 auto dof_it = entsFields.get<Unique_mi_tag>().find(
604 FieldEntity::getLocalUniqueIdCalculate(field_bit_number, ent));
605 if (dof_it != entsFields.get<Unique_mi_tag>().end()) {
606
607 if (add_to_data) {
608 fe_raw_ptr->getDataFieldEntsPtr()->emplace_back(*dof_it);
609 }
610 if (add_to_row && !row_as_data) {
611 fe_raw_ptr->getRowFieldEntsPtr()->emplace_back(*dof_it);
612 }
613 if (add_to_col && !col_as_row) {
614 fe_raw_ptr->getColFieldEntsPtr()->emplace_back(*dof_it);
615 }
616
617 }
618 }
619 }
620
621
622 auto uid_comp = [](
const auto &
a,
const auto &b) {
623 return a.lock()->getLocalUniqueId() < b.lock()->getLocalUniqueId();
624 };
625
626
627
628
629 sort(fe_raw_ptr->getDataFieldEntsPtr()->begin(),
630 fe_raw_ptr->getDataFieldEntsPtr()->end(), uid_comp);
631 last_data_field_ents_view_size =
632 fe_raw_ptr->getDataFieldEntsPtr()->size();
633
634
635 if (!row_as_data) {
636 sort(fe_raw_ptr->getRowFieldEntsPtr()->begin(),
637 fe_raw_ptr->getRowFieldEntsPtr()->end(), uid_comp);
638 last_row_field_ents_view_size =
639 fe_raw_ptr->getRowFieldEntsPtr()->size();
640 }
641
642
643 if (!col_as_row) {
644 sort(fe_raw_ptr->getColFieldEntsPtr()->begin(),
645 fe_raw_ptr->getColFieldEntsPtr()->end(), uid_comp);
646 last_col_field_ents_view_size =
647 fe_raw_ptr->getColFieldEntsPtr()->size();
648 }
649 }
650 }
651
653}
654
657
659 verb = verbose;
660
661
662 for (auto &fe : finiteElements)
663 CHKERR buildFiniteElements(fe, NULL, verb);
664
666
667 auto &fe_ents = entsFiniteElements.get<Unique_mi_tag>();
668 for (auto &fe : finiteElements) {
669 auto miit = fe_ents.lower_bound(
670 EntFiniteElement::getLocalUniqueIdCalculate(0, fe->getFEUId()));
671 auto hi_miit =
672 fe_ents.upper_bound(EntFiniteElement::getLocalUniqueIdCalculate(
673 get_id_for_max_type<MBENTITYSET>(), fe->getFEUId()));
674 const auto count = std::distance(miit, hi_miit);
676 << "Finite element " << fe->getName()
677 << " added. Nb. of elements added " << count;
679
681 for (auto &field : fIelds) {
682 auto rec = slg.open_record(keywords::severity = Sev::verbose);
683 if (rec) {
684 logging::record_ostream strm(rec);
685 strm << "Field " << field->getName() << " on finite element: ";
686 if ((field->getId() & fe->getBitFieldIdRow()).any())
687 strm << "row ";
688 if ((field->getId() & fe->getBitFieldIdCol()).any())
689 strm << "columns ";
690 if ((field->getId() & fe->getBitFieldIdData()).any())
691 strm << "data";
692 strm.flush();
693 slg.push_record(boost::move(rec));
694 }
695 }
696 }
697
699 }
700
701 *buildMoFEM |= 1 << 1;
703}
704
709}
710
712 const Range *
const ents_ptr,
713 int verb) {
715 if (verb == -1)
716 verb = verbose;
717
718 auto fe_miit = finiteElements.get<FiniteElement_name_mi_tag>().find(fe_name);
719 if (fe_miit == finiteElements.get<FiniteElement_name_mi_tag>().end())
721 fe_name.c_str());
722
723 CHKERR buildFiniteElements(*fe_miit, ents_ptr, verb);
724
726 auto &fe_ents = entsFiniteElements.get<Unique_mi_tag>();
727 auto miit = fe_ents.lower_bound(
728 EntFiniteElement::getLocalUniqueIdCalculate(0, (*fe_miit)->getFEUId()));
729 auto hi_miit =
730 fe_ents.upper_bound(EntFiniteElement::getLocalUniqueIdCalculate(
731 get_id_for_max_type<MBENTITYSET>(), (*fe_miit)->getFEUId()));
732 const auto count = std::distance(miit, hi_miit);
733 MOFEM_LOG(
"SYNC", Sev::inform) <<
"Finite element " << fe_name
734 << " added. Nb. of elements added " << count;
736 }
737
738 *buildMoFEM |= 1 << 1;
740}
741
745 verb = verbose;
746
747 if (!((*buildMoFEM) & BUILD_FIELD))
749 if (!((*buildMoFEM) & BUILD_FE))
751 for (auto peit = ents.pair_begin(); peit != ents.pair_end(); ++peit) {
752 auto fit = entsFiniteElements.get<Ent_mi_tag>().lower_bound(peit->first);
753 auto hi_fit =
754 entsFiniteElements.get<Ent_mi_tag>().upper_bound(peit->second);
755 for (; fit != hi_fit; ++fit) {
756 if ((*fit)->getBitFieldIdRow().none() &&
757 (*fit)->getBitFieldIdCol().none() &&
758 (*fit)->getBitFieldIdData().none())
759 continue;
761 if ((*fit)->getBitFieldIdRow() != (*fit)->getBitFieldIdCol())
763 if ((*fit)->getBitFieldIdRow() != (*fit)->getBitFieldIdData())
765 FieldEntityEntFiniteElementAdjacencyMap_change_ByWhat modify_row(by);
766 auto hint = entFEAdjacencies.end();
767 for (auto e : *(*fit)->getRowFieldEntsPtr()) {
768 hint = entFEAdjacencies.emplace_hint(hint, e.lock(), *fit);
769 bool success = entFEAdjacencies.modify(hint, modify_row);
770 if (!success)
772 "modification unsuccessful");
773 }
774 if ((*fit)->getBitFieldIdRow() != (*fit)->getBitFieldIdCol()) {
776 if ((*fit)->getBitFieldIdCol() != (*fit)->getBitFieldIdData())
778 FieldEntityEntFiniteElementAdjacencyMap_change_ByWhat modify_col(by);
779 auto hint = entFEAdjacencies.end();
780 for (auto e : *(*fit)->getColFieldEntsPtr()) {
781 hint = entFEAdjacencies.emplace_hint(hint, e.lock(), *fit);
782 bool success = entFEAdjacencies.modify(hint, modify_col);
783 if (!success)
785 "modification unsuccessful");
786 }
787 }
788 if ((*fit)->getBitFieldIdRow() != (*fit)->getBitFieldIdData() ||
789 (*fit)->getBitFieldIdCol() != (*fit)->getBitFieldIdData()) {
790 FieldEntityEntFiniteElementAdjacencyMap_change_ByWhat modify_data(
792 auto hint = entFEAdjacencies.end();
793 for (auto &e : (*fit)->getDataFieldEnts()) {
794 hint = entFEAdjacencies.emplace_hint(hint, e.lock(), *fit);
795 bool success = entFEAdjacencies.modify(hint, modify_data);
796 if (!success)
798 "modification unsuccessful");
799 }
800 }
801 }
802 }
803
806 << "Number of adjacencies " << entFEAdjacencies.size();
808 }
809
810 *buildMoFEM |= 1 << 2;
812}
813
815 const BitRefLevel &mask, int verb) {
817 if (verb == -1)
818 verb = verbose;
820 CHKERR BitRefManager(*this).getEntitiesByRefLevel(
bit, mask, ents);
821
822 CHKERR build_adjacencies(ents, verb);
823
825}
828 if (verb == -1)
829 verb = verbose;
831
833}
834
835EntFiniteElement_multiIndex::index<Unique_mi_tag>::type::iterator
836Core::get_fe_by_name_begin(const std::string &fe_name) const {
837 auto miit = finiteElements.get<FiniteElement_name_mi_tag>().find(fe_name);
838 if (miit != finiteElements.get<FiniteElement_name_mi_tag>().end()) {
839 return entsFiniteElements.get<Unique_mi_tag>().lower_bound(
840 EntFiniteElement::getLocalUniqueIdCalculate(0, (*miit)->getFEUId()));
841 } else {
842 return entsFiniteElements.get<Unique_mi_tag>().end();
843 }
844}
845
846EntFiniteElement_multiIndex::index<Unique_mi_tag>::type::iterator
847Core::get_fe_by_name_end(const std::string &fe_name) const {
848 auto miit = finiteElements.get<FiniteElement_name_mi_tag>().find(fe_name);
849 if (miit != finiteElements.get<FiniteElement_name_mi_tag>().end()) {
850 return entsFiniteElements.get<Unique_mi_tag>().upper_bound(
851 EntFiniteElement::getLocalUniqueIdCalculate(
852 get_id_for_max_type<MBENTITYSET>(), (*miit)->getFEUId()));
853 } else {
854 return entsFiniteElements.get<Unique_mi_tag>().end();
855 }
856}
857
859 const std::string &name) const {
861 FiniteElement_multiIndex::index<FiniteElement_name_mi_tag>::type::iterator it;
862 it = finiteElements.get<FiniteElement_name_mi_tag>().find(name);
863 if (it == finiteElements.get<FiniteElement_name_mi_tag>().end()) {
864 SETERRQ(mofemComm, 1, "finite element not found < %s >", name.c_str());
865 }
867
868 int num_entities;
869 CHKERR get_moab().get_number_entities_by_handle(meshset, num_entities);
870
871 auto counts_fes = [&]() {
872 return std::distance(get_fe_by_name_begin((*it)->getName()),
873 get_fe_by_name_end((*it)->getName()));
874 };
875
876 if (counts_fes() != static_cast<size_t>(num_entities)) {
878 "not equal number of entities in meshset and finite elements "
879 "multiindex < %s >",
880 (*it)->getName().c_str());
881 }
883}
884
885MoFEMErrorCode Core::check_number_of_ents_in_ents_finite_element()
const {
887 FiniteElement_multiIndex::index<FiniteElement_name_mi_tag>::type::iterator it;
888 it = finiteElements.get<FiniteElement_name_mi_tag>().begin();
889 for (; it != finiteElements.get<FiniteElement_name_mi_tag>().end(); it++) {
891
892 int num_entities;
893 CHKERR get_moab().get_number_entities_by_handle(meshset, num_entities);
894
895 auto counts_fes = [&]() {
896 return std::distance(get_fe_by_name_begin((*it)->getName()),
897 get_fe_by_name_end((*it)->getName()));
898 };
899
900 if (counts_fes() != static_cast<size_t>(num_entities)) {
902 "not equal number of entities in meshset and finite elements "
903 "multiindex < %s >",
904 (*it)->getName().c_str());
905 }
906 }
908}
909
911Core::get_problem_finite_elements_entities(const std::string problem_name,
912 const std::string &fe_name,
915 auto &prb = pRoblems.get<Problem_mi_tag>();
916 auto p_miit = prb.find(problem_name);
917 if (p_miit == prb.end())
919 "No such problem like < %s >", problem_name.c_str());
920
921 auto fe_miit = finiteElements.get<FiniteElement_name_mi_tag>().find(fe_name);
922 if (fe_miit != finiteElements.get<FiniteElement_name_mi_tag>().end()) {
923 auto miit =
924 p_miit->numeredFiniteElementsPtr->get<Unique_mi_tag>().lower_bound(
925 EntFiniteElement::getLocalUniqueIdCalculate(
926 0, (*fe_miit)->getFEUId()));
927 auto hi_miit =
928 p_miit->numeredFiniteElementsPtr->get<Unique_mi_tag>().upper_bound(
929 EntFiniteElement::getLocalUniqueIdCalculate(
930 get_id_for_max_type<MBENTITYSET>(), (*fe_miit)->getFEUId()));
931
932 if (miit != hi_miit) {
933 std::vector<EntityHandle> ents;
934 ents.reserve(std::distance(miit, hi_miit));
935 for (; miit != hi_miit; ++miit)
936 ents.push_back((*miit)->getEnt());
937 int part = (*miit)->getPart();
938 CHKERR get_moab().tag_clear_data(th_Part, &*ents.begin(), ents.size(),
939 &part);
940 CHKERR get_moab().add_entities(meshset, &*ents.begin(), ents.size());
941 }
942 }
943
945}
946
947}
#define FECoreFunctionBegin
#define MOFEM_LOG_SYNCHRONISE(comm)
Synchronise "SYNC" channel.
MoFEMTypes
Those types control how functions respond on arguments, f.e. error handling.
#define MoFEMFunctionReturnHot(a)
Last executable line of each PETSc function used for error handling. Replaces return()
@ MOFEM_OPERATION_UNSUCCESSFUL
@ MOFEM_DATA_INCONSISTENCY
#define MoFEMFunctionReturn(a)
Last executable line of each PETSc function used for error handling. Replaces return()
#define CHKERR
Inline error check.
#define MoFEMFunctionBeginHot
First executable line of each MoFEM function, used for error handling. Final line of MoFEM functions ...
#define THROW_MESSAGE(msg)
Throw MoFEM exception.
#define MOFEM_LOG(channel, severity)
Log.
static LoggerType & getLog(const std::string channel)
Get logger by channel.
PetscErrorCode MoFEMErrorCode
MoFEM/PETSc error code.
std::bitset< BITFEID_SIZE > BitFEId
Finite element Id.
std::bitset< BITFIELDID_SIZE > BitFieldId
Field Id.
std::bitset< BITREFLEVEL_SIZE > BitRefLevel
Bit structure attached to each entity identifying to what mesh entity is attached.
EntityHandle get_id_for_max_type()
EntityHandle get_id_for_min_type()
MoFEM::LogManager::SeverityLevel Sev
const EntityHandle no_handle
No entity handle is indicated by zero handle, i.e. root meshset.
constexpr auto field_name