Project
Loading...
Searching...
No Matches
test_AnalysisTask.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
12#include "Mocking.h"
13#include "TestClasses.h"
16#include <iostream>
17
18#include <catch_amalgamated.hpp>
19
20using namespace o2;
21using namespace o2::framework;
22
23namespace o2::aod
24{
25O2HASH("TestA/0");
26namespace test
27{
33DECLARE_SOA_COLUMN(EventProperty, eventProperty, float);
34DECLARE_SOA_DYNAMIC_COLUMN(Sum, sum, [](float x, float y) { return x + y; });
35DECLARE_SOA_EXPRESSION_COLUMN(Sqfoo, sqfoo, float, nsqrt(test::foo));
36} // namespace test
37
38DECLARE_SOA_TABLE(Foos, "AOD", "FOO",
39 test::Foo);
40DECLARE_SOA_EXTENDED_TABLE(Fooss, Foos, "FOOS", 0, test::Sqfoo);
41DECLARE_SOA_TABLE(Bars, "AOD", "BAR",
42 test::Bar);
43DECLARE_SOA_TABLE(FooBars, "AOD", "FOOBAR",
44 test::Foo, test::Bar,
45 test::Sum<test::Foo, test::Bar>);
46DECLARE_SOA_TABLE(XYZ, "AOD", "XYZ",
47 test::X, test::Y, test::Z);
48DECLARE_SOA_TABLE(Events, "AOD", "EVENTS",
49 test::EventProperty);
50
51DECLARE_SOA_TABLE(Roots, "AOD", "ROOTS", test::Foo);
52
53namespace idx
54{
56}
57
58DECLARE_SOA_TABLE(B1s, "AOD", "B1", idx::RootId, test::X);
59DECLARE_SOA_TABLE(B2s, "AOD", "B2", idx::RootId, test::Y);
60DECLARE_SOA_TABLE(B3s, "AOD", "B3", idx::RootId, test::Z);
61
62namespace idx
63{
67} // namespace idx
68
69DECLARE_SOA_INDEX_TABLE(Bs, Roots, "BS", idx::RootId, idx::B1Id, idx::B2Id, idx::B3Id);
70
71} // namespace o2::aod
72
73struct ATask {
75
77 {
78 }
79};
80
87
88struct BTask {
89 void process(o2::aod::Collision const&, o2::soa::Join<o2::aod::Tracks, o2::aod::TracksExtra, o2::aod::TracksCov> const&, o2::aod::AmbiguousTracks const&, o2::aod::Calos const&, o2::aod::CaloTriggers const&)
90 {
91 }
92};
93
94struct CTask {
95 void process(o2::aod::Collision const&, o2::aod::Tracks const&)
96 {
97 }
98};
99
100struct DTask {
101 void process(o2::aod::Tracks const&)
102 {
103 }
104};
105
106struct ETask {
107 void process(o2::aod::FooBars::iterator const& foobar)
108 {
109 foobar.sum();
110 }
111};
112
113struct FTask {
114 expressions::Filter fooFilter = aod::test::foo > 1.;
116 {
117 foobar.sum();
118 }
119};
120
121struct GTask {
123 {
124 for (auto foobar : foobars) {
125 foobar.x();
126 foobar.foo();
127 foobar.bar();
128 }
129 }
130};
131
132struct HTask {
134 {
135 foobar.x();
136 foobar.foo();
137 foobar.bar();
138 }
139};
140
141struct ITask {
142 expressions::Filter flt = aod::test::bar > 0.;
144 {
145 for (auto foobar : foobars) {
146 foobar.x();
147 foobar.foo();
148 foobar.bar();
149 }
150 }
151};
152
153struct JTask {
154 Configurable<o2::test::SimplePODClass> cfg{"someConfigurable", {}, "Some Configurable Object"};
156 {
157 REQUIRE(cfg->x == 1);
158 }
159};
160
163};
164
165struct KTask {
166 struct : public ConfigurableGroup {
167 std::string prefix = "foo";
168 Configurable<int> anInt{"someConfigurable", {}, "Some Configurable Object"};
169 Configurable<int> anotherInt{"someOtherConfigurable", {}, "Some Configurable Object"};
171
172 Configurable<int> anThirdInt{"someThirdConfigurable", {}, "Some Configurable Object"};
173 struct : public ConditionGroup {
176 std::unique_ptr<int> someInt;
177 std::shared_ptr<int> someSharedInt;
178};
179
188
189struct MTask {
191 struct : public PresliceGroup {
192 Preslice<aod::Tracks> perCol = aod::track::collisionId;
193 PresliceOptional<aod::Tracks> perPart = aod::mctracklabel::mcParticleId;
194 PresliceUnsorted<aod::McCollisionLabels> perMcCol = aod::mccollisionlabel::mcCollisionId;
195 PresliceUnsortedOptional<aod::Collisions> perMcColopt = aod::mccollisionlabel::mcCollisionId;
198};
199
200TEST_CASE("AdaptorCompilation")
201{
202 auto cfgc = makeEmptyConfigContext();
203
204 REQUIRE(brace_constructible_size<ATask>() == 1);
205 auto task1ng = adaptAnalysisTask<ATask>(*cfgc, TaskName{"test1"});
206 REQUIRE(task1ng.inputs.size() == 2);
207 REQUIRE(task1ng.outputs.size() == 1);
208 REQUIRE(task1ng.inputs[1].binding == std::string("TracksExtension"));
209 REQUIRE(task1ng.inputs[0].binding == std::string("Tracks"));
210 REQUIRE(task1ng.outputs[0].binding.value == std::string("FooBars"));
211
212 auto task1ngc = adaptAnalysisTask<ATaskconsumer>(*cfgc);
213 REQUIRE(task1ngc.inputs.size() == 5);
214 REQUIRE(task1ngc.inputs[0].binding == "Foos");
215 REQUIRE(task1ngc.inputs[1].binding == "Roots");
216 REQUIRE(task1ngc.inputs[2].binding == "B1s");
217 REQUIRE(task1ngc.inputs[3].binding == "B2s");
218 REQUIRE(task1ngc.inputs[4].binding == "B3s");
219
220 auto task2 = adaptAnalysisTask<BTask>(*cfgc, TaskName{"test2"});
221 REQUIRE(task2.inputs.size() == 10);
222 REQUIRE(task2.inputs[2].binding == "TracksExtension");
223 REQUIRE(task2.inputs[1].binding == "Tracks");
224 REQUIRE(task2.inputs[4].binding == "TracksExtra_002Extension");
225 REQUIRE(task2.inputs[3].binding == "TracksExtra");
226 REQUIRE(task2.inputs[6].binding == "TracksCovExtension");
227 REQUIRE(task2.inputs[5].binding == "TracksCov");
228 REQUIRE(task2.inputs[7].binding == "AmbiguousTracks");
229 REQUIRE(task2.inputs[8].binding == "Calos");
230 REQUIRE(task2.inputs[9].binding == "CaloTriggers");
231 REQUIRE(task2.inputs[0].binding == "Collisions_001");
232
233 auto task3 = adaptAnalysisTask<CTask>(*cfgc, TaskName{"test3"});
234 REQUIRE(task3.inputs.size() == 3);
235 REQUIRE(task3.inputs[0].binding == "Collisions_001");
236 REQUIRE(task3.inputs[1].binding == "Tracks");
237 REQUIRE(task3.inputs[2].binding == "TracksExtension");
238
239 auto task4 = adaptAnalysisTask<DTask>(*cfgc, TaskName{"test4"});
240 REQUIRE(task4.inputs.size() == 2);
241 REQUIRE(task4.inputs[0].binding == "Tracks");
242 REQUIRE(task4.inputs[1].binding == "TracksExtension");
243
244 auto task5 = adaptAnalysisTask<ETask>(*cfgc, TaskName{"test5"});
245 REQUIRE(task5.inputs.size() == 1);
246 REQUIRE(task5.inputs[0].binding == "FooBars");
247
248 auto task6ng = adaptAnalysisTask<FTask>(*cfgc, TaskName{"test6"});
249 REQUIRE(task6ng.inputs.size() == 1);
250 REQUIRE(task6ng.inputs[0].binding == "FooBars");
251
252 auto task7ng = adaptAnalysisTask<GTask>(*cfgc, TaskName{"test7"});
253 REQUIRE(task7ng.inputs.size() == 3);
254 REQUIRE(task7ng.inputs[0].binding == "Foos");
255 REQUIRE(task7ng.inputs[1].binding == "Bars");
256 REQUIRE(task7ng.inputs[2].binding == "XYZ");
257
258 auto task8ng = adaptAnalysisTask<HTask>(*cfgc, TaskName{"test8"});
259 REQUIRE(task8ng.inputs.size() == 3);
260
261 auto task9ng = adaptAnalysisTask<ITask>(*cfgc, TaskName{"test9"});
262 REQUIRE(task9ng.inputs.size() == 4);
263
264 auto task10 = adaptAnalysisTask<JTask>(*cfgc, TaskName{"test10"});
265 REQUIRE(task10.inputs.size() == 1);
266
267 auto task11 = adaptAnalysisTask<KTask>(*cfgc, TaskName{"test11"});
268 REQUIRE(task11.options.size() == 3);
269 REQUIRE(task11.inputs.size() == 1);
270
271 auto task12 = adaptAnalysisTask<LTask>(*cfgc, TaskName{"test12"});
272 REQUIRE(task12.inputs.size() == 3);
273
274 auto task13 = adaptAnalysisTask<MTask>(*cfgc, TaskName{"test13"});
275 REQUIRE(task13.inputs.size() == 3);
276}
277
278TEST_CASE("TestPartitionIteration")
279{
280 TableBuilder builderA;
281 auto rowWriterA = builderA.persist<float, float>({"fX", "fY"});
282 rowWriterA(0, 0.0f, 8.0f);
283 rowWriterA(0, 1.0f, 9.0f);
284 rowWriterA(0, 2.0f, 10.0f);
285 rowWriterA(0, 3.0f, 11.0f);
286 rowWriterA(0, 4.0f, 12.0f);
287 rowWriterA(0, 5.0f, 13.0f);
288 rowWriterA(0, 6.0f, 14.0f);
289 rowWriterA(0, 7.0f, 15.0f);
290 auto tableA = builderA.finalize();
291 REQUIRE(tableA->num_rows() == 8);
292
293 using TestA = soa::InPlaceTable<"TestA/0"_h, o2::soa::Index<>, aod::test::X, aod::test::Y>;
294 using FilteredTest = o2::soa::Filtered<TestA>;
295 using PartitionTest = Partition<TestA>;
296 using PartitionFilteredTest = Partition<o2::soa::Filtered<TestA>>;
297 using PartitionNestedFilteredTest = Partition<o2::soa::Filtered<o2::soa::Filtered<TestA>>>;
298 using namespace o2::framework;
299
300 TestA testA{tableA};
301
302 PartitionTest p1 = aod::test::x < 4.0f;
303 p1.bindTable(testA);
304 REQUIRE(4 == p1.size());
305 REQUIRE(p1.begin() != p1.end());
306 auto i = 0;
307 for (auto& p : p1) {
308 REQUIRE(i == p.x());
309 REQUIRE(i + 8 == p.y());
310 REQUIRE(i == p.index());
311 i++;
312 }
313 REQUIRE(i == 4);
314
315 expressions::Filter f1 = aod::test::x < 4.0f;
316 auto selection = expressions::createSelection(testA.asArrowTable(), f1);
317 FilteredTest filtered{{testA.asArrowTable()}, o2::soa::selectionToVector(selection)};
318 PartitionFilteredTest p2 = aod::test::y > 9.0f;
319 p2.bindTable(filtered);
320
321 REQUIRE(2 == p2.size());
322 i = 0;
323 for (auto& p : p2) {
324 REQUIRE(i + 2 == p.x());
325 REQUIRE(i + 10 == p.y());
326 REQUIRE(i + 2 == p.index());
327 i++;
328 }
329 REQUIRE(i == 2);
330
331 PartitionNestedFilteredTest p3 = aod::test::x < 3.0f;
332 p3.bindTable(*(p2.mFiltered));
333 REQUIRE(1 == p3.size());
334 i = 0;
335 for (auto& p : p3) {
336 REQUIRE(i + 2 == p.x());
337 REQUIRE(i + 10 == p.y());
338 REQUIRE(i + 2 == p.index());
339 i++;
340 }
341 REQUIRE(i == 1);
342}
#define O2HASH(_Str_)
Pre-declare Hash specialization for a generic string.
Definition ASoA.h:277
#define DECLARE_SOA_DYNAMIC_COLUMN(_Name_, _Getter_,...)
Definition ASoA.h:3044
#define DECLARE_SOA_TABLE(_Name_, _Origin_, _Desc_,...)
Definition ASoA.h:3130
#define DECLARE_SOA_EXPRESSION_COLUMN(_Name_, _Getter_, _Type_, _Expression_)
Definition ASoA.h:2429
#define DECLARE_SOA_COLUMN(_Name_, _Getter_, _Type_)
Definition ASoA.h:2355
#define DECLARE_SOA_INDEX_COLUMN(_Name_, _Getter_)
Definition ASoA.h:2812
#define DECLARE_SOA_EXTENDED_TABLE(_Name_, _Table_, _Description_, _Version_,...)
Definition ASoA.h:3172
#define DECLARE_SOA_INDEX_TABLE(_Name_, _Key_, _Description_,...)
Definition ASoA.h:3230
int32_t i
const GPUTPCGMMerger::trackCluster & b1
constexpr int p2()
constexpr int p1()
constexpr to accelerate the coordinates changing
std::unique_ptr< ConfigContext > makeEmptyConfigContext()
auto persist(std::array< char const *, sizeof...(ARGS)+1 > const &columnNames)
std::shared_ptr< arrow::Table > finalize()
T::template iterator_template_o< FilteredIndexPolicy, self_t > iterator
Definition ASoA.h:3659
float sum(float s, o2::dcs::DataPointValue v)
Definition dcs-ccdb.cxx:39
GLint GLenum GLint x
Definition glcorearb.h:403
GLint y
Definition glcorearb.h:270
GLdouble GLdouble GLdouble z
Definition glcorearb.h:843
McCollisions::iterator McCollision
Tracks::iterator Track
Collisions::iterator Collision
gandiva::Selection createSelection(std::shared_ptr< arrow::Table > const &table, Filter const &expression)
Function for creating gandiva selection from our internal filter tree.
Defining PrimaryVertex explicitly as messageable.
Definition TFIDInfo.h:20
SelectionVector selectionToVector(gandiva::Selection const &sel)
Definition ASoA.cxx:43
a couple of static helper functions to create timestamp values for CCDB queries or override obsolete ...
FIXME: do not use data model tables.
void process(o2::aod::Track const &)
Produces< aod::FooBars > foobars
void init(InitContext &)
Spawns< aod::Fooss > foos
Builds< aod::Bs > bs
void process(o2::aod::Collision const &, o2::soa::Join< o2::aod::Tracks, o2::aod::TracksExtra, o2::aod::TracksCov > const &, o2::aod::AmbiguousTracks const &, o2::aod::Calos const &, o2::aod::CaloTriggers const &)
void process(o2::aod::Collision const &, o2::aod::Tracks const &)
void process(o2::aod::Tracks const &)
void process(o2::aod::FooBars::iterator const &foobar)
void process(soa::Filtered< o2::aod::FooBars >::iterator const &foobar)
expressions::Filter fooFilter
void process(o2::soa::Join< o2::aod::Foos, o2::aod::Bars, o2::aod::XYZ > const &foobars)
void process(o2::soa::Join< o2::aod::Foos, o2::aod::Bars, o2::aod::XYZ >::iterator const &foobar)
expressions::Filter flt
void process(o2::aod::Collision const &, o2::soa::Filtered< o2::soa::Join< o2::aod::Foos, o2::aod::Bars, o2::aod::XYZ > > const &foobars)
Configurable< o2::test::SimplePODClass > cfg
void process(o2::aod::Collision const &)
Configurable< int > anInt
std::unique_ptr< int > someInt
Configurable< int > anThirdInt
std::shared_ptr< int > someSharedInt
Configurable< int > anotherInt
std::string prefix
SliceCache cache
void process(aod::McCollision const &, soa::SmallGroups< soa::Join< aod::Collisions, aod::McCollisionLabels > > const &)
PresliceUnsorted< aod::McCollisionLabels > perMcCol
Preslice< aod::Tracks > perCol
PresliceOptional< aod::Tracks > perPart
PresliceUnsortedOptional< aod::Collisions > perMcColopt
PresliceUnsorted< aod::McCollisionLabels > perMcCol
PresliceUnsortedOptional< aod::Collisions > perMcColopt
Preslice< aod::Tracks > perCol
SliceCache cache
void process(aod::McCollision const &, soa::SmallGroups< soa::Join< aod::Collisions, aod::McCollisionLabels > > const &)
PresliceOptional< aod::Tracks > perPart
Struct to differentiate task names from possible task string arguments.
A struct, containing the root of the expression tree.
table_t::template iterator_template< DefaultIndexPolicy, self_t, Ts... > iterator
Definition ASoA.h:3267
TEST_CASE("AdaptorCompilation")
HistogramRegistry foo()