73 ClassImp(ParamHistFunc);
78 ParamHistFunc::ParamHistFunc() : _numBins(0)
80 _dataSet.removeSelfFromDir();
96 ParamHistFunc::ParamHistFunc(
const char* name,
const char* title,
97 const RooArgList& vars,
const RooArgList& paramSet) :
98 RooAbsReal(name, title),
99 _dataVars(
"!dataVars",
"data Vars", this),
100 _paramSet(
"!paramSet",
"bin parameters", this),
102 _dataSet( (std::string(name)+
"_dataSet").c_str(),
"", vars)
109 _dataSet.removeSelfFromDir();
118 _numBins = GetNumBins( vars );
122 addParamSet( paramSet );
137 ParamHistFunc::ParamHistFunc(
const char* name,
const char* title,
138 const RooArgList& vars,
const RooArgList& paramSet,
140 RooAbsReal(name, title),
142 _dataVars(
"!dataVars",
"data Vars", this),
143 _paramSet(
"!paramSet",
"bin parameters", this),
145 _dataSet( (std::string(name)+
"_dataSet").c_str(),
"", vars, Hist)
148 _dataSet.removeSelfFromDir();
151 _numBins = GetNumBins( vars );
155 addParamSet( paramSet );
160 Int_t ParamHistFunc::GetNumBins(
const RooArgSet& vars ) {
164 if( vars.getSize() == 0 )
return 0;
168 RooFIter varIter = vars.fwdIterator() ;
170 while((comp = (RooAbsArg*) varIter.next())) {
171 if (!dynamic_cast<RooRealVar*>(comp)) {
172 std::cout <<
"ParamHistFunc::GetNumBins" << vars.GetName() <<
") ERROR: component "
174 <<
" in vars list is not of type RooRealVar" << std::endl ;
175 RooErrorHandler::softAbort() ;
178 RooRealVar* var = (RooRealVar*) comp;
180 Int_t varNumBins = var->numBins();
181 numBins *= varNumBins;
191 ParamHistFunc::ParamHistFunc(
const ParamHistFunc& other,
const char* name) :
192 RooAbsReal(other, name),
193 _dataVars(
"!dataVars", this, other._dataVars ),
194 _paramSet(
"!paramSet", this, other._paramSet),
195 _numBins( other._numBins ),
196 _binMap( other._binMap ),
197 _dataSet( other._dataSet )
199 _dataSet.removeSelfFromDir();
208 ParamHistFunc::~ParamHistFunc()
222 Int_t ParamHistFunc::getCurrentBin()
const {
223 Int_t dataSetIndex = _dataSet.getIndex( _dataVars );
235 RooRealVar& ParamHistFunc::getParameter( Int_t index )
const {
236 Int_t gammaIndex = -1;
237 if( _binMap.find( index ) != _binMap.end() ) {
238 gammaIndex = _binMap[ index ];
241 std::cout <<
"Error: ParamHistFunc internal bin index map "
242 <<
"not properly configured" << std::endl;
246 return (RooRealVar&) _paramSet[gammaIndex];
252 RooRealVar& ParamHistFunc::getParameter()
const {
253 Int_t index = getCurrentBin();
254 return getParameter( index );
258 void ParamHistFunc::setParamConst( Int_t index, Bool_t varConst ) {
259 RooRealVar& var = getParameter( index );
260 var.setConstant( varConst );
264 void ParamHistFunc::setConstant(
bool constant ) {
265 for(
int i=0; i < numBins(); ++i) {
266 setParamConst(i, constant);
273 void ParamHistFunc::setShape( TH1* shape ) {
274 int num_hist_bins = shape->GetNbinsX()*shape->GetNbinsY()*shape->GetNbinsZ();
276 if( num_hist_bins != numBins() ) {
277 std::cout <<
"Error - ParamHistFunc: cannot set Shape of ParamHistFunc: " << GetName()
278 <<
" using histogram: " << shape->GetName()
279 <<
". Bins don't match" << std::endl;
280 throw std::runtime_error(
"setShape");
284 Int_t TH1BinNumber = 0;
285 for( Int_t i = 0; i < numBins(); ++i) {
289 while( shape->IsBinUnderflow(TH1BinNumber) || shape->IsBinOverflow(TH1BinNumber) ){
294 RooRealVar& var =
dynamic_cast<RooRealVar&
>(_paramSet[i]);
295 var.setVal( shape->GetBinContent(TH1BinNumber) );
314 RooArgList ParamHistFunc::createParamSet(RooWorkspace& w,
const std::string& Prefix,
315 const RooArgList& vars) {
323 Int_t numVars = vars.getSize();
324 Int_t numBins = GetNumBins( vars );
327 std::cout <<
"Warning - ParamHistFunc::createParamSet() :"
328 <<
" No Variables provided. Not making constraint terms."
333 else if( numVars == 1 ) {
336 for( Int_t i = 0; i < numBins; ++i) {
338 std::stringstream VarNameStream;
339 VarNameStream << Prefix <<
"_bin_" << i;
340 std::string VarName = VarNameStream.str();
342 RooRealVar gamma( VarName.c_str(), VarName.c_str(), 1.0 );
345 gamma.setConstant(
false );
347 w.import( gamma, RooFit::RecycleConflictNodes() );
348 RooRealVar* gamma_wspace = (RooRealVar*) w.var( VarName.c_str() );
350 paramSet.add( *gamma_wspace );
355 else if( numVars == 2 ) {
359 std::vector< Int_t > Indices(numVars, 0);
361 RooRealVar* varx = (RooRealVar*) vars.at(0);
362 RooRealVar* vary = (RooRealVar*) vars.at(1);
365 for( Int_t j = 0; j < vary->numBins(); ++j) {
366 for( Int_t i = 0; i < varx->numBins(); ++i) {
372 std::stringstream VarNameStream;
373 VarNameStream << Prefix <<
"_bin_" << i <<
"_" << j;
374 std::string VarName = VarNameStream.str();
376 RooRealVar gamma( VarName.c_str(), VarName.c_str(), 1.0 );
379 gamma.setConstant(
false );
381 w.import( gamma, RooFit::RecycleConflictNodes() );
382 RooRealVar* gamma_wspace = (RooRealVar*) w.var( VarName.c_str() );
384 paramSet.add( *gamma_wspace );
390 else if( numVars == 3 ) {
394 std::vector< Int_t > Indices(numVars, 0);
396 RooRealVar* varx = (RooRealVar*) vars.at(0);
397 RooRealVar* vary = (RooRealVar*) vars.at(1);
398 RooRealVar* varz = (RooRealVar*) vars.at(2);
401 for( Int_t k = 0; k < varz->numBins(); ++k) {
402 for( Int_t j = 0; j < vary->numBins(); ++j) {
403 for( Int_t i = 0; i < varx->numBins(); ++i) {
409 std::stringstream VarNameStream;
410 VarNameStream << Prefix <<
"_bin_" << i <<
"_" << j <<
"_" << k;
411 std::string VarName = VarNameStream.str();
413 RooRealVar gamma( VarName.c_str(), VarName.c_str(), 1.0 );
416 gamma.setConstant(
false );
418 w.import( gamma, RooFit::RecycleConflictNodes() );
419 RooRealVar* gamma_wspace = (RooRealVar*) w.var( VarName.c_str() );
421 paramSet.add( *gamma_wspace );
429 std::cout <<
" Error: ParamHistFunc doesn't support dimensions > 3D " << std::endl;
450 RooArgList ParamHistFunc::createParamSet(RooWorkspace& w,
const std::string& Prefix,
451 const RooArgList& vars,
452 Double_t gamma_min, Double_t gamma_max) {
460 RooArgList params = ParamHistFunc::createParamSet( w, Prefix, vars );
462 for (
auto comp : params) {
464 RooRealVar* var = (RooRealVar*) comp;
466 var->setMin( gamma_min );
467 var->setMax( gamma_max );
480 RooArgList ParamHistFunc::createParamSet(
const std::string& Prefix, Int_t numBins,
481 Double_t gamma_min, Double_t gamma_max) {
491 if( gamma_max <= gamma_min ) {
493 std::cout <<
"Warning: gamma_min <= gamma_max: Using default values (0, 10)" << std::endl;
500 Double_t gamma_nominal = 1.0;
502 if( gamma_nominal < gamma_min ) {
503 gamma_nominal = gamma_min;
506 if( gamma_nominal > gamma_max ) {
507 gamma_nominal = gamma_max;
511 for( Int_t i = 0; i < numBins; ++i) {
513 std::stringstream VarNameStream;
514 VarNameStream << Prefix <<
"_bin_" << i;
515 std::string VarName = VarNameStream.str();
517 RooRealVar* gamma =
new RooRealVar( VarName.c_str(), VarName.c_str(),
518 gamma_nominal, gamma_min, gamma_max );
519 gamma->setConstant(
false );
520 paramSet.add( *gamma );
536 Int_t ParamHistFunc::addVarSet(
const RooArgList& vars ) {
541 RooFIter varIter = vars.fwdIterator() ;
543 while((comp = (RooAbsArg*) varIter.next())) {
544 if (!dynamic_cast<RooRealVar*>(comp)) {
545 coutE(InputArguments) <<
"ParamHistFunc::(" << GetName() <<
") ERROR: component "
546 << comp->GetName() <<
" in variables list is not of type RooRealVar"
548 RooErrorHandler::softAbort() ;
552 _dataVars.add( *comp );
562 RooRealVar* varX = (RooRealVar*) _dataVars.at(0);
563 numBinsX = varX->numBins();
566 }
else if( numVars == 2 ) {
567 RooRealVar* varX = (RooRealVar*) _dataVars.at(0);
568 RooRealVar* varY = (RooRealVar*) _dataVars.at(1);
569 numBinsX = varX->numBins();
570 numBinsY = varY->numBins();
572 }
else if( numVars == 3 ) {
573 RooRealVar* varX = (RooRealVar*) _dataVars.at(0);
574 RooRealVar* varY = (RooRealVar*) _dataVars.at(1);
575 RooRealVar* varZ = (RooRealVar*) _dataVars.at(2);
576 numBinsX = varX->numBins();
577 numBinsY = varY->numBins();
578 numBinsZ = varZ->numBins();
580 std::cout <<
"ParamHistFunc() - Only works for 1-3 variables (1d-3d)" << std::endl;
591 for( Int_t i = 0; i < numBinsX; ++i ) {
592 for( Int_t j = 0; j < numBinsY; ++j ) {
593 for( Int_t k = 0; k < numBinsZ; ++k ) {
595 Int_t RooDataSetBin = k + j*numBinsZ + i*numBinsY*numBinsZ;
596 Int_t TH1HistBin = i + j*numBinsX + k*numBinsX*numBinsY;
598 _binMap[RooDataSetBin] = TH1HistBin;
611 Int_t ParamHistFunc::addParamSet(
const RooArgList& params ) {
618 Int_t numVarBins = _numBins;
619 Int_t numElements = params.getSize();
621 if( numVarBins != numElements ) {
622 std::cout <<
"ParamHistFunc::addParamSet - ERROR - "
623 <<
"Supplied list of parameters " << params.GetName()
624 <<
" has " << numElements <<
" elements but the ParamHistFunc"
625 << GetName() <<
" has " << numVarBins <<
" bins."
636 RooFIter paramIter = params.fwdIterator() ;
638 while((comp = (RooAbsArg*) paramIter.next())) {
639 if (!dynamic_cast<RooRealVar*>(comp)) {
640 coutE(InputArguments) <<
"ParamHistFunc::(" << GetName() <<
") ERROR: component "
641 << comp->GetName() <<
" in paramater list is not of type RooRealVar"
643 RooErrorHandler::softAbort() ;
647 _paramSet.add( *comp );
658 Double_t ParamHistFunc::evaluate()
const
663 RooRealVar* param = (RooRealVar*) &(getParameter());
664 Double_t value = param->getVal();
673 Int_t ParamHistFunc::getAnalyticalIntegralWN(RooArgSet& allVars, RooArgSet& analVars,
674 const RooArgSet* normSet,
678 if (allVars.getSize()==0)
return 0 ;
679 if (_forceNumInt)
return 0 ;
683 analVars.add(allVars) ;
686 Int_t sterileIdx(-1) ;
687 CacheElem* cache = (CacheElem*) _normIntMgr.getObj(normSet,&analVars,&sterileIdx,(
const char*)0) ;
689 return _normIntMgr.lastIndex()+1 ;
693 cache =
new CacheElem ;
696 Int_t code = _normIntMgr.setObj(normSet,&analVars,(RooAbsCacheElement*)cache,0) ;
707 Double_t ParamHistFunc::analyticalIntegralWN(Int_t ,
const RooArgSet* ,
716 RooFIter paramIter = _paramSet.fwdIterator();
717 RooRealVar* param = NULL;
718 Int_t nominalItr = 0;
719 while((param = (RooRealVar*) paramIter.next())) {
722 Double_t paramVal = (*param).getVal();
725 _dataSet.get( nominalItr );
726 Double_t binVolumeDS = _dataSet.binVolume();
729 value += paramVal*binVolumeDS;
756 std::list<Double_t>* ParamHistFunc::plotSamplingHint(RooAbsRealLValue& obs, Double_t xlo,
760 RooAbsLValue* lvarg = &obs;
763 const RooAbsBinning* binning = lvarg->getBinningPtr(0) ;
764 Double_t* boundaries = binning->array() ;
766 std::list<Double_t>* hint =
new std::list<Double_t> ;
769 xlo = xlo - 0.01*(xhi-xlo) ;
770 xhi = xhi + 0.01*(xhi-xlo) ;
772 Double_t delta = (xhi-xlo)*1e-8 ;
776 for (Int_t i=0 ; i<binning->numBoundaries() ; i++) {
777 if (boundaries[i]>=xlo && boundaries[i]<=xhi) {
778 hint->push_back(boundaries[i]-delta) ;
779 hint->push_back(boundaries[i]+delta) ;
791 std::list<Double_t>* ParamHistFunc::binBoundaries(RooAbsRealLValue& obs, Double_t xlo,
795 RooAbsLValue* lvarg = &obs;
798 const RooAbsBinning* binning = lvarg->getBinningPtr(0) ;
799 Double_t* boundaries = binning->array() ;
801 std::list<Double_t>* hint =
new std::list<Double_t> ;
805 for (Int_t i=0 ; i<binning->numBoundaries() ; i++) {
806 if (boundaries[i]>=xlo && boundaries[i]<=xhi) {
807 hint->push_back(boundaries[i]) ;