Documentation of MARTY
A Modern ARtificial Theoretical phYsicist
datalist.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 #pragma once
24 
25 #include <vector>
26 #include <iostream>
27 #include <functional>
28 #include <type_traits>
29 #include "csl/std_vector_implementation.h"
30 
31 namespace mty::doc {
32 
33 template<class Printable>
35  void operator()(std::ostream &out, Printable const &printable) {
36  out << printable;
37  }
38 };
39 
40 template<class Comparable>
42  :public std::equal_to<std::remove_reference_t<std::remove_cv_t<Comparable>>>
43 {};
44 
45 template<class Comparable>
47  bool operator()(Comparable const &, Comparable const &) const {
48  return false;
49  }
50 };
51 
52 template<class ValueType, class Comparator, class HardComparator, class Printer>
53 struct DataDiff;
54 
55 template<
56  class ValueType,
57  class Comparator = doc::DefaultComparator<ValueType>,
58  class HardComparator = doc::DefaultHardComparator<ValueType>,
59  class Printer = doc::DefaultPrinter<ValueType>
60  >
61 class DataList {
62 
63  IMPLEMENTS_STD_VECTOR_NO_PB(ValueType, data)
64 
65 public:
66 
67  static std::vector<size_t> range(size_t N) {
68  std::vector<size_t> indices(N);
69  for (size_t i = 0; i != N; ++i)
70  indices[i] = i;
71  return indices;
72  }
73 
74  template<class ...Args>
75  DataList(Args &&...args): data(std::forward<Args>(args)...) {}
76 
77  template<class t_Comparator, class t_HardComparator, class t_Printer>
79  ValueType, t_Comparator, t_HardComparator, t_Printer
80  > const &other)
81  :DataList(other.data)
82  {}
83 
84  void push(ValueType const &value) { data.push_back(value); }
85  void push(ValueType &&value) { data.push_back(value); }
86 
87  [[nodiscard]]
88  bool compare(DataList<
89  ValueType, Comparator, HardComparator, Printer
90  > const &other) const;
91  [[nodiscard]]
92  bool operator==(DataList<
93  ValueType, Comparator, HardComparator, Printer
94  > const &other) const
95  {
96  return compare(other);
97  }
98 
99  [[nodiscard]]
101  DataList<
102  ValueType, Comparator, HardComparator, Printer
103  > const &other
104  ) const;
105 
106  [[nodiscard]]
108  DataList<
109  ValueType, Comparator, HardComparator, Printer
110  > const &other
111  ) const;
112 
113 private:
114 
115  std::vector<ValueType> data;
116 };
117 
118 template<class ValueType, class Comparator, class HardComparator, class Printer>
119 struct DataDiff {
122 
123  bool empty() const { return lhs.empty() && rhs.empty(); }
124  size_t size() const { return lhs.size() + rhs.size(); }
125 };
126 
127 template<class ValueType, class Comparator, class HardComparator, class Printer>
128 std::ostream &operator<<(
129  std::ostream &out,
131  )
132 {
133  out << "Diff of size " << diff.size() << '\n';
134 
135  out << "LHS : \n";
136  auto printer = Printer();
137  for (const auto &data : diff.lhs) {
138  printer(out, data);
139  out << '\n';
140  }
141 
142  out << "RHS : \n";
143  for (const auto &data : diff.rhs) {
144  printer(out, data);
145  out << '\n';
146  }
147  out.flush();
148 
149  return out;
150 }
151 
152 template<class ValueType, class Comparator, class HardComparator, class Printer>
155  ) const
156 {
157  if (size() != other.size())
158  return false;
159  std::vector<size_t> indices = range(size());
160 
161  auto comparator = Comparator();
162  auto iter = begin();
163  while (!indices.empty()) {
164  bool matched = false;
165  for (size_t k = 0; k != indices.size(); ++k) {
166  if (comparator(*iter, other[indices[k]])) {
167  matched = true;
168  indices.erase(indices.begin() + k);
169  break;
170  }
171  }
172  if (!matched)
173  return false;
174  ++iter;
175  }
176  return true;
177 }
178 
179 template<class ValueType, class Comparator, class HardComparator, class Printer>
183  ) const
184 {
185  std::vector<size_t> indicesLhs = range(size());
186  std::vector<size_t> indicesRhs = range(other.size());
188  auto comparator = Comparator();
189 
190  while (!indicesLhs.empty() && !indicesRhs.empty()) {
191  const size_t i = indicesLhs[0];
192  bool matched = false;
193  for (size_t k = 0; k != indicesRhs.size(); ++k) {
194  const size_t j = indicesRhs[k];
195  if (comparator(data[i], other[j])) {
196  matched = true;
197  indicesRhs.erase(indicesRhs.begin() + k);
198  break;
199  }
200  }
201  if (!matched)
202  diff.lhs.push(data[i]);
203  indicesLhs.erase(indicesLhs.begin());
204  }
205  if (!indicesLhs.empty()) {
206  for (size_t i : indicesLhs)
207  diff.lhs.push(data[i]);
208  }
209  if (!indicesRhs.empty()) {
210  for (size_t i : indicesRhs)
211  diff.rhs.push(other[i]);
212  }
213 
214  return diff;
215 }
216 
217 template<class ValueType, class Comparator, class HardComparator, class Printer>
221  ) const
222 {
223  auto diff = getDiff(other);
224  if (diff.lhs.empty() or diff.rhs.empty())
225  return diff;
226 
227  using HardList = typename doc::DataList<
228  ValueType, HardComparator, HardComparator, Printer
229  >;
230  return HardList(std::move(diff.lhs)).getDiff(HardList(std::move(diff.rhs)));
231 }
232 
233 }
std::ostream & operator<<(std::ostream &fout, csl::Type type)
Definition: datalist.h:53
Definition: checkpoint.h:38
Definition: datalist.h:46
bool operator==(const Expr &a, const Expr &b)
Definition: datalist.h:61
Definition: datalist.h:41
Definition: datalist.h:34