aGrUM 3.1.1
a C++ library for (probabilistic) graphical models
multiDimImplementation_tpl.h
Go to the documentation of this file.
1/****************************************************************************
2 * This file is part of the aGrUM/pyAgrum library. *
3 * *
4 * Copyright (c) 2005-2026 by *
5 * - Pierre-Henri WUILLEMIN(_at_LIP6) *
6 * - Christophe GONZALES(_at_AMU) *
7 * *
8 * The aGrUM/pyAgrum library is free software; you can redistribute it *
9 * and/or modify it under the terms of either : *
10 * *
11 * - the GNU Lesser General Public License as published by *
12 * the Free Software Foundation, either version 3 of the License, *
13 * or (at your option) any later version, *
14 * - the MIT license (MIT), *
15 * - or both in dual license, as here. *
16 * *
17 * (see https://agrum.gitlab.io/articles/dual-licenses-lgplv3mit.html) *
18 * *
19 * This aGrUM/pyAgrum library is distributed in the hope that it will be *
20 * useful, but WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, *
21 * INCLUDING BUT NOT LIMITED TO THE WARRANTIES MERCHANTABILITY or FITNESS *
22 * FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE *
23 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER *
24 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, *
25 * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR *
26 * OTHER DEALINGS IN THE SOFTWARE. *
27 * *
28 * See LICENCES for more details. *
29 * *
30 * SPDX-FileCopyrightText: Copyright 2005-2026 *
31 * - Pierre-Henri WUILLEMIN(_at_LIP6) *
32 * - Christophe GONZALES(_at_AMU) *
33 * SPDX-License-Identifier: LGPL-3.0-or-later OR MIT *
34 * *
35 * Contact : info_at_agrum_dot_org *
36 * homepage : http://agrum.gitlab.io *
37 * gitlab : https://gitlab.com/agrumery/agrum *
38 * *
39 ****************************************************************************/
40
41#pragma once
42
43
50
51// to ease IDE parser
53
54namespace gum {
55
56 // Default constructor
57
58 template < typename GUM_ELEMENT >
66
67 // Copy constructor
68
69 template < typename GUM_ELEMENT >
78
79 // destructor
80
81 template < typename GUM_ELEMENT >
83 GUM_DESTRUCTOR(MultiDimImplementation);
84 // unregister all remaining slave instantiations
85
87 iter != _slaveInstantiations_.endSafe();
88 ++iter)
89 (*iter)->forgetMaster();
90 }
91
92 // add a new var to the sequence of _vars_.
93
94 template < typename GUM_ELEMENT >
96 // check if the variable already belongs to the tuple of variables
97 // of the Instantiation
98 if (_vars_.exists(&v)) {
99 GUM_ERROR(DuplicateElement, "Var " << v.name() << " already exists in this instantiation")
100 }
101 for (const auto& w: _vars_) {
102 if (w->name() == v.name())
104 "A var with name '" << v.name() << "' already exists in this instantiation");
105 }
107 if (_domainSize_ > std::numeric_limits< Size >::max() / v.domainSize()) {
108 GUM_ERROR(OutOfBounds, "adding variable '" << v.name() << "' would overflow domainSize")
109 }
110 _domainSize_ *= v.domainSize();
111
112 _vars_.insert(&v);
113
114 // informs all the slaves that they have to update themselves
115 for (List< Instantiation* >::iterator_safe iter = _slaveInstantiations_.beginSafe();
116 iter != _slaveInstantiations_.endSafe();
117 ++iter) {
118 (*iter)->addWithMaster(this, v);
119 }
120
121 if (isInMultipleChangeMethod_()) _setNotCommitedChange_();
122 }
123
124 // removes a var from the variables of the multidimensional matrix
125
126 template < typename GUM_ELEMENT >
128 // check that the variable does actually belong to the
129 // MultiDimImplementation
130 if (!_vars_.exists(&v)) { GUM_ERROR(NotFound, "Var does not exist in this implementation") }
131
133
134 _vars_.erase(&v);
136 // informs all the slaves that they have to update themselves
138 iter != _slaveInstantiations_.endSafe();
139 ++iter) {
140 (*iter)->eraseWithMaster(this, v);
141 }
142
143 if (isInMultipleChangeMethod_()) _setNotCommitedChange_();
144 }
145
146 // adds a new var to the sequence of _vars_
147 template < typename GUM_ELEMENT >
148 MultiDimImplementation< GUM_ELEMENT >& operator<<(MultiDimImplementation< GUM_ELEMENT >& array,
149 const DiscreteVariable& v) {
150 array.add(v);
151 return array;
152 }
153
154 // add a Instantiation to the list of slave instantiations
155
156 template < typename GUM_ELEMENT >
158 // check that the Instantiation has the same variables as this
159 if (slave.nbrDim() != _vars_.size()) return false;
160
162 iter != _vars_.endSafe();
163 ++iter)
164 if (!slave.contains(*iter)) return false;
165
166 slave.synchronizeWithMaster(this);
167
168 _slaveInstantiations_ += (&slave);
169
170 return true;
171 }
172
173 // removes a Instantiation from the list of slave instantiations
174
175 template < typename GUM_ELEMENT >
177 _slaveInstantiations_.eraseByVal(&slave);
178 return true;
179 }
180
181 template < typename GUM_ELEMENT >
185
186 template < typename GUM_ELEMENT >
190
191 template < typename GUM_ELEMENT >
193 return *(_vars_.atPos(i));
194 }
196 template < typename GUM_ELEMENT >
199 for (const auto& v: _vars_) {
200 if (v->name() == name) return *v;
203 GUM_ERROR(NotFound, "'" << name << "' can not be found in the multidim structure.")
205
206 template < typename GUM_ELEMENT >
208 return _vars_.pos(&v);
209 }
210
211 template < typename GUM_ELEMENT >
213 return _vars_.exists(&v);
214 }
215
216 // returns a const ref to the sequence of DiscreteVariable*
217
218 template < typename GUM_ELEMENT >
223
224 // is this empty ?
225 template < typename GUM_ELEMENT >
227 GUM_ASSERT(!this->isCommitNeeded_());
228 return _vars_.empty();
229 }
235
236 template < typename GUM_ELEMENT >
245
246 template < typename GUM_ELEMENT >
248 if (_internalChangeState_ == _InternalChangeState_::NOT_COMMITTED_CHANGE) {
250 _internalChangeState_ = _InternalChangeState_::NO_CHANGE;
251 }
252
253 _internalChangeMethod_ = _InternalChangeMethod_::DIRECT_CHANGE;
254 }
255
256 template < typename GUM_ELEMENT >
260
261 template < typename GUM_ELEMENT >
263 // empty!
264 }
266 // get the actual change method of *this
267 template < typename GUM_ELEMENT >
271
272 // get the actual state of *this
273 template < typename GUM_ELEMENT >
277
278 // Returns a constant reference over the list of slaved instantiations.
279 template < typename GUM_ELEMENT >
283
284 // get the actual state of *this
285 template < typename GUM_ELEMENT >
289
290 // get the actual state of *this
291 template < typename GUM_ELEMENT >
293 return ((float)1) - (float)realSize() / (float)domainSize();
294 }
296 // returns a basename to be used for default operators
297 template < typename GUM_ELEMENT >
299 static const std::string str = "MultiDimImplementation";
300 return str;
301 }
303 template < typename GUM_ELEMENT >
305 const DiscreteVariable* y) {
306 _vars_.setAtPos(_vars_.pos(x), y);
309 iter != _slaveInstantiations_.endSafe();
310 ++iter) {
311 (**iter).replace(*x, *y);
312 }
313 }
314
315 template < typename GUM_ELEMENT >
317 _vars_.swap(p1, p2);
318 }
319
320 // for friendly displaying the content of the array
321 template < typename GUM_ELEMENT >
322 std::ostream& operator<<(std::ostream& out, const MultiDimImplementation< GUM_ELEMENT >& array) {
323 return out << static_cast< const MultiDimContainer< GUM_ELEMENT >& >(array);
324 }
325
326 // protected access to content_
327 template < typename GUM_ELEMENT >
331
332 // protected access to content_
333 template < typename GUM_ELEMENT >
336 return this;
337 }
338
339 template < typename GUM_ELEMENT >
340 const GUM_ELEMENT* MultiDimImplementation< GUM_ELEMENT >::data() const noexcept {
341 return nullptr;
342 }
343
344 template < typename GUM_ELEMENT >
346 return nullptr;
347 }
348
349} /* namespace gum */
Base class for discrete random variable.
virtual Size domainSize() const =0
Exception : a similar element already exists.
Class for assigning/browsing values to tuples of discrete variables.
void synchronizeWithMaster(const MultiDimAdressable *m)
Force the variables sequence to be the same as the master one.
bool contains(const DiscreteVariable &v) const final
Indicates whether a given variable belongs to the Instantiation.
Idx nbrDim() const final
Returns the number of variables in the Instantiation.
Generic doubly linked lists.
Definition list.h:378
ListIteratorSafe< Val > iterator_safe
Types for STL compliance.
Definition list.h:391
MultiDimContainer()
Default constructor.
<agrum/base/multidim/multiDimImplementation.h>
Idx pos(const DiscreteVariable &v) const override
Returns the index of a variable.
void erase(const DiscreteVariable &v) override
Removes a var from the variables of the multidimensional matrix.
void beginMultipleChanges() override
Call this method before doing important changes in this MultiDimContainer.
Size domainSize() const override
Returns the product of the variables domain size.
bool isInMultipleChangeMethod_() const
Get the actual change method of this MultiDimImplementation.
const Sequence< const DiscreteVariable * > & variablesSequence() const override
Returns a const ref to the sequence of DiscreteVariable*.
void add(const DiscreteVariable &v) override
Adds a new var to the variables of the multidimensional matrix.
float compressionRate() const
The compression ratio of the table (depending on the type of implementation).
const DiscreteVariable & variable(Idx i) const override
Returns a const ref to the ith var.
_InternalChangeState_ _internalChangeState_
The current change state.
MultiDimImplementation()
Default constructor.
bool registerSlave(Instantiation &slave) override
Register i as a slave of this MultiDimAdressable.
bool unregisterSlave(Instantiation &slave) override
Unregister i as a slave of this MultiDimAdressable.
const List< Instantiation * > & slaves_() const
Returns a constant reference over the list of slaved instantiations.
bool empty() const override
Returns true if no var is in *this.
Sequence< const DiscreteVariable * > _vars_
List of discrete variables (dimensions).
const MultiDimImplementation< GUM_ELEMENT > * content() const final
Returns the implementation for this object (may be *this).
const std::string & basename() const
Returns the base class name of this MultiDimImplementation.
void endMultipleChanges() override
Call this method after doing important changes in this MultiDimContainer.
void replace_(const DiscreteVariable *x, const DiscreteVariable *y) override
Replace variable x by y.
void _setNotCommitedChange_()
Change the internalChangeState to NOT_COMMITTED_CHANGE.
bool isCommitNeeded_() const
Get the actual state of *this.
virtual void commitMultipleChanges_()
Synchronize content after MultipleChanges.
_InternalChangeMethod_ _internalChangeMethod_
The current change method.
List< Instantiation * > _slaveInstantiations_
List of instantiations of the tuples (sequences) of variables.
virtual void invert_(Idx p1, Idx p2)
Inverts variables at position p1 and p2.
Idx nbrDim() const override
Returns the number of vars in the multidimensional container.
virtual const GUM_ELEMENT * data() const noexcept
Returns a pointer to the contiguous data buffer, or nullptr if the implementation does not store data...
~MultiDimImplementation() override
Class destructor.
virtual Size realSize() const =0
Returns the real number of parameters used for this table.
bool contains(const DiscreteVariable &v) const override
Returns true if var is in *this.
virtual const std::string & name() const =0
Returns the real name of the multiDim implementation.
Size _domainSize_
This MultiDimImplementation domain size.
Exception : the element we looked for cannot be found.
Exception : out of bound.
The generic class for storing (ordered) sequences of objects.
Definition sequence.h:994
SequenceIteratorSafe< Key > iterator_safe
Types for STL compliance.
Definition sequence.h:1007
const std::string & name() const
returns the name of the variable
#define GUM_ERROR(type, msg)
Definition exceptions.h:76
std::size_t Size
In aGrUM, hashed values are unsigned long int.
Definition types.h:74
Size Idx
Type for indexes.
Definition types.h:79
Headers of gum::MultiDimImplementation.
gum is the global namespace for all aGrUM entities
Definition agrum.h:46
std::ostream & operator<<(std::ostream &stream, const AVLTree< Val, Cmp > &tree)
display the content of a tree