Belle II Software development
cutNodes.cc
1/**************************************************************************
2 * basf2 (Belle II Analysis Software Framework) *
3 * Author: The Belle II Collaboration *
4 * *
5 * See git log for contributors and copyright holders. *
6 * This file is licensed under LGPL-3.0, see LICENSE.md. *
7 **************************************************************************/
8#include <functional>
9#include <iostream>
10#include <cmath>
11#include <boost/python.hpp>
12#include <framework/utilities/CutNodes.h>
13#include <framework/utilities/TestHelpers.h>
14#include <analysis/VariableManager/Manager.h>
15#include <framework/utilities/Conversion.h>
16#include <gtest/gtest.h>
17
18
19using namespace Belle2;
20namespace {
21 namespace py = boost::python;
24 struct MockObjectType {
26 explicit MockObjectType(const double& d) : m_value{d} {}
27 explicit MockObjectType(const int& i) : m_value{i} {}
28 explicit MockObjectType(const bool& b) : m_value{b} {}
29 VarVariant m_value;
30 };
32 std::function<VarVariant(const MockObjectType*)> mockMetaVariable(const std::vector<std::string>& arguments);
33
39 class MockVariableType {
40 public:
42 VarVariant function(const MockObjectType* object) const
43 {
44 return m_function(object);
45 }
46 explicit MockVariableType(const std::string& name) : m_name{name}
47 {
48 m_function = [](const MockObjectType * object) -> VarVariant {
49 if (object != nullptr)
50 {
51 return object->m_value;
52 } else
53 {
54 return std::numeric_limits<double>::quiet_NaN();
55 }
56 };
57 }
58
59 MockVariableType(const std::string& name, std::function<VarVariant(const MockObjectType*)> function) : m_name{name}, m_function{function}
60 {}
61
63 std::string m_name;
64 std::function<VarVariant(const MockObjectType*)> m_function;
65 };
66
71 class MockVariableManager {
72 public:
74 using Object = MockObjectType;
76 using Var = MockVariableType;
79
81 static MockVariableManager& Instance()
82 {
83 static MockVariableManager instance;
84 return instance;
85 }
86
88 Var* getVariable(const std::string& name)
89 {
90 if (name == "mocking_variable") {
91 return &m_mocking_variable;
92 } else {
93 return nullptr;
94 }
95 }
96
97 Var* getVariable(const std::string& functionName, const std::vector<std::string>& functionArguments)
98 {
99 auto function = mockMetaVariable(functionArguments);
100 m_mocking_metavariable = MockVariableType(functionName, function);
101 return &m_mocking_metavariable;
102 }
103
105 Var m_mocking_variable{"mocking_variable"};
106 Var m_mocking_metavariable{""};
107 };
108
109
110// Mock sum metavariable
111 std::function<VarVariant(const MockObjectType*)> mockMetaVariable(const std::vector<std::string>& arguments)
112 {
113 const MockVariableType* var = MockVariableManager::Instance().getVariable(arguments[0]);
114 if (var == nullptr) {
115 throw std::runtime_error("Variable could not be found.");
116 }
117 auto func = [var, arguments](const MockObjectType * object) -> VarVariant {
118 double sum = 0.0;
119 if (std::holds_alternative<int>(var->function(object)))
120 {
121 sum += std::get<int>(var->function(object));
122 } else if (std::holds_alternative<double>(var->function(object)))
123 {
124 sum += std::get<double>(var->function(object));
125 } else
126 {
127 sum += std::get<bool>(var->function(object));
128 }
129 for (size_t i = 1; i < arguments.size(); i++)
130 {
131 sum += Belle2::convertString<double>(arguments[i]);
132 }
133 return sum;
134 };
135 return func;
136 }
137
141 TEST(CutNodesTest, TupleLength)
142 {
143 Py_Initialize();
144 py::tuple tuple = py::tuple();
145 EXPECT_B2FATAL(NodeFactory::compile_boolean_node<MockVariableManager>(tuple));
146 EXPECT_B2FATAL(NodeFactory::compile_expression_node<MockVariableManager>(tuple));
147
148 tuple = py::make_tuple(static_cast<int>(NodeType::UnaryBooleanNode));
149 EXPECT_B2FATAL(NodeFactory::compile_boolean_node<MockVariableManager>(tuple));
150
151 tuple = py::make_tuple(static_cast<int>(NodeType::BinaryBooleanNode));
152 EXPECT_B2FATAL(NodeFactory::compile_boolean_node<MockVariableManager>(tuple));
153
154 tuple = py::make_tuple(static_cast<int>(NodeType::UnaryRelationalNode));
155 EXPECT_B2FATAL(NodeFactory::compile_boolean_node<MockVariableManager>(tuple));
156
157 tuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode));
158 EXPECT_B2FATAL(NodeFactory::compile_boolean_node<MockVariableManager>(tuple));
159
160 tuple = py::make_tuple(static_cast<int>(NodeType::TernaryRelationalNode));
161 EXPECT_B2FATAL(NodeFactory::compile_boolean_node<MockVariableManager>(tuple));
162
163 tuple = py::make_tuple(static_cast<int>(NodeType::UnaryExpressionNode));
164 EXPECT_B2FATAL(NodeFactory::compile_expression_node<MockVariableManager>(tuple));
165
166 tuple = py::make_tuple(static_cast<int>(NodeType::BinaryExpressionNode));
167 EXPECT_B2FATAL(NodeFactory::compile_expression_node<MockVariableManager>(tuple));
168
169 tuple = py::make_tuple(static_cast<int>(NodeType::BooleanNode));
170 EXPECT_B2FATAL(NodeFactory::compile_expression_node<MockVariableManager>(tuple));
171
172 tuple = py::make_tuple(static_cast<int>(NodeType::IntegerNode));
173 EXPECT_B2FATAL(NodeFactory::compile_expression_node<MockVariableManager>(tuple));
174
175 tuple = py::make_tuple(static_cast<int>(NodeType::DoubleNode));
176 EXPECT_B2FATAL(NodeFactory::compile_expression_node<MockVariableManager>(tuple));
177
178 tuple = py::make_tuple(static_cast<int>(NodeType::IdentifierNode));
179 EXPECT_B2FATAL(NodeFactory::compile_expression_node<MockVariableManager>(tuple));
180
181 tuple = py::make_tuple(static_cast<int>(NodeType::FunctionNode));
182 EXPECT_B2FATAL(NodeFactory::compile_expression_node<MockVariableManager>(tuple));
183
184 }
185
186
188 TEST(CutNodesTest, unaryBooleanNode)
189 {
190 Py_Initialize();
191 // Create two BooleanNode tuples with values true and false.
192 const py::tuple booleanTuple_true = py::make_tuple(static_cast<int>(NodeType::BooleanNode), true);
193 const py::tuple booleanTuple_false = py::make_tuple(static_cast<int>(NodeType::BooleanNode), false);
194 // Compile BooleanNodes and check evaluation
195 auto booleanNode_true = NodeFactory::compile_expression_node<MockVariableManager>(booleanTuple_true);
196 auto booleanNode_false = NodeFactory::compile_expression_node<MockVariableManager>(booleanTuple_false);
197 EXPECT_TRUE(std::get<bool>(booleanNode_true->evaluate(nullptr)));
198 EXPECT_FALSE(std::get<bool>(booleanNode_false->evaluate(nullptr)));
199
200 // Create two UnaryRelationalNodes tuples with each BooleanNode tuple as child.
201 const py::tuple uRelTuple_true = py::make_tuple(static_cast<int>(NodeType::UnaryRelationalNode), booleanTuple_true);
202 const py::tuple uRelTuple_false = py::make_tuple(static_cast<int>(NodeType::UnaryRelationalNode), booleanTuple_false);
203 // Compile UnaryExpressionNodes and check evaluation
204 auto uRelNode_true = NodeFactory::compile_boolean_node<MockVariableManager>(uRelTuple_true);
205 auto uRelNode_false = NodeFactory::compile_boolean_node<MockVariableManager>(uRelTuple_false);
206 EXPECT_TRUE(uRelNode_true->check(nullptr));
207 EXPECT_FALSE(uRelNode_false->check(nullptr));
208
209 // Create all tuple combinations of true/false children and flags
210 // True child
211 const py::tuple uBoolTuple_true = py::make_tuple(static_cast<int>(NodeType::UnaryBooleanNode), uRelTuple_true, false, false);
212 const py::tuple uBoolTuple_true_brack = py::make_tuple(static_cast<int>(NodeType::UnaryBooleanNode), uRelTuple_true, false, true);
213 const py::tuple uBoolTuple_true_neg = py::make_tuple(static_cast<int>(NodeType::UnaryBooleanNode), uRelTuple_true, true, false);
214 const py::tuple uBoolTuple_true_neg_brack = py::make_tuple(static_cast<int>(NodeType::UnaryBooleanNode), uRelTuple_true, true,
215 true);
216
217 auto uBoolNode_true = NodeFactory::compile_boolean_node<MockVariableManager>(uBoolTuple_true);
218 EXPECT_TRUE(uBoolNode_true->check(nullptr));
219 EXPECT_EQ(uBoolNode_true->decompile(), "true");
220
221 auto uBoolNode_true_brack = NodeFactory::compile_boolean_node<MockVariableManager>(uBoolTuple_true_brack);
222 EXPECT_TRUE(uBoolNode_true_brack->check(nullptr));
223 EXPECT_EQ(uBoolNode_true_brack->decompile(), "[true]");
224
225 auto uBoolNode_true_neg = NodeFactory::compile_boolean_node<MockVariableManager>(uBoolTuple_true_neg);
226 EXPECT_FALSE(uBoolNode_true_neg->check(nullptr));
227 EXPECT_EQ(uBoolNode_true_neg->decompile(), "not true");
228
229 auto uBoolNode_true_neg_brack = NodeFactory::compile_boolean_node<MockVariableManager>(uBoolTuple_true_neg_brack);
230 EXPECT_FALSE(uBoolNode_true_neg_brack->check(nullptr));
231 EXPECT_EQ(uBoolNode_true_neg_brack->decompile(), "not [true]");
232
233 // False child
234 const py::tuple uBoolTuple_false = py::make_tuple(static_cast<int>(NodeType::UnaryBooleanNode), uRelTuple_false, false, false);
235 const py::tuple uBoolTuple_false_brack = py::make_tuple(static_cast<int>(NodeType::UnaryBooleanNode), uRelTuple_false, false, true);
236 const py::tuple uBoolTuple_false_neg = py::make_tuple(static_cast<int>(NodeType::UnaryBooleanNode), uRelTuple_false, true, false);
237 const py::tuple uBoolTuple_false_neg_brack = py::make_tuple(static_cast<int>(NodeType::UnaryBooleanNode), uRelTuple_false, true,
238 true);
239
240 auto uBoolNode_false = NodeFactory::compile_boolean_node<MockVariableManager>(uBoolTuple_false);
241 EXPECT_FALSE(uBoolNode_false->check(nullptr));
242 EXPECT_EQ(uBoolNode_false->decompile(), "false");
243
244 auto uBoolNode_false_brack = NodeFactory::compile_boolean_node<MockVariableManager>(uBoolTuple_false_brack);
245 EXPECT_FALSE(uBoolNode_false_brack->check(nullptr));
246 EXPECT_EQ(uBoolNode_false_brack->decompile(), "[false]");
247
248 auto uBoolNode_false_neg = NodeFactory::compile_boolean_node<MockVariableManager>(uBoolTuple_false_neg);
249 EXPECT_TRUE(uBoolNode_false_neg->check(nullptr));
250 EXPECT_EQ(uBoolNode_false_neg->decompile(), "not false");
251
252 auto uBoolNode_false_neg_brack = NodeFactory::compile_boolean_node<MockVariableManager>(uBoolTuple_false_neg_brack);
253 EXPECT_TRUE(uBoolNode_false_neg_brack->check(nullptr));
254 EXPECT_EQ(uBoolNode_false_neg_brack->decompile(), "not [false]");
255
256 }
258 TEST(CutNodesTest, binaryBooleanNode)
259 {
260 // Create two BooleanNode tuples with values true and false.
261 const py::tuple booleanTuple_true = py::make_tuple(static_cast<int>(NodeType::BooleanNode), true);
262 const py::tuple booleanTuple_false = py::make_tuple(static_cast<int>(NodeType::BooleanNode), false);
263
264 // Create two UnaryRelationalNodes tuples with each BooleanNode tuple as child.
265 const py::tuple uRelTuple_true = py::make_tuple(static_cast<int>(NodeType::UnaryRelationalNode), booleanTuple_true);
266 const py::tuple uRelTuple_false = py::make_tuple(static_cast<int>(NodeType::UnaryRelationalNode), booleanTuple_false);
267
268 // Create all tuple combinations of children and BooleanOperators
269 const py::tuple binBoolTuple_AND_true_true = py::make_tuple(static_cast<int>(NodeType::BinaryBooleanNode), uRelTuple_true,
270 uRelTuple_true, static_cast<int>(BooleanOperator::AND));
271 const py::tuple binBoolTuple_AND_false_true = py::make_tuple(static_cast<int>(NodeType::BinaryBooleanNode), uRelTuple_false,
272 uRelTuple_true, static_cast<int>(BooleanOperator::AND));
273 const py::tuple binBoolTuple_AND_true_false = py::make_tuple(static_cast<int>(NodeType::BinaryBooleanNode), uRelTuple_true,
274 uRelTuple_false, static_cast<int>(BooleanOperator::AND));
275 const py::tuple binBoolTuple_AND_false_false = py::make_tuple(static_cast<int>(NodeType::BinaryBooleanNode), uRelTuple_false,
276 uRelTuple_false, static_cast<int>(BooleanOperator::AND));
277
278 const py::tuple binBoolTuple_OR_true_true = py::make_tuple(static_cast<int>(NodeType::BinaryBooleanNode), uRelTuple_true,
279 uRelTuple_true, static_cast<int>(BooleanOperator::OR));
280 const py::tuple binBoolTuple_OR_false_true = py::make_tuple(static_cast<int>(NodeType::BinaryBooleanNode), uRelTuple_false,
281 uRelTuple_true, static_cast<int>(BooleanOperator::OR));
282 const py::tuple binBoolTuple_OR_true_false = py::make_tuple(static_cast<int>(NodeType::BinaryBooleanNode), uRelTuple_true,
283 uRelTuple_false, static_cast<int>(BooleanOperator::OR));
284 const py::tuple binBoolTuple_OR_false_false = py::make_tuple(static_cast<int>(NodeType::BinaryBooleanNode), uRelTuple_false,
285 uRelTuple_false, static_cast<int>(BooleanOperator::OR));
286
287
288 auto binBoolNode_AND_true_true = NodeFactory::compile_boolean_node<MockVariableManager>(binBoolTuple_AND_true_true);
289 auto binBoolNode_AND_false_true = NodeFactory::compile_boolean_node<MockVariableManager>(binBoolTuple_AND_false_true);
290 auto binBoolNode_AND_true_false = NodeFactory::compile_boolean_node<MockVariableManager>(binBoolTuple_AND_true_false);
291 auto binBoolNode_AND_false_false = NodeFactory::compile_boolean_node<MockVariableManager>(binBoolTuple_AND_false_false);
292
293 auto binBoolNode_OR_true_true = NodeFactory::compile_boolean_node<MockVariableManager>(binBoolTuple_OR_true_true);
294 auto binBoolNode_OR_false_true = NodeFactory::compile_boolean_node<MockVariableManager>(binBoolTuple_OR_false_true);
295 auto binBoolNode_OR_true_false = NodeFactory::compile_boolean_node<MockVariableManager>(binBoolTuple_OR_true_false);
296 auto binBoolNode_OR_false_false = NodeFactory::compile_boolean_node<MockVariableManager>(binBoolTuple_OR_false_false);
297
298 EXPECT_TRUE(binBoolNode_AND_true_true->check(nullptr));
299 EXPECT_FALSE(binBoolNode_AND_false_true->check(nullptr));
300 EXPECT_FALSE(binBoolNode_AND_true_false->check(nullptr));
301 EXPECT_FALSE(binBoolNode_AND_false_false->check(nullptr));
302
303 EXPECT_TRUE(binBoolNode_OR_true_true->check(nullptr));
304 EXPECT_TRUE(binBoolNode_OR_false_true->check(nullptr));
305 EXPECT_TRUE(binBoolNode_OR_true_false->check(nullptr));
306 EXPECT_FALSE(binBoolNode_OR_false_false->check(nullptr));
307
308 }
310 TEST(CutNodesTest, unaryRelationalNode)
311 {
312 Py_Initialize();
313 // Get main module
314 py::object main = py::import("__main__");
315 py::object pyfloat = main.attr("__builtins__").attr("float");
316
317 // Test IntegerNode
318 py::tuple tuple = py::make_tuple(static_cast<int>(NodeType::IntegerNode), 1337);
319 py::tuple uRelTuple = py::make_tuple(static_cast<int>(NodeType::UnaryRelationalNode), tuple);
320 auto node = NodeFactory::compile_boolean_node<MockVariableManager>(uRelTuple);
321 EXPECT_TRUE(node->check(nullptr));
322
323 tuple = py::make_tuple(static_cast<int>(NodeType::IntegerNode), 0);
324 uRelTuple = py::make_tuple(static_cast<int>(NodeType::UnaryRelationalNode), tuple);
325 node = NodeFactory::compile_boolean_node<MockVariableManager>(uRelTuple);
326 EXPECT_FALSE(node->check(nullptr));
327
328 tuple = py::make_tuple(static_cast<int>(NodeType::IntegerNode), -0);
329 uRelTuple = py::make_tuple(static_cast<int>(NodeType::UnaryRelationalNode), tuple);
330 node = NodeFactory::compile_boolean_node<MockVariableManager>(uRelTuple);
331 EXPECT_FALSE(node->check(nullptr));
332
333 tuple = py::make_tuple(static_cast<int>(NodeType::IntegerNode), 1);
334 uRelTuple = py::make_tuple(static_cast<int>(NodeType::UnaryRelationalNode), tuple);
335 node = NodeFactory::compile_boolean_node<MockVariableManager>(uRelTuple);
336 EXPECT_TRUE(node->check(nullptr));
337
338 tuple = py::make_tuple(static_cast<int>(NodeType::IntegerNode), -1);
339 uRelTuple = py::make_tuple(static_cast<int>(NodeType::UnaryRelationalNode), tuple);
340 node = NodeFactory::compile_boolean_node<MockVariableManager>(uRelTuple);
341 EXPECT_TRUE(node->check(nullptr));
342
343 // Test DoubleNode
344 tuple = py::make_tuple(static_cast<int>(NodeType::DoubleNode), 0.0);
345 uRelTuple = py::make_tuple(static_cast<int>(NodeType::UnaryRelationalNode), tuple);
346 node = NodeFactory::compile_boolean_node<MockVariableManager>(uRelTuple);
347 EXPECT_FALSE(node->check(nullptr));
348
349 tuple = py::make_tuple(static_cast<int>(NodeType::DoubleNode), -0.0);
350 uRelTuple = py::make_tuple(static_cast<int>(NodeType::UnaryRelationalNode), tuple);
351 node = NodeFactory::compile_boolean_node<MockVariableManager>(uRelTuple);
352 EXPECT_FALSE(node->check(nullptr));
353
354 tuple = py::make_tuple(static_cast<int>(NodeType::DoubleNode), 1.0);
355 uRelTuple = py::make_tuple(static_cast<int>(NodeType::UnaryRelationalNode), tuple);
356 node = NodeFactory::compile_boolean_node<MockVariableManager>(uRelTuple);
357 EXPECT_TRUE(node->check(nullptr));
358
359 tuple = py::make_tuple(static_cast<int>(NodeType::DoubleNode), -1.0);
360 uRelTuple = py::make_tuple(static_cast<int>(NodeType::UnaryRelationalNode), tuple);
361 node = NodeFactory::compile_boolean_node<MockVariableManager>(uRelTuple);
362 EXPECT_TRUE(node->check(nullptr));
363
364 tuple = py::make_tuple(static_cast<int>(NodeType::DoubleNode), 1.1);
365 uRelTuple = py::make_tuple(static_cast<int>(NodeType::UnaryRelationalNode), tuple);
366 node = NodeFactory::compile_boolean_node<MockVariableManager>(uRelTuple);
367 EXPECT_TRUE(node->check(nullptr));
368
369 tuple = py::make_tuple(static_cast<int>(NodeType::DoubleNode), -1.1);
370 uRelTuple = py::make_tuple(static_cast<int>(NodeType::UnaryRelationalNode), tuple);
371 node = NodeFactory::compile_boolean_node<MockVariableManager>(uRelTuple);
372 EXPECT_TRUE(node->check(nullptr));
373
374 tuple = py::make_tuple(static_cast<int>(NodeType::DoubleNode), pyfloat("nan"));
375 uRelTuple = py::make_tuple(static_cast<int>(NodeType::UnaryRelationalNode), tuple);
376 node = NodeFactory::compile_boolean_node<MockVariableManager>(uRelTuple);
377 EXPECT_FALSE(node->check(nullptr));
378
379 tuple = py::make_tuple(static_cast<int>(NodeType::DoubleNode), pyfloat("inf"));
380 uRelTuple = py::make_tuple(static_cast<int>(NodeType::UnaryRelationalNode), tuple);
381 node = NodeFactory::compile_boolean_node<MockVariableManager>(uRelTuple);
382 EXPECT_TRUE(node->check(nullptr));
383
384
385 tuple = py::make_tuple(static_cast<int>(NodeType::DoubleNode), pyfloat("-inf"));
386 uRelTuple = py::make_tuple(static_cast<int>(NodeType::UnaryRelationalNode), tuple);
387 node = NodeFactory::compile_boolean_node<MockVariableManager>(uRelTuple);
388 EXPECT_TRUE(node->check(nullptr));
389
390 // Test BooleanNodes
391 tuple = py::make_tuple(static_cast<int>(NodeType::BooleanNode), true);
392 uRelTuple = py::make_tuple(static_cast<int>(NodeType::UnaryRelationalNode), tuple);
393 node = NodeFactory::compile_boolean_node<MockVariableManager>(uRelTuple);
394 EXPECT_TRUE(node->check(nullptr));
395
396 tuple = py::make_tuple(static_cast<int>(NodeType::BooleanNode), false);
397 uRelTuple = py::make_tuple(static_cast<int>(NodeType::UnaryRelationalNode), tuple);
398 node = NodeFactory::compile_boolean_node<MockVariableManager>(uRelTuple);
399 EXPECT_FALSE(node->check(nullptr));
400
401 }
403 TEST(CutNodesTest, binaryRelationalNode)
404 {
405 Py_Initialize();
406 // Get main module
407 py::object main = py::import("__main__");
408 py::object pyfloat = main.attr("__builtins__").attr("float");
409
410 py::tuple child1 = py::make_tuple(static_cast<int>(NodeType::IntegerNode), 1337);
411 py::tuple child2 = py::make_tuple(static_cast<int>(NodeType::IntegerNode), 1337);
412 py::tuple bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
413 static_cast<int>(ComparisonOperator::EQUALEQUAL));
414 auto node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
415 EXPECT_TRUE(node->check(nullptr));
416
417 child1 = py::make_tuple(static_cast<int>(NodeType::DoubleNode), 1337.0);
418 child2 = py::make_tuple(static_cast<int>(NodeType::IntegerNode), 1337);
419 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
420 static_cast<int>(ComparisonOperator::EQUALEQUAL));
421 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
422 EXPECT_TRUE(node->check(nullptr));
423
424 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child2, child1,
425 static_cast<int>(ComparisonOperator::EQUALEQUAL));
426 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
427 EXPECT_TRUE(node->check(nullptr));
428
429 child1 = py::make_tuple(static_cast<int>(NodeType::DoubleNode), 1337.0);
430 child2 = py::make_tuple(static_cast<int>(NodeType::DoubleNode), 1337.0);
431 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
432 static_cast<int>(ComparisonOperator::EQUALEQUAL));
433 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
434 EXPECT_TRUE(node->check(nullptr));
435
436 // NaN with NaN comparisons
437 child1 = py::make_tuple(static_cast<int>(NodeType::DoubleNode), pyfloat("nan"));
438 child2 = py::make_tuple(static_cast<int>(NodeType::DoubleNode), pyfloat("nan"));
439 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
440 static_cast<int>(ComparisonOperator::EQUALEQUAL));
441 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
442 EXPECT_TRUE(node->check(nullptr));
443
444 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
445 static_cast<int>(ComparisonOperator::GREATEREQUAL));
446 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
447 EXPECT_FALSE(node->check(nullptr));
448
449 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
450 static_cast<int>(ComparisonOperator::LESSEQUAL));
451 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
452 EXPECT_FALSE(node->check(nullptr));
453
454 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
455 static_cast<int>(ComparisonOperator::GREATER));
456 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
457 EXPECT_FALSE(node->check(nullptr));
458
459 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
460 static_cast<int>(ComparisonOperator::LESS));
461 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
462 EXPECT_FALSE(node->check(nullptr));
463
464 // NaN != NaN yields true
465 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
466 static_cast<int>(ComparisonOperator::NOTEQUAL));
467 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
468 EXPECT_FALSE(node->check(nullptr));
469
470 // Compare nan with a numerical value
471 child1 = py::make_tuple(static_cast<int>(NodeType::DoubleNode), pyfloat("nan"));
472 child2 = py::make_tuple(static_cast<int>(NodeType::DoubleNode), 0.0);
473 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
474 static_cast<int>(ComparisonOperator::EQUALEQUAL));
475 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
476 EXPECT_FALSE(node->check(nullptr));
477
478 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
479 static_cast<int>(ComparisonOperator::GREATEREQUAL));
480 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
481 EXPECT_FALSE(node->check(nullptr));
482
483 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
484 static_cast<int>(ComparisonOperator::LESSEQUAL));
485 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
486 EXPECT_FALSE(node->check(nullptr));
487
488 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
489 static_cast<int>(ComparisonOperator::GREATER));
490 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
491 EXPECT_FALSE(node->check(nullptr));
492
493 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
494 static_cast<int>(ComparisonOperator::LESS));
495 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
496 EXPECT_FALSE(node->check(nullptr));
497
498 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
499 static_cast<int>(ComparisonOperator::NOTEQUAL));
500 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
501 EXPECT_TRUE(node->check(nullptr));
502
503 // Compare nan with -inf
504 child1 = py::make_tuple(static_cast<int>(NodeType::DoubleNode), pyfloat("nan"));
505 child2 = py::make_tuple(static_cast<int>(NodeType::DoubleNode), pyfloat("inf"));
506 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
507 static_cast<int>(ComparisonOperator::EQUALEQUAL));
508 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
509 EXPECT_FALSE(node->check(nullptr));
510
511 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
512 static_cast<int>(ComparisonOperator::GREATEREQUAL));
513 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
514 EXPECT_FALSE(node->check(nullptr));
515
516 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
517 static_cast<int>(ComparisonOperator::LESSEQUAL));
518 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
519 EXPECT_FALSE(node->check(nullptr));
520
521 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
522 static_cast<int>(ComparisonOperator::GREATER));
523 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
524 EXPECT_FALSE(node->check(nullptr));
525
526 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
527 static_cast<int>(ComparisonOperator::LESS));
528 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
529 EXPECT_FALSE(node->check(nullptr));
530
531 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
532 static_cast<int>(ComparisonOperator::NOTEQUAL));
533 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
534 EXPECT_TRUE(node->check(nullptr));
535
536 // Compare nan with -inf
537 child1 = py::make_tuple(static_cast<int>(NodeType::DoubleNode), pyfloat("nan"));
538 child2 = py::make_tuple(static_cast<int>(NodeType::DoubleNode), pyfloat("-inf"));
539 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
540 static_cast<int>(ComparisonOperator::EQUALEQUAL));
541 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
542 EXPECT_FALSE(node->check(nullptr));
543
544 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
545 static_cast<int>(ComparisonOperator::GREATEREQUAL));
546 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
547 EXPECT_FALSE(node->check(nullptr));
548
549 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
550 static_cast<int>(ComparisonOperator::LESSEQUAL));
551 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
552 EXPECT_FALSE(node->check(nullptr));
553
554 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
555 static_cast<int>(ComparisonOperator::GREATER));
556 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
557 EXPECT_FALSE(node->check(nullptr));
558
559 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
560 static_cast<int>(ComparisonOperator::LESS));
561 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
562 EXPECT_FALSE(node->check(nullptr));
563
564 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
565 static_cast<int>(ComparisonOperator::NOTEQUAL));
566 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
567 EXPECT_TRUE(node->check(nullptr));
568
569 // Compare inf with numerical value
570 child1 = py::make_tuple(static_cast<int>(NodeType::DoubleNode), pyfloat("inf"));
571 child2 = py::make_tuple(static_cast<int>(NodeType::DoubleNode), 0.0);
572 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
573 static_cast<int>(ComparisonOperator::EQUALEQUAL));
574 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
575 EXPECT_FALSE(node->check(nullptr));
576
577 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
578 static_cast<int>(ComparisonOperator::GREATEREQUAL));
579 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
580 EXPECT_TRUE(node->check(nullptr));
581
582 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
583 static_cast<int>(ComparisonOperator::LESSEQUAL));
584 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
585 EXPECT_FALSE(node->check(nullptr));
586
587 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
588 static_cast<int>(ComparisonOperator::GREATER));
589 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
590 EXPECT_TRUE(node->check(nullptr));
591
592 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
593 static_cast<int>(ComparisonOperator::LESS));
594 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
595 EXPECT_FALSE(node->check(nullptr));
596
597 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
598 static_cast<int>(ComparisonOperator::NOTEQUAL));
599 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
600 EXPECT_TRUE(node->check(nullptr));
601
602 // Compare inf with inf
603 child1 = py::make_tuple(static_cast<int>(NodeType::DoubleNode), pyfloat("inf"));
604 child2 = py::make_tuple(static_cast<int>(NodeType::DoubleNode), pyfloat("inf"));
605 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
606 static_cast<int>(ComparisonOperator::EQUALEQUAL));
607 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
608 EXPECT_TRUE(node->check(nullptr));
609
610 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
611 static_cast<int>(ComparisonOperator::GREATEREQUAL));
612 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
613 EXPECT_TRUE(node->check(nullptr));
614
615 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
616 static_cast<int>(ComparisonOperator::LESSEQUAL));
617 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
618 EXPECT_TRUE(node->check(nullptr));
619
620 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
621 static_cast<int>(ComparisonOperator::GREATER));
622 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
623 EXPECT_FALSE(node->check(nullptr));
624
625 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
626 static_cast<int>(ComparisonOperator::LESS));
627 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
628 EXPECT_FALSE(node->check(nullptr));
629
630 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
631 static_cast<int>(ComparisonOperator::NOTEQUAL));
632 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
633 EXPECT_FALSE(node->check(nullptr));
634
635 // Compare inf with -inf
636 child1 = py::make_tuple(static_cast<int>(NodeType::DoubleNode), pyfloat("inf"));
637 child2 = py::make_tuple(static_cast<int>(NodeType::DoubleNode), pyfloat("-inf"));
638 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
639 static_cast<int>(ComparisonOperator::EQUALEQUAL));
640 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
641 EXPECT_FALSE(node->check(nullptr));
642
643 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
644 static_cast<int>(ComparisonOperator::GREATEREQUAL));
645 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
646 EXPECT_TRUE(node->check(nullptr));
647
648 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
649 static_cast<int>(ComparisonOperator::LESSEQUAL));
650 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
651 EXPECT_FALSE(node->check(nullptr));
652
653 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
654 static_cast<int>(ComparisonOperator::GREATER));
655 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
656 EXPECT_TRUE(node->check(nullptr));
657
658 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
659 static_cast<int>(ComparisonOperator::LESS));
660 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
661 EXPECT_FALSE(node->check(nullptr));
662
663 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
664 static_cast<int>(ComparisonOperator::NOTEQUAL));
665 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
666 EXPECT_TRUE(node->check(nullptr));
667
668 // Check double precision
669 child1 = py::make_tuple(static_cast<int>(NodeType::DoubleNode), 3.141592653589793);
670 child2 = py::make_tuple(static_cast<int>(NodeType::DoubleNode), 3.141592653589792);
671 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
672 static_cast<int>(ComparisonOperator::EQUALEQUAL));
673 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
674 EXPECT_FALSE(node->check(nullptr));
675
676 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
677 static_cast<int>(ComparisonOperator::GREATEREQUAL));
678 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
679 EXPECT_TRUE(node->check(nullptr));
680
681 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
682 static_cast<int>(ComparisonOperator::LESSEQUAL));
683 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
684 EXPECT_FALSE(node->check(nullptr));
685
686 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
687 static_cast<int>(ComparisonOperator::GREATER));
688 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
689 EXPECT_TRUE(node->check(nullptr));
690
691 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
692 static_cast<int>(ComparisonOperator::LESS));
693 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
694 EXPECT_FALSE(node->check(nullptr));
695
696 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
697 static_cast<int>(ComparisonOperator::NOTEQUAL));
698 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
699 EXPECT_TRUE(node->check(nullptr));
700
701 // Check almost equal doubles
702 child1 = py::make_tuple(static_cast<int>(NodeType::DoubleNode), 3.1415926535897931234567890);
703 child2 = py::make_tuple(static_cast<int>(NodeType::DoubleNode), 3.1415926535897931234567891);
704 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
705 static_cast<int>(ComparisonOperator::EQUALEQUAL));
706 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
707 EXPECT_TRUE(node->check(nullptr));
708
709 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
710 static_cast<int>(ComparisonOperator::GREATEREQUAL));
711 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
712 EXPECT_TRUE(node->check(nullptr));
713
714 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
715 static_cast<int>(ComparisonOperator::LESSEQUAL));
716 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
717 EXPECT_TRUE(node->check(nullptr));
718
719 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
720 static_cast<int>(ComparisonOperator::GREATER));
721 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
722 EXPECT_FALSE(node->check(nullptr));
723
724 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
725 static_cast<int>(ComparisonOperator::LESS));
726 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
727 EXPECT_FALSE(node->check(nullptr));
728
729 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
730 static_cast<int>(ComparisonOperator::NOTEQUAL));
731 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
732 EXPECT_FALSE(node->check(nullptr));
733
734 // Check almost equal comparison for doubles and integers
735 child1 = py::make_tuple(static_cast<int>(NodeType::DoubleNode), 3.0000000000000000000000001);
736 child2 = py::make_tuple(static_cast<int>(NodeType::IntegerNode), 3);
737 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
738 static_cast<int>(ComparisonOperator::EQUALEQUAL));
739 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
740 EXPECT_TRUE(node->check(nullptr));
741
742 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
743 static_cast<int>(ComparisonOperator::GREATEREQUAL));
744 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
745 EXPECT_TRUE(node->check(nullptr));
746
747 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
748 static_cast<int>(ComparisonOperator::LESSEQUAL));
749 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
750 EXPECT_TRUE(node->check(nullptr));
751
752 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
753 static_cast<int>(ComparisonOperator::GREATER));
754 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
755 EXPECT_FALSE(node->check(nullptr));
756
757 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
758 static_cast<int>(ComparisonOperator::LESS));
759 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
760 EXPECT_FALSE(node->check(nullptr));
761
762 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
763 static_cast<int>(ComparisonOperator::NOTEQUAL));
764 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
765 EXPECT_FALSE(node->check(nullptr));
766
767 // Note: almostEqualDouble does not work if one input is exactely 0.0
768 // and the other input is almost equal to 0.0
769 child1 = py::make_tuple(static_cast<int>(NodeType::DoubleNode), 0.0);
770 child2 = py::make_tuple(static_cast<int>(NodeType::IntegerNode), 0);
771 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
772 static_cast<int>(ComparisonOperator::EQUALEQUAL));
773 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
774 EXPECT_TRUE(node->check(nullptr));
775
776 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
777 static_cast<int>(ComparisonOperator::GREATEREQUAL));
778 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
779 EXPECT_TRUE(node->check(nullptr));
780
781 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
782 static_cast<int>(ComparisonOperator::LESSEQUAL));
783 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
784 EXPECT_TRUE(node->check(nullptr));
785
786 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
787 static_cast<int>(ComparisonOperator::GREATER));
788 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
789 EXPECT_FALSE(node->check(nullptr));
790
791 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
792 static_cast<int>(ComparisonOperator::LESS));
793 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
794 EXPECT_FALSE(node->check(nullptr));
795
796 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
797 static_cast<int>(ComparisonOperator::NOTEQUAL));
798 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
799 EXPECT_FALSE(node->check(nullptr));
800
801 // Check double and int that are not almost equal but notequal 0.0
802 child1 = py::make_tuple(static_cast<int>(NodeType::DoubleNode), 3.00000000000001);
803 child2 = py::make_tuple(static_cast<int>(NodeType::IntegerNode), 3);
804 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
805 static_cast<int>(ComparisonOperator::EQUALEQUAL));
806 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
807 EXPECT_FALSE(node->check(nullptr));
808
809 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
810 static_cast<int>(ComparisonOperator::GREATEREQUAL));
811 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
812 EXPECT_TRUE(node->check(nullptr));
813
814 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
815 static_cast<int>(ComparisonOperator::LESSEQUAL));
816 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
817 EXPECT_FALSE(node->check(nullptr));
818
819 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
820 static_cast<int>(ComparisonOperator::GREATER));
821 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
822 EXPECT_TRUE(node->check(nullptr));
823
824 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
825 static_cast<int>(ComparisonOperator::LESS));
826 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
827 EXPECT_FALSE(node->check(nullptr));
828
829 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
830 static_cast<int>(ComparisonOperator::NOTEQUAL));
831 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
832 EXPECT_TRUE(node->check(nullptr));
833
834 // Check almost equal comparison for double and bool
835 child1 = py::make_tuple(static_cast<int>(NodeType::DoubleNode), 1.0000000000000001);
836 child2 = py::make_tuple(static_cast<int>(NodeType::BooleanNode), true);
837 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
838 static_cast<int>(ComparisonOperator::EQUALEQUAL));
839 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
840 // Uses almostEqualDouble and should evaluate to true
841 EXPECT_TRUE(node->check(nullptr));
842
843 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
844 static_cast<int>(ComparisonOperator::GREATEREQUAL));
845 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
846 EXPECT_TRUE(node->check(nullptr));
847
848 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
849 static_cast<int>(ComparisonOperator::LESSEQUAL));
850 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
851 EXPECT_TRUE(node->check(nullptr));
852
853 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
854 static_cast<int>(ComparisonOperator::GREATER));
855 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
856 EXPECT_FALSE(node->check(nullptr));
857
858 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
859 static_cast<int>(ComparisonOperator::LESS));
860 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
861 EXPECT_FALSE(node->check(nullptr));
862
863 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
864 static_cast<int>(ComparisonOperator::NOTEQUAL));
865 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
866 // Uses almostEqualDouble and should evaluate to false
867 EXPECT_FALSE(node->check(nullptr));
868
869 // Note: almostEqualDouble does not work if one input is exactely 0.0
870 // and the other input is almost equal to 0.0
871 child1 = py::make_tuple(static_cast<int>(NodeType::DoubleNode), 0.0);
872 child2 = py::make_tuple(static_cast<int>(NodeType::BooleanNode), false);
873 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
874 static_cast<int>(ComparisonOperator::EQUALEQUAL));
875 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
876 EXPECT_TRUE(node->check(nullptr));
877
878 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
879 static_cast<int>(ComparisonOperator::GREATEREQUAL));
880 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
881 EXPECT_TRUE(node->check(nullptr));
882
883 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
884 static_cast<int>(ComparisonOperator::LESSEQUAL));
885 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
886 EXPECT_TRUE(node->check(nullptr));
887
888 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
889 static_cast<int>(ComparisonOperator::GREATER));
890 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
891 EXPECT_FALSE(node->check(nullptr));
892
893 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
894 static_cast<int>(ComparisonOperator::LESS));
895 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
896 EXPECT_FALSE(node->check(nullptr));
897
898 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
899 static_cast<int>(ComparisonOperator::NOTEQUAL));
900 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
901 EXPECT_FALSE(node->check(nullptr));
902
903
904 // Check double and bool that are not almost equal
905 child1 = py::make_tuple(static_cast<int>(NodeType::DoubleNode), 1.00000000000001);
906 child2 = py::make_tuple(static_cast<int>(NodeType::BooleanNode), true);
907 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
908 static_cast<int>(ComparisonOperator::EQUALEQUAL));
909 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
910 EXPECT_FALSE(node->check(nullptr));
911
912 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
913 static_cast<int>(ComparisonOperator::GREATEREQUAL));
914 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
915 EXPECT_TRUE(node->check(nullptr));
916
917 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
918 static_cast<int>(ComparisonOperator::LESSEQUAL));
919 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
920 EXPECT_FALSE(node->check(nullptr));
921
922 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
923 static_cast<int>(ComparisonOperator::GREATER));
924 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
925 EXPECT_TRUE(node->check(nullptr));
926
927 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
928 static_cast<int>(ComparisonOperator::LESS));
929 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
930 EXPECT_FALSE(node->check(nullptr));
931
932 bRelTuple = py::make_tuple(static_cast<int>(NodeType::BinaryRelationalNode), child1, child2,
933 static_cast<int>(ComparisonOperator::NOTEQUAL));
934 node = NodeFactory::compile_boolean_node<MockVariableManager>(bRelTuple);
935 EXPECT_TRUE(node->check(nullptr));
936
937 }
939 TEST(CutNodesTest, ternaryRelationalNode)
940 {
941 Py_Initialize();
942 // Get main module
943 py::object main = py::import("__main__");
944 py::object pyfloat = main.attr("__builtins__").attr("float");
945
946 auto child1 = py::make_tuple(static_cast<int>(NodeType::IntegerNode), 1);
947 auto child2 = py::make_tuple(static_cast<int>(NodeType::IntegerNode), 2);
948 auto child3 = py::make_tuple(static_cast<int>(NodeType::IntegerNode), 3);
949 auto tuple = py::make_tuple(static_cast<int>(NodeType::TernaryRelationalNode), child1, child2, child3,
950 static_cast<int>(ComparisonOperator::LESS), static_cast<int>(ComparisonOperator::LESS));
951
952 auto node = NodeFactory::compile_boolean_node<MockVariableManager>(tuple);
953 EXPECT_TRUE(node->check(nullptr));
954 EXPECT_EQ(node->decompile(), "1 < 2 < 3");
955
956 tuple = py::make_tuple(static_cast<int>(NodeType::TernaryRelationalNode), child1, child1, child1,
957 static_cast<int>(ComparisonOperator::EQUALEQUAL), static_cast<int>(ComparisonOperator::EQUALEQUAL));
958 node = NodeFactory::compile_boolean_node<MockVariableManager>(tuple);
959 EXPECT_TRUE(node->check(nullptr));
960 EXPECT_EQ(node->decompile(), "1 == 1 == 1");
961
962
963 tuple = py::make_tuple(static_cast<int>(NodeType::TernaryRelationalNode), child1, child1, child1,
964 static_cast<int>(ComparisonOperator::EQUALEQUAL), static_cast<int>(ComparisonOperator::LESSEQUAL));
965 node = NodeFactory::compile_boolean_node<MockVariableManager>(tuple);
966 EXPECT_TRUE(node->check(nullptr));
967 EXPECT_EQ(node->decompile(), "1 == 1 <= 1");
968
969
970 tuple = py::make_tuple(static_cast<int>(NodeType::TernaryRelationalNode), child1, child1, child2,
971 static_cast<int>(ComparisonOperator::EQUALEQUAL), static_cast<int>(ComparisonOperator::LESSEQUAL));
972 node = NodeFactory::compile_boolean_node<MockVariableManager>(tuple);
973 EXPECT_TRUE(node->check(nullptr));
974 EXPECT_EQ(node->decompile(), "1 == 1 <= 2");
975
976
977 tuple = py::make_tuple(static_cast<int>(NodeType::TernaryRelationalNode), child1, child1, child2,
978 static_cast<int>(ComparisonOperator::EQUALEQUAL), static_cast<int>(ComparisonOperator::LESS));
979 node = NodeFactory::compile_boolean_node<MockVariableManager>(tuple);
980 EXPECT_TRUE(node->check(nullptr));
981 EXPECT_EQ(node->decompile(), "1 == 1 < 2");
982
983 tuple = py::make_tuple(static_cast<int>(NodeType::TernaryRelationalNode), child1, child1, child2,
984 static_cast<int>(ComparisonOperator::EQUALEQUAL), static_cast<int>(ComparisonOperator::NOTEQUAL));
985 node = NodeFactory::compile_boolean_node<MockVariableManager>(tuple);
986 EXPECT_TRUE(node->check(nullptr));
987 EXPECT_EQ(node->decompile(), "1 == 1 != 2");
988
989 tuple = py::make_tuple(static_cast<int>(NodeType::TernaryRelationalNode), child1, child1, child1,
990 static_cast<int>(ComparisonOperator::EQUALEQUAL), static_cast<int>(ComparisonOperator::GREATEREQUAL));
991 node = NodeFactory::compile_boolean_node<MockVariableManager>(tuple);
992 EXPECT_TRUE(node->check(nullptr));
993 EXPECT_EQ(node->decompile(), "1 == 1 >= 1");
994
995 tuple = py::make_tuple(static_cast<int>(NodeType::TernaryRelationalNode), child1, child1, child2,
996 static_cast<int>(ComparisonOperator::EQUALEQUAL), static_cast<int>(ComparisonOperator::GREATER));
997 node = NodeFactory::compile_boolean_node<MockVariableManager>(tuple);
998 EXPECT_FALSE(node->check(nullptr));
999 EXPECT_EQ(node->decompile(), "1 == 1 > 2");
1000
1001 tuple = py::make_tuple(static_cast<int>(NodeType::TernaryRelationalNode), child1, child1, child1,
1002 static_cast<int>(ComparisonOperator::EQUALEQUAL), static_cast<int>(ComparisonOperator::NOTEQUAL));
1003 node = NodeFactory::compile_boolean_node<MockVariableManager>(tuple);
1004 EXPECT_FALSE(node->check(nullptr));
1005 EXPECT_EQ(node->decompile(), "1 == 1 != 1");
1006
1007
1008 tuple = py::make_tuple(static_cast<int>(NodeType::TernaryRelationalNode), child1, child1, child2,
1009 static_cast<int>(ComparisonOperator::EQUALEQUAL), static_cast<int>(ComparisonOperator::LESSEQUAL));
1010 node = NodeFactory::compile_boolean_node<MockVariableManager>(tuple);
1011 EXPECT_TRUE(node->check(nullptr));
1012 EXPECT_EQ(node->decompile(), "1 == 1 <= 2");
1013
1014 // Create new double tuple
1015 child3 = py::make_tuple(static_cast<int>(NodeType::DoubleNode), 3.141);
1016
1017 tuple = py::make_tuple(static_cast<int>(NodeType::TernaryRelationalNode), child1, child1, child3,
1018 static_cast<int>(ComparisonOperator::EQUALEQUAL), static_cast<int>(ComparisonOperator::LESSEQUAL));
1019 node = NodeFactory::compile_boolean_node<MockVariableManager>(tuple);
1020 EXPECT_TRUE(node->check(nullptr));
1021 EXPECT_EQ(node->decompile(), "1 == 1 <= 3.141");
1022
1023 tuple = py::make_tuple(static_cast<int>(NodeType::TernaryRelationalNode), child1, child3, child3,
1024 static_cast<int>(ComparisonOperator::EQUALEQUAL), static_cast<int>(ComparisonOperator::LESSEQUAL));
1025 node = NodeFactory::compile_boolean_node<MockVariableManager>(tuple);
1026 EXPECT_FALSE(node->check(nullptr));
1027 EXPECT_EQ(node->decompile(), "1 == 3.141 <= 3.141");
1028
1029
1030 tuple = py::make_tuple(static_cast<int>(NodeType::TernaryRelationalNode), child3, child3, child3,
1031 static_cast<int>(ComparisonOperator::EQUALEQUAL), static_cast<int>(ComparisonOperator::LESSEQUAL));
1032 node = NodeFactory::compile_boolean_node<MockVariableManager>(tuple);
1033 EXPECT_TRUE(node->check(nullptr));
1034 EXPECT_EQ(node->decompile(), "3.141 == 3.141 <= 3.141");
1035
1036
1037 tuple = py::make_tuple(static_cast<int>(NodeType::TernaryRelationalNode), child3, child3, child3,
1038 static_cast<int>(ComparisonOperator::NOTEQUAL), static_cast<int>(ComparisonOperator::LESSEQUAL));
1039 node = NodeFactory::compile_boolean_node<MockVariableManager>(tuple);
1040 EXPECT_FALSE(node->check(nullptr));
1041 EXPECT_EQ(node->decompile(), "3.141 != 3.141 <= 3.141");
1042
1043 child3 = py::make_tuple(static_cast<int>(NodeType::DoubleNode), pyfloat("nan"));
1044
1045 tuple = py::make_tuple(static_cast<int>(NodeType::TernaryRelationalNode), child3, child3, child3,
1046 static_cast<int>(ComparisonOperator::EQUALEQUAL), static_cast<int>(ComparisonOperator::EQUALEQUAL));
1047 node = NodeFactory::compile_boolean_node<MockVariableManager>(tuple);
1048 EXPECT_TRUE(node->check(nullptr));
1049 EXPECT_EQ(node->decompile(), "nan == nan == nan");
1050
1051 tuple = py::make_tuple(static_cast<int>(NodeType::TernaryRelationalNode), child3, child3, child2,
1052 static_cast<int>(ComparisonOperator::EQUALEQUAL), static_cast<int>(ComparisonOperator::EQUALEQUAL));
1053 node = NodeFactory::compile_boolean_node<MockVariableManager>(tuple);
1054 EXPECT_FALSE(node->check(nullptr));
1055 EXPECT_EQ(node->decompile(), "nan == nan == 2");
1056
1057
1058 tuple = py::make_tuple(static_cast<int>(NodeType::TernaryRelationalNode), child3, child3, child2,
1059 static_cast<int>(ComparisonOperator::EQUALEQUAL), static_cast<int>(ComparisonOperator::NOTEQUAL));
1060 node = NodeFactory::compile_boolean_node<MockVariableManager>(tuple);
1061 EXPECT_TRUE(node->check(nullptr));
1062 EXPECT_EQ(node->decompile(), "nan == nan != 2");
1063
1064 tuple = py::make_tuple(static_cast<int>(NodeType::TernaryRelationalNode), child3, child3, child3,
1065 static_cast<int>(ComparisonOperator::EQUALEQUAL), static_cast<int>(ComparisonOperator::NOTEQUAL));
1066 node = NodeFactory::compile_boolean_node<MockVariableManager>(tuple);
1067 EXPECT_FALSE(node->check(nullptr));
1068 EXPECT_EQ(node->decompile(), "nan == nan != nan");
1069
1070 child2 = py::make_tuple(static_cast<int>(NodeType::DoubleNode), pyfloat("inf"));
1071
1072 tuple = py::make_tuple(static_cast<int>(NodeType::TernaryRelationalNode), child3, child3, child2,
1073 static_cast<int>(ComparisonOperator::EQUALEQUAL), static_cast<int>(ComparisonOperator::NOTEQUAL));
1074 node = NodeFactory::compile_boolean_node<MockVariableManager>(tuple);
1075 EXPECT_TRUE(node->check(nullptr));
1076 EXPECT_EQ(node->decompile(), "nan == nan != inf");
1077
1078
1079 tuple = py::make_tuple(static_cast<int>(NodeType::TernaryRelationalNode), child3, child3, child2,
1080 static_cast<int>(ComparisonOperator::EQUALEQUAL), static_cast<int>(ComparisonOperator::EQUALEQUAL));
1081 node = NodeFactory::compile_boolean_node<MockVariableManager>(tuple);
1082 EXPECT_FALSE(node->check(nullptr));
1083 EXPECT_EQ(node->decompile(), "nan == nan == inf");
1084
1085 tuple = py::make_tuple(static_cast<int>(NodeType::TernaryRelationalNode), child3, child3, child2,
1086 static_cast<int>(ComparisonOperator::EQUALEQUAL), static_cast<int>(ComparisonOperator::LESS));
1087 node = NodeFactory::compile_boolean_node<MockVariableManager>(tuple);
1088 EXPECT_FALSE(node->check(nullptr));
1089 EXPECT_EQ(node->decompile(), "nan == nan < inf");
1090
1091 tuple = py::make_tuple(static_cast<int>(NodeType::TernaryRelationalNode), child3, child3, child2,
1092 static_cast<int>(ComparisonOperator::EQUALEQUAL), static_cast<int>(ComparisonOperator::LESSEQUAL));
1093 node = NodeFactory::compile_boolean_node<MockVariableManager>(tuple);
1094 EXPECT_FALSE(node->check(nullptr));
1095 EXPECT_EQ(node->decompile(), "nan == nan <= inf");
1096
1097 tuple = py::make_tuple(static_cast<int>(NodeType::TernaryRelationalNode), child3, child3, child2,
1098 static_cast<int>(ComparisonOperator::EQUALEQUAL), static_cast<int>(ComparisonOperator::GREATER));
1099 node = NodeFactory::compile_boolean_node<MockVariableManager>(tuple);
1100 EXPECT_FALSE(node->check(nullptr));
1101 EXPECT_EQ(node->decompile(), "nan == nan > inf");
1102
1103 tuple = py::make_tuple(static_cast<int>(NodeType::TernaryRelationalNode), child3, child3, child2,
1104 static_cast<int>(ComparisonOperator::EQUALEQUAL), static_cast<int>(ComparisonOperator::GREATEREQUAL));
1105 node = NodeFactory::compile_boolean_node<MockVariableManager>(tuple);
1106 EXPECT_FALSE(node->check(nullptr));
1107 EXPECT_EQ(node->decompile(), "nan == nan >= inf");
1108
1109 }
1111 TEST(CutNodesTest, unaryExpressionNode)
1112 {
1113 Py_Initialize();
1114 auto child1 = py::make_tuple(static_cast<int>(NodeType::IntegerNode), 1);
1115 auto tuple = py::make_tuple(static_cast<int>(NodeType::UnaryExpressionNode), child1, false, false);
1116 auto node = NodeFactory::compile_expression_node<MockVariableManager>(tuple);
1117 EXPECT_EQ(std::get<int>(node->evaluate(nullptr)), 1);
1118
1119 // Check docompiling
1120 EXPECT_EQ(node->decompile(), "1");
1121
1122 tuple = py::make_tuple(static_cast<int>(NodeType::UnaryExpressionNode), child1, true, false);
1123 node = NodeFactory::compile_expression_node<MockVariableManager>(tuple);
1124 EXPECT_EQ(std::get<int>(node->evaluate(nullptr)), -1);
1125
1126 // Check docompiling
1127 EXPECT_EQ(node->decompile(), "-1");
1128
1129 tuple = py::make_tuple(static_cast<int>(NodeType::UnaryExpressionNode), child1, true, true);
1130 node = NodeFactory::compile_expression_node<MockVariableManager>(tuple);
1131 EXPECT_EQ(std::get<int>(node->evaluate(nullptr)), -1);
1132
1133 // Check docompiling
1134 EXPECT_EQ(node->decompile(), "-( 1 )");
1135
1136 tuple = py::make_tuple(static_cast<int>(NodeType::UnaryExpressionNode), child1, false, true);
1137 node = NodeFactory::compile_expression_node<MockVariableManager>(tuple);
1138 EXPECT_EQ(std::get<int>(node->evaluate(nullptr)), 1);
1139
1140 // Check docompiling
1141 EXPECT_EQ(node->decompile(), "( 1 )");
1142
1143 }
1145 TEST(CutNodesTest, binaryExpressionNode)
1146 {
1147 Py_Initialize();
1148 auto child1 = py::make_tuple(static_cast<int>(NodeType::IntegerNode), 1);
1149 auto child2 = py::make_tuple(static_cast<int>(NodeType::DoubleNode), 2.5);
1150 auto tuple = py::make_tuple(static_cast<int>(NodeType::BinaryExpressionNode), child1, child1,
1151 static_cast<int>(ArithmeticOperation::PLUS));
1152 auto node = NodeFactory::compile_expression_node<MockVariableManager>(tuple);
1153 EXPECT_EQ(std::get<int>(node->evaluate(nullptr)), 2);
1154
1155 // Check docompiling
1156 EXPECT_EQ(node->decompile(), "1 + 1");
1157
1158 tuple = py::make_tuple(static_cast<int>(NodeType::BinaryExpressionNode), child1, child2,
1159 static_cast<int>(ArithmeticOperation::PLUS));
1160 node = NodeFactory::compile_expression_node<MockVariableManager>(tuple);
1161 EXPECT_EQ(std::get<double>(node->evaluate(nullptr)), 3.5);
1162 EXPECT_EQ(node->decompile(), "1 + 2.5");
1163
1164 tuple = py::make_tuple(static_cast<int>(NodeType::BinaryExpressionNode), child1, child2,
1165 static_cast<int>(ArithmeticOperation::MINUS));
1166 node = NodeFactory::compile_expression_node<MockVariableManager>(tuple);
1167 EXPECT_EQ(std::get<double>(node->evaluate(nullptr)), -1.5);
1168 EXPECT_EQ(node->decompile(), "1 - 2.5");
1169
1170
1171 tuple = py::make_tuple(static_cast<int>(NodeType::BinaryExpressionNode), child1, child2,
1172 static_cast<int>(ArithmeticOperation::PRODUCT));
1173 node = NodeFactory::compile_expression_node<MockVariableManager>(tuple);
1174 EXPECT_EQ(std::get<double>(node->evaluate(nullptr)), 2.5);
1175 EXPECT_EQ(node->decompile(), "1 * 2.5");
1176
1177
1178 tuple = py::make_tuple(static_cast<int>(NodeType::BinaryExpressionNode), child1, child2,
1179 static_cast<int>(ArithmeticOperation::DIVISION));
1180 node = NodeFactory::compile_expression_node<MockVariableManager>(tuple);
1181 EXPECT_EQ(std::get<double>(node->evaluate(nullptr)), 0.4);
1182 EXPECT_EQ(node->decompile(), "1 / 2.5");
1183
1184
1185 tuple = py::make_tuple(static_cast<int>(NodeType::BinaryExpressionNode), child1, child1,
1186 static_cast<int>(ArithmeticOperation::POWER));
1187 node = NodeFactory::compile_expression_node<MockVariableManager>(tuple);
1188 EXPECT_EQ(std::get<double>(node->evaluate(nullptr)), 1.0);
1189 EXPECT_EQ(node->decompile(), "1 ** 1");
1190
1191 child1 = py::make_tuple(static_cast<int>(NodeType::IntegerNode), 2);
1192 child2 = py::make_tuple(static_cast<int>(NodeType::IntegerNode), 3);
1193
1194 tuple = py::make_tuple(static_cast<int>(NodeType::BinaryExpressionNode), child1, child2,
1195 static_cast<int>(ArithmeticOperation::POWER));
1196 node = NodeFactory::compile_expression_node<MockVariableManager>(tuple);
1197 EXPECT_EQ(std::get<double>(node->evaluate(nullptr)), 8.0);
1198 EXPECT_EQ(node->decompile(), "2 ** 3");
1199
1200 child2 = py::make_tuple(static_cast<int>(NodeType::IdentifierNode), "mocking_variable");
1201 MockObjectType part{10};
1202 tuple = py::make_tuple(static_cast<int>(NodeType::BinaryExpressionNode), child1, child2,
1203 static_cast<int>(ArithmeticOperation::POWER));
1204 node = NodeFactory::compile_expression_node<MockVariableManager>(tuple);
1205 EXPECT_EQ(std::get<double>(node->evaluate(&part)), 1024);
1206 EXPECT_EQ(node->decompile(), "2 ** mocking_variable");
1207
1208
1209 tuple = py::make_tuple(static_cast<int>(NodeType::BinaryExpressionNode), child2, child2,
1210 static_cast<int>(ArithmeticOperation::PLUS));
1211 node = NodeFactory::compile_expression_node<MockVariableManager>(tuple);
1212 EXPECT_EQ(std::get<int>(node->evaluate(&part)), 20);
1213 EXPECT_EQ(node->decompile(), "mocking_variable + mocking_variable");
1214
1215 tuple = py::make_tuple(static_cast<int>(NodeType::BinaryExpressionNode), child2, child2,
1216 static_cast<int>(ArithmeticOperation::MINUS));
1217 node = NodeFactory::compile_expression_node<MockVariableManager>(tuple);
1218 EXPECT_EQ(std::get<int>(node->evaluate(&part)), 0);
1219 EXPECT_EQ(node->decompile(), "mocking_variable - mocking_variable");
1220
1221 tuple = py::make_tuple(static_cast<int>(NodeType::BinaryExpressionNode), child2, child2,
1222 static_cast<int>(ArithmeticOperation::PRODUCT));
1223 node = NodeFactory::compile_expression_node<MockVariableManager>(tuple);
1224 EXPECT_EQ(std::get<int>(node->evaluate(&part)), 100);
1225 EXPECT_EQ(node->decompile(), "mocking_variable * mocking_variable");
1226
1227
1228 tuple = py::make_tuple(static_cast<int>(NodeType::BinaryExpressionNode), child2, child2,
1229 static_cast<int>(ArithmeticOperation::DIVISION));
1230 node = NodeFactory::compile_expression_node<MockVariableManager>(tuple);
1231 EXPECT_EQ(std::get<double>(node->evaluate(&part)), 1);
1232 EXPECT_EQ(node->decompile(), "mocking_variable / mocking_variable");
1233
1234
1235 part = MockObjectType{20};
1236 tuple = py::make_tuple(static_cast<int>(NodeType::BinaryExpressionNode), child1, child2,
1237 static_cast<int>(ArithmeticOperation::DIVISION));
1238 node = NodeFactory::compile_expression_node<MockVariableManager>(tuple);
1239 EXPECT_EQ(std::get<double>(node->evaluate(&part)), 0.1);
1240 EXPECT_EQ(node->decompile(), "2 / mocking_variable");
1241
1242 part = MockObjectType{0.1};
1243 tuple = py::make_tuple(static_cast<int>(NodeType::BinaryExpressionNode), child2, child1,
1244 static_cast<int>(ArithmeticOperation::DIVISION));
1245 node = NodeFactory::compile_expression_node<MockVariableManager>(tuple);
1246 EXPECT_EQ(std::get<double>(node->evaluate(&part)), 0.05);
1247 EXPECT_EQ(node->decompile(), "mocking_variable / 2");
1248
1249
1250 }
1252 TEST(CutNodesTest, identifierNode)
1253 {
1254 Py_Initialize();
1255 MockObjectType part{4.2};
1256 auto tuple = py::make_tuple(static_cast<int>(NodeType::IdentifierNode), "mocking_variable");
1257 auto node = NodeFactory::compile_expression_node<MockVariableManager>(tuple);
1258 EXPECT_EQ(std::get<double>(node->evaluate(&part)), 4.2);
1259
1260 tuple = py::make_tuple(static_cast<int>(NodeType::IdentifierNode), "THISDOESNOTEXIST");
1261 EXPECT_THROW(NodeFactory::compile_expression_node<MockVariableManager>(tuple), std::runtime_error);
1262
1263 // Check nested runtime_error
1264 tuple = py::make_tuple(static_cast<int>(NodeType::UnaryExpressionNode), tuple, false, false);
1265 EXPECT_THROW(NodeFactory::compile_expression_node<MockVariableManager>(tuple), std::runtime_error);
1266
1267 }
1269 TEST(CutNodesTest, functionNode)
1270 {
1271 Py_Initialize();
1272 MockObjectType part{4};
1273 auto tuple = py::make_tuple(
1274 static_cast<int>(NodeType::FunctionNode),
1275 "sum",
1276 "mocking_variable, 2, 1"
1277 );
1278 auto node = NodeFactory::compile_expression_node<MockVariableManager>(tuple);
1279 EXPECT_EQ(std::get<double>(node->evaluate(&part)), 7);
1280 EXPECT_EQ(node->decompile(), "sum(mocking_variable, 2, 1)");
1281 part = MockObjectType{4.2};
1282 EXPECT_EQ(std::get<double>(node->evaluate(&part)), 7.2);
1283 part = MockObjectType{false};
1284 EXPECT_EQ(std::get<double>(node->evaluate(&part)), 3.0);
1285 part = MockObjectType{true};
1286 EXPECT_EQ(std::get<double>(node->evaluate(&part)), 4.0);
1287
1288 }
1290 TEST(CutNodesTest, integerNode)
1291 {
1292 Py_Initialize();
1293 // Get main module
1294 py::object main = py::import("__main__");
1295
1296 // Create IntegerNode tuples.
1297 const py::tuple iTuple_val = py::make_tuple(static_cast<int>(NodeType::IntegerNode), 1337);
1298 const py::tuple iTuple_val_neg = py::make_tuple(static_cast<int>(NodeType::IntegerNode), -1337);
1299 const py::tuple iTuple_val_zero = py::make_tuple(static_cast<int>(NodeType::IntegerNode), 0);
1300
1301 // Check overflow management
1302 const py::tuple iTuple_max = py::make_tuple(static_cast<int>(NodeType::IntegerNode),
1303 main.attr("__builtins__").attr("int")("2147483647"));
1304 const py::tuple iTuple_min = py::make_tuple(static_cast<int>(NodeType::IntegerNode),
1305 main.attr("__builtins__").attr("int")("-2147483648"));
1306 const py::tuple iTuple_pos_overflow = py::make_tuple(static_cast<int>(NodeType::IntegerNode),
1307 main.attr("__builtins__").attr("int")("2147483648"));
1308 const py::tuple iTuple_neg_overflow = py::make_tuple(static_cast<int>(NodeType::IntegerNode),
1309 main.attr("__builtins__").attr("int")("-2147483649"));
1310
1311 // Compile IntegerNodes and check evaluation
1312 auto iNode_val = NodeFactory::compile_expression_node<MockVariableManager>(iTuple_val);
1313 auto iNode_val_neg = NodeFactory::compile_expression_node<MockVariableManager>(iTuple_val_neg);
1314 auto iNode_val_zero = NodeFactory::compile_expression_node<MockVariableManager>(iTuple_val_zero);
1315 // Compile overflow management
1316 auto iNode_max = NodeFactory::compile_expression_node<MockVariableManager>(iTuple_max);
1317 auto iNode_min = NodeFactory::compile_expression_node<MockVariableManager>(iTuple_min);
1318 auto iNode_pos_overflow = NodeFactory::compile_expression_node<MockVariableManager>(iTuple_pos_overflow);
1319 auto iNode_neg_overflow = NodeFactory::compile_expression_node<MockVariableManager>(iTuple_neg_overflow);
1320
1321 // test evaluation
1322 EXPECT_EQ(std::get<int>(iNode_val->evaluate(nullptr)), 1337);
1323 EXPECT_EQ(std::get<int>(iNode_val_neg->evaluate(nullptr)), -1337);
1324 EXPECT_EQ(std::get<int>(iNode_val_zero->evaluate(nullptr)), 0);
1325 EXPECT_EQ(std::get<int>(iNode_max->evaluate(nullptr)), 2147483647);
1326 EXPECT_EQ(std::get<int>(iNode_min->evaluate(nullptr)), -2147483648);
1327 // test overflowing node evaluation (returned as double)
1328 EXPECT_EQ(std::get<double>(iNode_pos_overflow->evaluate(nullptr)), 2147483648.);
1329 EXPECT_EQ(std::get<double>(iNode_neg_overflow->evaluate(nullptr)), -2147483649.);
1330
1331 // test decompiling
1332 EXPECT_EQ(iNode_val->decompile(), "1337");
1333 EXPECT_EQ(iNode_val_neg->decompile(), "-1337");
1334 EXPECT_EQ(iNode_val_zero->decompile(), "0");
1335 EXPECT_EQ(iNode_max->decompile(), "2147483647");
1336 EXPECT_EQ(iNode_min->decompile(), "-2147483648");
1337 // test overflowing node decompiling
1338 EXPECT_EQ(iNode_pos_overflow->decompile(), "2.14748e+09");
1339 EXPECT_EQ(iNode_neg_overflow->decompile(), "-2.14748e+09");
1340 }
1342 TEST(CutNodesTest, booleanNode)
1343 {
1344 Py_Initialize();
1345 // Create two BooleanNode tuples with values true and false.
1346 const py::tuple booleanTuple_true = py::make_tuple(static_cast<int>(NodeType::BooleanNode), true);
1347 const py::tuple booleanTuple_false = py::make_tuple(static_cast<int>(NodeType::BooleanNode), false);
1348 // Compile BooleanNodes and check evaluation
1349 auto booleanNode_true = NodeFactory::compile_expression_node<MockVariableManager>(booleanTuple_true);
1350 auto booleanNode_false = NodeFactory::compile_expression_node<MockVariableManager>(booleanTuple_false);
1351 // test evaluation
1352 EXPECT_TRUE(std::get<bool>(booleanNode_true->evaluate(nullptr)));
1353 EXPECT_FALSE(std::get<bool>(booleanNode_false->evaluate(nullptr)));
1354 // test decompiling
1355 EXPECT_EQ(booleanNode_true->decompile(), "true");
1356 EXPECT_EQ(booleanNode_false->decompile(), "false");
1357 }
1359 TEST(CutNodesTest, doubleNode)
1360 {
1361 Py_Initialize();
1362 // Get main module
1363 py::object main = py::import("__main__");
1364
1365 // Value tuples
1366 const py::tuple tuple_val = py::make_tuple(static_cast<int>(NodeType::DoubleNode), 3.141);
1367 const py::tuple tuple_val_neg = py::make_tuple(static_cast<int>(NodeType::DoubleNode), -3.141);
1368 const py::tuple tuple_val_zero = py::make_tuple(static_cast<int>(NodeType::DoubleNode), 0.0);
1369 // Infinity tuples
1370 const py::tuple tuple_inf = py::make_tuple(static_cast<int>(NodeType::DoubleNode), main.attr("__builtins__").attr("float")("inf"));
1371 const py::tuple tuple_neg_inf = py::make_tuple(static_cast<int>(NodeType::DoubleNode),
1372 main.attr("__builtins__").attr("float")("-inf"));
1373 // nan tuple
1374 const py::tuple tuple_nan = py::make_tuple(static_cast<int>(NodeType::DoubleNode), main.attr("__builtins__").attr("float")("nan"));
1375
1376 // Value nodes
1377 auto doubleNode_val = NodeFactory::compile_expression_node<MockVariableManager>(tuple_val);
1378 auto doubleNode_val_neg = NodeFactory::compile_expression_node<MockVariableManager>(tuple_val_neg);
1379 auto doubleNode_val_zero = NodeFactory::compile_expression_node<MockVariableManager>(tuple_val_zero);
1380
1381 // Infinity nodes
1382 auto doubleNode_inf = NodeFactory::compile_expression_node<MockVariableManager>(tuple_inf);
1383 auto doubleNode_neg_inf = NodeFactory::compile_expression_node<MockVariableManager>(tuple_neg_inf);
1384 // NaN nodes
1385 auto doubleNode_nan = NodeFactory::compile_expression_node<MockVariableManager>(tuple_nan);
1386
1387 // test value evaluation
1388 EXPECT_EQ(std::get<double>(doubleNode_val->evaluate(nullptr)), 3.141);
1389 EXPECT_EQ(std::get<double>(doubleNode_val_neg->evaluate(nullptr)), -3.141);
1390 EXPECT_EQ(std::get<double>(doubleNode_val_zero->evaluate(nullptr)), 0);
1391
1392 // test infinity evaluation
1393 EXPECT_EQ(std::get<double>(doubleNode_inf->evaluate(nullptr)), std::numeric_limits<double>::infinity());
1394 EXPECT_EQ(std::get<double>(doubleNode_neg_inf->evaluate(nullptr)), -1 * std::numeric_limits<double>::infinity());
1395
1396 // test NaN evaluation
1397 EXPECT_TRUE(std::isnan(std::get<double>(doubleNode_nan->evaluate(nullptr))));
1398
1399 // test value decompiling
1400 EXPECT_EQ(doubleNode_val->decompile(), "3.141");
1401 EXPECT_EQ(doubleNode_val_neg->decompile(), "-3.141");
1402 EXPECT_EQ(doubleNode_val_zero->decompile(), "0");
1403 // test infinity decompiling
1404 EXPECT_EQ(doubleNode_inf->decompile(), "inf");
1405 EXPECT_EQ(doubleNode_neg_inf->decompile(), "-inf");
1406 // test nan decompiling
1407 EXPECT_EQ(doubleNode_nan->decompile(), "nan");
1408 }
1409} // namespace
std::variant< double, int, bool > VarVariant
NOTE: the python interface is documented manually in analysis/doc/Variables.rst (because we use ROOT ...
Definition: Manager.h:111
Abstract base class for different kinds of events.