Project
Loading...
Searching...
No Matches
test_Expressions.cxx
Go to the documentation of this file.
1// Copyright 2019-2020 CERN and copyright holders of ALICE O2.
2// See https://alice-o2.web.cern.ch/copyright for details of the copyright holders.
3// All rights not expressly granted are reserved.
4//
5// This software is distributed under the terms of the GNU General Public
6// License v3 (GPL Version 3), copied verbatim in the file "COPYING".
7//
8// In applying this license CERN does not waive the privileges and immunities
9// granted to it by virtue of its status as an Intergovernmental Organization
10// or submit itself to any jurisdiction.
11
15#include <catch_amalgamated.hpp>
16#include <arrow/util/config.h>
17#include <iostream>
18
19using namespace o2::framework;
20using namespace o2::framework::expressions;
21
22namespace nodes
23{
24static BindingNode pt{"pt", 1, atype::FLOAT};
25static BindingNode phi{"phi", 2, atype::FLOAT};
26static BindingNode eta{"eta", 3, atype::FLOAT};
27
28static BindingNode tgl{"tgl", 4, atype::FLOAT};
29static BindingNode signed1Pt{"signed1Pt", 5, atype::FLOAT};
30static BindingNode testInt{"testInt", 6, atype::INT32};
31} // namespace nodes
32
33namespace o2::aod::track
34{
35DECLARE_SOA_EXPRESSION_COLUMN(Pze, pz, float, o2::aod::track::tgl * (1.f / o2::aod::track::signed1Pt));
36} // namespace o2::aod::track
37
38TEST_CASE("TestTreeParsing")
39{
40 expressions::Filter f = ((nodes::phi > 1) && (nodes::phi < 2)) && (nodes::eta < 1);
41 auto specs = createOperations(f);
42 REQUIRE(specs[0].left == (DatumSpec{1u, atype::BOOL}));
43 REQUIRE(specs[0].right == (DatumSpec{2u, atype::BOOL}));
44 REQUIRE(specs[0].result == (DatumSpec{0u, atype::BOOL}));
45
46 REQUIRE(specs[1].left == (DatumSpec{std::string{"eta"}, 3, atype::FLOAT}));
47 REQUIRE(specs[1].right == (DatumSpec{LiteralNode::var_t{1}, atype::INT32}));
48 REQUIRE(specs[1].result == (DatumSpec{2u, atype::BOOL}));
49
50 REQUIRE(specs[2].left == (DatumSpec{3u, atype::BOOL}));
51 REQUIRE(specs[2].right == (DatumSpec{4u, atype::BOOL}));
52 REQUIRE(specs[2].result == (DatumSpec{1u, atype::BOOL}));
53
54 REQUIRE(specs[3].left == (DatumSpec{std::string{"phi"}, 2, atype::FLOAT}));
55 REQUIRE(specs[3].right == (DatumSpec{LiteralNode::var_t{2}, atype::INT32}));
56 REQUIRE(specs[3].result == (DatumSpec{4u, atype::BOOL}));
57
58 REQUIRE(specs[4].left == (DatumSpec{std::string{"phi"}, 2, atype::FLOAT}));
59 REQUIRE(specs[4].right == (DatumSpec{LiteralNode::var_t{1}, atype::INT32}));
60 REQUIRE(specs[4].result == (DatumSpec{3u, atype::BOOL}));
61
62 expressions::Filter g = ((nodes::eta + 2.f) > 0.5) || ((nodes::phi - M_PI) < 3);
63 auto gspecs = createOperations(g);
64 REQUIRE(gspecs[0].left == (DatumSpec{1u, atype::BOOL}));
65 REQUIRE(gspecs[0].right == (DatumSpec{2u, atype::BOOL}));
66 REQUIRE(gspecs[0].result == (DatumSpec{0u, atype::BOOL}));
67
68 REQUIRE(gspecs[1].left == (DatumSpec{3u, atype::DOUBLE}));
69 REQUIRE(gspecs[1].right == (DatumSpec{LiteralNode::var_t{3}, atype::INT32}));
70 REQUIRE(gspecs[1].result == (DatumSpec{2u, atype::BOOL}));
71
72 REQUIRE(gspecs[2].left == (DatumSpec{std::string{"phi"}, 2, atype::FLOAT}));
73 REQUIRE(gspecs[2].right == (DatumSpec{LiteralNode::var_t{M_PI}, atype::DOUBLE}));
74 REQUIRE(gspecs[2].result == (DatumSpec{3u, atype::DOUBLE}));
75
76 REQUIRE(gspecs[3].left == (DatumSpec{4u, atype::FLOAT}));
77 REQUIRE(gspecs[3].right == (DatumSpec{LiteralNode::var_t{0.5}, atype::DOUBLE}));
78 REQUIRE(gspecs[3].result == (DatumSpec{1u, atype::BOOL}));
79
80 REQUIRE(gspecs[4].left == (DatumSpec{std::string{"eta"}, 3, atype::FLOAT}));
81 REQUIRE(gspecs[4].right == (DatumSpec{LiteralNode::var_t{2.f}, atype::FLOAT}));
82 REQUIRE(gspecs[4].result == (DatumSpec{4u, atype::FLOAT}));
83
84 expressions::Filter h = (nodes::phi == 0) || (nodes::phi == 3);
85 auto hspecs = createOperations(h);
86
87 REQUIRE(hspecs[0].left == (DatumSpec{1u, atype::BOOL}));
88 REQUIRE(hspecs[0].right == (DatumSpec{2u, atype::BOOL}));
89 REQUIRE(hspecs[0].result == (DatumSpec{0u, atype::BOOL}));
90
91 REQUIRE(hspecs[1].left == (DatumSpec{std::string{"phi"}, 2, atype::FLOAT}));
92 REQUIRE(hspecs[1].right == (DatumSpec{LiteralNode::var_t{3}, atype::INT32}));
93 REQUIRE(hspecs[1].result == (DatumSpec{2u, atype::BOOL}));
94
95 REQUIRE(hspecs[2].left == (DatumSpec{std::string{"phi"}, 2, atype::FLOAT}));
96 REQUIRE(hspecs[2].right == (DatumSpec{LiteralNode::var_t{0}, atype::INT32}));
97 REQUIRE(hspecs[2].result == (DatumSpec{1u, atype::BOOL}));
98
99 expressions::Filter u = nabs(nodes::eta) < 1.0 && nexp(nodes::phi + 2.0 * M_PI) > 3.0;
100 auto uspecs = createOperations(std::move(u));
101 REQUIRE(uspecs[0].left == (DatumSpec{1u, atype::BOOL}));
102 REQUIRE(uspecs[0].right == (DatumSpec{2u, atype::BOOL}));
103 REQUIRE(uspecs[0].result == (DatumSpec{0u, atype::BOOL}));
104
105 REQUIRE(uspecs[1].left == (DatumSpec{3u, atype::DOUBLE}));
106 REQUIRE(uspecs[1].right == (DatumSpec{LiteralNode::var_t{3.0}, atype::DOUBLE}));
107 REQUIRE(uspecs[1].result == (DatumSpec{2u, atype::BOOL}));
108
109 REQUIRE(uspecs[2].left == (DatumSpec{4u, atype::DOUBLE}));
110 REQUIRE(uspecs[2].right == (DatumSpec{}));
111 REQUIRE(uspecs[2].result == (DatumSpec{3u, atype::DOUBLE}));
112
113 REQUIRE(uspecs[3].left == (DatumSpec{std::string{"phi"}, 2, atype::FLOAT}));
114 REQUIRE(uspecs[3].right == (DatumSpec{LiteralNode::var_t{2.0 * M_PI}, atype::DOUBLE}));
115 REQUIRE(uspecs[3].result == (DatumSpec{4u, atype::DOUBLE}));
116
117 REQUIRE(uspecs[4].left == (DatumSpec{5u, atype::FLOAT}));
118 REQUIRE(uspecs[4].right == (DatumSpec{LiteralNode::var_t{1.0}, atype::DOUBLE}));
119 REQUIRE(uspecs[4].result == (DatumSpec{1u, atype::BOOL}));
120
121 REQUIRE(uspecs[5].left == (DatumSpec{std::string{"eta"}, 3, atype::FLOAT}));
122 REQUIRE(uspecs[5].right == (DatumSpec{}));
123 REQUIRE(uspecs[5].result == (DatumSpec{5u, atype::FLOAT}));
124
125 Configurable<float> pTCut{"pTCut", 0.5f, "Lower pT limit"};
126 Filter ptfilter = o2::aod::track::pt > pTCut;
127 REQUIRE(ptfilter.node->self.index() == 2);
128 REQUIRE(ptfilter.node->left->self.index() == 1);
129 REQUIRE(ptfilter.node->right->self.index() == 3);
130 auto ptfilterspecs = createOperations(ptfilter);
131 REQUIRE(ptfilterspecs[0].left == (DatumSpec{std::string{"fPt"}, "o2::aod::track::pt"_h, atype::FLOAT}));
132 REQUIRE(ptfilterspecs[0].right == (DatumSpec{LiteralNode::var_t{0.5f}, atype::FLOAT}));
133 REQUIRE(ptfilterspecs[0].result == (DatumSpec{0u, atype::BOOL}));
134
135 struct : ConfigurableGroup {
136 std::string prefix = "prefix";
137 Configurable<float> pTCut{"pTCut", 1.0f, "Lower pT limit"};
138 } group;
139 Filter ptfilter2 = o2::aod::track::pt > group.pTCut;
140 group.pTCut.name.insert(0, 1, '.');
141 group.pTCut.name.insert(0, group.prefix);
142 REQUIRE(ptfilter2.node->self.index() == 2);
143 REQUIRE(ptfilter2.node->left->self.index() == 1);
144 REQUIRE(ptfilter2.node->right->self.index() == 3);
145 REQUIRE(std::get<PlaceholderNode>(ptfilter2.node->right->self).name == "prefix.pTCut");
146 auto ptfilterspecs2 = createOperations(ptfilter2);
147 REQUIRE(ptfilterspecs2[0].left == (DatumSpec{std::string{"fPt"}, "o2::aod::track::pt"_h, atype::FLOAT}));
148 REQUIRE(ptfilterspecs2[0].right == (DatumSpec{LiteralNode::var_t{1.0f}, atype::FLOAT}));
149 REQUIRE(ptfilterspecs2[0].result == (DatumSpec{0u, atype::BOOL}));
150
151 Configurable<int> cvalue{"cvalue", 1, "test value"};
152 Filter testFilter = o2::aod::track::tpcNClsShared < as<uint8_t>(cvalue);
153 REQUIRE(testFilter.node->self.index() == 2);
154 REQUIRE(testFilter.node->left->self.index() == 1);
155 REQUIRE(testFilter.node->right->self.index() == 3);
156 REQUIRE(std::get<PlaceholderNode>(testFilter.node->right->self).name == "cvalue");
157 auto testSpecs = createOperations(testFilter);
158 REQUIRE(testSpecs[0].right == (DatumSpec{LiteralNode::var_t{(uint8_t)1}, atype::UINT8}));
159}
160
161TEST_CASE("TestGandivaTreeCreation")
162{
163 Projector pze = o2::aod::track::Pze::Projector();
164 auto pzspecs = createOperations(pze);
165 REQUIRE(pzspecs[0].left == (DatumSpec{std::string{"fTgl"}, "o2::aod::track::tgl"_h, atype::FLOAT}));
166 REQUIRE(pzspecs[0].right == (DatumSpec{1u, atype::FLOAT}));
167 REQUIRE(pzspecs[0].result == (DatumSpec{0u, atype::FLOAT}));
168
169 REQUIRE(pzspecs[1].left == (DatumSpec{LiteralNode::var_t{1.f}, atype::FLOAT}));
170 REQUIRE(pzspecs[1].right == (DatumSpec{std::string{"fSigned1Pt"}, "o2::aod::track::signed1Pt"_h, atype::FLOAT}));
171 REQUIRE(pzspecs[1].result == (DatumSpec{1u, atype::FLOAT}));
172 auto infield1 = o2::aod::track::Signed1Pt::asArrowField();
173 auto infield2 = o2::aod::track::Tgl::asArrowField();
174 auto resfield = o2::aod::track::Pze::asArrowField();
175 auto schema = std::make_shared<arrow::Schema>(std::vector{infield1, infield2, resfield});
176 auto gandiva_tree = createExpressionTree(pzspecs, schema);
177
178 auto gandiva_expression = makeExpression(gandiva_tree, resfield);
179 REQUIRE(std::string(gandiva_expression->ToString()) == std::string("float multiply((float) fTgl, float divide((const float) 1 raw(3f800000), (float) fSigned1Pt))"));
180 auto projector = createProjector(schema, pzspecs, resfield);
181
182 Projector pte = o2::aod::track::Pt::Projector();
183 auto ptespecs = createOperations(pte);
184
185 auto infield3 = o2::aod::track::Signed1Pt::asArrowField();
186 auto resfield2 = o2::aod::track::Pt::asArrowField();
187 auto schema2 = std::make_shared<arrow::Schema>(std::vector{infield3, resfield2});
188 auto gandiva_tree2 = createExpressionTree(ptespecs, schema2);
189
190 auto gandiva_expression2 = makeExpression(gandiva_tree2, resfield2);
191 REQUIRE(gandiva_expression2->ToString() == "if (bool less_than_or_equal_to(float absf((float) fSigned1Pt), (const float) 1.17549e-38 raw(800000))) { (const float) 8.50706e+37 raw(7e800000) } else { float absf(float divide((const float) 1 raw(3f800000), (float) fSigned1Pt)) }");
192
193 auto projector_b = createProjector(schema2, ptespecs, resfield2);
194 auto fields = o2::soa::createFieldsFromColumns(o2::aod::Tracks::persistent_columns_t{});
195 auto schema_p = std::make_shared<arrow::Schema>(fields);
197
198 Filter bitwiseFilter = (o2::aod::track::flags & static_cast<uint32_t>(o2::aod::track::TPCrefit)) != 0u;
199 auto bwf = createOperations(bitwiseFilter);
200 REQUIRE(bwf[0].left == (DatumSpec{1u, atype::UINT32}));
201 REQUIRE(bwf[0].right == (DatumSpec{LiteralNode::var_t{0u}, atype::UINT32}));
202 REQUIRE(bwf[0].result == (DatumSpec{0u, atype::BOOL}));
203
204 REQUIRE(bwf[1].left == (DatumSpec{std::string{"fFlags"}, "o2::aod::track::flags"_h, atype::UINT32}));
205 REQUIRE(bwf[1].right == (DatumSpec{LiteralNode::var_t{static_cast<uint32_t>(o2::aod::track::TPCrefit)}, atype::UINT32}));
206 REQUIRE(bwf[1].result == (DatumSpec{1u, atype::UINT32}));
207
208 auto infield4 = o2::aod::track::Flags::asArrowField();
209 auto resfield3 = std::make_shared<arrow::Field>("out", arrow::boolean());
210 auto schema_b = std::make_shared<arrow::Schema>(std::vector{infield4, resfield3});
211 auto gandiva_tree3 = createExpressionTree(bwf, schema_b);
212 REQUIRE(gandiva_tree3->ToString() == "bool not_equal(uint32 bitwise_and((uint32) fFlags, (const uint32) 2), (const uint32) 0)");
213 auto condition = expressions::makeCondition(gandiva_tree3);
214 std::shared_ptr<gandiva::Filter> flt;
215 auto s = gandiva::Filter::Make(schema_b, condition, &flt);
216 REQUIRE(s.ok());
217
218 Filter rounding = nround(o2::aod::track::pt) > 0.1f;
219 auto rf = createOperations(rounding);
220 REQUIRE(rf[0].left == (DatumSpec{1u, atype::FLOAT}));
221 REQUIRE(rf[0].right == (DatumSpec{LiteralNode::var_t{0.1f}, atype::FLOAT}));
222 REQUIRE(rf[0].result == (DatumSpec{0u, atype::BOOL}));
223
224 REQUIRE(rf[1].left == (DatumSpec{std::string{"fPt"}, "o2::aod::track::pt"_h, atype::FLOAT}));
225 REQUIRE(rf[1].right == (DatumSpec{}));
226 REQUIRE(rf[1].result == (DatumSpec{1u, atype::FLOAT}));
227
228 auto infield5 = o2::aod::track::Pt::asArrowField();
229 auto resfield4 = std::make_shared<arrow::Field>("out", arrow::boolean());
230 auto schema_c = std::make_shared<arrow::Schema>(std::vector{infield5, resfield4});
231 auto gandiva_tree4 = createExpressionTree(rf, schema_c);
232 REQUIRE(gandiva_tree4->ToString() == "bool greater_than(float round((float) fPt), (const float) 0.1 raw(3dcccccd))");
233 auto condition2 = expressions::makeCondition(gandiva_tree4);
234 std::shared_ptr<gandiva::Filter> flt2;
235 auto s2 = gandiva::Filter::Make(schema_c, condition2, &flt2);
236 REQUIRE(s2.ok());
237}
238
239TEST_CASE("TestConditionalExpressions")
240{
241 // simple conditional
242 Filter cf = nabs(o2::aod::track::eta) < 1.0f && ifnode((o2::aod::track::pt < 1.0f), (o2::aod::track::phi > (float)(M_PI / 2.)), (o2::aod::track::phi < (float)(M_PI / 2.)));
243 auto cfspecs = createOperations(cf);
244 REQUIRE(cfspecs[0].left == (DatumSpec{1u, atype::BOOL}));
245 REQUIRE(cfspecs[0].right == (DatumSpec{2u, atype::BOOL}));
246 REQUIRE(cfspecs[0].result == (DatumSpec{0u, atype::BOOL}));
247
248 REQUIRE(cfspecs[1].left == (DatumSpec{3u, atype::BOOL}));
249 REQUIRE(cfspecs[1].right == (DatumSpec{4u, atype::BOOL}));
250 REQUIRE(cfspecs[1].condition == (DatumSpec{5u, atype::BOOL}));
251 REQUIRE(cfspecs[1].result == (DatumSpec{2u, atype::BOOL}));
252
253 REQUIRE(cfspecs[2].left == (DatumSpec{std::string{"fPt"}, "o2::aod::track::pt"_h, atype::FLOAT}));
254 REQUIRE(cfspecs[2].right == (DatumSpec{LiteralNode::var_t{1.0f}, atype::FLOAT}));
255 REQUIRE(cfspecs[2].result == (DatumSpec{5u, atype::BOOL}));
256
257 REQUIRE(cfspecs[3].left == (DatumSpec{std::string{"fPhi"}, "o2::aod::track::phi"_h, atype::FLOAT}));
258 REQUIRE(cfspecs[3].right == (DatumSpec{LiteralNode::var_t{(float)(M_PI / 2.)}, atype::FLOAT}));
259 REQUIRE(cfspecs[3].result == (DatumSpec{4u, atype::BOOL}));
260
261 REQUIRE(cfspecs[4].left == (DatumSpec{std::string{"fPhi"}, "o2::aod::track::phi"_h, atype::FLOAT}));
262 REQUIRE(cfspecs[4].right == (DatumSpec{LiteralNode::var_t{(float)(M_PI / 2.)}, atype::FLOAT}));
263 REQUIRE(cfspecs[4].result == (DatumSpec{3u, atype::BOOL}));
264
265 REQUIRE(cfspecs[5].left == (DatumSpec{6u, atype::FLOAT}));
266 REQUIRE(cfspecs[5].right == (DatumSpec{LiteralNode::var_t{1.0f}, atype::FLOAT}));
267 REQUIRE(cfspecs[5].result == (DatumSpec{1u, atype::BOOL}));
268
269 REQUIRE(cfspecs[6].left == (DatumSpec{std::string{"fEta"}, "o2::aod::track::eta"_h, atype::FLOAT}));
270 REQUIRE(cfspecs[6].right == (DatumSpec{}));
271 REQUIRE(cfspecs[6].result == (DatumSpec{6u, atype::FLOAT}));
272
273 auto infield1 = o2::aod::track::Pt::asArrowField();
274 auto infield2 = o2::aod::track::Eta::asArrowField();
275 auto infield3 = o2::aod::track::Phi::asArrowField();
276 auto schema = std::make_shared<arrow::Schema>(std::vector{infield1, infield2, infield3});
277 auto gandiva_tree = createExpressionTree(cfspecs, schema);
278 auto gandiva_condition = makeCondition(gandiva_tree);
279 auto gandiva_filter = createFilter(schema, gandiva_condition);
280
281 REQUIRE(gandiva_tree->ToString() == "bool less_than(float absf((float) fEta), (const float) 1 raw(3f800000)) && if (bool less_than((float) fPt, (const float) 1 raw(3f800000))) { bool greater_than((float) fPhi, (const float) 1.5708 raw(3fc90fdb)) } else { bool less_than((float) fPhi, (const float) 1.5708 raw(3fc90fdb)) }");
282
283 // nested conditional
284 Filter cfn = o2::aod::track::signed1Pt > 0.f && ifnode(std::move(*cf.node), nabs(o2::aod::track::x) > 1.0f, nabs(o2::aod::track::y) > 1.0f);
285 auto cfnspecs = createOperations(cfn);
286 auto infield4 = o2::aod::track::Signed1Pt::asArrowField();
287 auto infield5 = o2::aod::track::X::asArrowField();
288 auto infield6 = o2::aod::track::Y::asArrowField();
289 auto schema2 = std::make_shared<arrow::Schema>(std::vector{infield1, infield2, infield3, infield4, infield5, infield6});
290 auto gandiva_tree2 = createExpressionTree(cfnspecs, schema2);
291 auto gandiva_condition2 = makeCondition(gandiva_tree2);
292 auto gandiva_filter2 = createFilter(schema2, gandiva_condition2);
293 REQUIRE(gandiva_tree2->ToString() == "bool greater_than((float) fSigned1Pt, (const float) 0 raw(0)) && if (bool less_than(float absf((float) fEta), (const float) 1 raw(3f800000)) && if (bool less_than((float) fPt, (const float) 1 raw(3f800000))) { bool greater_than((float) fPhi, (const float) 1.5708 raw(3fc90fdb)) } else { bool less_than((float) fPhi, (const float) 1.5708 raw(3fc90fdb)) }) { bool greater_than(float absf((float) fX), (const float) 1 raw(3f800000)) } else { bool greater_than(float absf((float) fY), (const float) 1 raw(3f800000)) }");
294
295 // clamp
296 Projector clp = clamp(o2::aod::track::pt, 1.0f, 10.f);
297 auto clpspecs = createOperations(clp);
298 auto schemaclp = std::make_shared<arrow::Schema>(std::vector{o2::aod::track::Pt::asArrowField()});
299 auto gandiva_tree_clp = createExpressionTree(clpspecs, schemaclp);
300 REQUIRE(gandiva_tree_clp->ToString() == "if (bool less_than((float) fPt, (const float) 1 raw(3f800000))) { (const float) 1 raw(3f800000) } else { if (bool greater_than((float) fPt, (const float) 10 raw(41200000))) { (const float) 10 raw(41200000) } else { (float) fPt } }");
301}
302
303TEST_CASE("TestBinnedExpressions")
304{
305 std::vector<float> bins{0.5, 1.5, 2.5, 3.5, 4.5};
306 std::vector<float> params{1.0, 1.1, 1.2, 1.3, 2.0, 2.1, 2.2, 2.3, 3.0, 3.1, 3.2, 3.3, 4.0, 4.1, 4.2, 4.3};
307 Projector p = binned(bins, params, o2::aod::track::pt, par(0) * o2::aod::track::x + par(1) * o2::aod::track::y + par(2) * o2::aod::track::z + par(3) * o2::aod::track::phi, LiteralNode{0.f});
308 auto pspecs = createOperations(p);
309 auto schema = std::make_shared<arrow::Schema>(std::vector{o2::aod::track::Pt::asArrowField(), o2::aod::track::X::asArrowField(), o2::aod::track::Y::asArrowField(), o2::aod::track::Z::asArrowField(), o2::aod::track::Phi::asArrowField()});
310 auto tree = createExpressionTree(pspecs, schema);
311 REQUIRE(tree->ToString() == "if (bool less_than((float) fPt, (const float) 0.5 raw(3f000000))) { (const float) 0 raw(0) } else { if (bool less_than((float) fPt, (const float) 1.5 raw(3fc00000))) { float add(float add(float add(float multiply((const float) 1 raw(3f800000), (float) fX), float multiply((const float) 2 raw(40000000), (float) fY)), float multiply((const float) 3 raw(40400000), (float) fZ)), float multiply((const float) 4 raw(40800000), (float) fPhi)) } else { if (bool less_than((float) fPt, (const float) 2.5 raw(40200000))) { float add(float add(float add(float multiply((const float) 1.1 raw(3f8ccccd), (float) fX), float multiply((const float) 2.1 raw(40066666), (float) fY)), float multiply((const float) 3.1 raw(40466666), (float) fZ)), float multiply((const float) 4.1 raw(40833333), (float) fPhi)) } else { if (bool less_than((float) fPt, (const float) 3.5 raw(40600000))) { float add(float add(float add(float multiply((const float) 1.2 raw(3f99999a), (float) fX), float multiply((const float) 2.2 raw(400ccccd), (float) fY)), float multiply((const float) 3.2 raw(404ccccd), (float) fZ)), float multiply((const float) 4.2 raw(40866666), (float) fPhi)) } else { if (bool less_than((float) fPt, (const float) 4.5 raw(40900000))) { float add(float add(float add(float multiply((const float) 1.3 raw(3fa66666), (float) fX), float multiply((const float) 2.3 raw(40133333), (float) fY)), float multiply((const float) 3.3 raw(40533333), (float) fZ)), float multiply((const float) 4.3 raw(4089999a), (float) fPhi)) } else { (const float) 0 raw(0) } } } } }");
312
314 std::vector<float> parameters{1.0, 1.1, 1.2, 1.3, // par 0
315 2.0, 2.1, 2.2, 2.3, // par 1
316 3.0, 3.1, 3.2, 3.3, // par 2
317 4.0, 4.1, 4.2, 4.3}; // par 3
318
319 Projector p2 = binned((std::vector<float>)binning,
320 (std::vector<float>)parameters,
321 o2::aod::track::phi, par(0) * o2::aod::track::x * o2::aod::track::x + par(1) * o2::aod::track::y * o2::aod::track::y + par(2) * o2::aod::track::z * o2::aod::track::z,
322 LiteralNode{-1.f});
323 auto p2specs = createOperations(p2);
324 auto schema2 = std::make_shared<arrow::Schema>(std::vector{o2::aod::track::Phi::asArrowField(), o2::aod::track::X::asArrowField(), o2::aod::track::Y::asArrowField(), o2::aod::track::Z::asArrowField()});
325 auto tree2 = createExpressionTree(p2specs, schema2);
326 REQUIRE(tree2->ToString() == "if (bool less_than((float) fPhi, (const float) 0 raw(0))) { (const float) -1 raw(bf800000) } else { if (bool less_than((float) fPhi, (const float) 1.5708 raw(3fc90fdb))) { float add(float add(float multiply(float multiply((const float) 1 raw(3f800000), (float) fX), (float) fX), float multiply(float multiply((const float) 2 raw(40000000), (float) fY), (float) fY)), float multiply(float multiply((const float) 3 raw(40400000), (float) fZ), (float) fZ)) } else { if (bool less_than((float) fPhi, (const float) 3.14159 raw(40490fdb))) { float add(float add(float multiply(float multiply((const float) 1.1 raw(3f8ccccd), (float) fX), (float) fX), float multiply(float multiply((const float) 2.1 raw(40066666), (float) fY), (float) fY)), float multiply(float multiply((const float) 3.1 raw(40466666), (float) fZ), (float) fZ)) } else { if (bool less_than((float) fPhi, (const float) 4.71239 raw(4096cbe4))) { float add(float add(float multiply(float multiply((const float) 1.2 raw(3f99999a), (float) fX), (float) fX), float multiply(float multiply((const float) 2.2 raw(400ccccd), (float) fY), (float) fY)), float multiply(float multiply((const float) 3.2 raw(404ccccd), (float) fZ), (float) fZ)) } else { if (bool less_than((float) fPhi, (const float) 6.28319 raw(40c90fdb))) { float add(float add(float multiply(float multiply((const float) 1.3 raw(3fa66666), (float) fX), (float) fX), float multiply(float multiply((const float) 2.3 raw(40133333), (float) fY), (float) fY)), float multiply(float multiply((const float) 3.3 raw(40533333), (float) fZ), (float) fZ)) } else { (const float) -1 raw(bf800000) } } } } }");
327}
328
330{
331 int token;
332 while ((token = t.nextToken()) && (token != Token::EoL)) {
333 std::cout << t.TokenStr << " ";
334 };
335 std::cout << std::endl;
336}
337
338TEST_CASE("TestStringExpressionsParsing")
339{
340 Filter f = (o2::aod::track::flags & 1u) != 0u && (o2::aod::track::pt <= 10.f);
341 std::string input = "(o2::aod::track::flags & 1u) != 0u && (o2::aod::track::pt <= 10.f)";
342
343 auto t1 = createOperations(f);
344 Filter ff = Parser::parse(input);
345 auto t2 = createOperations(ff);
346
347 auto schema = std::make_shared<arrow::Schema>(std::vector{o2::aod::track::Flags::asArrowField(), o2::aod::track::Pt::asArrowField()});
348 auto tree1 = createExpressionTree(t1, schema);
349 auto tree2 = createExpressionTree(t2, schema);
350
351 REQUIRE(tree1->ToString() == tree2->ToString());
352
353 Projector p = -1.f * nlog(ntan(o2::constants::math::PIQuarter - 0.5f * natan(o2::aod::fwdtrack::tgl)));
354 input = "-1.f * nlog(ntan(PIQuarter - 0.5f * natan(o2::aod::fwdtrack::tgl)))";
355
356 auto tp1 = createOperations(p);
357 Projector pp = Parser::parse(input);
358 auto tp2 = createOperations(pp);
359
360 schema = std::make_shared<arrow::Schema>(std::vector{o2::aod::fwdtrack::Tgl::asArrowField()});
361 auto treep1 = createExpressionTree(tp1, schema);
362 auto treep2 = createExpressionTree(tp2, schema);
363
364 REQUIRE(treep1->ToString() == treep2->ToString());
365
366 Filter f2 = o2::aod::track::signed1Pt > 0.f && ifnode(nabs(o2::aod::track::eta) < 1.0f, nabs(o2::aod::track::x) > 2.0f, nabs(o2::aod::track::y) > 3.0f);
367 input = "o2::aod::track::signed1Pt > 0.f && ifnode(nabs(o2::aod::track::eta) < 1.0f, nabs(o2::aod::track::x) > 2.0f, nabs(o2::aod::track::y) > 3.0f)";
368
369 auto tf1 = createOperations(f2);
370 Filter ff2 = Parser::parse(input);
371 auto tf2 = createOperations(ff2);
372
373 schema = std::make_shared<arrow::Schema>(std::vector{o2::aod::track::Eta::asArrowField(), o2::aod::track::Signed1Pt::asArrowField(), o2::aod::track::X::asArrowField(), o2::aod::track::Y::asArrowField()});
374 auto treef1 = createExpressionTree(tf1, schema);
375 auto treef2 = createExpressionTree(tf2, schema);
376
377 REQUIRE(treef1->ToString() == treef2->ToString());
378
379 Configurable<float> pTCut{"pTCut", 0.5f, "Lower pT limit"};
380 Filter pcfg1 = o2::aod::track::pt > pTCut;
381 Filter pcfg2 = Parser::parse("o2::aod::track::pt > ncfg(float, 0.5, \"pTCut\")");
382 auto pcfg1specs = createOperations(pcfg1);
383 auto pcfg2specs = createOperations(pcfg2);
384
385 REQUIRE(pcfg2.node->right->self.index() == 3);
386 REQUIRE(pcfg2specs[0].right == (DatumSpec{LiteralNode::var_t{0.5f}, atype::FLOAT}));
387
388 schema = std::make_shared<arrow::Schema>(std::vector{o2::aod::track::Pt::asArrowField()});
389 auto tree1c = createExpressionTree(pcfg1specs, schema);
390 auto tree2c = createExpressionTree(pcfg2specs, schema);
391
392 REQUIRE(tree1c->ToString() == tree2c->ToString());
393}
#define DECLARE_SOA_EXPRESSION_COLUMN(_Name_, _Getter_, _Type_, _Expression_)
Definition ASoA.h:2469
const auto bins
Definition PID.cxx:49
constexpr int p2()
Class for time synchronization of RawReader instances.
GLuint64EXT * result
Definition glcorearb.h:5662
GLdouble GLdouble right
Definition glcorearb.h:4077
GLdouble f
Definition glcorearb.h:310
GLenum const GLfloat * params
Definition glcorearb.h:272
GLboolean GLuint group
Definition glcorearb.h:3991
GLboolean GLboolean g
Definition glcorearb.h:1233
GLenum clamp
Definition glcorearb.h:1245
GLuint GLfloat GLfloat GLfloat GLfloat GLfloat GLfloat GLfloat GLfloat GLfloat t1
Definition glcorearb.h:5034
constexpr float TwoPI
constexpr float PI
constexpr float PIQuarter
constexpr float PIHalf
std::shared_ptr< gandiva::Filter > createFilter(gandiva::SchemaPtr const &Schema, gandiva::ConditionPtr condition)
Function to create gandiva filter from gandiva condition.
gandiva::ExpressionPtr makeExpression(gandiva::NodePtr node, gandiva::FieldPtr result)
Function to create gandiva projecting expression from generic gandiva expression tree.
Node par(int index)
Parameters.
Operations createOperations(Filter const &expression)
Function to create an internal operation sequence from a filter tree.
gandiva::ConditionPtr makeCondition(gandiva::NodePtr node)
Function to create gandiva condition expression from generic gandiva expression tree.
Node ifnode(Node &&condition_, Node &&then_, Node &&else_)
conditionals
gandiva::NodePtr createExpressionTree(Operations const &opSpecs, gandiva::SchemaPtr const &Schema)
Function to create gandiva expression tree from operation sequence.
Node binned(std::vector< T > const &binning, std::vector< T > const &parameters, Node &&binned, Node &&pexp, Node &&out)
binned functional
std::shared_ptr< gandiva::Projector > createProjector(gandiva::SchemaPtr const &Schema, Operations const &opSpecs, gandiva::FieldPtr result)
Function to create gandiva projector from operation sequence.
std::shared_ptr< gandiva::Projector > createProjectors(framework::pack< C... >, std::vector< std::shared_ptr< arrow::Field > > const &fields, gandiva::SchemaPtr schema)
Defining PrimaryVertex explicitly as messageable.
Definition TFIDInfo.h:20
TEST_CASE("test_prepareArguments")
auto createFieldsFromColumns(framework::pack< C... >)
Definition ASoA.h:410
An expression tree node corresponding to a column binding.
A struct, containing the root of the expression tree.
std::unique_ptr< Node > node
An expression tree node corresponding to a literal value.
LiteralValue::stored_type var_t
static Node parse(std::string const &input)
void printTokens(Tokenizer &t)
std::unique_ptr< TTree > tree((TTree *) flIn.Get(std::string(o2::base::NameConf::CTFTREENAME).c_str()))