Wildmeshing Toolkit
Loading...
Searching...
No Matches
InvariantCollection.cpp
Go to the documentation of this file.
2#include <type_traits>
3#include <wmtk/Mesh.hpp>
5
6namespace wmtk::invariants {
7
9 : Invariant(m, true, true, true)
10{}
15{
16 assert(o.mesh() == mesh());
18 return *this;
19}
21{
22 assert(o.mesh() == mesh());
23 m_invariants = std::move(o.m_invariants);
24 return *this;
25}
26
27void InvariantCollection::add(std::shared_ptr<Invariant> invariant)
28{
29 m_invariants.emplace_back(std::move(invariant));
30}
32{
33 for (const auto& invariant : m_invariants) {
34 if (&mesh() != &invariant->mesh()) {
35 for (const Tuple& ct : mesh().map_tuples(invariant->mesh(), t)) {
36 if (!invariant->before(
37 simplex::Simplex(invariant->mesh(), t.primitive_type(), ct))) {
38 return false;
39 }
40 }
41 } else {
42 if (!invariant->before(t)) {
43 return false;
44 }
45 }
46 }
47 return true;
48}
50 const std::vector<Tuple>& top_dimension_tuples_before,
51 const std::vector<Tuple>& top_dimension_tuples_after) const
52{
53 for (const auto& invariant : m_invariants) {
54 if (&mesh() != &invariant->mesh()) {
55 const bool invariant_uses_old_state = invariant->use_old_state_in_after();
56 const bool invariant_uses_new_state = invariant->use_new_state_in_after();
57 if (!(invariant_uses_old_state || invariant_uses_new_state)) {
58 continue;
59 }
60 auto map = [&](const auto& tuples) {
61 return mesh().map_tuples(invariant->mesh(), mesh().top_simplex_type(), tuples);
62 };
63 const std::vector<Tuple> mapped_tuples_after =
64 invariant_uses_new_state ? map(top_dimension_tuples_after) : std::vector<Tuple>{};
65 const std::vector<Tuple> mapped_tuples_before =
66 invariant_uses_old_state ? mesh().parent_scope(map, top_dimension_tuples_before)
67 : std::vector<Tuple>{};
68 if (!invariant->after(mapped_tuples_before, mapped_tuples_after)) {
69 return false;
70 }
71 } else {
72 if (!invariant->after(top_dimension_tuples_before, top_dimension_tuples_after)) {
73 return false;
74 }
75 }
76 // assert(&mesh() != &invariant->mesh());
77 // if (!invariant->after(type, tuples)) {
78 // return false;
79 // }
80 }
81 return true;
82}
83
85 const std::vector<simplex::Simplex>& simplices_before,
86 const std::vector<simplex::Simplex>& simplices_after) const
87{
88#ifndef NDEBUG
89 for (const auto& s : simplices_before) {
90 mesh().parent_scope([&]() { assert(mesh().is_valid(s.tuple())); });
91 }
92 for (const auto& s : simplices_after) {
93 assert(mesh().is_valid(s.tuple()));
94 }
95#endif
96
97 for (const auto& invariant : m_invariants) {
98 if (&mesh() != &invariant->mesh()) {
99 auto mapped_simplices_after = mesh().map(invariant->mesh(), simplices_after);
100 auto mapped_simplices_before = mesh().parent_scope(
101 [&]() { return mesh().map(invariant->mesh(), simplices_before); });
102#ifndef NDEBUG
103 for (const auto& s : mapped_simplices_before) {
104 mesh().parent_scope([&]() { assert(invariant->mesh().is_valid(s.tuple())); });
105 }
106 for (const auto& s : mapped_simplices_after) {
107 assert(invariant->mesh().is_valid(s.tuple()));
108 }
109 assert(mesh().is_from_same_multi_mesh_structure(invariant->mesh()));
110#endif
111 if (!invariant->directly_modified_after(
112 mapped_simplices_before,
113 mapped_simplices_after)) {
114 return false;
115 }
116 } else {
117 if (!invariant->directly_modified_after(simplices_before, simplices_after)) {
118 return false;
119 }
120 }
121 }
122 return true;
123}
124
125const std::shared_ptr<Invariant>& InvariantCollection::get(int64_t index) const
126{
127 return m_invariants.at(index);
128}
130{
131 return m_invariants.size();
132}
134{
135 return m_invariants.empty();
136}
137const std::vector<std::shared_ptr<Invariant>>& InvariantCollection::invariants() const
138{
139 return m_invariants;
140}
141
142std::map<Mesh const*, std::vector<std::shared_ptr<Invariant>>>
144{
145 decltype(get_map_mesh_to_invariants()) mesh_invariants_map;
146
147 throw std::runtime_error("Untested code. Potentially wrong.");
148
149 for (std::shared_ptr<Invariant> inv : m_invariants) {
150 // TODO check if that if statement is correct
151 if (std::is_base_of<InvariantCollection, decltype(inv)::element_type>()) {
152 // go through invariant collections
153 InvariantCollection& sub_ic = static_cast<InvariantCollection&>(*inv);
154 decltype(mesh_invariants_map) sub_map = sub_ic.get_map_mesh_to_invariants();
155
156 for (const auto& [mptr, i] : sub_map) {
157 auto& vec = mesh_invariants_map[mptr];
158 vec.insert(vec.end(), i.begin(), i.end());
159 }
160 } else {
161 mesh_invariants_map[&(inv->mesh())].push_back(inv);
162 }
163 }
164 //
165}
166
167} // namespace wmtk::invariants
std::vector< Tuple > map_tuples(const Mesh &other_mesh, const simplex::Simplex &my_simplex) const
maps a simplex from this mesh to any other mesh
std::vector< simplex::Simplex > map(const Mesh &other_mesh, const simplex::Simplex &my_simplex) const
maps a simplex from this mesh to any other mesh
decltype(auto) parent_scope(Functor &&f, Args &&... args) const
Evaluate the passed in function inside the parent scope.
Definition Mesh.hpp:941
The Tuple is the basic navigation tool in our mesh data structure.
Definition Tuple.hpp:19
bool directly_modified_after(const std::vector< simplex::Simplex > &simplices_before, const std::vector< simplex::Simplex > &simplices_after) const override
void add(std::shared_ptr< Invariant > invariant)
std::map< Mesh const *, std::vector< std::shared_ptr< Invariant > > > get_map_mesh_to_invariants()
bool before(const simplex::Simplex &t) const override
bool after(const std::vector< Tuple > &top_dimension_tuples_before, const std::vector< Tuple > &top_dimension_tuples_after) const override
std::vector< std::shared_ptr< Invariant > > m_invariants
const std::shared_ptr< Invariant > & get(int64_t index) const
const std::vector< std::shared_ptr< Invariant > > & invariants() const
InvariantCollection & operator=(const InvariantCollection &)
const Mesh & mesh() const
Definition Invariant.cpp:35
PrimitiveType primitive_type() const
Definition Simplex.hpp:51