Documentation of CSL
objectSymmetry.h
Go to the documentation of this file.
1 // This file is part of MARTY.
2 //
3 // MARTY is free software: you can redistribute it and/or modify
4 // it under the terms of the GNU General Public License as published by
5 // the Free Software Foundation, either version 3 of the License, or
6 // (at your option) any later version.
7 //
8 // MARTY is distributed in the hope that it will be useful,
9 // but WITHOUT ANY WARRANTY; without even the implied warranty of
10 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 // GNU General Public License for more details.
12 //
13 // You should have received a copy of the GNU General Public License
14 // along with MARTY. If not, see <https://www.gnu.org/licenses/>.
15 
23 #ifndef OBJECT_SYMMETRY_H_INCLUDED
24 #define OBJECT_SYMMETRY_H_INCLUDED
25 
26 #include <iostream>
27 #include <csignal>
28 #include <vector>
29 #include <map>
31 
32 namespace csl {
33 
35 /*************************************************/
36 // Class ObjectPermutation<T> declaration //
37 /*************************************************/
39 
40 template<class T>
42 
43 #define Id_Perm(T) csl::ObjectPermutation<T>()
44 #define Id_Sym(T) csl::ObjectSymmetry<T>(Id_Perm(T))
45 
46 template<class T>
48 
49  public:
50 
52 
53  explicit
54  ObjectPermutation(const std::map<T, T>& otherMap);
55 
56  explicit
57  ObjectPermutation(std::map<T, T>&& otherMap);
58 
60  T b,
61  bool symmetric = true);
62 
63  ObjectPermutation(const ObjectPermutation<T>& other) = default;
64 
65  ObjectPermutation(ObjectPermutation<T>&& other) = default;
66 
67  ObjectPermutation& operator=(const ObjectPermutation<T>& other) = default;
68 
69  ObjectPermutation& operator=(ObjectPermutation<T>&& other) = default;
70 
72 
73  size_t size() const {
74  return permutation.size();
75  }
76 
77  bool empty() const {
78  return permutation.empty();
79  }
80 
81  typename std::map<T, T>::iterator begin() {
82  return permutation.begin();
83  }
84 
85  typename std::map<T, T>::iterator end() {
86  return permutation.end();
87  }
88 
89  typename std::map<T, T>::const_iterator begin() const {
90  return permutation.begin();
91  }
92 
93  typename std::map<T, T>::const_iterator end() const {
94  return permutation.end();
95  }
96 
97  void clear() {
98  rightForm = true;
99  permutation.clear();
100  }
101 
102  bool getRightForm() const {
103  return rightForm;
104  }
105 
106  std::map<T, T> getPermutation() const {
107  return permutation;
108  }
109 
110  void add(T a,
111  T b);
112 
113  bool operator==(const ObjectPermutation<T>& other) const;
114 
115  ObjectSymmetry<T> operator+(const ObjectPermutation<T>& other) const;
116 
117  ObjectSymmetry<T> operator+(const ObjectSymmetry<T>& other) const;
118 
119  ObjectPermutation<T> operator*(const ObjectPermutation<T>& other) const;
120 
121  ObjectSymmetry<T> operator*(const ObjectSymmetry<T>& other) const;
122 
123  ObjectPermutation<T> inverse() const;
124 
125  T operator[](const T& key) const;
126 
127  std::vector<T> operator[](const std::vector<T>& keys) const;
128 
129  static void toggleDisplayMode();
130 
131  template<class U>
132  friend
133  std::ostream& operator<<(std::ostream& fout,
134  const ObjectPermutation<U>& perm);
135 
136  private:
137 
138  void checkRightForm();
139 
140  private:
141 
142  bool rightForm = true;
143 
144  std::map<T, T> permutation;
145 
146  static bool displayMode;
147 };
148 
149 template<class T>
151 
153 /*************************************************/
154 // Class ObjectSymmetry<T> declaration //
155 /*************************************************/
157 
158 template<class T>
159 class ObjectSymmetry {
160 
161  IMPLEMENTS_STD_VECTOR_NO_PB(ObjectPermutation<T>, permutations)
162 
163  public:
164 
165  ObjectSymmetry();
166 
167  explicit
168  ObjectSymmetry(const ObjectPermutation<T>& first);
169 
170  explicit
171  ObjectSymmetry(const std::vector<ObjectPermutation<T>>& t_perm);
172 
173  explicit
174  ObjectSymmetry(std::vector<ObjectPermutation<T>>&& t_perm);
175 
176  ObjectSymmetry(const ObjectSymmetry<T>& other) = default;
177 
178  ObjectSymmetry(ObjectSymmetry<T>&& other) = default;
179 
180  ObjectSymmetry& operator=(const ObjectSymmetry<T>& other) = default;
181 
182  ObjectSymmetry& operator=(ObjectSymmetry<T>&& other) = default;
183 
184  void push_back(T a,
185  T b,
186  bool symmetric = true);
187 
188  void push_back(const ObjectPermutation<T>& object);
189 
190  std::vector<std::vector<T>> operator[](const std::vector<T>& keys) const;
191 
193 
194  ObjectSymmetry<T> operator+(const ObjectSymmetry<T>& other) const;
195 
196  ObjectSymmetry<T> operator*(const ObjectSymmetry<T>& other) const;
197 
198  ObjectSymmetry<T> operator*(const ObjectPermutation<T>& other) const;
199 
200  template<class U>
201  friend
202  std::ostream& operator<<(std::ostream& fout,
203  const ObjectSymmetry<U>& perm);
204 
205  private:
206 
207  std::vector<ObjectPermutation<T>> permutations;
208 };
209 
211 /*************************************************/
212 // Class ObjectPermutation<T> definition //
213 /*************************************************/
215 
216 template<class T>
218 {
219 
220 }
221 
222 template<class T>
224  T b,
225  bool symmetric)
226 {
227  add(a, b);
228  if (symmetric)
229  add(b, a);
230 }
231 
232 template<class T>
233 ObjectPermutation<T>::ObjectPermutation(const std::map<T, T>& otherMap)
234  :permutation(otherMap)
235 {
236  checkRightForm();
237 }
238 
239 template<class T>
240 ObjectPermutation<T>::ObjectPermutation(std::map<T, T>&& otherMap)
241  :permutation(otherMap)
242 {
243  checkRightForm();
244 }
245 
246 template<class T>
248 {
249 
250 }
251 
252 template<class T>
254 {
255  for (const auto& pair : permutation)
256  if (permutation.count(pair.second) != 1) {
257  rightForm = false;
258  return;
259  }
260  rightForm = true;
261 }
262 
263 template<class T>
265  T b)
266 {
267  permutation[a] = b;
268  checkRightForm();
269 }
270 
271 template<class T>
273 {
274  return (rightForm == other.rightForm
275  and permutation == other.permutation);
276 }
277 
278 template<class T>
280  const ObjectPermutation<T>& other) const
281 {
282  return ObjectSymmetry<T>({*this, other});
283 }
284 
285 template<class T>
287  const ObjectSymmetry<T>& other) const
288 {
289  return other + *this;
290 }
291 
292 template<class T>
294  const ObjectPermutation<T>& other) const
295 {
296  std::map<T, T> newMap;
297  for (const auto& pair : other.permutation)
298  newMap[pair.first] = (*this)[pair.second];
299  for (const auto& pair : permutation)
300  if (other.permutation.find(pair.first) == other.permutation.end())
301  newMap[pair.first] = pair.second;
302 
303  return ObjectPermutation<T>(std::move(newMap));
304 }
305 
306 template<class T>
308  const ObjectSymmetry<T>& other) const
309 {
310  ObjectSymmetry<T> newSym(other);
311  for (auto& perm : other)
312  perm = *this * perm;
313 }
314 
315 template<class T>
317 {
318  ObjectPermutation<T> newPerm;
319  newPerm.rightForm = rightForm;
320  newPerm.displayMode = displayMode;
321  for (const auto& pair : *this)
322  newPerm[pair.second] = pair.first;
323 }
324 
325 template<class T>
326 T ObjectPermutation<T>::operator[](const T& key) const
327 {
328  auto pos = permutation.find(key);
329  if (pos != permutation.end())
330  return pos->second;
331  return key;
332 }
333 
334 template<class T>
335 std::vector<T> ObjectPermutation<T>::operator[](
336  const std::vector<T>& keys) const
337 {
338  if (not rightForm)
339  std::cerr << "Warning: applying a non-cyclic permutation.";
340  std::vector<T> res;
341  for (const auto& key : keys)
342  res.push_back((*this)[key]);
343 
344  return res;
345 }
346 
347 template<class T>
349 {
350  displayMode = not displayMode;
351 }
352 
353 template<class T>
354 std::ostream& operator<<(std::ostream& fout,
355  const ObjectPermutation<T>& perm)
356 {
357  if (ObjectPermutation<T>::displayMode) {
358  fout << "Permutation of " << perm.size() << " elements.\n";
359  for (const auto& pair : perm.permutation)
360  fout << pair.first << " --> " << pair.second << std::endl;
361  }
362  else {
363  for (const auto& pair : perm.permutation)
364  fout << ": ( " << pair.first << ", " << pair.second << " ) ";
365  }
366 
367  return fout;
368 }
369 
371 /*************************************************/
372 // Class ObjectSymmetry<T> definition //
373 /*************************************************/
375 
376 template<class T>
378 {
379 
380 }
381 
382 template<class T>
384  :permutations(1, first)
385 {
386 
387 }
388 
389 template<class T>
391  const std::vector<ObjectPermutation<T>>& t_perm)
392  :permutations(t_perm)
393 {
394 
395 }
396 
397 template<class T>
399  std::vector<ObjectPermutation<T>>&& t_perm)
400  :permutations(t_perm)
401 {
402 
403 }
404 
405 template<class T>
407  T b,
408  bool symmetric)
409 {
410  ObjectPermutation<T> perm(a, b);
411  if (symmetric)
412  perm.add(b, a);
413  push_back(perm);
414 }
415 
416 template<class T>
418 {
419  permutations.push_back(value);
420 }
421 
422 template<class T>
423 std::vector<std::vector<T>> ObjectSymmetry<T>::operator[](
424  const std::vector<T>& keys) const
425 {
426  std::vector<std::vector<T>> res;
427  for (const auto& perm : permutations)
428  res.push_back(perm[keys]);
429 
430  return res;
431 }
432 
433 template<class T>
435  const ObjectPermutation<T>& other) const
436 {
437  ObjectSymmetry<T> newSym(*this);
438  newSym.push_back(other);
439 
440  return newSym;
441 }
442 
443 template<class T>
445  const ObjectSymmetry<T>& other) const
446 {
447  ObjectSymmetry<T> newSym(*this);
448  newSym.insert(newSym.end(), other.begin(), other.end());
449 
450  return newSym;
451 }
452 
453 template<class T>
455  const ObjectPermutation<T>& other) const
456 {
457  ObjectSymmetry<T> newSym(*this);
458  for (auto& perm : newSym)
459  perm = perm * other;
460 
461  return newSym;
462 }
463 
464 template<class T>
466  const ObjectSymmetry<T>& other) const
467 {
468  ObjectSymmetry<T> newSym;
469  for (const auto& permSelf : *this)
470  for (const auto& permOther : other)
471  newSym.push_back(permSelf * permOther);
472 
473  return newSym;
474 }
475 
476 template<class T>
477 std::ostream& operator<<(std::ostream& fout,
478  const ObjectSymmetry<T>& sym)
479 {
481  fout << "Symmetry of " << sym.size() << " elements.\n";
482  for (const auto& perm : sym)
483  fout << " " << perm << std::endl;
485 
486  return fout;
487 }
488 
489 } // End of namespace csl
490 
491 #endif
Namespace for csl library.
Definition: abreviation.h:34
Expr operator+(const Expr &a, const Expr &b)
Shortcut function that allows to use arithmetic operator + with Expr (== shared_ptr<Abstract>).
Definition: abstract.cpp:1298
Definition: objectSymmetry.h:41
Expr operator*(const Expr &a, const Expr &b)
Shortcut function that allows to use arithmetic operator * with Expr (== shared_ptr<Abstract>).
Definition: abstract.cpp:1351
std::vector< std::vector< int > > permutations(std::vector< int > init)
Gets all permutations (int the form of vectors of integers) of n elements, n beeing the size of init...
Definition: objectSymmetry.h:47