23#include "TCollection.h"
73template <
class TemplateArray>
81 LOGF(warning,
"StepTHn: Requesting more than 250M bins (%lld). This will need extensive memory.",
mNBins);
83 mPrototype =
new THnSparseT<TemplateArray>(Form(
"%s_sparse",
name), title, nAxes, nBins, xmin, xmax);
86template <
class TemplateArray>
88 Int_t* nBins, std::vector<Double_t> binEdges[],
const char** axisTitles) :
StepTHn(
name, title, nSteps, nAxes)
95 LOGF(warning,
"StepTHn: Requesting more than 250M bins (%lld). This will need extensive memory.",
mNBins);
97 mPrototype =
new THnSparseT<TemplateArray>(Form(
"%s_sparse",
name), title, nAxes, nBins);
100 if (nBins[
i] + 1 == binEdges[
i].
size()) {
102 }
else if (binEdges[
i].
size() == 2) {
103 mPrototype->GetAxis(
i)->Set(nBins[
i], binEdges[
i][0], binEdges[
i][1]);
105 LOGF(fatal,
"Invalid binning information for axis %d with %d bins and %d entries for bin edges",
i, nBins[
i], binEdges[
i].
size());
107 LOGF(
debug,
"Histogram %s Axis %d created with %d bins and %d edges",
name,
i, nBins[
i], binEdges[
i].
size());
128 mValues(new TArray*[
c.mNSteps]),
129 mSumw2(new TArray*[
c.mNSteps]),
132 mNbinsCache(nullptr),
228template <
class TemplateArray>
238 if (list->IsEmpty()) {
242 TIterator* iter = list->MakeIterator();
246 while ((obj = iter->Next())) {
249 if (
entry ==
nullptr) {
253 for (Int_t
i = 0;
i < mNSteps;
i++) {
256 mValues[
i] = createArray();
259 auto source =
dynamic_cast<TemplateArray*
>(
entry->mValues[
i])->GetArray();
260 auto target =
dynamic_cast<TemplateArray*
>(mValues[
i])->GetArray();
261 for (Long64_t l = 0; l < mNBins; l++) {
268 mSumw2[
i] = createArray();
271 auto source =
dynamic_cast<TemplateArray*
>(
entry->mSumw2[
i])->GetArray();
272 auto target =
dynamic_cast<TemplateArray*
>(mSumw2[
i])->GetArray();
273 for (Long64_t l = 0; l < mNBins; l++) {
294 bin += binIdx[
i] - 1;
305 LOGF(fatal,
"Histogram request for step %d which is empty.", step);
322 TArray* sourceSumw2 =
source;
324 sourceSumw2 =
mSumw2[step];
328 mTarget[step] = THnSparse::CreateSparse(Form(
"%s_%d", GetName(), step), Form(
"%s_%d", GetTitle(), step),
mPrototype);
330 mTarget[step] = THn::CreateHn(Form(
"%s_%d", GetName(), step), Form(
"%s_%d", GetTitle(), step),
mPrototype);
338 Int_t* binIdx =
new Int_t[
mNVars];
339 Int_t* nBins =
new Int_t[
mNVars];
342 nBins[
j] =
target->GetAxis(
j)->GetNbins();
358 target->SetBinError(binIdx, TMath::Sqrt(sourceSumw2->GetAt(globalBin)));
366 if (binIdx[
j] > nBins[
j]) {
372 if (binIdx[0] > nBins[0]) {
389 LOGF(fatal,
"Selected step for filling is not in range of StepTHn.");
393 if (nParams ==
mNVars + 1) {
395 }
else if (nParams !=
mNVars) {
396 LOGF(fatal,
"Fill called with invalid number of parameters (%d vs %d)",
mNVars, nParams);
415 if (lut.edges && lut.xmax > lut.xmin) {
417 Double_t slotWidth = (lut.xmax - lut.xmin) /
kLookupSize;
418 lut.invSlotWidth = 1.0 / slotWidth;
420 Double_t
x = lut.xmin + (
s + 0.5) * slotWidth;
426 lut.invSlotWidth = lut.xmax > lut.xmin ? lut.nBins / (lut.xmax - lut.xmin) : 0;
450 Double_t
x = positionAndWeight[
i];
459 tmpBin = 1 +
static_cast<Int_t
>(std::floor(rawBin));
460 if (tmpBin >= 1 && tmpBin <= lut.nBins) {
464 Double_t binWidth = (lut.xmax - lut.xmin) / lut.nBins;
465 Double_t upperEdge = lut.xmin + tmpBin * binWidth;
466 if (
x >= upperEdge && tmpBin < lut.nBins) {
472 }
else if (tmpBin > lut.nBins) {
473 tmpBin = lut.nBins + 1;
477 Int_t slot =
static_cast<Int_t
>((
x - lut.xmin) * lut.invSlotWidth);
479 tmpBin = (slot < 0) ? 0 : lut.nBins + 1;
481 tmpBin = lut.table[slot];
484 while (tmpBin > 1 &&
x < lut.edges[tmpBin - 1]) {
488 while (tmpBin < lut.nBins && x >= lut.edges[tmpBin]) {
Timeframe settings Average distance in cm of events merged into Randomize distance around average distance of merged events Simulate correct bunch interactions instead of placing only the average number of events A value[n] sets TFlen for[n] collisions in Number of bunches per trainsort Number of bunch trains Instantaneous interaction rate Do not simulate border Total number of collisions to be placed in the interior of all time Do not select random but walk over array of events in stride steps h Event generator settings h configStandalone Use CPU for GPU Force usage of the specified GPU device no CPU fallback Continue processing after an error s
templateClassImp(StepTHnT)
Long64_t Merge(TCollection *list) override
Double_t * mLastVars
cache Nbins per axis
Int_t * mLastBins
caching of last used bins (in many loops some vars are the same for a while)
void Fill(int iStep, const Ts &... valuesAndWeight)
TAxis ** mAxisCache
target histogram
Long64_t getGlobalBinIndex(const Int_t *binIdx)
StepTHn & operator=(const StepTHn &corr)
virtual TArray * createArray(const TArray *src=nullptr) const =0
Int_t * mNbinsCache
cache axis pointers (about 50% of the time in Fill is spent in GetAxis otherwise)
virtual void updateBin(int iStep, Long64_t bin, double weight)=0
void createTarget(Int_t step, Bool_t sparse)
THnSparse * mPrototype
per-axis lookup tables
void Copy(TObject &c) const override
static constexpr Int_t kLookupSize
caching of last used bins (in many loops some vars are the same for a while)
GLuint const GLchar * name
GLuint GLuint GLfloat weight
GLsizei GLsizei GLchar * source
GLsizei const GLfloat * value