Logo ROOT  
Reference Guide
 
Loading...
Searching...
No Matches
OptimizeConfigParameters.cxx
Go to the documentation of this file.
1/**********************************************************************************
2 * Project: TMVA - a Root-integrated toolkit for multivariate data analysis *
3 * Package: TMVA *
4 * Class : OptimizeConfigParameters *
5 * *
6 * *
7 * Description: The OptimizeConfigParameters takes care of "scanning/fitting" *
8 * different tuning parameters in order to find the best set of *
9 * tuning paraemters which will be used in the end *
10 * *
11 * Authors (alphabetical): *
12 * Helge Voss <Helge.Voss@cern.ch> - MPI-K Heidelberg, Germany *
13 * *
14 * Copyright (c) 2005: *
15 * CERN, Switzerland *
16 * MPI-K Heidelberg, Germany *
17 * *
18 * Redistribution and use in source and binary forms, with or without *
19 * modification, are permitted according to the terms listed in LICENSE *
20 * (http://ttmva.sourceforge.net/LICENSE) *
21 **********************************************************************************/
22
23/*! \class TMVA::OptimizeConfigParameters
24\ingroup TMVA
25
26*/
27
29#include "TMVA/Config.h"
30#include "TMVA/DataSet.h"
31#include "TMVA/DataSetInfo.h"
32#include "TMVA/Event.h"
33#include "TMVA/IFitterTarget.h"
34#include "TMVA/FitterBase.h"
35#include "TMVA/GeneticFitter.h"
36#include "TMVA/IMethod.h"
37#include "TMVA/Interval.h"
38#include "TMVA/MethodBase.h"
39#include "TMVA/MethodFDA.h"
40#include "TMVA/MsgLogger.h"
41#include "TMVA/MinuitFitter.h"
42#include "TMVA/PDF.h"
43#include "TMVA/Tools.h"
44#include "TMVA/Types.h"
45
46#include "TGraph.h"
47#include "TH1.h"
48#include "TH2.h"
49#include "TMath.h"
50
51#include <cstdlib>
52#include <limits>
53
54
55
56////////////////////////////////////////////////////////////////////////////////
57/// Constructor which sets either "Classification or Regression"
58
60: fMethod(method),
61 fTuneParameters(tuneParameters),
62 fFOMType(fomType),
63 fOptimizationFitType(optimizationFitType),
64 fMvaSig(NULL),
65 fMvaBkg(NULL),
66 fMvaSigFineBin(NULL),
67 fMvaBkgFineBin(NULL),
68 fNotDoneYet(kFALSE)
69{
70 std::string name = "OptimizeConfigParameters_";
71 name += std::string(GetMethod()->GetName());
72 fLogger = new MsgLogger(name);
73 if (fMethod->DoRegression()){
74 Log() << kFATAL << " ERROR: Sorry, Regression is not yet implement for automatic parameter optimization"
75 << " --> exit" << Endl;
76 }
77
78 Log() << kINFO << "Automatic optimisation of tuning parameters in "
79 << GetMethod()->GetName() << " uses:" << Endl;
80
81 std::map<TString,TMVA::Interval*>::iterator it;
82 for (it=fTuneParameters.begin(); it!=fTuneParameters.end();++it) {
83 Log() << kINFO << it->first
84 << " in range from: " << it->second->GetMin()
85 << " to: " << it->second->GetMax()
86 << " in : " << it->second->GetNbins() << " steps"
87 << Endl;
88 }
89 Log() << kINFO << " using the options: " << fFOMType << " and " << fOptimizationFitType << Endl;
90}
91
92////////////////////////////////////////////////////////////////////////////////
93/// the destructor (delete the OptimizeConfigParameters, store the graph and .. delete it)
94
96{
97 if(!GetMethod()->IsSilentFile()) GetMethod()->BaseDir()->cd();
98 Int_t n=Int_t(fFOMvsIter.size());
99 Float_t *x = new Float_t[n];
100 Float_t *y = new Float_t[n];
101 Float_t ymin=(Float_t)+999999999;
102 Float_t ymax=(Float_t)-999999999;
103
104 for (Int_t i=0;i<n;i++){
105 x[i] = Float_t(i);
106 y[i] = fFOMvsIter[i];
107 if (ymin>y[i]) ymin=y[i];
108 if (ymax<y[i]) ymax=y[i];
109 }
110
111 TH2D *h=new TH2D(TString(GetMethod()->GetName())+"_FOMvsIterFrame","",2,0,n,2,ymin*0.95,ymax*1.05);
112 h->SetXTitle("#iteration "+fOptimizationFitType);
113 h->SetYTitle(fFOMType);
114 TGraph *gFOMvsIter = new TGraph(n,x,y);
115 gFOMvsIter->SetName((TString(GetMethod()->GetName())+"_FOMvsIter").Data());
116 if(!GetMethod()->IsSilentFile()) gFOMvsIter->Write();
117 if(!GetMethod()->IsSilentFile()) h->Write();
118
119 delete [] x;
120 delete [] y;
121 // delete fFOMvsIter;
122}
123
124////////////////////////////////////////////////////////////////////////////////
125
127{
128 if (fOptimizationFitType == "Scan" ) this->optimizeScan();
129 else if (fOptimizationFitType == "FitGA" || fOptimizationFitType == "Minuit" ) this->optimizeFit();
130 else {
131 Log() << kFATAL << "You have chosen as optimization type " << fOptimizationFitType
132 << " that is not (yet) coded --> exit()" << Endl;
133 }
134
135 Log() << kINFO << "For " << GetMethod()->GetName() << " the optimized Parameters are: " << Endl;
136 std::map<TString,Double_t>::iterator it;
137 for(it=fTunedParameters.begin(); it!= fTunedParameters.end(); ++it){
138 Log() << kINFO << it->first << " = " << it->second << Endl;
139 }
140 return fTunedParameters;
141
142}
143
144////////////////////////////////////////////////////////////////////////////////
145/// helper function to scan through the all the combinations in the
146/// parameter space
147
148std::vector< int > TMVA::OptimizeConfigParameters::GetScanIndices( int val, std::vector<int> base){
149 std::vector < int > indices;
150 for (UInt_t i=0; i< base.size(); i++){
151 indices.push_back(val % base[i] );
152 val = int( floor( float(val) / float(base[i]) ) );
153 }
154 return indices;
155}
156
157////////////////////////////////////////////////////////////////////////////////
158/// do the actual optimization using a simple scan method,
159/// i.e. calculate the FOM for
160/// different tuning paraemters and remember which one is
161/// gave the best FOM
162
164{
165
166 Double_t bestFOM=-1000000, currentFOM;
167
168 std::map<TString,Double_t> currentParameters;
169 std::map<TString,TMVA::Interval*>::iterator it;
170
171 // for the scan, start at the lower end of the interval and then "move upwards"
172 // initialize all parameters in currentParameter
173 currentParameters.clear();
174 fTunedParameters.clear();
175
176 for (it=fTuneParameters.begin(); it!=fTuneParameters.end(); ++it){
177 currentParameters.insert(std::pair<TString,Double_t>(it->first,it->second->GetMin()));
178 fTunedParameters.insert(std::pair<TString,Double_t>(it->first,it->second->GetMin()));
179 }
180 // now loop over all the parameters and get for each combination the figure of merit
181
182 // in order to loop over all the parameters, I first create an "array" (tune parameters)
183 // of arrays (the different values of the tune parameter)
184
185 std::vector< std::vector <Double_t> > v;
186 for (it=fTuneParameters.begin(); it!=fTuneParameters.end(); ++it){
187 std::vector< Double_t > tmp;
188 for (Int_t k=0; k<it->second->GetNbins(); k++){
189 tmp.push_back(it->second->GetElement(k));
190 }
191 v.push_back(tmp);
192 }
193 Int_t Ntot = 1;
194 std::vector< int > Nindividual;
195 for (UInt_t i=0; i<v.size(); i++) {
196 Ntot *= v[i].size();
197 Nindividual.push_back(v[i].size());
198 }
199 //loop on the total number of different combinations
200
201 for (int i=0; i<Ntot; i++){
202 UInt_t index=0;
203 std::vector<int> indices = GetScanIndices(i, Nindividual );
204 for (it=fTuneParameters.begin(), index=0; index< indices.size(); ++index, ++it){
205 currentParameters[it->first] = v[index][indices[index]];
206 }
207 Log() << kINFO << "--------------------------" << Endl;
208 Log() << kINFO <<"Settings being evaluated:" << Endl;
209 for (std::map<TString,Double_t>::iterator it_print=currentParameters.begin();
211 Log() << kINFO << " " << it_print->first << " = " << it_print->second << Endl;
212 }
213
214 GetMethod()->Reset();
215 GetMethod()->SetTuneParameters(currentParameters);
216 // now do the training for the current parameters:
217 if(!GetMethod()->IsSilentFile()) GetMethod()->BaseDir()->cd();
218 if (i==0) GetMethod()->GetTransformationHandler().CalcTransformations(
219 GetMethod()->Data()->GetEventCollection());
221 GetMethod()->Train();
223 currentFOM = GetFOM();
224 Log() << kINFO << "FOM was found : " << currentFOM << "; current best is " << bestFOM << Endl;
225
226 if (currentFOM > bestFOM) {
228 for (std::map<TString,Double_t>::iterator iter=currentParameters.begin();
229 iter != currentParameters.end(); ++iter){
230 fTunedParameters[iter->first]=iter->second;
231 }
232 }
233 }
234
235 GetMethod()->Reset();
236 GetMethod()->SetTuneParameters(fTunedParameters);
237}
238
239////////////////////////////////////////////////////////////////////////////////
240
242{
243 // ranges (intervals) in which the fit varies the parameters
244 std::vector<TMVA::Interval*> ranges; // intervals of the fit ranges
245 std::map<TString, TMVA::Interval*>::iterator it;
246 std::vector<Double_t> pars; // current (starting) fit parameters
247
248 for (it=fTuneParameters.begin(); it != fTuneParameters.end(); ++it){
249 ranges.push_back(new TMVA::Interval(*(it->second)));
250 pars.push_back( (it->second)->GetMean() ); // like this the order is "right". Always keep the
251 // order in the vector "pars" the same as the iterator
252 // iterates through the tuneParameters !!!!
253 }
254
255 // added to allow for transformation on input variables i.e. norm
256 GetMethod()->GetTransformationHandler().CalcTransformations(GetMethod()->Data()->GetEventCollection());
257
258 // create the fitter
259
260 FitterBase* fitter = NULL;
261
262 if ( fOptimizationFitType == "Minuit" ) {
263 TString opt="FitStrategy=0:UseImprove=False:UseMinos=False:Tolerance=100";
264 if (!TMVA::gConfig().IsSilent() ) opt += TString(":PrintLevel=0");
265
266 fitter = new MinuitFitter( *this,
267 "FitterMinuit_BDTOptimize",
268 ranges, opt );
269 }else if ( fOptimizationFitType == "FitGA" ) {
270 TString opt="PopSize=20:Steps=30:Cycles=3:ConvCrit=0.01:SaveBestCycle=5";
271 fitter = new GeneticFitter( *this,
272 "FitterGA_BDTOptimize",
273 ranges, opt );
274 } else {
275 Log() << kWARNING << " you did not specify a valid OptimizationFitType "
276 << " will use the default (FitGA) " << Endl;
277 TString opt="PopSize=20:Steps=30:Cycles=3:ConvCrit=0.01:SaveBestCycle=5";
278 fitter = new GeneticFitter( *this,
279 "FitterGA_BDTOptimize",
280 ranges, opt );
281 }
282
283 fitter->CheckForUnusedOptions();
284
285 // perform the fit
286 fitter->Run(pars);
287
288 // clean up
289 for (UInt_t ipar=0; ipar<ranges.size(); ipar++) delete ranges[ipar];
290
291 GetMethod()->Reset();
292
293 fTunedParameters.clear();
294 Int_t jcount=0;
295 for (it=fTuneParameters.begin(); it!=fTuneParameters.end(); ++it){
296 fTunedParameters.insert(std::pair<TString,Double_t>(it->first,pars[jcount++]));
297 }
298
299 GetMethod()->SetTuneParameters(fTunedParameters);
300
301}
302
303////////////////////////////////////////////////////////////////////////////////
304/// return the estimator (from current FOM) for the fitting interface
305
307{
308 std::map< std::vector<Double_t> , Double_t>::const_iterator iter;
309 iter = fAlreadyTrainedParCombination.find(pars);
310
311 if (iter != fAlreadyTrainedParCombination.end()) {
312 // std::cout << "I had trained Depth=" <<Int_t(pars[0])
313 // <<" MinEv=" <<Int_t(pars[1])
314 // <<" already --> FOM="<< iter->second <<std::endl;
315 return iter->second;
316 }else{
317 std::map<TString,Double_t> currentParameters;
318 Int_t icount =0; // map "pars" to the map of Tuneparameter, make sure
319 // you never screw up this order!!
320 std::map<TString, TMVA::Interval*>::iterator it;
321 for (it=fTuneParameters.begin(); it!=fTuneParameters.end(); ++it){
322 currentParameters[it->first] = pars[icount++];
323 }
324 GetMethod()->Reset();
325 GetMethod()->SetTuneParameters(currentParameters);
326 if(!GetMethod()->IsSilentFile()) GetMethod()->BaseDir()->cd();
327
328 if (fNotDoneYet){
329 GetMethod()->GetTransformationHandler().
330 CalcTransformations(GetMethod()->Data()->GetEventCollection());
331 fNotDoneYet=kFALSE;
332 }
334 GetMethod()->Train();
336
337
338 Double_t currentFOM = GetFOM();
339
340 fAlreadyTrainedParCombination.insert(std::make_pair(pars,-currentFOM));
341 return -currentFOM;
342 }
343}
344
345////////////////////////////////////////////////////////////////////////////////
346/// Return the Figure of Merit (FOM) used in the parameter
347/// optimization process
348
350{
351 auto parsePercent = [this](TString input) -> Double_t {
352 // Expects input e.g. SigEffAtBkgEff0 (14 chars) followed by a fraction
353 // either as e.g. 01 or .01 (meaning the same thing 1 %).
354 TString percent = TString(input(14, input.Sizeof()));
355 if (!percent.CountChar('.')) percent.Insert(1,".");
356
357 if (percent.IsFloat()) {
358 return percent.Atof();
359 } else {
360 Log() << kFATAL << " ERROR, " << percent << " in " << fFOMType
361 << " is not a valid floating point number" << Endl;
362 return 0; // Cannot happen
363 }
364 };
365
366 Double_t fom = 0;
367 if (fMethod->DoRegression()){
368 std::cout << " ERROR: Sorry, Regression is not yet implement for automatic parameter optimisation"
369 << " --> exit" << std::endl;
370 std::exit(1);
371 } else {
372 if (fFOMType == "Separation") fom = GetSeparation();
373 else if (fFOMType == "ROCIntegral") fom = GetROCIntegral();
374 else if (fFOMType.BeginsWith("SigEffAtBkgEff0")) fom = GetSigEffAtBkgEff(parsePercent(fFOMType));
375 else if (fFOMType.BeginsWith("BkgRejAtSigEff0")) fom = GetBkgRejAtSigEff(parsePercent(fFOMType));
376 else if (fFOMType.BeginsWith("BkgEffAtSigEff0")) fom = GetBkgEffAtSigEff(parsePercent(fFOMType));
377 else {
378 Log()<< kFATAL << " ERROR, you've specified as Figure of Merit in the "
379 << " parameter optimisation " << fFOMType << " which has not"
380 << " been implemented yet!! ---> exit " << Endl;
381 }
382 }
383
384 fFOMvsIter.push_back(fom);
385 // std::cout << "fom="<<fom<<std::endl; // should write that into a debug log (as option)
386 return fom;
387}
388
389////////////////////////////////////////////////////////////////////////////////
390/// fill the private histograms with the mva distributions for sig/bkg
391
393{
394 if (fMvaSig) fMvaSig->Delete();
395 if (fMvaBkg) fMvaBkg->Delete();
396 if (fMvaSigFineBin) fMvaSigFineBin->Delete();
397 if (fMvaBkgFineBin) fMvaBkgFineBin->Delete();
398
399 // maybe later on this should be done a bit more clever (time consuming) by
400 // first determining proper ranges, removing outliers, as we do in the
401 // MVA output calculation in MethodBase::TestClassifier...
402 // --> then it might be possible also to use the splined PDF's which currently
403 // doesn't seem to work
404
405 fMvaSig = new TH1D("fMvaSig","",100,-1.5,1.5); //used for spline fit
406 fMvaBkg = new TH1D("fMvaBkg","",100,-1.5,1.5); //used for spline fit
407 fMvaSigFineBin = new TH1D("fMvaSigFineBin","",100000,-1.5,1.5);
408 fMvaBkgFineBin = new TH1D("fMvaBkgFineBin","",100000,-1.5,1.5);
409
410 const std::vector< Event*> events=fMethod->Data()->GetEventCollection(Types::kTesting);
411
412 UInt_t signalClassNr = fMethod->DataInfo().GetClassInfo("Signal")->GetNumber();
413
414 // fMethod->GetTransformationHandler().CalcTransformations(fMethod->Data()->GetEventCollection(Types::kTesting));
415
416 for (UInt_t iev=0; iev < events.size() ; iev++){
417 // std::cout << " GetMVADists event " << iev << std::endl;
418 // std::cout << " Class = " << events[iev]->GetClass() << std::endl;
419 // std::cout << " MVA Value = " << fMethod->GetMvaValue(events[iev]) << std::endl;
420 if (events[iev]->GetClass() == signalClassNr) {
421 fMvaSig->Fill(fMethod->GetMvaValue(events[iev]),events[iev]->GetWeight());
422 fMvaSigFineBin->Fill(fMethod->GetMvaValue(events[iev]),events[iev]->GetWeight());
423 } else {
424 fMvaBkg->Fill(fMethod->GetMvaValue(events[iev]),events[iev]->GetWeight());
425 fMvaBkgFineBin->Fill(fMethod->GetMvaValue(events[iev]),events[iev]->GetWeight());
426 }
427 }
428}
429////////////////////////////////////////////////////////////////////////////////
430/// return the separation between the signal and background
431/// MVA ouput distribution
432
434{
435 GetMVADists();
436 if (1){
437 PDF *splS = new PDF( " PDF Sig", fMvaSig, PDF::kSpline2 );
438 PDF *splB = new PDF( " PDF Bkg", fMvaBkg, PDF::kSpline2 );
439 return gTools().GetSeparation(*splS,*splB);
440 }else{
441 std::cout << "Separation calculation via histograms (not PDFs) seems to give still strange results!! Don't do that, check!!"<<std::endl;
442 return gTools().GetSeparation(fMvaSigFineBin,fMvaBkgFineBin); // somehow still gives strange results!!!! Check!!!
443 }
444}
445
446////////////////////////////////////////////////////////////////////////////////
447/// calculate the area (integral) under the ROC curve as a
448/// overall quality measure of the classification
449///
450/// making pdfs out of the MVA-output distributions doesn't work
451/// reliably for cases where the MVA-output isn't a smooth distribution.
452/// this happens "frequently" in BDTs for example when the number of
453/// trees is small resulting in only some discrete possible MVA output values.
454/// (I still leave the code here, but use this with care!!! The default
455/// however is to use the distributions!!!
456
458{
459 GetMVADists();
460
461 Double_t integral = 0;
462 if (0){
463 PDF *pdfS = new PDF( " PDF Sig", fMvaSig, PDF::kSpline2 );
464 PDF *pdfB = new PDF( " PDF Bkg", fMvaBkg, PDF::kSpline2 );
465
466 Double_t xmin = TMath::Min(pdfS->GetXmin(), pdfB->GetXmin());
467 Double_t xmax = TMath::Max(pdfS->GetXmax(), pdfB->GetXmax());
468
469 UInt_t nsteps = 1000;
470 Double_t step = (xmax-xmin)/Double_t(nsteps);
471 Double_t cut = xmin;
472 for (UInt_t i=0; i<nsteps; i++){
473 integral += (1-pdfB->GetIntegral(cut,xmax)) * pdfS->GetVal(cut);
474 cut+=step;
475 }
476 integral*=step;
477 }else{
478 // sanity checks
479 if ( (fMvaSigFineBin->GetXaxis()->GetXmin() != fMvaBkgFineBin->GetXaxis()->GetXmin()) ||
480 (fMvaSigFineBin->GetNbinsX() != fMvaBkgFineBin->GetNbinsX()) ){
481 std::cout << " Error in OptimizeConfigParameters GetROCIntegral, unequal histograms for sig and bkg.." << std::endl;
482 std::exit(1);
483 }else{
484
485 Double_t *cumulator = fMvaBkgFineBin->GetIntegral();
486 Int_t nbins = fMvaSigFineBin->GetNbinsX();
487 // get the true signal integral (ComputeIntegral just return 1 as they
488 // automatically normalize. IN ADDITION, they do not account for variable
489 // bin sizes (which you might perhaps use later on for the fMvaSig/Bkg histograms)
491 for (Int_t ibin=1; ibin<=nbins; ibin++){
492 sigIntegral += fMvaSigFineBin->GetBinContent(ibin) * fMvaSigFineBin->GetBinWidth(ibin);
493 }
494 //gTools().NormHist( fMvaSigFineBin ); // also doesn't use variable bin width. And calls TH1::Scale, which oddly enough does not change the SumOfWeights !!!
495
496 for (Int_t ibin=1; ibin <= nbins; ibin++){ // don't include under- and overflow bin
497 integral += (cumulator[ibin]) * fMvaSigFineBin->GetBinContent(ibin)/sigIntegral * fMvaSigFineBin->GetBinWidth(ibin) ;
498 }
499 }
500 }
501
502 return integral;
503}
504
505////////////////////////////////////////////////////////////////////////////////
506/// calculate the signal efficiency for a given background efficiency
507
509{
510 GetMVADists();
512
513 // sanity checks
514 if ( (fMvaSigFineBin->GetXaxis()->GetXmin() != fMvaBkgFineBin->GetXaxis()->GetXmin()) ||
515 (fMvaSigFineBin->GetNbinsX() != fMvaBkgFineBin->GetNbinsX()) ){
516 std::cout << " Error in OptimizeConfigParameters GetSigEffAt, unequal histograms for sig and bkg.." << std::endl;
517 std::exit(1);
518 }else{
519 Double_t *bkgCumulator = fMvaBkgFineBin->GetIntegral();
520 Double_t *sigCumulator = fMvaSigFineBin->GetIntegral();
521
522 Int_t nbins=fMvaBkgFineBin->GetNbinsX();
523 Int_t ibin=0;
524
525 // std::cout << " bkgIntegral="<<bkgIntegral
526 // << " sigIntegral="<<sigIntegral
527 // << " bkgCumulator[nbins]="<<bkgCumulator[nbins]
528 // << " sigCumulator[nbins]="<<sigCumulator[nbins]
529 // << std::endl;
530
531 while (bkgCumulator[nbins-ibin] > (1-bkgEff)) {
532 sigEff = sigCumulator[nbins]-sigCumulator[nbins-ibin];
533 ibin++;
534 }
535 }
536 return sigEff;
537}
538
539
540////////////////////////////////////////////////////////////////////////////////
541/// calculate the background efficiency for a given signal efficiency
542///
543/// adapted by marc-olivier.bettler@cern.ch
544
546{
547 GetMVADists();
549
550 // sanity checks
551 if ( (fMvaSigFineBin->GetXaxis()->GetXmin() != fMvaBkgFineBin->GetXaxis()->GetXmin()) ||
552 (fMvaSigFineBin->GetNbinsX() != fMvaBkgFineBin->GetNbinsX()) ){
553 std::cout << " Error in OptimizeConfigParameters GetBkgEffAt, unequal histograms for sig and bkg.." << std::endl;
554 std::exit(1);
555 }else{
556
557 Double_t *bkgCumulator = fMvaBkgFineBin->GetIntegral();
558 Double_t *sigCumulator = fMvaSigFineBin->GetIntegral();
559
560 Int_t nbins=fMvaBkgFineBin->GetNbinsX();
561 Int_t ibin=0;
562
563 // std::cout << " bkgIntegral="<<bkgIntegral
564 // << " sigIntegral="<<sigIntegral
565 // << " bkgCumulator[nbins]="<<bkgCumulator[nbins]
566 // << " sigCumulator[nbins]="<<sigCumulator[nbins]
567 // << std::endl;
568
569 while ( sigCumulator[nbins]-sigCumulator[nbins-ibin] < sigEff) {
570 bkgEff = bkgCumulator[nbins]-bkgCumulator[nbins-ibin];
571 ibin++;
572 }
573 }
574 return bkgEff;
575}
576
577////////////////////////////////////////////////////////////////////////////////
578/// calculate the background rejection for a given signal efficiency
579///
580/// adapted by marc-olivier.bettler@cern.ch
581
583{
584 GetMVADists();
586
587 // sanity checks
588 if ( (fMvaSigFineBin->GetXaxis()->GetXmin() != fMvaBkgFineBin->GetXaxis()->GetXmin()) ||
589 (fMvaSigFineBin->GetNbinsX() != fMvaBkgFineBin->GetNbinsX()) ){
590 std::cout << " Error in OptimizeConfigParameters GetBkgEffAt, unequal histograms for sig and bkg.." << std::endl;
591 std::exit(1);
592 }else{
593
594 Double_t *bkgCumulator = fMvaBkgFineBin->GetIntegral();
595 Double_t *sigCumulator = fMvaSigFineBin->GetIntegral();
596
597 Int_t nbins=fMvaBkgFineBin->GetNbinsX();
598 Int_t ibin=0;
599
600 // std::cout << " bkgIntegral="<<bkgIntegral
601 // << " sigIntegral="<<sigIntegral
602 // << " bkgCumulator[nbins]="<<bkgCumulator[nbins]
603 // << " sigCumulator[nbins]="<<sigCumulator[nbins]
604 // << std::endl;
605
606 while ( sigCumulator[nbins]-sigCumulator[nbins-ibin] < sigEff) {
607 bkgRej = bkgCumulator[nbins-ibin];
608 ibin++;
609 }
610 }
611 return bkgRej;
612}
#define h(i)
Definition RSha256.hxx:106
size_t size(const MatrixT &matrix)
retrieve the size of a square matrix
int Int_t
Signed integer 4 bytes (int)
Definition RtypesCore.h:59
float Float_t
Float 4 bytes (float)
Definition RtypesCore.h:71
constexpr Bool_t kFALSE
Definition RtypesCore.h:108
double Double_t
Double 8 bytes.
Definition RtypesCore.h:73
constexpr Bool_t kTRUE
Definition RtypesCore.h:107
ROOT::Detail::TRangeCast< T, true > TRangeDynCast
TRangeDynCast is an adapter class that allows the typed iteration through a TCollection.
Option_t Option_t TPoint TPoint const char GetTextMagnitude GetFillStyle GetLineColor GetLineWidth GetMarkerStyle GetTextAlign GetTextColor GetTextSize void input
Option_t Option_t TPoint TPoint const char GetTextMagnitude GetFillStyle GetLineColor GetLineWidth GetMarkerStyle GetTextAlign GetTextColor GetTextSize void char Point_t Rectangle_t WindowAttributes_t index
Option_t Option_t TPoint TPoint percent
char name[80]
Definition TGX11.cxx:110
float xmin
float ymin
float xmax
float ymax
const_iterator begin() const
const_iterator end() const
A TGraph is an object made of two arrays X and Y with npoints each.
Definition TGraph.h:41
1-D histogram with a double per channel (see TH1 documentation)
Definition TH1.h:927
2-D histogram with a double per channel (see TH1 documentation)
Definition TH2.h:356
void CheckForUnusedOptions() const
checks for unused options in option string
static void SetIsTraining(Bool_t)
when this static function is called, it sets the flag whether events with negative event weight shoul...
Definition Event.cxx:399
Base class for TMVA fitters.
Definition FitterBase.h:51
Double_t Run()
estimator function interface for fitting
Fitter using a Genetic Algorithm.
The TMVA::Interval Class.
Definition Interval.h:61
Virtual base Class for all MVA method.
Definition MethodBase.h:111
const char * GetName() const override
Definition MethodBase.h:334
Bool_t DoRegression() const
Definition MethodBase.h:438
/Fitter using MINUIT
ostringstream derivative to redirect and format output
Definition MsgLogger.h:57
std::vector< int > GetScanIndices(int val, std::vector< int > base)
helper function to scan through the all the combinations in the parameter space
MsgLogger * fLogger
! message logger
Double_t GetBkgRejAtSigEff(Double_t sigEff=0.5)
calculate the background rejection for a given signal efficiency
virtual ~OptimizeConfigParameters()
the destructor (delete the OptimizeConfigParameters, store the graph and .. delete it)
Double_t GetBkgEffAtSigEff(Double_t sigEff=0.5)
calculate the background efficiency for a given signal efficiency
void optimizeScan()
do the actual optimization using a simple scan method, i.e.
OptimizeConfigParameters(MethodBase *const method, std::map< TString, TMVA::Interval * > tuneParameters, TString fomType="Separation", TString optimizationType="GA")
Constructor which sets either "Classification or Regression".
Double_t EstimatorFunction(std::vector< Double_t > &) override
return the estimator (from current FOM) for the fitting interface
std::map< TString, TMVA::Interval * > fTuneParameters
parameters included in the tuning
MethodBase *const fMethod
The MVA method to be evaluated.
TString fOptimizationFitType
which type of optimisation procedure to be used
std::map< TString, Double_t > optimize()
Double_t GetSeparation()
return the separation between the signal and background MVA ouput distribution
TString fFOMType
the FOM type (Separation, ROC integra.. whatever you implemented..
Double_t GetFOM()
Return the Figure of Merit (FOM) used in the parameter optimization process.
Double_t GetSigEffAtBkgEff(Double_t bkgEff=0.1)
calculate the signal efficiency for a given background efficiency
Double_t GetROCIntegral()
calculate the area (integral) under the ROC curve as a overall quality measure of the classification
void GetMVADists()
fill the private histograms with the mva distributions for sig/bkg
PDF wrapper for histograms; uses user-defined spline interpolation.
Definition PDF.h:63
@ kSpline2
Definition PDF.h:70
Double_t GetSeparation(TH1 *S, TH1 *B) const
compute "separation" defined as
Definition Tools.cxx:121
Basic string class.
Definition TString.h:138
Double_t y[n]
Definition legend1.C:17
Double_t x[n]
Definition legend1.C:17
const Int_t n
Definition legend1.C:16
Config & gConfig()
Tools & gTools()
MsgLogger & Endl(MsgLogger &ml)
Definition MsgLogger.h:148
Short_t Max(Short_t a, Short_t b)
Returns the largest of a and b.
Definition TMathBase.h:251
Short_t Min(Short_t a, Short_t b)
Returns the smallest of a and b.
Definition TMathBase.h:199