aGrUM
0.20.3
a C++ library for (probabilistic) graphical models
scheduleCombinationBasic_tpl.h
Go to the documentation of this file.
1
/**
2
*
3
* Copyright (c) 2005-2021 by Pierre-Henri WUILLEMIN(@LIP6) & Christophe GONZALES(@AMU)
4
* info_at_agrum_dot_org
5
*
6
* This library is free software: you can redistribute it and/or modify
7
* it under the terms of the GNU Lesser General Public License as published by
8
* the Free Software Foundation, either version 3 of the License, or
9
* (at your option) any later version.
10
*
11
* This library is distributed in the hope that it will be useful,
12
* but WITHOUT ANY WARRANTY; without even the implied warranty of
13
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14
* GNU Lesser General Public License for more details.
15
*
16
* You should have received a copy of the GNU Lesser General Public License
17
* along with this library. If not, see <http://www.gnu.org/licenses/>.
18
*
19
*/
20
21
22
/** @file
23
* @brief A class to combine efficiently several ScheduleMultiDims
24
*
25
* @author Christophe GONZALES(@AMU) and Pierre-Henri WUILLEMIN(@LIP6)
26
*/
27
28
#
ifndef
DOXYGEN_SHOULD_SKIP_THIS
29
30
#
include
<
agrum
/
agrum
.
h
>
31
#
include
<
limits
>
32
33
#
include
<
agrum
/
tools
/
graphicalModels
/
inference
/
scheduler
/
scheduleCombinationBasic
.
h
>
34
35
namespace
gum
{
36
37
/// constructor
38
template
<
typename
GUM_SCALAR >
39
ScheduleCombinationBasic< GUM_SCALAR >::ScheduleCombinationBasic(
40
MultiDimImplementation
<
GUM_SCALAR
>* (*
combine
)(
41
const
MultiDimImplementation
<
GUM_SCALAR
>&,
42
const
MultiDimImplementation
<
GUM_SCALAR
>&)) :
43
ScheduleCombination
<
GUM_SCALAR
>(),
44
combine_
(
combine
) {
45
/// for debugging purposes
46
GUM_CONSTRUCTOR
(
ScheduleCombinationBasic
);
47
}
48
49
/// copy constructor
50
template
<
typename
GUM_SCALAR
>
51
ScheduleCombinationBasic
<
GUM_SCALAR
>::
ScheduleCombinationBasic
(
52
const
ScheduleCombinationBasic
<
GUM_SCALAR
>&
from
) :
53
ScheduleCombination
<
GUM_SCALAR
>(
from
),
54
combine_
(
from
.
combine_
) {
55
/// for debugging purposes
56
GUM_CONS_CPY
(
ScheduleCombinationBasic
);
57
}
58
59
/// destructor
60
template
<
typename
GUM_SCALAR
>
61
ScheduleCombinationBasic
<
GUM_SCALAR
>::~
ScheduleCombinationBasic
() {
62
/// for debugging purposes
63
GUM_DESTRUCTOR
(
ScheduleCombinationBasic
);
64
}
65
66
/// virtual constructor
67
template
<
typename
GUM_SCALAR
>
68
ScheduleCombinationBasic
<
GUM_SCALAR
>*
69
ScheduleCombinationBasic
<
GUM_SCALAR
>::
newFactory
()
const
{
70
return
new
ScheduleCombinationBasic
<
GUM_SCALAR
>(*
this
);
71
}
72
73
/// changes the function used for combining two MultiDimImplementations
74
template
<
typename
GUM_SCALAR
>
75
void
ScheduleCombinationBasic
<
GUM_SCALAR
>::
setCombineFunction
(
76
MultiDimImplementation
<
GUM_SCALAR
>* (*
combine
)(
77
const
MultiDimImplementation
<
GUM_SCALAR
>&,
78
const
MultiDimImplementation
<
GUM_SCALAR
>&)) {
79
combine_
=
combine
;
80
}
81
82
/// returns the combination function currently used by the combinator
83
template
<
typename
GUM_SCALAR
>
84
MultiDimImplementation
<
GUM_SCALAR
>* (
85
*
ScheduleCombinationBasic
<
GUM_SCALAR
>::
combineFunction
())(
86
const
MultiDimImplementation
<
GUM_SCALAR
>&,
87
const
MultiDimImplementation
<
GUM_SCALAR
>&) {
88
return
combine_
;
89
}
90
91
/// returns the domain size of the Cartesian product of the union of all the
92
/// variables in seq1 and seq2
93
template
<
typename
GUM_SCALAR
>
94
Size
ScheduleCombinationBasic
<
GUM_SCALAR
>::
combinedSize_
(
95
const
Sequence
<
const
DiscreteVariable
* >&
seq1
,
96
const
Sequence
<
const
DiscreteVariable
* >&
seq2
)
const
{
97
if
(
seq1
.
empty
() &&
seq2
.
empty
())
return
0;
98
99
Size
size
= 1;
100
101
for
(
const
auto
var
:
seq1
)
102
size
*=
var
->
domainSize
();
103
104
for
(
const
auto
var
:
seq2
)
105
if
(!
seq1
.
exists
(
var
))
size
*=
var
->
domainSize
();
106
107
return
size
;
108
}
109
110
// adds operations to an already created schedule
111
template
<
typename
GUM_SCALAR
>
112
ScheduleMultiDim
<
GUM_SCALAR
>
ScheduleCombinationBasic
<
GUM_SCALAR
>::
combine
(
113
const
Set
<
const
ScheduleMultiDim
<
GUM_SCALAR
>* >&
set
,
114
Schedule
<
GUM_SCALAR
>&
schedule
) {
115
// check if the set passed in argument is empty. If so, raise an exception
116
if
(
set
.
size
() < 2) {
117
GUM_ERROR
(
InvalidArgumentsNumber
,
118
"the set passed to a ScheduleCombinationBasic"
119
" should at least contain two elements"
);
120
}
121
122
// create a vector with all the tables to combine
123
std
::
vector
<
const
ScheduleMultiDim
<
GUM_SCALAR
>* >
tables
(
set
.
size
());
124
125
{
126
Idx
i
= 0;
127
128
for
(
const
auto
sched
:
set
) {
129
tables
[
i
] =
sched
;
130
i
+= 1;
131
}
132
}
133
134
// create a vector indicating wether the elements in tables are freshly
135
// created ScheduleMultiDim<GUM_SCALAR>* due to the combination of some
136
// ScheduleMultiDims or if they were added by the user into the
137
// combination container
138
std
::
vector
<
bool
>
is_t_new
(
tables
.
size
(),
false
);
139
140
// for each pair of tables (i,j), compute the size of the table that would
141
// result from the addition of tables i and j and store the result into a
142
// priorityQueue
143
std
::
pair
<
Idx
,
Idx
>
pair
;
144
145
PriorityQueue
<
std
::
pair
<
Idx
,
Idx
>,
Size
>
queue
;
146
147
for
(
Idx
i
= 0;
i
<
tables
.
size
(); ++
i
) {
148
pair
.
first
=
i
;
149
const
Sequence
<
const
DiscreteVariable
* >&
seq1
=
tables
[
i
]->
variablesSequence
();
150
151
for
(
Idx
j
=
i
+ 1;
j
<
tables
.
size
(); ++
j
) {
152
pair
.
second
=
j
;
153
queue
.
insert
(
pair
,
combinedSize_
(
seq1
,
tables
[
j
]->
variablesSequence
()));
154
}
155
}
156
157
// now parse the priority queue: the top element (i,j) gives the combination
158
// to perform. When the result R has been computed, substitute i by R,
159
// remove
160
// table j and recompute all the priorities of all the pairs (R,k) still
161
// available.
162
// Timer timer;
163
for
(
Idx
k
= 1;
k
<
tables
.
size
(); ++
k
) {
164
// get the combination to perform and do it
165
pair
=
queue
.
pop
();
166
Idx
ti
=
pair
.
first
;
167
Idx
tj
=
pair
.
second
;
168
169
// create the combination that will be performed later on and put it into
170
// the schedule
171
ScheduleCombine
<
GUM_SCALAR
>
comb
(*(
tables
[
ti
]), *(
tables
[
tj
]),
combine_
);
172
NodeId
comb_id
=
schedule
.
insert
(
comb
);
173
174
// substitute tables[pair.first] by the result and delete the temporary
175
// multidim tables
176
177
if
(
tables
[
ti
] &&
is_t_new
[
ti
]) {
178
ScheduleDeleteMultiDim
<
GUM_SCALAR
>
del
(*(
tables
[
ti
]));
179
NodeId
del_id
=
schedule
.
insert
(
del
);
180
const
NodeSet
&
set_i
=
schedule
.
operationsInvolving
(*(
tables
[
ti
]));
181
schedule
.
forceAfter
(
del_id
,
set_i
);
182
}
183
184
if
(
tables
[
tj
] &&
is_t_new
[
tj
]) {
185
ScheduleDeleteMultiDim
<
GUM_SCALAR
>
del
(*(
tables
[
tj
]));
186
NodeId
del_id
=
schedule
.
insert
(
del
);
187
const
NodeSet
&
set_j
=
schedule
.
operationsInvolving
(*(
tables
[
tj
]));
188
schedule
.
forceAfter
(
del_id
,
set_j
);
189
}
190
191
tables
[
ti
] = &(
static_cast
<
const
ScheduleCombine
<
GUM_SCALAR
>& >
192
193
(
schedule
.
operation
(
comb_id
))
194
.
result
());
195
is_t_new
[
ti
] =
true
;
196
tables
[
tj
] = 0;
197
198
// remove all the pairs involving tj in the priority queue
199
200
for
(
Idx
ind
= 0;
ind
<
tj
; ++
ind
) {
201
if
(
tables
[
ind
]) {
202
pair
.
first
=
ind
;
203
queue
.
erase
(
pair
);
204
}
205
}
206
207
pair
.
first
=
tj
;
208
209
for
(
Idx
ind
=
tj
+ 1;
ind
<
tables
.
size
(); ++
ind
) {
210
if
(
tables
[
ind
]) {
211
pair
.
second
=
ind
;
212
queue
.
erase
(
pair
);
213
}
214
}
215
216
// update the "combinated" size of all the pairs involving "result"
217
{
218
const
Sequence
<
const
DiscreteVariable
* >&
seq1
=
tables
[
ti
]->
variablesSequence
();
219
pair
.
second
=
ti
;
220
Size
newsize
;
221
222
for
(
Idx
ind
= 0;
ind
<
ti
; ++
ind
) {
223
if
(
tables
[
ind
]) {
224
pair
.
first
=
ind
;
225
newsize
=
combinedSize_
(
seq1
,
tables
[
ind
]->
variablesSequence
());
226
queue
.
setPriority
(
pair
,
newsize
);
227
}
228
}
229
230
pair
.
first
=
ti
;
231
232
for
(
Idx
ind
=
ti
+ 1;
ind
<
tables
.
size
(); ++
ind
) {
233
if
(
tables
[
ind
]) {
234
pair
.
second
=
ind
;
235
newsize
=
combinedSize_
(
seq1
,
tables
[
ind
]->
variablesSequence
());
236
queue
.
setPriority
(
pair
,
newsize
);
237
}
238
}
239
}
240
}
241
242
// here, there remains only one nonzero pointer in tables:
243
// the result of our combination
244
Idx
k
= 0;
245
246
while
(!
tables
[
k
])
247
++
k
;
248
249
return
*(
tables
[
k
]);
250
}
251
252
// adds operations to an already created schedule
253
template
<
typename
GUM_SCALAR
>
254
INLINE
ScheduleMultiDim
<
GUM_SCALAR
>
ScheduleCombinationBasic
<
GUM_SCALAR
>::
combine
(
255
const
Set
<
const
MultiDimImplementation
<
GUM_SCALAR
>* >&
set
,
256
Schedule
<
GUM_SCALAR
>&
schedule
) {
257
return
ScheduleCombination
<
GUM_SCALAR
>::
combine
(
set
,
schedule
);
258
}
259
260
// adds operations to an already created schedule
261
template
<
typename
GUM_SCALAR
>
262
template
<
template
<
typename
>
class
TABLE
>
263
INLINE
ScheduleMultiDim
<
GUM_SCALAR
>
264
ScheduleCombinationBasic
<
GUM_SCALAR
>::
combine
(
const
Set
<
const
TABLE
<
GUM_SCALAR
>* >&
set
,
265
Schedule
<
GUM_SCALAR
>&
schedule
) {
266
return
ScheduleCombination
<
GUM_SCALAR
>::
combine
(
set
,
schedule
);
267
}
268
269
/// returns the result of the combination
270
template
<
typename
GUM_SCALAR
>
271
float
ScheduleCombinationBasic
<
GUM_SCALAR
>::
nbOperations
(
272
const
Set
<
const
ScheduleMultiDim
<
GUM_SCALAR
>* >&
set
,
273
const
Schedule
<
GUM_SCALAR
>&
schedule
) {
274
// check if the set passed in argument is empty.
275
if
(
set
.
size
() < 2)
return
0.0f;
276
277
float
result
= 0.0f;
278
279
// create a vector with all the tables to combine
280
std
::
vector
<
const
Sequence
<
const
DiscreteVariable
* >* >
tables
(
set
.
size
());
281
282
{
283
Idx
i
= 0;
284
285
for
(
const
auto
sched
:
set
) {
286
tables
[
i
] = &(
sched
->
variablesSequence
());
287
i
+= 1;
288
}
289
}
290
291
// create a vector indicating wether the elements in tables are freshly
292
// created Sequence<const DiscreteVariable *>* due to the combination of
293
// some
294
// ScheduleMultiDims or if they were added by the user into the combination
295
// container
296
std
::
vector
<
bool
>
is_t_new
(
tables
.
size
(),
false
);
297
298
// for each pair of tables (i,j), compute the size of the table that would
299
// result from the addition of tables i and j and store the result into a
300
// priorityQueue
301
std
::
pair
<
Idx
,
Idx
>
pair
;
302
PriorityQueue
<
std
::
pair
<
Idx
,
Idx
>,
Size
>
queue
;
303
304
for
(
Idx
i
= 0;
i
<
tables
.
size
(); ++
i
) {
305
pair
.
first
=
i
;
306
307
for
(
Idx
j
=
i
+ 1;
j
<
tables
.
size
(); ++
j
) {
308
pair
.
second
=
j
;
309
queue
.
insert
(
pair
,
combinedSize_
(*(
tables
[
i
]), *(
tables
[
j
])));
310
}
311
}
312
313
// now parse the priority queue: the top element (i,j) gives the combination
314
// to perform. When the result R has been computed, substitute i by R,
315
// remove
316
// table j and recompute all the priorities of all the pairs (R,k) still
317
// available.
318
for
(
Idx
k
= 1;
k
<
tables
.
size
(); ++
k
) {
319
// get the combination to perform and do it
320
pair
=
queue
.
pop
();
321
Idx
ti
=
pair
.
first
;
322
Idx
tj
=
pair
.
second
;
323
324
// compute the result
325
Sequence
<
const
DiscreteVariable
* >*
new_seq
=
new
Sequence
<
const
DiscreteVariable
* >;
326
const
Sequence
<
const
DiscreteVariable
* >&
seq1
= *(
tables
[
ti
]);
327
const
Sequence
<
const
DiscreteVariable
* >&
seq2
= *(
tables
[
tj
]);
328
329
Size
new_size
= 1;
330
331
for
(
const
auto
var
:
seq1
) {
332
new_size
*=
var
->
domainSize
();
333
new_seq
->
insert
(
var
);
334
}
335
336
for
(
const
auto
var
:
seq2
)
337
if
(!
seq1
.
exists
(
var
)) {
338
new_size
*=
var
->
domainSize
();
339
new_seq
->
insert
(
var
);
340
}
341
342
result
+=
new_size
;
343
344
// substitute tables[pair.first] by the result
345
346
if
(
tables
[
ti
] &&
is_t_new
[
ti
])
delete
tables
[
ti
];
347
348
if
(
tables
[
tj
] &&
is_t_new
[
tj
])
delete
tables
[
tj
];
349
350
tables
[
ti
] =
new_seq
;
351
352
is_t_new
[
ti
] =
true
;
353
354
tables
[
tj
] = 0;
355
356
// remove all the pairs involving tj in the priority queue
357
for
(
Idx
ind
= 0;
ind
<
tj
; ++
ind
) {
358
if
(
tables
[
ind
]) {
359
pair
.
first
=
ind
;
360
queue
.
erase
(
pair
);
361
}
362
}
363
364
pair
.
first
=
tj
;
365
366
for
(
Idx
ind
=
tj
+ 1;
ind
<
tables
.
size
(); ++
ind
) {
367
if
(
tables
[
ind
]) {
368
pair
.
second
=
ind
;
369
queue
.
erase
(
pair
);
370
}
371
}
372
373
// update the "combined" size of all the pairs involving "new_seq"
374
{
375
pair
.
second
=
ti
;
376
Size
newsize
;
377
378
for
(
Idx
ind
= 0;
ind
<
ti
; ++
ind
) {
379
if
(
tables
[
ind
]) {
380
pair
.
first
=
ind
;
381
newsize
=
combinedSize_
(*
new_seq
, *(
tables
[
ind
]));
382
queue
.
setPriority
(
pair
,
newsize
);
383
}
384
}
385
386
pair
.
first
=
ti
;
387
388
for
(
Idx
ind
=
ti
+ 1;
ind
<
tables
.
size
(); ++
ind
) {
389
if
(
tables
[
ind
]) {
390
pair
.
second
=
ind
;
391
newsize
=
combinedSize_
(*
new_seq
, *(
tables
[
ind
]));
392
queue
.
setPriority
(
pair
,
newsize
);
393
}
394
}
395
}
396
}
397
398
// here, there remains only one nonzero pointer in tables:
399
// the result of our combination
400
Idx
k
= 0;
401
402
while
(!
tables
[
k
])
403
++
k
;
404
405
delete
tables
[
k
];
406
407
return
result
;
408
}
409
410
/// returns the result of the combination
411
template
<
typename
GUM_SCALAR
>
412
INLINE
float
ScheduleCombinationBasic
<
GUM_SCALAR
>::
nbOperations
(
413
const
Set
<
const
MultiDimImplementation
<
GUM_SCALAR
>* >&
set
,
414
const
Schedule
<
GUM_SCALAR
>&
schedule
) {
415
return
ScheduleCombination
<
GUM_SCALAR
>::
nbOperations
(
set
,
schedule
);
416
}
417
418
/// returns the result of the combination
419
template
<
typename
GUM_SCALAR
>
420
template
<
template
<
typename
>
class
TABLE
>
421
INLINE
float
ScheduleCombinationBasic
<
GUM_SCALAR
>::
nbOperations
(
422
const
Set
<
const
TABLE
<
GUM_SCALAR
>* >&
set
,
423
const
Schedule
<
GUM_SCALAR
>&
schedule
) {
424
return
ScheduleCombination
<
GUM_SCALAR
>::
nbOperations
(
set
,
schedule
);
425
}
426
427
/// returns the result of the combination
428
template
<
typename
GUM_SCALAR
>
429
std
::
pair
<
long
,
long
>
ScheduleCombinationBasic
<
GUM_SCALAR
>::
memoryUsage
(
430
const
Set
<
const
ScheduleMultiDim
<
GUM_SCALAR
>* >&
set
,
431
const
Schedule
<
GUM_SCALAR
>&
schedule
) {
432
// check if the set passed in argument is empty.
433
if
(
set
.
size
() < 2)
return
std
::
pair
<
long
,
long
>(0, 0);
434
435
long
max_memory
= 0;
436
long
current_memory
= 0;
437
438
// create a vector with all the tables to combine
439
std
::
vector
<
const
Sequence
<
const
DiscreteVariable
* >* >
tables
(
set
.
size
());
440
std
::
vector
<
Size
>
table_size
(
set
.
size
());
441
442
{
443
Idx
i
= 0;
444
445
for
(
const
auto
tab
:
set
) {
446
tables
[
i
] = &(
tab
->
variablesSequence
());
447
Size
size
= 0;
448
449
for
(
const
auto
var
:
tab
->
variablesSequence
())
450
size
*=
var
->
domainSize
();
451
452
table_size
[
i
] =
size
;
453
i
+= 1;
454
}
455
}
456
457
// create a vector indicating wether the elements in tables are freshly
458
// created Sequence<const DiscreteVariable *>* due to the combination of
459
// some
460
// ScheduleMultiDims or if they were added by the user into the combination
461
// container
462
std
::
vector
<
bool
>
is_t_new
(
tables
.
size
(),
false
);
463
464
// for each pair of tables (i,j), compute the size of the table that would
465
// result from the addition of tables i and j and store the result into a
466
// priorityQueue
467
std
::
pair
<
Idx
,
Idx
>
pair
;
468
469
PriorityQueue
<
std
::
pair
<
Idx
,
Idx
>,
Size
>
queue
;
470
471
for
(
Idx
i
= 0;
i
<
tables
.
size
(); ++
i
) {
472
pair
.
first
=
i
;
473
474
for
(
Idx
j
=
i
+ 1;
j
<
tables
.
size
(); ++
j
) {
475
pair
.
second
=
j
;
476
queue
.
insert
(
pair
,
combinedSize_
(*(
tables
[
i
]), *(
tables
[
j
])));
477
}
478
}
479
480
// now parse the priority queue: the top element (i,j) gives the combination
481
// to perform. When the result R has been computed, substitute i by R,
482
// remove
483
// table j and recompute all the priorities of all the pairs (R,k) still
484
// available.
485
for
(
Idx
k
= 1;
k
<
tables
.
size
(); ++
k
) {
486
// get the combination to perform and do it
487
pair
=
queue
.
pop
();
488
Idx
ti
=
pair
.
first
;
489
Idx
tj
=
pair
.
second
;
490
491
// compute the result
492
Sequence
<
const
DiscreteVariable
* >*
new_seq
=
new
Sequence
<
const
DiscreteVariable
* >;
493
const
Sequence
<
const
DiscreteVariable
* >&
seq1
= *(
tables
[
ti
]);
494
const
Sequence
<
const
DiscreteVariable
* >&
seq2
= *(
tables
[
tj
]);
495
496
long
new_size
= 1;
497
498
for
(
const
auto
var
:
seq1
) {
499
if
(
std
::
numeric_limits
<
long
>::
max
() / (
long
)
var
->
domainSize
() <
new_size
)
500
GUM_ERROR
(
OutOfBounds
,
"memory usage out of long int range"
)
501
502
new_size
*=
long
(
var
->
domainSize
());
503
new_seq
->
insert
(
var
);
504
}
505
506
for
(
const
auto
var
:
seq2
) {
507
if
(!
seq1
.
exists
(
var
)) {
508
if
(
std
::
numeric_limits
<
long
>::
max
() / (
long
)
var
->
domainSize
() <
new_size
)
509
GUM_ERROR
(
OutOfBounds
,
"memory usage out of long int range"
)
510
511
new_size
*=
long
(
var
->
domainSize
());
512
new_seq
->
insert
(
var
);
513
}
514
}
515
516
if
(
std
::
numeric_limits
<
long
>::
max
() -
current_memory
<
new_size
) {
517
GUM_ERROR
(
OutOfBounds
,
"memory usage out of long int range"
)
518
}
519
520
current_memory
+=
new_size
;
521
522
if
(
current_memory
>
max_memory
) {
max_memory
=
current_memory
; }
523
524
// substitute tables[pair.first] by the result
525
if
(
tables
[
ti
] &&
is_t_new
[
ti
]) {
526
delete
tables
[
ti
];
527
current_memory
-=
long
(
table_size
[
ti
]);
528
}
529
530
if
(
tables
[
tj
] &&
is_t_new
[
tj
]) {
531
delete
tables
[
tj
];
532
current_memory
-=
long
(
table_size
[
tj
]);
533
}
534
535
tables
[
ti
] =
new_seq
;
536
537
table_size
[
ti
] =
new_size
;
538
is_t_new
[
ti
] =
true
;
539
tables
[
tj
] = 0;
540
541
// remove all the pairs involving tj in the priority queue
542
543
for
(
Idx
ind
= 0;
ind
<
tj
; ++
ind
) {
544
if
(
tables
[
ind
]) {
545
pair
.
first
=
ind
;
546
queue
.
erase
(
pair
);
547
}
548
}
549
550
pair
.
first
=
tj
;
551
552
for
(
Idx
ind
=
tj
+ 1;
ind
<
tables
.
size
(); ++
ind
) {
553
if
(
tables
[
ind
]) {
554
pair
.
second
=
ind
;
555
queue
.
erase
(
pair
);
556
}
557
}
558
559
// update the "combined" size of all the pairs involving "new_seq"
560
{
561
pair
.
second
=
ti
;
562
Size
newsize
;
563
564
for
(
Idx
ind
= 0;
ind
<
ti
; ++
ind
) {
565
if
(
tables
[
ind
]) {
566
pair
.
first
=
ind
;
567
newsize
=
combinedSize_
(*
new_seq
, *(
tables
[
ind
]));
568
queue
.
setPriority
(
pair
,
newsize
);
569
}
570
}
571
572
pair
.
first
=
ti
;
573
574
for
(
Idx
ind
=
ti
+ 1;
ind
<
tables
.
size
(); ++
ind
) {
575
if
(
tables
[
ind
]) {
576
pair
.
second
=
ind
;
577
newsize
=
combinedSize_
(*
new_seq
, *(
tables
[
ind
]));
578
queue
.
setPriority
(
pair
,
newsize
);
579
}
580
}
581
}
582
}
583
584
// here, there remains only one nonzero pointer in tables:
585
// the result of our combination
586
Idx
k
= 0;
587
588
while
(!
tables
[
k
])
589
++
k
;
590
591
delete
tables
[
k
];
592
593
return
std
::
pair
<
long
,
long
>(
max_memory
,
current_memory
);
594
}
595
596
/// returns the memory consumption used during the combination
597
template
<
typename
GUM_SCALAR
>
598
INLINE
std
::
pair
<
long
,
long
>
ScheduleCombinationBasic
<
GUM_SCALAR
>::
memoryUsage
(
599
const
Set
<
const
MultiDimImplementation
<
GUM_SCALAR
>* >&
set
,
600
const
Schedule
<
GUM_SCALAR
>&
schedule
) {
601
return
ScheduleCombination
<
GUM_SCALAR
>::
memoryUsage
(
set
,
schedule
);
602
}
603
604
/// returns the memory consumption used during the combination
605
template
<
typename
GUM_SCALAR
>
606
template
<
template
<
typename
>
class
TABLE
>
607
INLINE
std
::
pair
<
long
,
long
>
ScheduleCombinationBasic
<
GUM_SCALAR
>::
memoryUsage
(
608
const
Set
<
const
TABLE
<
GUM_SCALAR
>* >&
set
,
609
const
Schedule
<
GUM_SCALAR
>&
schedule
) {
610
return
ScheduleCombination
<
GUM_SCALAR
>::
memoryUsage
(
set
,
schedule
);
611
}
612
613
}
/* namespace gum */
614
615
#
endif
/* DOXYGEN_SHOULD_SKIP_THIS */
gum::Set::emplace
INLINE void emplace(Args &&... args)
Definition:
set_tpl.h:643