33
44#include " RooFitResult.h"
55#include " RooAbsPdf.h"
6- #include " RooWorkspace.h"
6+ #include " RooGaussian.h"
7+ #include " RooExponential.h"
8+ #include " RooAddPdf.h"
79#include " RooRandom.h"
810#include " RooDataHist.h"
911#include " RooDataSet.h"
@@ -17,51 +19,55 @@ TEST(SumW2Error, BatchMode)
1719 auto &msg = RooMsgService::instance ();
1820 msg.setGlobalKillBelow (RooFit::WARNING);
1921
20- RooWorkspace ws{" workspace" };
21-
22- auto *x = ws.factory (" x[-10, 10]" );
23- ws.factory (" Gaussian::sig(x, mu[-1, 1], s[0.1, 5])" );
24- ws.factory (" Chebychev::bkg(x, {c1[0.1, -1, 1]})" );
25- auto *shp = static_cast <RooAbsPdf *>(ws.factory (" SUM::shp(Nsig[0, 20000] * sig, Nbkg[0, 20000] * bkg)" ));
26- auto &model = *shp;
27-
28- // parameters
29- auto *mu = ws.var (" mu" );
30- auto *s = ws.var (" s" );
31- auto *c1 = ws.var (" c1" );
32- auto *Nsig = ws.var (" Nsig" );
33- auto *Nbkg = ws.var (" Nbkg" );
34-
35- auto resetParameters = [&]() {
36- mu->setVal (0.0 );
37- mu->setError (0.0 );
38- s->setVal (2.0 );
39- s->setError (0.0 );
40- c1->setVal (0.1 );
41- c1->setError (0.0 );
42- Nsig->setVal (10000.0 );
43- Nsig->setError (0.0 );
44- Nbkg->setVal (10000.0 );
45- Nbkg->setError (0.0 );
22+ RooRealVar x{" x" , " x" , 0 , 0 , 10 };
23+ RooRealVar mu{" mu" , " mu" , 3 , 0 , 10 };
24+ RooRealVar s{" s" , " s" , 1.0 , 0.1 , 5 };
25+ RooRealVar c1{" c1" , " c1" , -0.5 , -3 , -0.1 };
26+ RooRealVar f{" f" , " f" , 0.2 , 0.0 , 1.0 };
27+
28+ RooGaussian sig{" sig" , " sig" , x, mu, s};
29+ RooExponential bkg{" bkg" , " bkg" , x, c1};
30+ RooAddPdf model{" model" , " model" , {sig, bkg}, {f}};
31+
32+ auto resetParametersToInitialFitValues = [&]() {
33+ mu.setVal (4.0 );
34+ mu.setError (0.0 );
35+ s.setVal (2.0 );
36+ s.setError (0.0 );
37+ c1.setVal (-0.4 );
38+ c1.setError (0.0 );
39+ f.setVal (0.3 );
40+ f.setError (0.0 );
4641 };
4742
4843 std::size_t nEvents = 1000 ;
4944
5045 RooRandom::randomGenerator ()->SetSeed (4357 );
51- std::unique_ptr<RooAbsData> dataHist{shp->generateBinned (*x, nEvents)};
52- std::unique_ptr<RooAbsData> dataSet{shp->generate (*x, nEvents)};
46+ std::unique_ptr<RooAbsData> dataHist{model.generateBinned (x, nEvents)};
47+ std::unique_ptr<RooAbsData> dataSet{model.generate (x, nEvents)};
48+
49+ // these datasets will be filled with a weight that is not unity
50+ RooRealVar weight (" weight" , " weight" , 0.5 , 0.0 , 1.0 );
51+ RooDataHist dataHistWeighted (" dataHistWeighted" , " dataHistWeighted" , x);
52+ RooDataSet dataSetWeighted (" dataSetWeighted" , " dataSetWeighted" , {x, weight}, " weight" );
53+
54+ for (std::size_t i = 0 ; i < nEvents; ++i) {
55+ dataHistWeighted.add (*dataSet->get (), 0.5 ); // filling the histogram from a dataset is easier
56+ dataSetWeighted.add (*dataSet->get (), 0.5 );
57+ }
5358
5459 auto fit = [&](RooAbsData &data, bool sumw2 = false , bool batchmode = false , std::string const &minimizer = " Minuit" ,
5560 int printLevel = -1 ) {
5661 using namespace RooFit ;
5762
58- resetParameters ();
63+ resetParametersToInitialFitValues ();
5964
60- return std::unique_ptr<RooFitResult>{model.fitTo (data, Extended (), Save (), SumW2Error (sumw2), Strategy (1 ),
65+ return std::unique_ptr<RooFitResult>{model.fitTo (data, Save (), SumW2Error (sumw2), Strategy (1 ),
6166 BatchMode (batchmode), Minimizer (minimizer.c_str ()),
6267 PrintLevel (printLevel))};
6368 };
6469
70+ // Compare batch mode vs. scalar mode for non-SumW2 fits on UNWEIGHTED datasets
6571 EXPECT_TRUE (fit (*dataSet, 0 , 0 , " Minuit" )->isIdentical (*fit (*dataSet, 0 , 1 , " Minuit" )))
6672 << " different results for Minuit fit to RooDataSet without SumW2Error correction." ;
6773 EXPECT_TRUE (fit (*dataHist, 0 , 0 , " Minuit" )->isIdentical (*fit (*dataHist, 0 , 1 , " Minuit" )))
@@ -71,10 +77,12 @@ TEST(SumW2Error, BatchMode)
7177 EXPECT_TRUE (fit (*dataHist, 0 , 0 , " Minuit2" )->isIdentical (*fit (*dataHist, 0 , 1 , " Minuit2" )))
7278 << " different results for Minuit2 fit to RooDataHist without SumW2Error correction." ;
7379
74- // We can't compare the covariance matrix in these cases, because it is
80+ // We can't compare the covariance matrix in these next cases, because it is
7581 // externally provided. Still, it's okay because the parameter values and
7682 // errors are compared, where the errors are inferred from the external
7783 // covariance matrix.
84+
85+ // Compare batch mode vs. scalar mode for SumW2 fits on UNWEIGHTED datasets
7886 EXPECT_TRUE (fit (*dataSet, 1 , 0 , " Minuit" )->isIdenticalNoCov (*fit (*dataSet, 1 , 1 , " Minuit" )))
7987 << " different results for Minuit fit to RooDataSet with SumW2Error correction." ;
8088 EXPECT_TRUE (fit (*dataHist, 1 , 0 , " Minuit" )->isIdenticalNoCov (*fit (*dataHist, 1 , 1 , " Minuit" )))
@@ -83,4 +91,14 @@ TEST(SumW2Error, BatchMode)
8391 << " different results for Minuit2 fit to RooDataSet with SumW2Error correction." ;
8492 EXPECT_TRUE (fit (*dataHist, 1 , 0 , " Minuit2" )->isIdenticalNoCov (*fit (*dataHist, 1 , 1 , " Minuit2" )))
8593 << " different results for Minuit2 fit to RooDataHist with SumW2Error correction." ;
94+
95+ // Compare batch mode vs. scalar mode for SumW2 fits on WEIGHTED datasets
96+ EXPECT_TRUE (fit (dataSetWeighted, 1 , 0 , " Minuit" )->isIdenticalNoCov (*fit (dataSetWeighted, 1 , 1 , " Minuit" )))
97+ << " different results for Minuit fit to weighted RooDataSet with SumW2Error correction." ;
98+ EXPECT_TRUE (fit (dataHistWeighted, 1 , 0 , " Minuit" )->isIdenticalNoCov (*fit (dataHistWeighted, 1 , 1 , " Minuit" )))
99+ << " different results for Minuit fit to weighted RooDataHist with SumW2Error correction." ;
100+ EXPECT_TRUE (fit (dataSetWeighted, 1 , 0 , " Minuit2" )->isIdenticalNoCov (*fit (dataSetWeighted, 1 , 1 , " Minuit2" )))
101+ << " different results for Minuit2 fit to weighted RooDataSet with SumW2Error correction." ;
102+ EXPECT_TRUE (fit (dataHistWeighted, 1 , 0 , " Minuit2" )->isIdenticalNoCov (*fit (dataHistWeighted, 1 , 1 , " Minuit2" )))
103+ << " different results for Minuit2 fit to weighted RooDataHist with SumW2Error correction." ;
86104}
0 commit comments