Logo ROOT  
Reference Guide
 
Loading...
Searching...
No Matches
RAction.hxx
Go to the documentation of this file.
1// Author: Enrico Guiraud, Danilo Piparo CERN 09/2018
2
3/*************************************************************************
4 * Copyright (C) 1995-2020, Rene Brun and Fons Rademakers. *
5 * All rights reserved. *
6 * *
7 * For the licensing terms see $ROOTSYS/LICENSE. *
8 * For the list of contributors see $ROOTSYS/README/CREDITS. *
9 *************************************************************************/
10
11#ifndef ROOT_RACTION
12#define ROOT_RACTION
13
18#include "ROOT/RDF/Utils.hxx" // ColumnNames_t, IsInternalColumn
20
21#include <array>
22#include <cstddef> // std::size_t
23#include <memory>
24#include <string>
25#include <vector>
26
27namespace ROOT {
28namespace Internal {
29namespace RDF {
30
33
34namespace GraphDrawing {
35std::shared_ptr<GraphNode> AddDefinesToGraph(std::shared_ptr<GraphNode> node,
36 const RDFInternal::RBookedDefines &defines,
37 const std::vector<std::string> &prevNodeDefines);
38} // namespace GraphDrawing
39
40// clang-format off
41/**
42 * \class ROOT::Internal::RDF::RAction
43 * \ingroup dataframe
44 * \brief A RDataFrame node that produces a result
45 * \tparam Helper The action helper type, which implements the concrete action logic (e.g. FillHelper, SnapshotHelper)
46 * \tparam PrevDataFrame The type of the parent node in the computation graph
47 * \tparam ColumnTypes_t A TypeList with the types of the input columns
48 *
49 */
50// clang-format on
51template <typename Helper, typename PrevDataFrame, typename ColumnTypes_t = typename Helper::ColumnTypes_t>
52class R__CLING_PTRCHECK(off) RAction : public RActionBase {
53 using TypeInd_t = std::make_index_sequence<ColumnTypes_t::list_size>;
54
55 Helper fHelper;
56 const std::shared_ptr<PrevDataFrame> fPrevDataPtr;
57 PrevDataFrame &fPrevData;
58 /// Column readers per slot and per input column
59 std::vector<std::array<std::unique_ptr<RColumnReaderBase>, ColumnTypes_t::list_size>> fValues;
60
61 /// The nth flag signals whether the nth input column is a custom column or not.
62 std::array<bool, ColumnTypes_t::list_size> fIsDefine;
63
64public:
65 RAction(Helper &&h, const ColumnNames_t &columns, std::shared_ptr<PrevDataFrame> pd, const RBookedDefines &defines)
66 : RActionBase(pd->GetLoopManagerUnchecked(), columns, defines), fHelper(std::forward<Helper>(h)),
67 fPrevDataPtr(std::move(pd)), fPrevData(*fPrevDataPtr), fValues(GetNSlots()), fIsDefine()
68 {
69 const auto nColumns = columns.size();
70 const auto &customCols = GetDefines();
71 for (auto i = 0u; i < nColumns; ++i)
72 fIsDefine[i] = customCols.HasName(columns[i]);
73 }
74
75 RAction(const RAction &) = delete;
76 RAction &operator=(const RAction &) = delete;
77 // must call Deregister here, before fPrevDataFrame is destroyed,
78 // otherwise if fPrevDataFrame is fLoopManager we get a use after delete
79 ~RAction() { fLoopManager->Deregister(this); }
80
81 /**
82 Retrieve a wrapper to the result of the action that knows how to merge
83 with others of the same type.
84 */
85 std::unique_ptr<RDFDetail::RMergeableValueBase> GetMergeableValue() const final
86 {
87 return fHelper.GetMergeableValue();
88 }
89
90 void Initialize() final { fHelper.Initialize(); }
91
92 void InitSlot(TTreeReader *r, unsigned int slot) final
93 {
94 for (auto &bookedBranch : GetDefines().GetColumns())
95 bookedBranch.second->InitSlot(r, slot);
96 RDFInternal::RColumnReadersInfo info{RActionBase::GetColumnNames(), RActionBase::GetDefines(), fIsDefine.data(),
97 fLoopManager->GetDSValuePtrs(), fLoopManager->GetDataSource()};
98 fValues[slot] = RDFInternal::MakeColumnReaders(slot, r, ColumnTypes_t{}, info);
99 fHelper.InitTask(r, slot);
100 }
101
102 template <typename... ColTypes, std::size_t... S>
103 void CallExec(unsigned int slot, Long64_t entry, TypeList<ColTypes...>, std::index_sequence<S...>)
104 {
105 fHelper.Exec(slot, fValues[slot][S]->template Get<ColTypes>(entry)...);
106 (void)entry; // avoid "unused parameter" warnings
107 }
108
109 void Run(unsigned int slot, Long64_t entry) final
110 {
111 // check if entry passes all filters
112 if (fPrevData.CheckFilters(slot, entry))
113 CallExec(slot, entry, ColumnTypes_t{}, TypeInd_t{});
114 }
115
116 void TriggerChildrenCount() final { fPrevData.IncrChildrenCount(); }
117
118 /// Clean-up operations to be performed at the end of a task.
119 void FinalizeSlot(unsigned int slot) final
120 {
121 for (auto &column : GetDefines().GetColumns())
122 column.second->FinaliseSlot(slot);
123 for (auto &v : fValues[slot])
124 v.reset();
125 fHelper.CallFinalizeTask(slot);
126 }
127
128 /// Clean-up and finalize the action result (e.g. merging slot-local results).
129 /// It invokes the helper's Finalize method.
130 void Finalize() final
131 {
132 fHelper.Finalize();
133 SetHasRun();
134 }
135
136 std::shared_ptr<RDFGraphDrawing::GraphNode> GetGraph()
137 {
138 auto prevNode = fPrevData.GetGraph();
139 auto prevColumns = prevNode->GetDefinedColumns();
140
141 // Action nodes do not need to go through CreateFilterNode: they are never common nodes between multiple branches
142 auto thisNode = std::make_shared<RDFGraphDrawing::GraphNode>(fHelper.GetActionName());
143
144 auto upmostNode = AddDefinesToGraph(thisNode, GetDefines(), prevColumns);
145
146 thisNode->AddDefinedColumns(GetDefines().GetNames());
147 thisNode->SetAction(HasRun());
148 upmostNode->SetPrevNode(prevNode);
149 return thisNode;
150 }
151
152 /// This method is invoked to update a partial result during the event loop, right before passing the result to a
153 /// user-defined callback registered via RResultPtr::RegisterCallback
154 void *PartialUpdate(unsigned int slot) final { return PartialUpdateImpl(slot); }
155
156 std::function<void(unsigned int)> GetDataBlockCallback() final { return fHelper.GetDataBlockCallback(); }
157
158private:
159 // this overload is SFINAE'd out if Helper does not implement `PartialUpdate`
160 // the template parameter is required to defer instantiation of the method to SFINAE time
161 template <typename H = Helper>
162 auto PartialUpdateImpl(unsigned int slot) -> decltype(std::declval<H>().PartialUpdate(slot), (void *)(nullptr))
163 {
164 return &fHelper.PartialUpdate(slot);
165 }
166
167 // this one is always available but has lower precedence thanks to `...`
168 void *PartialUpdateImpl(...) { throw std::runtime_error("This action does not support callbacks!"); }
169};
170
171} // namespace RDF
172} // namespace Internal
173} // namespace ROOT
174
175#endif // ROOT_RACTION
ROOT::R::TRInterface & r
Definition Object.C:4
#define h(i)
Definition RSha256.hxx:106
long long Long64_t
Definition RtypesCore.h:73
typedef void((*Func_t)())
A RDataFrame node that produces a result.
Definition RAction.hxx:52
void Run(unsigned int slot, Long64_t entry) final
Definition RAction.hxx:109
auto PartialUpdateImpl(unsigned int slot) -> decltype(std::declval< H >().PartialUpdate(slot),(void *)(nullptr))
Definition RAction.hxx:162
const std::shared_ptr< PrevDataFrame > fPrevDataPtr
Definition RAction.hxx:56
void CallExec(unsigned int slot, Long64_t entry, TypeList< ColTypes... >, std::index_sequence< S... >)
Definition RAction.hxx:103
void FinalizeSlot(unsigned int slot) final
Clean-up operations to be performed at the end of a task.
Definition RAction.hxx:119
RAction & operator=(const RAction &)=delete
PrevDataFrame & fPrevData
Definition RAction.hxx:57
void * PartialUpdate(unsigned int slot) final
This method is invoked to update a partial result during the event loop, right before passing the res...
Definition RAction.hxx:154
std::make_index_sequence< ColumnTypes_t::list_size > TypeInd_t
Definition RAction.hxx:53
std::array< bool, ColumnTypes_t::list_size > fIsDefine
The nth flag signals whether the nth input column is a custom column or not.
Definition RAction.hxx:62
std::unique_ptr< RDFDetail::RMergeableValueBase > GetMergeableValue() const final
Retrieve a wrapper to the result of the action that knows how to merge with others of the same type.
Definition RAction.hxx:85
std::vector< std::array< std::unique_ptr< RColumnReaderBase >, ColumnTypes_t::list_size > > fValues
Column readers per slot and per input column.
Definition RAction.hxx:59
void Finalize() final
Clean-up and finalize the action result (e.g.
Definition RAction.hxx:130
std::function< void(unsigned int)> GetDataBlockCallback() final
Definition RAction.hxx:156
void InitSlot(TTreeReader *r, unsigned int slot) final
Definition RAction.hxx:92
RAction(const RAction &)=delete
void TriggerChildrenCount() final
Definition RAction.hxx:116
RAction(Helper &&h, const ColumnNames_t &columns, std::shared_ptr< PrevDataFrame > pd, const RBookedDefines &defines)
Definition RAction.hxx:65
std::shared_ptr< RDFGraphDrawing::GraphNode > GetGraph()
Definition RAction.hxx:136
Encapsulates the columns defined by the user.
A simple, robust and fast interface to read values from ROOT columnar datasets such as TTree,...
Definition TTreeReader.h:44
std::vector< std::string > ColumnNames_t
std::shared_ptr< GraphNode > AddDefinesToGraph(std::shared_ptr< GraphNode > node, const RDFInternal::RBookedDefines &defines, const std::vector< std::string > &prevNodeDefines)
Add the Defines that have been added between this node and the previous to the graph.
unsigned int GetNSlots()
Definition RDFUtils.cxx:286
std::array< std::unique_ptr< RDFDetail::RColumnReaderBase >, sizeof...(ColTypes)> MakeColumnReaders(unsigned int slot, TTreeReader *r, TypeList< ColTypes... >, const RColumnReadersInfo &colInfo)
Create a group of column readers, one per type in the parameter pack.
tbb::task_arena is an alias of tbb::interface7::task_arena, which doesn't allow to forward declare tb...
This type aggregates some of the arguments passed to InitColumnReaders.
Lightweight storage for a collection of types.