@@ -65,21 +65,18 @@ concept is_enumeration = is_enumeration_v<std::decay_t<T>>;
6565// the contents of an AnalysisTask...
6666namespace {
6767struct AnalysisDataProcessorBuilder {
68- template <typename G, typename ... Args>
69- static void addGroupingCandidates (std::vector<StringPair> & bk, std::vector<StringPair> & bku)
68+ template <soa::is_iterator G, typename ... Args>
69+ static void addGroupingCandidates (Cache & bk, Cache & bku, bool enabled )
7070 {
71- [&bk, &bku]<typename ... As>(framework::pack<As...>) mutable {
72- std::string key;
73- if constexpr (soa::is_iterator<std::decay_t <G>>) {
74- key = std::string{" fIndex" } + o2::framework::cutString (soa::getLabelFromType<std::decay_t <G>>());
75- }
76- ([&bk, &bku, &key]() mutable {
71+ [&bk, &bku, enabled]<typename ... As>(framework::pack<As...>) mutable {
72+ auto key = std::string{" fIndex" } + o2::framework::cutString (soa::getLabelFromType<std::decay_t <G>>());
73+ ([&bk, &bku, &key, enabled]() mutable {
7774 if constexpr (soa::relatedByIndex<std::decay_t <G>, std::decay_t <As>>()) {
7875 auto binding = soa::getLabelFromTypeForKey<std::decay_t <As>>(key);
7976 if constexpr (o2::soa::is_smallgroups<std::decay_t <As>>) {
80- framework::updatePairList (bku, binding, key);
77+ framework::updatePairList (bku, binding, key, enabled );
8178 } else {
82- framework::updatePairList (bk, binding, key);
79+ framework::updatePairList (bk, binding, key, enabled );
8380 }
8481 }
8582 }(),
@@ -145,34 +142,72 @@ struct AnalysisDataProcessorBuilder {
145142 }
146143
147144 // / helper to parse the process arguments
145+ template <typename T>
146+ inline static bool requestInputsFromArgs (T&, std::string const &, std::vector<InputSpec>&, std::vector<ExpressionInfo>&)
147+ {
148+ return false ;
149+ }
150+ template <is_process_configurable T>
151+ inline static bool requestInputsFromArgs (T& pc, std::string const & name, std::vector<InputSpec>& inputs, std::vector<ExpressionInfo>& eis)
152+ {
153+ AnalysisDataProcessorBuilder::inputsFromArgs (pc.process , (name + " /" + pc.name ).c_str (), pc.value , inputs, eis);
154+ return true ;
155+ }
156+ template <typename T>
157+ inline static bool requestCacheFromArgs (T&, Cache&, Cache&)
158+ {
159+ return false ;
160+ }
161+ template <is_process_configurable T>
162+ inline static bool requestCacheFromArgs (T& pc, Cache& bk, Cache& bku)
163+ {
164+ AnalysisDataProcessorBuilder::cacheFromArgs (pc.process , pc.value , bk, bku);
165+ return true ;
166+ }
148167 // / 1. enumeration (must be the only argument)
149168 template <typename R, typename C, is_enumeration A>
150- static void inputsFromArgs (R (C::*)(A), const char* /* name*/ , bool /* value*/ , std::vector<InputSpec>& inputs, std::vector<ExpressionInfo>&, std::vector<StringPair> &, std::vector<StringPair> &)
169+ static void inputsFromArgs (R (C::*)(A), const char* /* name*/ , bool /* value*/ , std::vector<InputSpec>& inputs, std::vector<ExpressionInfo>&) // , Cache &, Cache &)
151170 {
152171 std::vector<ConfigParamSpec> inputMetadata;
153172 // FIXME: for the moment we do not support begin, end and step.
154173 DataSpecUtils::updateInputList (inputs, InputSpec{" enumeration" , " DPL" , " ENUM" , 0 , Lifetime::Enumeration, inputMetadata});
155174 }
156175
157- // / 2. grouping case - 1st argument is an iterator
176+ // / 2. 1st argument is an iterator
158177 template <typename R, typename C, soa::is_iterator A, soa::is_table... Args>
159- static void inputsFromArgs (R (C::*)(A, Args...), const char* name, bool value, std::vector<InputSpec>& inputs, std::vector<ExpressionInfo>& eInfos, std::vector<StringPair> & bk, std::vector<StringPair> & bku)
178+ static void inputsFromArgs (R (C::*)(A, Args...), const char* name, bool value, std::vector<InputSpec>& inputs, std::vector<ExpressionInfo>& eInfos) // , Cache & bk, Cache & bku)
160179 requires(std::is_lvalue_reference_v<A> && (std::is_lvalue_reference_v<Args> && ...))
161180 {
162- addGroupingCandidates<A, Args...>(bk, bku);
163181 constexpr auto hash = o2::framework::TypeIdHelpers::uniqueId<R (C::*)(A, Args...)>();
164182 addInputsAndExpressions<typename std::decay_t <A>::parent_t , Args...>(hash, name, value, inputs, eInfos);
165183 }
166184
167185 // / 3. generic case
168186 template <typename R, typename C, soa::is_table... Args>
169- static void inputsFromArgs (R (C::*)(Args...), const char* name, bool value, std::vector<InputSpec>& inputs, std::vector<ExpressionInfo>& eInfos, std::vector<StringPair> &, std::vector<StringPair> &)
187+ static void inputsFromArgs (R (C::*)(Args...), const char* name, bool value, std::vector<InputSpec>& inputs, std::vector<ExpressionInfo>& eInfos) // , Cache &, Cache &)
170188 requires(std::is_lvalue_reference_v<Args> && ...)
171189 {
172190 constexpr auto hash = o2::framework::TypeIdHelpers::uniqueId<R (C::*)(Args...)>();
173191 addInputsAndExpressions<Args...>(hash, name, value, inputs, eInfos);
174192 }
175193
194+ // / 1. enumeration (no grouping)
195+ template <typename R, typename C, is_enumeration A>
196+ static void cacheFromArgs (R (C::*)(A), bool, Cache&, Cache&)
197+ {
198+ }
199+ // / 2. iterator (the only grouping case)
200+ template <typename R, typename C, soa::is_iterator A, soa::is_table... Args>
201+ static void cacheFromArgs (R (C::*)(A, Args...), bool value, Cache& bk, Cache& bku)
202+ {
203+ addGroupingCandidates<A, Args...>(bk, bku, value);
204+ }
205+ // / 3. generic case (no grouping)
206+ template <typename R, typename C, soa::is_table A, soa::is_table... Args>
207+ static void cacheFromArgs (R (C::*)(A, Args...), bool, Cache&, Cache&)
208+ {
209+ }
210+
176211 template <soa::TableRef R>
177212 static auto extractTableFromRecord (InputRecord& record)
178213 {
@@ -480,8 +515,6 @@ DataProcessorSpec adaptAnalysisTask(ConfigContext const& ctx, Args&&... args)
480515 std::vector<InputSpec> inputs;
481516 std::vector<ConfigParamSpec> options;
482517 std::vector<ExpressionInfo> expressionInfos;
483- std::vector<StringPair> bindingsKeys;
484- std::vector<StringPair> bindingsKeysUnsorted;
485518
486519 // / make sure options and configurables are set before expression infos are created
487520 homogeneous_apply_refs ([&options, &hash](auto & element) { return analysis_task_parsers::appendOption (options, element); }, *task.get ());
@@ -490,23 +523,15 @@ DataProcessorSpec adaptAnalysisTask(ConfigContext const& ctx, Args&&... args)
490523
491524 // / parse process functions defined by corresponding configurables
492525 if constexpr (requires { &T::process; }) {
493- AnalysisDataProcessorBuilder::inputsFromArgs (&T::process, " default" , true , inputs, expressionInfos, bindingsKeys, bindingsKeysUnsorted );
526+ AnalysisDataProcessorBuilder::inputsFromArgs (&T::process, " default" , true , inputs, expressionInfos);
494527 }
495528 homogeneous_apply_refs (
496- overloaded{
497- [name = name_str, &expressionInfos, &inputs, &bindingsKeys, &bindingsKeysUnsorted](framework::is_process_configurable auto & x) mutable {
498- // this pushes (argumentIndex,processHash,schemaPtr,nullptr) into expressionInfos for arguments that are Filtered/filtered_iterators
499- AnalysisDataProcessorBuilder::inputsFromArgs (x.process , (name + " /" + x.name ).c_str (), x.value , inputs, expressionInfos, bindingsKeys, bindingsKeysUnsorted);
500- return true ;
501- },
502- [](auto &) {
503- return false ;
504- }},
529+ [name = name_str, &expressionInfos, &inputs](auto & x) mutable {
530+ // this pushes (argumentIndex, processHash, schemaPtr, nullptr) into expressionInfos for arguments that are Filtered/filtered_iterators
531+ return AnalysisDataProcessorBuilder::requestInputsFromArgs (x, name, inputs, expressionInfos);
532+ },
505533 *task.get ());
506534
507- // add preslice declarations to slicing cache definition
508- homogeneous_apply_refs ([&bindingsKeys, &bindingsKeysUnsorted](auto & element) { return analysis_task_parsers::registerCache (element, bindingsKeys, bindingsKeysUnsorted); }, *task.get ());
509-
510535 // request base tables for spawnable extended tables and indices to be built
511536 // this checks for duplications
512537 homogeneous_apply_refs ([&inputs](auto & element) {
@@ -526,7 +551,12 @@ DataProcessorSpec adaptAnalysisTask(ConfigContext const& ctx, Args&&... args)
526551 requiredServices.insert (requiredServices.end (), arrowServices.begin (), arrowServices.end ());
527552 homogeneous_apply_refs ([&requiredServices](auto & element) { return analysis_task_parsers::addService (requiredServices, element); }, *task.get ());
528553
529- auto algo = AlgorithmSpec::InitCallback{[task = task, expressionInfos, bindingsKeys, bindingsKeysUnsorted](InitContext& ic) mutable {
554+ auto algo = AlgorithmSpec::InitCallback{[task = task, expressionInfos](InitContext& ic) mutable {
555+ Cache bindingsKeys;
556+ Cache bindingsKeysUnsorted;
557+ // add preslice declarations to slicing cache definition
558+ homogeneous_apply_refs ([&bindingsKeys, &bindingsKeysUnsorted](auto & element) { return analysis_task_parsers::registerCache (element, bindingsKeys, bindingsKeysUnsorted); }, *task.get ());
559+
530560 homogeneous_apply_refs ([&ic](auto && element) { return analysis_task_parsers::prepareOption (ic, element); }, *task.get ());
531561 homogeneous_apply_refs ([&ic](auto && element) { return analysis_task_parsers::prepareService (ic, element); }, *task.get ());
532562
@@ -556,6 +586,16 @@ DataProcessorSpec adaptAnalysisTask(ConfigContext const& ctx, Args&&... args)
556586 task->init (ic);
557587 }
558588
589+ // / parse process functions to enable requested grouping caches - note that at this state process configurables have their final values
590+ if constexpr (requires { &T::process; }) {
591+ AnalysisDataProcessorBuilder::cacheFromArgs (&T::process, true , bindingsKeys, bindingsKeysUnsorted);
592+ }
593+ homogeneous_apply_refs (
594+ [&bindingsKeys, &bindingsKeysUnsorted](auto & x) mutable {
595+ return AnalysisDataProcessorBuilder::requestCacheFromArgs (x, bindingsKeys, bindingsKeysUnsorted);
596+ },
597+ *task.get ());
598+
559599 ic.services ().get <ArrowTableSlicingCacheDef>().setCaches (std::move (bindingsKeys));
560600 ic.services ().get <ArrowTableSlicingCacheDef>().setCachesUnsorted (std::move (bindingsKeysUnsorted));
561601 // initialize global caches
0 commit comments