Open
Graph Drawing
Framework

 v. 2023.09 (Elderberry)
 

SubsetEnumerator.h
Go to the documentation of this file.
1 
32 #pragma once
33 
34 #include <ogdf/basic/List.h>
35 
36 namespace ogdf {
37 
39 
87 template<typename T>
89 protected:
90  bool m_valid;
91  int m_maxCard;
94 
95  void initSubset(int card) {
96  if (card >= 0 && card <= m_subset.size()) {
97  m_index.init(card);
98  for (int i = 0; i < card; ++i) {
99  m_index[i] = i;
100  }
101  m_valid = true;
102  }
103  }
104 
105 public:
111  template<typename ContainerType>
112  explicit SubsetEnumerator(const ContainerType& set)
113  : m_valid(false), m_maxCard(-1), m_subset(set.size()) {
114  for (auto x : set) {
115  m_subset.push(x);
116  }
117  }
118 
120  void begin(int low, int high) {
121  if (high >= low) {
122  m_maxCard = high;
123  m_maxCard = min(m_maxCard, m_subset.size());
124  initSubset(low);
125  } else {
126  m_valid = false;
127  }
128  }
129 
131  void begin(int card) { begin(card, card); }
132 
134  void begin() { begin(0, m_subset.size()); }
135 
137  int size() const { return m_index.size(); }
138 
141  int numberOfMembersAndNonmembers() const { return m_subset.size(); }
142 
145  bool valid() const { return m_valid; }
146 
148  bool hasMember(const T& element) const {
149  for (int index : m_index) {
150  if (element == m_subset[index]) {
151  return true;
152  }
153  }
154  return false;
155  }
156 
158  T operator[](int i) const {
159  OGDF_ASSERT(i >= 0);
160  OGDF_ASSERT(i < m_index.size());
161  return m_subset[m_index[i]];
162  }
163 
165  void next() {
166  if (m_valid) {
167  const int t = m_index.size();
168  if (t == 0) { // last (empty) subset has been found
169  if (t < m_maxCard) {
170  initSubset(t + 1);
171  } else {
172  m_valid = false;
173  }
174  return;
175  }
176  const int n = m_subset.size();
177  int i;
178  for (i = t - 1; m_index[i] == i + n - t; --i) {
179  if (i == 0) { // the last subset of this cardinality has been found
180  if (t < m_maxCard) {
181  initSubset(t + 1);
182  } else {
183  m_valid = false;
184  }
185  return;
186  }
187  }
188  for (++m_index[i]; i < t - 1; ++i) {
189  m_index[i + 1] = m_index[i] + 1;
190  }
191  }
192  }
193 
195  void forEachMember(std::function<void(const T&)> func) const {
196  for (int index : m_index) {
197  func(m_subset[index]);
198  }
199  }
200 
202  void list(List<T>& subset) const {
203  forEachMember([&](const T& member) { subset.pushBack(member); });
204  }
205 
207  void array(Array<T>& array) const {
208  array.init(m_index.size());
209  for (int i = 0; i < m_index.size(); ++i) {
210  array[i] = m_subset[m_index[i]];
211  }
212  }
213 
215  void forEachMemberAndNonmember(std::function<void(const T&)> funcIn,
216  std::function<void(const T&)> funcNotIn) const {
217  for (int i = 0, j = 0; i < m_subset.size(); ++i) {
218  if (j < m_index.size() && m_index[j] == i) {
219  funcIn(m_subset[i]);
220  ++j;
221  } else {
222  funcNotIn(m_subset[i]);
223  }
224  }
225  }
226 
228  template<typename ContainerType>
229  void getSubsetAndComplement(ContainerType& subset, ContainerType& complement,
230  std::function<void(ContainerType&, T)> func) const {
231  forEachMemberAndNonmember([&](const T& member) { func(subset, member); },
232  [&](const T& nonmember) { func(complement, nonmember); });
233  }
234 
236  void list(List<T>& subset, List<T>& complement) const {
237  getSubsetAndComplement<List<T>>(subset, complement,
238  [](List<T>& lc, T element) { lc.pushBack(element); });
239  }
240 
242  bool testForAll(std::function<bool(const T&)> predicate) const {
243  for (int index : m_index) {
244  if (!predicate(m_subset[index])) {
245  return false;
246  }
247  }
248  return true;
249  }
250 
252  void print(std::ostream& os, string delim = " ") const {
253  if (valid()) {
254  if (size() > 0) {
255  os << m_subset[m_index[0]];
256  for (int i = 1; i < size(); ++i) {
257  os << delim << m_subset[m_index[i]];
258  }
259  }
260  } else {
261  os << "<<invalid subset>>";
262  }
263  }
264 };
265 
266 template<class T>
267 std::ostream& operator<<(std::ostream& os, const SubsetEnumerator<T>& subset) {
268  subset.print(os);
269  return os;
270 }
271 
272 }
ogdf::ArrayBuffer< T >
ogdf
The namespace for all OGDF objects.
Definition: AugmentationModule.h:36
ogdf::SubsetEnumerator::size
int size() const
Returns the cardinality of the subset.
Definition: SubsetEnumerator.h:137
ogdf::SubsetEnumerator
Enumerator for k-subsets of a given type.
Definition: SubsetEnumerator.h:88
ogdf::SubsetEnumerator::array
void array(Array< T > &array) const
Obtains an array of the subset members.
Definition: SubsetEnumerator.h:207
OGDF_ASSERT
#define OGDF_ASSERT(expr)
Assert condition expr. See doc/build.md for more information.
Definition: basic.h:54
ogdf::SubsetEnumerator::begin
void begin(int card)
Initializes the SubsetEnumerator to enumerate subsets of given cardinality.
Definition: SubsetEnumerator.h:131
ogdf::SubsetEnumerator::begin
void begin(int low, int high)
Initializes the SubsetEnumerator to enumerate subsets of cardinalities from low to high.
Definition: SubsetEnumerator.h:120
ogdf::SubsetEnumerator::valid
bool valid() const
Checks if the current subset is valid. If not, the subset is either not initialized or all subsets ha...
Definition: SubsetEnumerator.h:145
ogdf::SubsetEnumerator::m_index
Array< int > m_index
Definition: SubsetEnumerator.h:93
ogdf::Array::init
void init()
Reinitializes the array to an array with empty index set.
Definition: Array.h:367
ogdf::SubsetEnumerator::print
void print(std::ostream &os, string delim=" ") const
Prints subset to output stream os using delimiter delim.
Definition: SubsetEnumerator.h:252
ogdf::SubsetEnumerator::SubsetEnumerator
SubsetEnumerator(const ContainerType &set)
Constructor.
Definition: SubsetEnumerator.h:112
ogdf::SubsetEnumerator::begin
void begin()
Initializes the SubsetEnumerator to enumerate all subsets.
Definition: SubsetEnumerator.h:134
ogdf::SubsetEnumerator::hasMember
bool hasMember(const T &element) const
Checks in O(subset cardinality) whether element is a member of the subset.
Definition: SubsetEnumerator.h:148
ogdf::SubsetEnumerator::list
void list(List< T > &subset) const
Obtains (appends) a list of the subset members.
Definition: SubsetEnumerator.h:202
ogdf::SubsetEnumerator::m_subset
ArrayBuffer< T > m_subset
Definition: SubsetEnumerator.h:92
ogdf::Array< int >
ogdf::ArrayBuffer::size
INDEX size() const
Returns number of elements in the buffer.
Definition: ArrayBuffer.h:236
ogdf::SubsetEnumerator::getSubsetAndComplement
void getSubsetAndComplement(ContainerType &subset, ContainerType &complement, std::function< void(ContainerType &, T)> func) const
Obtains a container of the subset members and a container of the other elements of the set.
Definition: SubsetEnumerator.h:229
ogdf::ArrayBuffer::push
void push(E e)
Puts a new element in the buffer.
Definition: ArrayBuffer.h:209
ogdf::operator<<
std::ostream & operator<<(std::ostream &os, const ogdf::Array< E, INDEX > &a)
Prints array a to output stream os.
Definition: Array.h:978
ogdf::SubsetEnumerator::list
void list(List< T > &subset, List< T > &complement) const
Obtains (appends) a list of the subset members and a list of the other elements of the set.
Definition: SubsetEnumerator.h:236
ogdf::List
Doubly linked lists (maintaining the length of the list).
Definition: List.h:42
ogdf::SubsetEnumerator::initSubset
void initSubset(int card)
Definition: SubsetEnumerator.h:95
ogdf::SubsetEnumerator::forEachMemberAndNonmember
void forEachMemberAndNonmember(std::function< void(const T &)> funcIn, std::function< void(const T &)> funcNotIn) const
Calls funcIn for each subset member and funcNotIn for each other element of the set.
Definition: SubsetEnumerator.h:215
ogdf::SubsetEnumerator::operator[]
T operator[](int i) const
Gets a member of subset by index (starting from 0).
Definition: SubsetEnumerator.h:158
List.h
Declaration of doubly linked lists and iterators.
ogdf::SubsetEnumerator::next
void next()
Obtains the next subset if possible. The result should be checked using the valid() method.
Definition: SubsetEnumerator.h:165
ogdf::SubsetEnumerator::forEachMember
void forEachMember(std::function< void(const T &)> func) const
Calls func for each member in the subset.
Definition: SubsetEnumerator.h:195
ogdf::Array::size
INDEX size() const
Returns the size (number of elements) of the array.
Definition: Array.h:297
ogdf::SubsetEnumerator::testForAll
bool testForAll(std::function< bool(const T &)> predicate) const
Tests predicate for all subset members.
Definition: SubsetEnumerator.h:242
ogdf::SubsetEnumerator::m_valid
bool m_valid
Definition: SubsetEnumerator.h:90
ogdf::List::pushBack
iterator pushBack(const E &x)
Adds element x at the end of the list.
Definition: List.h:1537
ogdf::SubsetEnumerator::numberOfMembersAndNonmembers
int numberOfMembersAndNonmembers() const
Returns the cardinality of the (super-)set. This is the maximum size that can be used for a subset.
Definition: SubsetEnumerator.h:141
ogdf::SubsetEnumerator::m_maxCard
int m_maxCard
Definition: SubsetEnumerator.h:91