79using std::string, std::ostream;
92std::unique_ptr<RooAbsDataStore>
96 ?
static_cast<std::unique_ptr<RooAbsDataStore>
>(std::make_unique<RooTreeDataStore>(
name, title, vars))
97 :
static_cast<std::unique_ptr<RooAbsDataStore>
>(std::make_unique<RooVectorDataStore>(
name, title, vars));
170 std::map<string,TH1*> histMap,
double wgt) :
194 std::map<string,RooDataHist*> dhistMap,
double wgt) :
222 std::stringstream errorMsgStream;
223 errorMsgStream <<
"RooDataHist::ctor(" <<
GetName() <<
") ERROR: dimension of input histogram must match "
224 <<
"number of dimension variables";
225 const std::string errorMsg = errorMsgStream.str();
226 coutE(InputArguments) << errorMsg << std::endl;
227 throw std::invalid_argument(errorMsg);
277 RooAbsData(
name,title,
RooArgSet(vars,static_cast<
RooAbsArg*>(
RooCmdConfig::decodeObjOnTheFly(
"RooDataHist::RooDataHist",
"IndexCat",0,nullptr,arg1,arg2,arg3,arg4,arg5,arg6,arg7,arg8))))
285 pc.
defineInt(
"impDens",
"ImportHisto",0) ;
287 pc.
defineObject(
"impSliceData",
"ImportDataSlice",0,
nullptr,
true) ;
288 pc.
defineString(
"impSliceState",
"ImportDataSlice",0,
"",
true) ;
291 pc.
defineSet(
"glObs",
"GlobalObservables",0,
nullptr) ;
304 throw std::invalid_argument(
"Invalid command arguments passed to RooDataHist constructor!");
310 bool impDens = pc.
getInt(
"impDens") ;
311 double initWgt = pc.
getDouble(
"weight") ;
313 const char* impSliceNames = pc.
getString(
"impSliceState",
"",
true) ;
320 importTH1(vars,*impHist,initWgt, impDens) ;
322 }
else if (indexCat) {
326 std::map<std::string,RooDataHist*> dmap ;
327 std::map<std::string,TH1*> hmap ;
328 auto hiter = impSliceHistos.
begin() ;
329 for (
const auto& token :
ROOT::Split(impSliceNames,
",",
true)) {
332 std::stringstream errorMsgStream;
333 errorMsgStream <<
"RooDataHist::RooDataHist(\"" <<
GetName() <<
"\") "
334 <<
"you are providing import data for the category state \"" << token
335 <<
"\", but the index category \"" << indexCat->
GetName() <<
"\" has no such state!";
336 const std::string errorMsg = errorMsgStream.str();
337 coutE(InputArguments) << errorMsg << std::endl;
338 throw std::invalid_argument(errorMsg);
341 if(
auto dHist =
dynamic_cast<RooDataHist*
>(*hiter)) {
344 if(
auto hHist =
dynamic_cast<TH1*
>(*hiter)) {
349 if(!dmap.empty() && !hmap.empty()) {
350 std::stringstream errorMsgStream;
351 errorMsgStream <<
"RooDataHist::ctor(" <<
GetName() <<
") ERROR: you can't import mix of TH1 and RooDataHist";
352 const std::string errorMsg = errorMsgStream.str();
353 coutE(InputArguments) << errorMsg << std::endl;
354 throw std::invalid_argument(errorMsg);
384 Int_t offset[3]{0, 0, 0};
413 for (iX=0 ; iX < xvar->
getBins() ; iX++) {
416 for (iY=0 ; iY < yvar->
getBins() ; iY++) {
419 for (iz=0 ; iz < zvar->
getBins() ; iz++) {
421 double bv = doDensityCorrection ?
binVolume(vset) : 1;
425 double bv = doDensityCorrection ?
binVolume(vset) : 1;
430 double bv = doDensityCorrection ?
binVolume(vset) : 1 ;
438bool checkConsistentAxes(
const TH1* first,
const TH1* second) {
454 constexpr double tolerance = 1
e-6;
456 auto const& vars1 = *
h1.get();
457 auto const& vars2 = *h2.
get();
460 if(!vars1.hasSameLayout(vars2)) {
464 for(std::size_t iVar = 0; iVar < vars1.size(); ++iVar) {
465 auto * var1 =
dynamic_cast<RooRealVar*
>(vars1[iVar]);
466 auto * var2 =
dynamic_cast<RooRealVar*
>(vars2[iVar]);
469 if((!var1 && var2) || (var1 && !var2))
return false;
476 auto const& bng2 = var2->getBinning();
479 if(bng1.numBins() != bng2.numBins())
return false;
481 std::size_t nBins = bng1.
numBins();
484 for(std::size_t iBin = 0; iBin < nBins; ++iBin) {
485 double v1 = bng1.binLow(iBin);
486 double v2 = bng2.binLow(iBin);
487 if(std::abs((
v1 -
v2) /
v1) > tolerance)
return false;
489 double v1 = bng1.binHigh(nBins - 1);
490 double v2 = bng2.binHigh(nBins - 1);
491 if(std::abs((
v1 -
v2) /
v1) > tolerance)
return false;
507 TH1* histo(
nullptr) ;
509 for (
const auto& hiter : hmap) {
512 histo = hiter.second;
514 if (!checkConsistentAxes(histo, hiter.second)) {
515 coutE(InputArguments) <<
"Axes of histogram " << hiter.second->GetName() <<
" are not consistent with first processed "
516 <<
"histogram " << histo->
GetName() << std::endl;
517 throw std::invalid_argument(
"Axes of inputs for RooDataHist are inconsistent");
521 if (!indexCat.
hasLabel(hiter.first)) {
523 coutI(InputArguments) <<
"RooDataHist::importTH1Set(" <<
GetName() <<
") defining state \"" << hiter.first <<
"\" in index category " << indexCat.
GetName() << std::endl ;
532 coutE(InputArguments) <<
"RooDataHist::importTH1Set(" <<
GetName() <<
"): dimension of input histogram must match "
533 <<
"number of continuous variables" << std::endl ;
534 throw std::invalid_argument(
"Inputs histograms for RooDataHist are not compatible with dimensions of variables.");
575 for (ic=0 ; ic < icat->
numBins(
nullptr) ; ic++) {
578 for (iX=0 ; iX < xvar->
getBins() ; iX++) {
581 for (iY=0 ; iY < yvar->
getBins() ; iY++) {
584 for (iz=0 ; iz < zvar->
getBins() ; iz++) {
586 double bv = doDensityCorrection ?
binVolume(vset)/avgBV : 1;
590 double bv = doDensityCorrection ?
binVolume(vset)/avgBV : 1;
595 double bv = doDensityCorrection ?
binVolume(vset)/avgBV : 1;
611 std::map<std::string, RooDataHist *> dmap,
double initWgt)
617 for (
const auto &diter : dmap) {
619 std::string
const &label = diter.first;
622 if (!dhistForBinning) {
623 dhistForBinning = dhist;
625 if (!hasConsistentLayoutAndBinning(*dhistForBinning, *dhist)) {
626 coutE(InputArguments) <<
"Layout or binning of histogram " << dhist->
GetName()
627 <<
" is not consistent with first processed "
628 <<
"histogram " << dhistForBinning->
GetName() << std::endl;
629 throw std::invalid_argument(
"Layout or binning of inputs for RooDataHist is inconsistent");
636 coutI(InputArguments) <<
"RooDataHist::importDHistSet(" <<
GetName() <<
") defining state \"" << label
637 <<
"\" in index category " << indexCat.
GetName() << std::endl;
639 if (!icat->hasLabel(label)) {
640 icat->defineType(label);
646 auto *ourVar =
dynamic_cast<RooRealVar *
>(
_vars.find(theirVar->GetName()));
647 if (!theirVar || !ourVar)
654 for (
const auto &diter : dmap) {
655 std::string
const &label = diter.first;
658 icat->setLabel(label.c_str());
674 const std::string ourVarName(ourVar->
GetName() ? ourVar->
GetName() :
"");
681 coutE(InputArguments) <<
"RooDataHist::adjustBinning(" << ownName <<
") ERROR: dimension " << ourVarName
682 <<
" must be real\n";
683 throw std::logic_error(
"Incorrect type object (" + ourVarName +
684 ") passed as argument to RooDataHist::_adjustBinning. Please report this issue.");
687 const double xlo = theirVar.
getMin();
688 const double xhi = theirVar.
getMax();
691 std::unique_ptr<RooAbsBinning> xbins;
699 const double tolerance = 1
e-6 * xbins->averageBinWidth();
702 const int iBinLo = xbins->binNumber(xlo + tolerance);
703 const int iBinHi = xbins->binNumber(xhi - tolerance);
704 const int nBinsAdj = iBinHi - iBinLo + 1;
705 const double xloAdj = xbins->binLow(iBinLo);
706 const double xhiAdj = xbins->binHigh(iBinHi);
709 xbins = std::make_unique<RooUniformBinning>(xloAdj, xhiAdj, nBinsAdj);
712 xbins->setRange(xloAdj, xhiAdj);
716 if (std::abs(xloAdj - xlo) > tolerance || std::abs(xhiAdj - xhi) > tolerance) {
717 coutI(DataHandling) <<
"RooDataHist::adjustBinning(" << ownName <<
"): fit range of variable " << ourVarName
718 <<
" expanded to nearest bin boundaries: [" << xlo <<
"," << xhi <<
"] --> [" << xloAdj <<
","
728 *offset = axis.
FindFixBin(xloAdj + tolerance) - 1;
763void cloneArray(
double*& ours,
const double* theirs, std::size_t
n) {
764 if (ours)
delete[] ours;
767 ours =
new double[
n];
768 std::copy(theirs, theirs+
n, ours);
772void initArray(
double*& arr, std::size_t
n,
double val) {
773 if (arr)
delete[] arr;
777 std::fill(arr, arr+
n, val);
793 for (
unsigned int i = 0; i <
_vars.size(); ++i) {
805 const RooAbsBinning* binning = lvarg->getBinningPtr(
nullptr);
806 _lvbins.emplace_back(binning ? binning->
clone() :
nullptr);
815 for (
const auto var :
_vars) {
820 for (
unsigned int i = 0u; i<
n; i++) {
853 double theBinVolume(1) ;
858 theBinVolume *= arg2->getBinWidth(idx) ;
860 _binv[ibin] = theBinVolume ;
877 std::vector<double>& bounds =
_binbounds.back();
878 bounds.reserve(2 * it->numBins());
879 for (
Int_t i = 0; i < it->numBins(); ++i) {
880 bounds.push_back(it->binLow(i));
881 bounds.push_back(it->binHigh(i));
903 for (
const auto rvarg :
_vars) {
907 const RooAbsBinning* binning = lvarg->getBinningPtr(
nullptr);
908 _lvbins.emplace_back(binning ? binning->
clone() :
nullptr) ;
919 std::size_t nStart, std::size_t nStop)
const
923 _vars.selectCommon(varSubset, myVarSubset);
924 auto rdh = std::make_unique<RooDataHist>(
GetName(),
GetTitle(), myVarSubset);
927 std::unique_ptr<RooArgSet> tmp;
929 tmp = std::make_unique<RooArgSet>();
932 coutE(DataHandling) <<
"RooDataHist::reduceEng(" <<
GetName() <<
") Couldn't deep-clone cut variable, abort," << std::endl ;
941 const std::size_t nevt = nStop < static_cast<std::size_t>(
numEntries()) ? nStop :
static_cast<std::size_t
>(
numEntries());
942 for (
auto i=nStart; i<nevt ; i++) {
945 bool doSelect(
true) ;
947 for (
const auto arg : *row) {
948 if (!arg->inRange(cutRange)) {
954 if (!doSelect) continue ;
956 if (!cloneVar || cloneVar->
getVal()) {
958 rdh->add(*row,
weight(i),lo*lo) ;
998 bool correctForBinSize)
const
1000 std::vector<double> vals(
_arrSize);
1001 for (std::size_t i = 0; i < vals.size(); ++i) {
1015 for (std::size_t i = 0; i <
_vars.size(); ++i) {
1017 std::size_t iVar = reverse ?
_vars.size() - 1 - i : i;
1023 coutE(InputArguments) <<
"RooHistPdf::weight(" <<
GetName()
1024 <<
") ERROR: Code Squashing currently does not support category values." << std::endl;
1034 idxMult *=
dynamic_cast<RooAbsLValue const *
>(internalVar)->numBins();
1037 return _vars.size() == 1 ? code :
"(" + code +
")";
1058 if (&
_vars == &coords)
1061 std::size_t masterIdx = 0;
1063 for (
unsigned int i=0; i <
_vars.size(); ++i) {
1070 const RooAbsArg* theVar = fast ? coords[i] : coords.
find(*internalVar);
1073 theVar = internalVar;
1083 assert(
dynamic_cast<const RooAbsReal*
>(theVar));
1084 const double val =
static_cast<const RooAbsReal*
>(theVar)->getVal();
1090 masterIdx +=
_idxMult[i] * cat->getBin(
static_cast<const char*
>(
nullptr));
1116 <<
":plotOn: frame does not specify a plot variable" << std::endl;
1123 <<
":plotOn: dataset doesn't contain plot frame variable" << std::endl;
1127 o.
bins = &dataVar->getBinning() ;
1148 bool correctForBinSize,
bool cdfBoundaries)
1151 const std::size_t nEvents = xVals.size();
1155 auto binIndices =
reinterpret_cast<int*
>(output + nEvents) - nEvents;
1156 std::fill(binIndices, binIndices + nEvents, 0);
1157 binning.
binNumbers(xVals.data(), binIndices, nEvents);
1162 std::vector<double> coordsExt(nBins+3);
1163 double* binCoords = coordsExt.data() + 2;
1165 for (std::size_t binIdx = 1; binIdx < nBins ; ++binIdx) {
1167 double binWidth =
_binv[0];
1168 binCoords[binIdx] = binIdx*binWidth + binCoords[0];
1171 double binCentDiff = 0.5*
_binv[binIdx-1] + 0.5*
_binv[binIdx];
1172 binCoords[binIdx] = binCoords[binIdx-1] + binCentDiff;
1176 std::vector<double> weightsExt(nBins+3);
1178 for (std::size_t binIdx = 0; binIdx < nBins; ++binIdx) {
1179 weightsExt[binIdx+2] = correctForBinSize ?
_wgt[binIdx] /
_binv[binIdx] :
_wgt[binIdx];
1182 if (cdfBoundaries) {
1183 coordsExt[0] = - 1
e-10 + binning.
lowBound();
1189 coordsExt[nBins+2] = binning.
highBound();
1190 weightsExt[nBins+2] = 1.;
1194 coordsExt[0] = binCoords[1] - 2*
_binv[0] -
_binv[1];
1195 weightsExt[0] = weightsExt[3];
1197 coordsExt[1] = binCoords[0] -
_binv[0];
1198 weightsExt[1] = weightsExt[2];
1200 coordsExt[nBins+2] = binCoords[nBins-1] +
_binv[nBins-1];
1201 weightsExt[nBins+2] = weightsExt[nBins+1];
1206 for (std::size_t i = 0; i < nEvents ; ++i) {
1207 double xVal = xVals[i];
1208 std::size_t binIdx = binIndices[i] + 2;
1212 if (xVal > coordsExt[binIdx]) {
1216 double x1 = coordsExt[binIdx-2];
1217 double y1 = weightsExt[binIdx-2];
1219 double x2 = coordsExt[binIdx-1];
1220 double y2 = weightsExt[binIdx-1];
1222 double x3 = coordsExt[binIdx];
1223 double y3 = weightsExt[binIdx];
1226 double quotient = (x3-x1) / (x2-x1);
1227 double x1Sqrd = x1*x1;
1228 double x3Sqrd = x3*x3;
1230 double secondCoeff = (y3 - y1 - (y2-y1) * quotient) / (x3Sqrd - x1Sqrd - (x2*x2 - x1Sqrd) * quotient);
1231 double firstCoeff = (y3 - y1 - secondCoeff*(x3Sqrd - x1Sqrd)) / (x3-x1);
1232 double zerothCoeff = y1 - secondCoeff*x1Sqrd - firstCoeff*x1;
1234 output[i] = secondCoeff * xVal * xVal + firstCoeff * xVal + zerothCoeff;
1255 bool correctForBinSize,
bool cdfBoundaries)
1258 const std::size_t nEvents = xVals.size();
1262 auto binIndices =
reinterpret_cast<int*
>(output + nEvents) - nEvents;
1263 std::fill(binIndices, binIndices + nEvents, 0);
1264 binning.
binNumbers(xVals.data(), binIndices, nEvents);
1269 std::vector<double> coordsExt(nBins+2);
1270 double* binCoords = coordsExt.data() + 1;
1272 for (std::size_t binIdx = 1; binIdx < nBins ; ++binIdx) {
1274 double binWidth =
_binv[0];
1275 binCoords[binIdx] = binIdx*binWidth + binCoords[0];
1278 double binCentDiff = 0.5*
_binv[binIdx-1] + 0.5*
_binv[binIdx];
1279 binCoords[binIdx] = binCoords[binIdx-1] + binCentDiff;
1283 std::vector<double> weightsExt(nBins+2);
1285 for (std::size_t binIdx = 0; binIdx < nBins; ++binIdx) {
1286 weightsExt[binIdx+1] = correctForBinSize ?
_wgt[binIdx] /
_binv[binIdx] :
_wgt[binIdx];
1290 if (cdfBoundaries) {
1293 coordsExt[nBins+1] = binning.
highBound();
1294 weightsExt[nBins+1] = 1.;
1298 coordsExt[0] = binCoords[0] -
_binv[0];
1299 weightsExt[0] = weightsExt[1];
1300 coordsExt[nBins+1] = binCoords[nBins-1] +
_binv[nBins-1];
1301 weightsExt[nBins+1] = weightsExt[nBins];
1306 for (std::size_t i = 0; i < nEvents ; ++i) {
1307 double xVal = xVals[i];
1308 std::size_t binIdx = binIndices[i] + 1;
1312 if (xVal > coordsExt[binIdx]) { binIdx += 1; }
1314 double x1 = coordsExt[binIdx-1];
1315 double y1 = weightsExt[binIdx-1];
1316 double x2 = coordsExt[binIdx];
1317 double y2 = weightsExt[binIdx];
1320 double firstCoeff = (y2-y1) / (x2-x1);
1321 double zerothCoeff = y1 - firstCoeff * x1;
1323 output[i] = firstCoeff * xVal + zerothCoeff;
1342void RooDataHist::weights(
double* output, std::span<double const> xVals,
int intOrder,
bool correctForBinSize,
bool cdfBoundaries)
1344 auto const nEvents = xVals.size();
1346 if (intOrder == 0) {
1350 auto binIndices =
reinterpret_cast<int*
>(output + nEvents) - nEvents;
1351 std::fill(binIndices, binIndices + nEvents, 0);
1352 binning.
binNumbers(xVals.data(), binIndices, nEvents);
1354 for (std::size_t i=0; i < nEvents; ++i) {
1355 auto binIdx = binIndices[i];
1356 output[i] = correctForBinSize ?
_wgt[binIdx] /
_binv[binIdx] :
_wgt[binIdx];
1359 else if (intOrder == 1) {
1362 else if (intOrder == 2) {
1367 coutE(InputArguments) <<
"RooDataHist::weights(" <<
GetName() <<
") interpolation in "
1368 << intOrder <<
" dimensions not yet implemented" << std::endl ;
1370 weights(output, xVals, 1, correctForBinSize, cdfBoundaries);
1396 coutE(InputArguments) <<
"RooDataHist::weight(" <<
GetName() <<
") ERROR: interpolation order must be positive" << std::endl ;
1403 return correctForBinSize ?
_wgt[idx] /
_binv[idx] :
_wgt[idx];
1431 coutE(InputArguments) <<
"RooDataHist::weight(" <<
GetName() <<
") ERROR: interpolation order must be positive" << std::endl ;
1438 return correctForBinSize ?
_wgt[idx] /
_binv[idx] :
_wgt[idx];
1442 _vars.assignValueOnly(bin) ;
1485 double xval = realX.
getVal() ;
1486 double yval = realY.getVal() ;
1491 int ybinLo = ybinC-intOrder/2 - ((yval<binningY.
binCenter(ybinC))?1:0) ;
1492 int ybinM = binningY.
numBins() ;
1495 auto offsetIdx = centralIdx - idxMultY * ybinC;
1499 double * xarr = yarr + intOrder + 1;
1500 for (
int i=ybinLo ; i<=intOrder+ybinLo ; i++) {
1502 if (i>=0 && i<ybinM) {
1505 xarr[i-ybinLo] = binningY.
binCenter(ibin) ;
1506 }
else if (i>=ybinM) {
1508 ibin = 2*ybinM-i-1 ;
1515 auto centralIdxX = offsetIdx + idxMultY * ibin;
1520 std::cout <<
"RooDataHist interpolating data is" << std::endl ;
1521 std::cout <<
"xarr = " ;
1522 for (
int q=0;
q<=intOrder ;
q++) std::cout << xarr[
q] <<
" " ;
1523 std::cout <<
" yarr = " ;
1524 for (
int q=0;
q<=intOrder ;
q++) std::cout << yarr[
q] <<
" " ;
1525 std::cout << std::endl ;
1532 coutE(InputArguments) <<
"RooDataHist::weight(" <<
GetName() <<
") interpolation in "
1533 << varInfo.
nRealVars <<
" dimensions not yet implemented" << std::endl ;
1534 return weightFast(bin,0,correctForBinSize,cdfBoundaries) ;
1568 throw std::invalid_argument(
"RooDataHist::weightError(" + std::string(
GetName()) +
") error type Auto not allowed here");
1572 throw std::invalid_argument(
"RooDataHist::weightError(" + std::string(
GetName()) +
") error type Expected not allowed here");
1633 auto const& binning =
static_cast<RooRealVar&
>(*
_vars[iDim]).getBinning();
1636 int fbinC = binning.binNumber(xval) ;
1637 int fbinLo = fbinC-intOrder/2 - ((xval<binning.binCenter(fbinC))?1:0) ;
1638 int fbinM = binning.numBins() ;
1641 auto offsetIdx = centralIdx - idxMult * fbinC;
1645 double * xarr = yarr + intOrder + 1;
1647 for (
int i=fbinLo ; i<=intOrder+fbinLo ; i++) {
1649 if (i>=0 && i<fbinM) {
1652 xarr[i-fbinLo] = binning.binCenter(ibin) ;
1653 auto idx = offsetIdx + idxMult * ibin;
1654 yarr[i - fbinLo] =
_wgt[idx];
1655 if (correctForBinSize) yarr[i-fbinLo] /=
_binv[idx] ;
1656 }
else if (i>=fbinM) {
1658 ibin = 2*fbinM-i-1 ;
1659 if (cdfBoundaries) {
1660 xarr[i-fbinLo] = binning.highBound()+1
e-10*(i-fbinM+1) ;
1661 yarr[i-fbinLo] = 1.0 ;
1663 auto idx = offsetIdx + idxMult * ibin;
1664 xarr[i-fbinLo] = 2*binning.highBound()-binning.binCenter(ibin) ;
1665 yarr[i - fbinLo] =
_wgt[idx];
1666 if (correctForBinSize)
1667 yarr[i - fbinLo] /=
_binv[idx];
1672 if (cdfBoundaries) {
1673 xarr[i-fbinLo] = binning.lowBound()-ibin*(1
e-10) ;
1674 yarr[i-fbinLo] = 0.0 ;
1676 auto idx = offsetIdx + idxMult * ibin;
1677 xarr[i-fbinLo] = 2*binning.lowBound()-binning.binCenter(ibin) ;
1678 yarr[i - fbinLo] =
_wgt[idx];
1679 if (correctForBinSize)
1680 yarr[i - fbinLo] /=
_binv[idx];
1701 if ((sumw2 > 0. || wgt != 1.) && !
_sumw2) {
1712 if (
_sumw2)
_sumw2[idx] += (sumw2 > 0 ? sumw2 : wgt*wgt);
1750 if (wgtErr > 0. && !
_sumw2) {
1757 _wgt[binNumber] = wgt ;
1771 if (
_curIndex == std::numeric_limits<std::size_t>::max()) {
1798 add(dset,&cutVar,wgt) ;
1812 std::unique_ptr<RooArgSet> tmp;
1815 tmp = std::make_unique<RooArgSet>();
1817 coutE(DataHandling) <<
"RooDataHist::add(" <<
GetName() <<
") Couldn't deep-clone cut variable, abort," << std::endl ;
1821 cloneVar =
static_cast<RooFormulaVar*
>(tmp->find(*cutVar)) ;
1829 if (!cloneVar || cloneVar->
getVal()) {
1858 const double theBinVolume = correctForBinSize ? (inverseBinCor ? 1/
_binv[i] :
_binv[i]) : 1.0 ;
1859 kahanSum +=
_wgt[i] * theBinVolume;
1866 return kahanSum.Sum();
1890 sliceOnlySet.
remove(sumSet,
true,
true) ;
1892 _vars.assign(sliceOnlySet);
1893 std::vector<double>
const * pbinv =
nullptr;
1895 if(correctForBinSize && inverseBinCor) {
1897 }
else if(correctForBinSize && !inverseBinCor) {
1902 std::vector<bool> mask(
_vars.size());
1903 std::vector<int> refBin(
_vars.size());
1905 for (
unsigned int i = 0; i <
_vars.size(); ++i) {
1909 if (sumSet.
find(*arg)) {
1913 refBin[i] = argLv->
getBin();
1921 std::size_t tmpibin = ibin;
1925 for (
unsigned int ivar = 0; !skip && ivar <
_vars.size(); ++ivar) {
1928 if (mask[ivar] && idx!=refBin[ivar])
1933 const double theBinVolume = correctForBinSize ? (inverseBinCor ? 1/(*pbinv)[ibin] : (*pbinv)[ibin] ) : 1.0 ;
1938 _vars.assign(varSave) ;
1960 bool correctForBinSize,
bool inverseBinCor,
1961 const std::map<
const RooAbsArg*, std::pair<double, double> >& ranges,
1962 std::function<
double(
int)> getBinScale)
1970 sliceOnlySet.
remove(sumSet,
true,
true);
1971 _vars.assign(sliceOnlySet);
1976 std::vector<bool> mask(
_vars.size());
1977 std::vector<int> refBin(
_vars.size());
1978 std::vector<double> rangeLo(
_vars.size(), -std::numeric_limits<double>::infinity());
1979 std::vector<double> rangeHi(
_vars.size(), +std::numeric_limits<double>::infinity());
1981 for (std::size_t i = 0; i <
_vars.size(); ++i) {
1990 refBin[i] = argLV->
getBin();
1993 auto it = ranges.find(sumsetv ? sumsetv : slicesetv);
1994 if (ranges.end() != it) {
1995 rangeLo[i] = it->second.first;
1996 rangeHi[i] = it->second.second;
2005 for (
int ivar = 0, tmp = ibin; !skip && ivar <
int(
_vars.size()); ++ivar) {
2008 if (mask[ivar] && idx!=refBin[ivar]) skip =
true;
2017 double binVolumeSumSetFull = 1.;
2018 double binVolumeSumSetInRange = 1.;
2019 for (
Int_t ivar = 0, tmp = ibin; ivar < (
int)
_vars.size(); ++ivar) {
2024 const auto arg =
_vars[ivar];
2025 if (!sumSet.
find(*arg)) {
2030 const double binLo =
_binbounds[ivar][2 * idx];
2031 const double binHi =
_binbounds[ivar][2 * idx + 1];
2032 if (binHi < rangeLo[ivar] || binLo > rangeHi[ivar]) {
2034 binVolumeSumSetInRange = 0.;
2038 binVolumeSumSetFull *= binHi - binLo;
2039 binVolumeSumSetInRange *= std::min(rangeHi[ivar], binHi) - std::max(rangeLo[ivar], binLo);
2041 const double corrPartial = binVolumeSumSetInRange / binVolumeSumSetFull;
2042 if (0. == corrPartial)
continue;
2043 const double corr = correctForBinSize ? (inverseBinCor ? binVolumeSumSetFull /
_binv[ibin] : binVolumeSumSetFull ) : 1.0;
2044 total += getBinScale(ibin)*(
_wgt[ibin] * corr * corrPartial);
2047 _vars.assign(varSave);
2065 for (
auto const&
v :
_vars) {
2066 code += ((dimSet.
find(*
v) ? 1 : 0) << i) ;
2072 if(!pbinv.empty()) {
2078 std::vector<bool> selDim(
_vars.size());
2079 for (std::size_t i = 0; i < selDim.size(); ++i) {
2080 selDim[i] = (code >> i) & 1 ;
2087 double theBinVolume(1) ;
2088 for (
unsigned int j=0; j <
_lvvars.size(); ++j) {
2098 pbinv[ibin] = theBinVolume ;
2122 if (cutSpec==
nullptr && cutRange==
nullptr) {
2127 std::unique_ptr<RooFormula> select;
2129 select = std::make_unique<RooFormula>(
"select",cutSpec,*
get());
2136 if ((select && select->eval() == 0.) || (cutRange && !
_vars.allInRange(cutRange)))
2142 return kahanSum.Sum();
2208 _vars.assign(otherArgs) ;
2213 coutE(InputArguments) <<
"RooDataHist::sliceIterator() variable " << sliceArg.
GetName() <<
" is not part of this RooDataHist" << std::endl ;
2225 if (
_dir)
_dir->GetList()->Remove(
this);
2228 if (
_dir)
_dir->GetList()->Add(
this);
2260 for (
const auto arg :
_vars) {
2266 os << arg->GetName() ;
2279 const double wgt =
_wgt[i];
2281 if (std::abs(std::modf(wgt, &intpart)) > 1.E-10)
2300 os <<
indent <<
" Observables " <<
_vars << std::endl ;
2302 os <<
indent <<
" Observables: " ;
2325 os <<
"Contents of RooDataHist \"" <<
GetName() <<
"\"" << std::endl;
2328 os <<
"(dataset is empty)" << std::endl;
2334 os <<
" Bin " << i <<
": ";
2337 for (
const auto* var : *obs) {
2338 if (!first) os <<
", ";
2341 os << var->GetName() <<
"=";
2342 if (
auto realVar =
dynamic_cast<const RooRealVar*
>(var)) {
2343 os << realVar->getVal();
2344 }
else if (
auto catVar =
dynamic_cast<const RooCategory*
>(var)) {
2345 os << catVar->getCurrentLabel();
2347 os <<
"(unsupported type)";
2353 os <<
", weight=" <<
weight(i) <<
" +/- [" << lo <<
"," <<
hi <<
"]"
2385 TTree* X_tree(
nullptr) ; R__b >> X_tree;
2392 _dstore = std::make_unique<RooTreeDataStore>(X_tree,
_vars);
2463 for (
const auto real :
_vars) {
2465 if(info.nRealVars == 0) info.realVarIdx1 = iVar;
2466 if(info.nRealVars == 1) info.realVarIdx2 = iVar;
2475 for (
unsigned int i=0; i <
_vars.size(); ++i) {
2484 info.initialized =
true;
ROOT::RRangeCast< T, true, Range_t > dynamic_range_cast(Range_t &&coll)
int Int_t
Signed integer 4 bytes (int).
short Version_t
Class version identifier (short).
unsigned int UInt_t
Unsigned integer 4 bytes (unsigned int).
static void indent(ostringstream &buf, int indent_level)
static unsigned int total
The Kahan summation is a compensated summation algorithm, which significantly reduces numerical error...
static KahanSum< T, N > Accumulate(Iterator begin, Iterator end, T initialValue=T{})
Iterate over a range and return an instance of a KahanSum.
Common abstract base class for objects that represent a value and a "shape" in RooFit.
void attachDataSet(const RooAbsData &set)
Replace server nodes with names matching the dataset variable names with those data set variables,...
Abstract base class for RooRealVar binning definitions.
int binNumber(double x) const
Returns the bin number corresponding to the value x.
virtual void binNumbers(double const *x, int *bins, std::size_t n, int coef=1) const =0
Compute the bin indices for multiple values of x.
virtual double binCenter(Int_t bin) const =0
Int_t numBins() const
Return number of bins.
virtual bool isUniform() const
virtual double highBound() const =0
virtual double lowBound() const =0
virtual std::string translateBinNumber(RooFit::Experimental::CodegenContext &ctx, RooAbsArg const &var, int coef) const
virtual RooAbsBinning * clone(const char *name=nullptr) const =0
Abstract base class for objects that represent a discrete value that can be set from the outside,...
Int_t numBins(const char *rangeName=nullptr) const override
Return the number of fit bins ( = number of types ).
void setBin(Int_t ibin, const char *rangeName=nullptr) override
Set category to i-th fit bin, which is the i-th registered state.
bool hasLabel(const std::string &label) const
Check if a state with name label exists.
virtual const char * getCurrentLabel() const
Return label string of current state.
Abstract container object that can hold multiple RooAbsArg objects.
virtual bool remove(const RooAbsArg &var, bool silent=false, bool matchByNameOnly=false)
Remove the specified argument from our list.
virtual bool add(const RooAbsArg &var, bool silent=false)
Add the specified argument to list.
Storage_t::size_type size() const
virtual RooAbsArg * addClone(const RooAbsArg &var, bool silent=false)
Add a clone of the specified argument to list.
RooAbsArg * find(const char *name) const
Find object with given name in list.
virtual double weight() const =0
virtual const RooArgSet * get() const
void printMultiline(std::ostream &os, Int_t contents, bool verbose=false, TString indent="") const override
Interface for detailed printing of object.
RooAbsData()
Default constructor.
void SetName(const char *name) override
Set the name of the TNamed.
void setGlobalObservables(RooArgSet const &globalObservables)
Sets the global observables stored in this data.
static StorageType defaultStorageType
std::unique_ptr< RooAbsDataStore > _dstore
Data storage implementation.
RooArgSet _vars
Dimensions of this data set.
RooArgSet _cachedVars
! External variables cached with this data set
virtual Int_t numEntries() const
Return number of entries in dataset, i.e., count unweighted entries.
virtual double weightSquared() const =0
void Streamer(TBuffer &) override
Stream an object of class RooAbsData.
virtual RooPlot * plotOnImpl(RooPlot *frame, PlotOpt o) const
Create and fill a histogram of the frame's variable and append it to the frame.
Abstract base class for objects that are lvalues, i.e.
virtual Int_t getBin(const char *rangeName=nullptr) const =0
virtual double getBinWidth(Int_t i, const char *rangeName=nullptr) const =0
Abstract base class for objects that represent a real value that may appear on the left hand side of ...
virtual Int_t getBins(const char *name=nullptr) const
Get number of bins of currently defined range.
virtual double getMax(const char *name=nullptr) const
Get maximum of currently defined range.
void setBin(Int_t ibin, const char *rangeName=nullptr) override
Set value to center of bin 'ibin' of binning 'rangeName' (or of default binning if no range is specif...
virtual double getMin(const char *name=nullptr) const
Get minimum of currently defined range.
Abstract base class for objects that represent a real value and implements functionality common to al...
double getVal(const RooArgSet *normalisationSet=nullptr) const
Evaluate object.
RooArgList is a container object that can hold multiple RooAbsArg objects.
RooAbsArg * at(Int_t idx) const
Return object at given index, or nullptr if index is out of range.
RooArgSet is a container object that can hold multiple RooAbsArg objects.
RooArgSet * snapshot(bool deepCopy=true) const
Use RooAbsCollection::snapshot(), but return as RooArgSet.
void Streamer(TBuffer &) override
Stream an object of class TObject.
Object to represent discrete states.
bool defineType(const std::string &label)
Define a state with given name.
Named container for two doubles, two integers two object points and three string pointers that can be...
Configurable parser for RooCmdArg named arguments.
void defineMutex(const char *head, Args_t &&... tail)
Define arguments where any pair is mutually exclusive.
bool process(const RooCmdArg &arg)
Process given RooCmdArg.
double getDouble(const char *name, double defaultValue=0.0) const
Return double property registered with name 'name'.
void defineDependency(const char *refArgName, const char *neededArgName)
Define that processing argument name refArgName requires processing of argument named neededArgName t...
bool defineDouble(const char *name, const char *argName, int doubleNum, double defValue=0.0)
Define double property name 'name' mapped to double in slot 'doubleNum' in RooCmdArg with name argNam...
RooArgSet * getSet(const char *name, RooArgSet *set=nullptr) const
Return RooArgSet property registered with name 'name'.
bool defineSet(const char *name, const char *argName, int setNum, const RooArgSet *set=nullptr)
Define TObject property name 'name' mapped to object in slot 'setNum' in RooCmdArg with name argName ...
bool ok(bool verbose) const
Return true of parsing was successful.
bool defineObject(const char *name, const char *argName, int setNum, const TObject *obj=nullptr, bool isArray=false)
Define TObject property name 'name' mapped to object in slot 'setNum' in RooCmdArg with name argName ...
const char * getString(const char *name, const char *defaultValue="", bool convEmptyToNull=false) const
Return string property registered with name 'name'.
bool defineString(const char *name, const char *argName, int stringNum, const char *defValue="", bool appendMode=false)
Define double property name 'name' mapped to double in slot 'stringNum' in RooCmdArg with name argNam...
const RooLinkedList & getObjectList(const char *name) const
Return list of objects registered with name 'name'.
bool defineInt(const char *name, const char *argName, int intNum, int defValue=0)
Define integer property name 'name' mapped to integer in slot 'intNum' in RooCmdArg with name argName...
int getInt(const char *name, int defaultValue=0) const
Return integer property registered with name 'name'.
TObject * getObject(const char *name, TObject *obj=nullptr) const
Return TObject property registered with name 'name'.
Container class to hold N-dimensional binned data.
std::span< const double > getWeightBatch(std::size_t first, std::size_t len, bool sumW2=false) const override
Return event weights of all events in range [first, first+len).
void interpolateQuadratic(double *output, std::span< const double > xVals, bool correctForBinSize, bool cdfBoundaries)
A vectorized version of interpolateDim for boundary safe quadratic interpolation of one dimensional h...
double sum(bool correctForBinSize, bool inverseCorr=false) const
Return the sum of the weights of all bins in the histogram.
void weights(double *output, std::span< double const > xVals, int intOrder, bool correctForBinSize, bool cdfBoundaries)
A vectorized version of RooDataHist::weight() for one dimensional histograms with up to one dimension...
Int_t _cache_sum_valid
! Is cache sum valid? Needs to be Int_t instead of CacheSumState_t for subclasses.
void printContents(std::ostream &os=std::cout) const override
Print the contents of the dataset to the specified output stream.
double interpolateDim(int iDim, double xval, size_t centralIdx, int intOrder, bool correctForBinSize, bool cdfBoundaries)
Perform boundary safe 'intOrder'-th interpolation of weights in dimension 'dim' at current value 'xva...
double weightSquared() const override
Return squared weight of last bin that was requested with get().
friend class RooDataHistSliceIter
void importTH1(const RooArgList &vars, const TH1 &histo, double initWgt, bool doDensityCorrection)
Import data from given TH1/2/3 into this RooDataHist.
TClass * IsA() const override
void SetNameTitle(const char *name, const char *title) override
Change the title of this RooDataHist.
double _cache_sum
! Cache for sum of entries ;
void initialize(const char *binningName=nullptr, bool fillTree=true)
Initialization procedure: allocate weights array, calculate multipliers needed for N-space to 1-dim a...
std::string declWeightArrayForCodeSquash(RooFit::Experimental::CodegenContext &ctx, bool correctForBinSize) const
Int_t getIndex(const RooAbsCollection &coord, bool fast=false) const
Calculate bin number of the given coordinates.
void add(const RooArgSet &row, double wgt=1.0) override
Add wgt to the bin content enclosed by the coordinates passed in row.
const std::vector< double > & calculatePartialBinVolume(const RooArgSet &dimSet) const
Fill the transient cache with partial bin volumes with up-to-date values for the partial volume speci...
static std::unique_ptr< RooAbsDataStore > makeDefaultDataStore(RooStringView name, RooStringView title, RooArgSet const &vars)
double weightInterpolated(const RooArgSet &bin, int intOrder, bool correctForBinSize, bool cdfBoundaries)
Return the weight at given coordinates with interpolation.
std::unordered_map< int, std::vector< double > > _pbinvCache
! Cache for arrays of partial bin volumes
void checkBinBounds() const
void initializeAsymErrArrays() const
double weight(std::size_t i) const
Return weight of i-th bin.
void set(std::size_t binNumber, double weight, double wgtErr)
Set bin content of bin that was last loaded with get(std::size_t).
void weightError(double &lo, double &hi, ErrorType etype=Poisson) const override
Return the asymmetric errors on the current weight.
double * _errHi
[_arrSize] High-side error on weight array
void importTH1Set(const RooArgList &vars, RooCategory &indexCat, std::map< std::string, TH1 * > hmap, double initWgt, bool doDensityCorrection)
Import data from given set of TH1/2/3 into this RooDataHist.
void adjustBinning(const RooArgList &vars, const TH1 &href, Int_t *offset=nullptr)
Adjust binning specification on first and optionally second and third observable to binning in given ...
double * _binv
[_arrSize] Bin volume array
RooDataHist()
Default constructor.
ULong64_t _curIndex
Current index.
std::string calculateTreeIndexForCodeSquash(RooFit::Experimental::CodegenContext &ctx, const RooAbsCollection &coords, bool reverse=false) const
double weightFast(const RooArgSet &bin, int intOrder, bool correctForBinSize, bool cdfBoundaries)
A faster version of RooDataHist::weight that assumes the passed arguments are aligned with the histog...
double weight() const override
Return weight of last bin that was requested with get().
std::vector< std::vector< double > > _binbounds
! list of bin bounds per dimension
void printArgs(std::ostream &os) const override
Print argument of dataset, i.e. the observable names.
void importDHistSet(const RooArgList &vars, RooCategory &indexCat, std::map< std::string, RooDataHist * > dmap, double initWgt)
Import data from given set of TH1/2/3 into this RooDataHist.
void _adjustBinning(RooRealVar &theirVar, const TAxis &axis, RooRealVar *ourVar, Int_t *offset)
Helper doing the actual work of adjustBinning().
void printMultiline(std::ostream &os, Int_t content, bool verbose=false, TString indent="") const override
Print the details on the dataset contents.
double * _sumw2
[_arrSize] Sum of weights^2
TIterator * sliceIterator(RooAbsArg &sliceArg, const RooArgSet &otherArgs)
Create an iterator over all bins in a slice defined by the subset of observables listed in sliceArg.
Int_t calcTreeIndex() const
Legacy overload to calculate the tree index from the current value of _vars.
~RooDataHist() override
Destructor.
bool isNonPoissonWeighted() const override
Returns true if dataset contains entries with a non-integer weight.
std::vector< RooAbsLValue * > _lvvars
! List of observables casted as RooAbsLValue
void SetName(const char *name) override
Change the name of the RooDataHist.
std::vector< std::unique_ptr< const RooAbsBinning > > _lvbins
! List of used binnings associated with lvalues
void Streamer(TBuffer &) override
Stream an object of class RooDataHist.
std::vector< double > _interpolationBuffer
! Buffer to contain values used for weight interpolation
std::vector< Int_t > _idxMult
void registerWeightArraysToDataStore() const
Hand over pointers to our weight arrays to the data store implementation.
void reset() override
Reset all bin weights to zero.
double * _errLo
[_arrSize] Low-side error on weight array
double * _wgt
[_arrSize] Weight array
RooPlot * plotOnImpl(RooPlot *frame, PlotOpt o) const override
Back end function to plotting functionality.
void printValue(std::ostream &os) const override
Print value of the dataset, i.e. the sum of weights contained in the dataset.
VarInfo const & getVarInfo()
Return reference to VarInfo struct with cached histogram variable information that is frequently used...
std::unique_ptr< RooAbsData > reduceEng(const RooArgSet &varSubset, const RooFormulaVar *cutVar, const char *cutRange=nullptr, std::size_t nStart=0, std::size_t nStop=std::numeric_limits< std::size_t >::max()) const override
Implementation of RooAbsData virtual method that drives the RooAbsData::reduce() methods.
const RooArgSet * get() const override
Get bin centre of current bin.
void interpolateLinear(double *output, std::span< const double > xVals, bool correctForBinSize, bool cdfBoundaries)
A vectorized version of interpolateDim for boundary safe linear interpolation of one dimensional hist...
double binVolume() const
Return volume of current bin.
double sumEntries() const override
Sum the weights of all bins.
virtual void Streamer(TBuffer &)
void removeFromDir(TObject *obj)
Remove object from directory it was added to.
TDirectory * _dir
! Associated directory
A class to maintain the context for squashing of RooFit models into code.
std::string buildArg(RooAbsCollection const &x, std::string const &arrayType="double")
Function to save a RooListProxy as an array in the squashed code.
static const RooHistError & instance()
Return a reference to a singleton object that is created the first time this method is called.
bool getPoissonInterval(Int_t n, double &mu1, double &mu2, double nSigma=1) const
Calculate a confidence interval for the expected number of events given n observed (unweighted) event...
Collection class for internal use, storing a collection of RooAbsArg pointers in a doubly linked list...
RooLinkedListIterImpl begin() const
static double interpolate(double yArr[], Int_t nOrder, double x)
Plot frame and a container for graphics objects within that frame.
RooAbsRealLValue * getPlotVar() const
Variable that can be changed from the outside.
void setRange(const char *name, double min, double max, bool shared=true)
Set a fit or plotting range.
void setBinning(const RooAbsBinning &binning, const char *name=nullptr, bool shared=true)
Add given binning under name 'name' with this variable.
const RooAbsBinning & getBinning(const char *name=nullptr, bool verbose=true, bool createOnTheFly=false, bool shared=true) const override
Return binning definition with name.
The RooStringView is a wrapper around a C-style string that can also be constructed from a std::strin...
const Double_t * GetArray() const
Class to manage histogram axis.
const TArrayD * GetXbins() const
virtual Int_t FindFixBin(Double_t x) const
Find bin number corresponding to abscissa x.
Buffer base class used for serializing objects.
virtual Version_t ReadVersion(UInt_t *start=nullptr, UInt_t *bcnt=nullptr, const TClass *cl=nullptr)=0
virtual Int_t CheckByteCount(UInt_t startpos, UInt_t bcnt, const TClass *clss)=0
virtual void ReadFastArray(Bool_t *b, Int_t n)=0
virtual Int_t ReadClassBuffer(const TClass *cl, void *pointer, const TClass *onfile_class=nullptr)=0
virtual Int_t WriteClassBuffer(const TClass *cl, void *pointer)=0
static TClass * GetClass(const char *name, Bool_t load=kTRUE, Bool_t silent=kFALSE)
Static method returning pointer to TClass of the specified class name.
TH1 is the base class of all histogram classes in ROOT.
virtual Int_t GetNbinsY() const
virtual Double_t GetBinError(Int_t bin) const
Return value of error associated to bin number bin.
virtual Int_t GetNbinsZ() const
virtual Int_t GetDimension() const
virtual Int_t GetNbinsX() const
virtual Double_t GetBinContent(Int_t bin) const
Return content of bin number bin.
Iterator abstract base class.
virtual void SetTitle(const char *title="")
Set the title of the TNamed.
const char * GetName() const override
Returns name of object.
const char * GetTitle() const override
Returns title of object.
virtual const char * ClassName() const
Returns name of class to which the object belongs.
TObject()
TObject constructor.
virtual void Streamer(TBuffer &)
Stream a string object.
A TTree represents a columnar dataset.
std::vector< std::string > Split(std::string_view str, std::string_view delims, bool skipEmpty=false)
Splits a string at each character in delims.
Structure to cache information on the histogram variable that is frequently used for histogram weight...