Fastest way to sum values of one branch

What is the fastest way to sum all the values of one branch? What I am doing know is:

TH1F h("h", "h", 1, 1, 2);
chain->Draw("branchname>>h", "", "goff");
h.GetMean() * h.GetEntries()

This works, but it is doing much more than what I need.

Second question: Is there a general reduce function to apply recursively?

f(f(f(f(x0, x1), x2), x3), ..., xn)

in my case f(a, b) -> a + b

I would imagine that the fastest way would be to disable all the branches except the ones you need, then write a small loop that does chain->GetEntry() and adds the branch value to a variable. That also doesn’t put the values into bins like your method does.

Jean-François

[quote=“jfcaron”]I would imagine that the fastest way would be to disable all the branches except the ones you need, then write a small loop that does chain->GetEntry() and adds the branch value to a variable. That also doesn’t put the values into bins like your method does.

Jean-François[/quote]

Yes, thank you. By the way I don’t need only a fast computation, but also a fast code to be written. Writing an explicit loop, linking variables with SetBranchAddress, manually accumulate, … is very verbose for this simple problem.

[quote=“wiso”]Second question: Is there a general reduce function to apply recursively?

f(f(f(f(x0, x1), x2), x3), ..., xn)

in my case f(a, b) -> a + b[/quote]

Is it somehow a ROOT-related question? May be something like std::accumulate/std::inner_product can help (though they work with sequences)?
C++ is not a functional programming language, so you have to clarify what do you understand as ‘reduce function to apply recursively’. Oh, and accumulate/inner_product both contains iteration under the hood instead of recursion you want.

P.S. Ah, and if you were asking about something TTree-related, please ignore my reply, since I understood your question as a general C++ question :slight_smile: (though why not write your own TTreeIterator which works as an input iterator (C++ iterator category)) :slight_smile:)) .

And about ‘too much code’ - with ROOT 6 we have new classes in $ROOTSYS/tree/treeplayer - TTreeReader and others who intend to significantly improve/simplify work with trees. I’m not sure if they are documented already in a ROOT user’s guide, but probably, you can have a look

[quote=“tpochep”][quote=“wiso”]Second question: Is there a general reduce function to apply recursively?

f(f(f(f(x0, x1), x2), x3), ..., xn)

in my case f(a, b) -> a + b[/quote]

Is it somehow a ROOT-related question? May be something like std::accumulate/std::inner_product can help (though they work with sequences)?
C++ is not a functional programming language, so you have to clarify what do you understand as ‘reduce function to apply recursively’. Oh, and accumulate/inner_product both contains iteration under the hood instead of recursion you want.
[/quote]

C++ is not a functional programming language, but you can use functional programming pattern in C++, in fact std::accumulate does what I need, but I would like to have it directly in the TTree, for example:

tree->reduce("my_branch ** 2", function)

where function is what you prefer: TF1, functor, *function, lambda, … for example

float function(float a, float b) {return a + b; }

I can dump the content of a branch in a std::vector and then use std::transform, std::accumulate, but I need to dump everything in memory and it is not necessary.

[quote]
P.S. Ah, and if you were asking about something TTree-related, please ignore my reply, since I understood your question as a general C++ question :slight_smile: (though why not write your own TTreeIterator which works as an input iterator (C++ iterator category)) :slight_smile:)) .

And about ‘too much code’ - with ROOT 6 we have new classes in $ROOTSYS/tree/treeplayer - TTreeReader and others who intend to significantly improve/simplify work with trees. I’m not sure if they are documented already in a ROOT user’s guide, but probably, you can have a look[/quote]

thank you. I am curious to see it.

Well, I guess you can easily implement such a general reduce yourself, right? All you need is - somehow wrap the code for quite low-level SetBranchAddress/GetBranch/etc. into something type-safe and more robust (and here we have TTreeReader I believe :slight_smile: ) + functors or whatever (some people also like C++11 lambdas :slight_smile: )

I have the same question and my solution is a variant of yours. Instead of filling the histogram with branch values, fill the histogram with a fixed value (within the bin boundaries) and use the branch values as weights:

chain->Draw(" 1.5 >>h", “branchname”, “goff”);
double sum = h->GetBinContent(1)

Isn’t

RDataFrame DF
DF.Sum(“column”)
What you look for ?

In 2021: yes

1 Like