Logo ROOT  
Reference Guide
 
Loading...
Searching...
No Matches
RooDataSet.cxx
Go to the documentation of this file.
1/*****************************************************************************
2 * Project: RooFit *
3 * Package: RooFitCore *
4 * @(#)root/roofitcore:$Id$
5 * Authors: *
6 * WV, Wouter Verkerke, UC Santa Barbara, verkerke@slac.stanford.edu *
7 * DK, David Kirkby, UC Irvine, dkirkby@uci.edu *
8 * *
9 * Copyright (c) 2000-2005, Regents of the University of California *
10 * and Stanford University. All rights reserved. *
11 * *
12 * Redistribution and use in source and binary forms, *
13 * with or without modification, are permitted according to the terms *
14 * listed in LICENSE (http://roofit.sourceforge.net/license.txt) *
15 *****************************************************************************/
16
17/**
18\file RooDataSet.cxx
19\class RooDataSet
20\ingroup Roofitcore
21
22Container class to hold unbinned data. The binned equivalent is
23RooDataHist. In RooDataSet, each data point in N-dimensional space is represented
24by a RooArgSet of RooRealVar, RooCategory or RooStringVar objects, which can be
25retrieved using get().
26
27Since RooDataSet saves every event, it allows for fits with highest precision. With a large
28amount of data, however, it could be beneficial to represent them in binned form,
29i.e., RooDataHist. Binning the data will incur a loss of information, though.
30RooDataHist on the other hand may suffer from the curse of dimensionality if a high-dimensional
31problem with a lot of bins on each axis is tackled.
32
33### Inspecting a dataset
34Inspect a dataset using Print() with the "verbose" option:
35```
36dataset->Print("V");
37dataset->get(0)->Print("V");
38dataset->get(1)->Print("V");
39...
40```
41
42### Plotting data.
43See RooAbsData::plotOn().
44
45
46### Storage strategy
47There are two storage backends:
48- RooVectorDataStore (default): std::vectors in memory. They are fast, but they
49cannot be serialised if the dataset exceeds a size of 1 Gb
50- RooTreeDataStore: Uses a TTree under the hood. Note that the TTree is not
51attached to any currently-opened TFile in order to avoid double-ownership.
52 - Enable tree-backed storage similar to this:
53 ```
54 TFile outputFile("filename.root", "RECREATE");
55 RooAbsData::setDefaultStorageType(RooAbsData::Tree);
56 RooDataSet mydata(...);
57 ```
58 - Or convert an existing memory-backed data storage:
59 ```
60 RooDataSet mydata(...);
61
62 TFile outputFile("filename.root", "RECREATE");
63 mydata.convertToTreeStore();
64 ```
65
66For the inverse conversion, see `RooAbsData::convertToVectorStore()`.
67
68
69### Creating a dataset using RDataFrame
70See RooAbsDataHelper, rf408_RDataFrameToRooFit.C
71
72### Uniquely identifying RooDataSet objects
73
74\warning Before v6.28, it was ensured that no RooDataSet objects on the heap
75were located at an address that had already been used for a RooDataSet before.
76With v6.28, this is not guaranteed anymore. Hence, if your code uses pointer
77comparisons to uniquely identify RooDataSet instances, please consider using
78the new `RooAbsData::uniqueId()`.
79
80
81**/
82
83#include "RooDataSet.h"
84
85#include "RooPlot.h"
86#include "RooAbsReal.h"
87#include "Roo1DTable.h"
88#include "RooCategory.h"
89#include "RooFormula.h"
90#include "RooFormulaVar.h"
91#include "RooArgList.h"
92#include "RooRealVar.h"
93#include "RooDataHist.h"
94#include "RooMsgService.h"
95#include "RooCmdConfig.h"
96#include "RooHist.h"
97#include "RooTreeDataStore.h"
98#include "RooVectorDataStore.h"
100#include "RooSentinel.h"
101#include "RooTrace.h"
102#include "RooFitImplHelpers.h"
103
104#include "ROOT/StringUtils.hxx"
105
106#include "Math/Util.h"
107#include "TTree.h"
108#include "TFile.h"
109#include "TBuffer.h"
110#include "strlcpy.h"
111#include "snprintf.h"
112
113#include <iostream>
114#include <memory>
115#include <fstream>
116
117
118using std::endl, std::string, std::map, std::list, std::ifstream, std::ofstream, std::ostream;
119
120
122
123////////////////////////////////////////////////////////////////////////////////
124/// Default constructor for persistence
125
130
131namespace {
132
133struct FinalizeVarsOutput {
134 RooArgSet finalVars;
135 std::unique_ptr<RooRealVar> weight;
136 std::string weightVarName;
137 RooArgSet errorSet;
138};
139
140FinalizeVarsOutput finalizeVars(RooArgSet const &vars,
141 RooAbsArg * indexCat,
142 const char* wgtVarName,
145 RooArgSet * errorSet)
146{
147 FinalizeVarsOutput out;
148 out.finalVars.add(vars);
149
150 // Gather all imported weighted datasets to infer the weight variable name
151 // and whether we need weight errors
152 std::vector<RooAbsData*> weightedImpDatasets;
153 if(impData && impData->isWeighted()) weightedImpDatasets.push_back(impData);
155 if(data->isWeighted()) {
156 weightedImpDatasets.push_back(data);
157 }
158 }
159
160 bool needsWeightErrors = false;
161
162 // Figure out if the weight needs to store errors
164 if(dynamic_cast<RooDataHist const*>(data)) {
165 needsWeightErrors = true;
166 }
167 }
168
169 if (indexCat) {
170 out.finalVars.add(*indexCat, true);
171 }
172
173 out.weightVarName = wgtVarName ? wgtVarName : "";
174
175 if(out.weightVarName.empty()) {
176 // Even if no weight variable is specified, we want to have one if we are
177 // importing weighted datasets
179 if(auto ds = dynamic_cast<RooDataSet const*>(data)) {
180 // If the imported data is a RooDataSet, we take over its weight variable name
181 out.weightVarName = ds->weightVar()->GetName();
182 break;
183 } else {
185 // Don't break here! The next imported data might be a RooDataSet,
186 // and in that case we want to take over its weight name instead of
187 // using the default one.
188 }
189 }
190 }
191
192 // If the weight variable is required but is not in the set, create and add
193 // it on the fly
194 RooAbsArg * wgtVar = out.finalVars.find(out.weightVarName.c_str());
195 if (!out.weightVarName.empty() && !wgtVar) {
196 const char* name = out.weightVarName.c_str();
197 out.weight = std::make_unique<RooRealVar>(name, name, 1.0);
198 wgtVar = out.weight.get();
199 out.finalVars.add(*out.weight);
200 }
201
203 out.errorSet.add(*wgtVar);
204 }
205
206 // Combine the error set figured out by finalizeVars and the ones passed by the user
207 if(errorSet) out.errorSet.add(*errorSet, /*silent=*/true);
208
209 return out;
210}
211
212// generating an unbinned dataset from a binned one
213std::unique_ptr<RooDataSet> makeDataSetFromDataHist(RooDataHist const &hist)
214{
215 using namespace RooFit;
216
218 const char* wgtName = wgtVarCmdArg.getString(0);
219 // Instantiate weight variable here such that we can pass it to StoreError()
221
222 RooArgSet vars{*hist.get(), wgtVar};
223
224 // We have to explicitly store the errors that are implied by the sum of weights squared.
225 auto data = std::make_unique<RooDataSet>(hist.GetName(), hist.GetTitle(), vars, wgtVarCmdArg, StoreError(wgtVar));
226 for (int i = 0; i < hist.numEntries(); ++i) {
227 data->add(*hist.get(i), hist.weight(i), std::sqrt(hist.weightSquared(i)));
228 }
229
230 return data;
231}
232
233} // namespace
234
235////////////////////////////////////////////////////////////////////////////////
236/// Construct an unbinned dataset from a RooArgSet defining the dimensions of the data space. Optionally, data
237/// can be imported at the time of construction.
238///
239/// <table>
240/// <tr><th> %RooCmdArg <th> Effect
241/// <tr><td> Import(TTree&) <td> Import contents of given TTree. Only branches of the TTree that have names
242/// corresponding to those of the RooAbsArgs that define the RooDataSet are
243/// imported.
244/// <tr><td> ImportFromFile(const char* fileName, const char* treeName) <td> Import tree with given name from file with given name.
245/// <tr><td> Import(RooAbsData&)
246/// <td> Import contents of given RooDataSet or RooDataHist. Only observables that are common with the definition of this dataset will be imported
247/// <tr><td> Index(RooCategory&) <td> Prepare import of datasets into a N+1 dimensional RooDataSet
248/// where the extra discrete dimension labels the source of the imported histogram.
249/// <tr><td> Import(const char*, RooAbsData&)
250/// <td> Import a RooDataSet or RooDataHist to be associated with the given state name of the index category
251/// specified in Index(). If the given state name is not yet defined in the index
252/// category it will be added on the fly. The import command can be specified multiple times.
253/// <tr><td> Link(const char*, RooDataSet&) <td> Link contents of supplied RooDataSet to this dataset for given index category state name.
254/// In this mode, no data is copied and the linked dataset must be remain live for the duration
255/// of this dataset. Note that link is active for both reading and writing, so modifications
256/// to the aggregate dataset will also modify its components. Link() and Import() are mutually exclusive.
257/// <tr><td> OwnLinked() <td> Take ownership of all linked datasets
258/// <tr><td> Import(std::map<string,RooAbsData*>&) <td> As above, but allows specification of many imports in a single operation
259/// <tr><td> Link(std::map<string,RooDataSet*>&) <td> As above, but allows specification of many links in a single operation
260/// <tr><td> Cut(const char*) <br>
261/// Cut(RooFormulaVar&)
262/// <td> Apply the given cut specification when importing data
263/// <tr><td> CutRange(const char*) <td> Only accept events in the observable range with the given name
264/// <tr><td> WeightVar(const char*) <br>
265/// WeightVar(const RooAbsArg&)
266/// <td> Interpret the given variable as event weight rather than as observable
267/// <tr><td> StoreError(const RooArgSet&) <td> Store symmetric error along with value for given subset of observables
268/// <tr><td> StoreAsymError(const RooArgSet&) <td> Store asymmetric error along with value for given subset of observables
269/// <tr><td> `GlobalObservables(const RooArgSet&)` <td> Define the set of global observables to be stored in this RooDataSet.
270/// A snapshot of the passed RooArgSet is stored, meaning the values wont't change unexpectedly.
271/// </table>
272///
273
275 const RooCmdArg& arg4,const RooCmdArg& arg5,const RooCmdArg& arg6,const RooCmdArg& arg7,const RooCmdArg& arg8) :
276 RooAbsData(name,title,{})
277{
279
280 // Define configuration for this method
281 RooCmdConfig pc("RooDataSet::ctor(" + std::string(GetName()) + ")");
282 pc.defineInt("ownLinked","OwnLinked",0) ;
283 pc.defineObject("impTree","ImportTree",0) ;
284 pc.defineObject("impData","ImportData",0) ;
285 pc.defineObject("indexCat","IndexCat",0) ;
286 pc.defineObject("impSliceData","ImportDataSlice",0,nullptr,true) ; // array
287 pc.defineString("impSliceState","ImportDataSlice",0,"",true) ; // array
288 pc.defineObject("lnkSliceData","LinkDataSlice",0,nullptr,true) ; // array
289 pc.defineString("lnkSliceState","LinkDataSlice",0,"",true) ; // array
290 pc.defineString("cutSpec","CutSpec",0,"") ;
291 pc.defineObject("cutVar","CutVar",0) ;
292 pc.defineString("cutRange","CutRange",0,"") ;
293 pc.defineString("wgtVarName","WeightVarName",0,"") ;
294 pc.defineInt("newWeight1","WeightVarName",0,0) ;
295 pc.defineString("fname","ImportFromFile",0,"") ;
296 pc.defineString("tname","ImportFromFile",1,"") ;
297 pc.defineObject("wgtVar","WeightVar",0) ;
298 pc.defineInt("newWeight2","WeightVar",0,0) ;
299 pc.defineObject("dummy1","ImportDataSliceMany",0) ;
300 pc.defineObject("dummy2","LinkDataSliceMany",0) ;
301 pc.defineSet("errorSet","StoreError",0) ;
302 pc.defineSet("asymErrSet","StoreAsymError",0) ;
303 pc.defineSet("glObs","GlobalObservables",0,nullptr) ;
304 pc.defineMutex("ImportTree","ImportData","ImportDataSlice","LinkDataSlice","ImportFromFile") ;
305 pc.defineMutex("CutSpec","CutVar") ;
306 pc.defineMutex("WeightVarName","WeightVar") ;
307 pc.defineDependency("ImportDataSlice","IndexCat") ;
308 pc.defineDependency("LinkDataSlice","IndexCat") ;
309 pc.defineDependency("OwnLinked","LinkDataSlice") ;
310
311
313 l.Add((TObject*)&arg1) ; l.Add((TObject*)&arg2) ;
314 l.Add((TObject*)&arg3) ; l.Add((TObject*)&arg4) ;
315 l.Add((TObject*)&arg5) ; l.Add((TObject*)&arg6) ;
316 l.Add((TObject*)&arg7) ; l.Add((TObject*)&arg8) ;
317
318 // Process & check varargs
319 pc.process(l) ;
320 if (!pc.ok(true)) {
321 const std::string errMsg = "Error in RooDataSet constructor: command argument list could not be processed";
322 coutE(InputArguments) << errMsg << std::endl;
323 throw std::invalid_argument(errMsg);
324 }
325
326 if(pc.getSet("glObs")) setGlobalObservables(*pc.getSet("glObs"));
327
328 // Extract relevant objects
329 TTree* impTree = static_cast<TTree*>(pc.getObject("impTree")) ;
330 auto impData = static_cast<RooAbsData*>(pc.getObject("impData")) ;
331 RooFormulaVar* cutVar = static_cast<RooFormulaVar*>(pc.getObject("cutVar")) ;
332 const char* cutSpec = pc.getString("cutSpec","",true) ;
333 const char* cutRange = pc.getString("cutRange","",true) ;
334 const char* wgtVarName = pc.getString("wgtVarName","",true) ;
335 RooRealVar* wgtVar = static_cast<RooRealVar*>(pc.getObject("wgtVar")) ;
336 const char* impSliceNames = pc.getString("impSliceState","",true) ;
337 const RooLinkedList& impSliceData = pc.getObjectList("impSliceData") ;
338 const char* lnkSliceNames = pc.getString("lnkSliceState","",true) ;
339 const RooLinkedList& lnkSliceData = pc.getObjectList("lnkSliceData") ;
340 RooCategory* indexCat = static_cast<RooCategory*>(pc.getObject("indexCat")) ;
341 RooArgSet* asymErrorSet = pc.getSet("asymErrSet") ;
342 const char* fname = pc.getString("fname") ;
343 const char* tname = pc.getString("tname") ;
344 Int_t ownLinked = pc.getInt("ownLinked") ;
345 Int_t newWeight = pc.getInt("newWeight1") + pc.getInt("newWeight2") ;
346
347 // Lookup name of weight variable if it was specified by object reference
348 if(wgtVar) {
349 wgtVarName = wgtVar->GetName();
350 }
351
352 auto finalVarsInfo = finalizeVars(vars,indexCat,wgtVarName,impData,impSliceData, pc.getSet("errorSet"));
353 initializeVars(finalVarsInfo.finalVars);
354 if(!finalVarsInfo.weightVarName.empty()) {
355 wgtVarName = finalVarsInfo.weightVarName.c_str();
356 }
357
358 RooArgSet* errorSet = finalVarsInfo.errorSet.empty() ? nullptr : &finalVarsInfo.errorSet;
359
360 // Case 1 --- Link multiple dataset as slices
361 if (lnkSliceNames) {
362
363 // Make import mapping if index category is specified
365 if (indexCat) {
366 char tmp[64000];
367 strlcpy(tmp, lnkSliceNames, 64000);
368 char *token = strtok(tmp, ",");
369 auto hiter = lnkSliceData.begin();
370 while (token) {
371 hmap[token] = static_cast<RooAbsData *>(*hiter);
372 token = strtok(nullptr, ",");
373 ++hiter;
374 }
375 }
376
377 // Initialize RooDataSet with optional weight variable
378 initialize(nullptr) ;
379
381 RooCategory* icat = static_cast<RooCategory*> (indexCat ? _vars.find(indexCat->GetName()) : nullptr ) ;
382 if (!icat) {
383 throw std::string("RooDataSet::RooDataSet() ERROR in constructor, cannot find index category") ;
384 }
385 for (map<string,RooAbsData*>::iterator hiter = hmap.begin() ; hiter!=hmap.end() ; ++hiter) {
386 // Define state labels in index category (both in provided indexCat and in internal copy in dataset)
387 if (indexCat && !indexCat->hasLabel(hiter->first)) {
388 indexCat->defineType(hiter->first) ;
389 coutI(InputArguments) << "RooDataSet::ctor(" << GetName() << ") defining state \"" << hiter->first << "\" in index category " << indexCat->GetName() << std::endl ;
390 }
391 if (icat && !icat->hasLabel(hiter->first)) {
392 icat->defineType(hiter->first) ;
393 }
394 icat->setLabel(hiter->first.c_str()) ;
395 storeMap[icat->getCurrentLabel()]=hiter->second->store() ;
396
397 // Take ownership of slice if requested
398 if (ownLinked) {
399 addOwnedComponent(hiter->first.c_str(),*hiter->second) ;
400 }
401 }
402
403 // Create composite datastore
404 _dstore = std::make_unique<RooCompositeDataStore>(name,title,_vars,*icat,storeMap) ;
405
406 return;
407 }
408
409 // Create empty datastore
410 RooTreeDataStore* tstore = nullptr;
411 if (defaultStorageType==Tree) {
412 _dstore = std::make_unique<RooTreeDataStore>(name,title,_vars,wgtVarName) ;
413 tstore = static_cast<RooTreeDataStore*>(_dstore.get());
414 } else if (defaultStorageType==Vector) {
415 if (wgtVarName && newWeight) {
416 RooAbsArg* wgttmp = _vars.find(wgtVarName) ;
417 if (wgttmp) {
418 wgttmp->setAttribute("NewWeight") ;
419 }
420 }
421 _dstore = std::make_unique<RooVectorDataStore>(name,title,_vars,wgtVarName) ;
422 }
423
424
425 // Make import mapping if index category is specified
426 std::map<string,RooAbsData*> hmap ;
427 if (indexCat) {
428 auto hiter = impSliceData.begin() ;
429 for (const auto& token : ROOT::Split(impSliceNames, ",")) {
430
431 if (!indexCat->hasLabel(token)) {
432 std::stringstream errorMsgStream;
433 errorMsgStream << "RooDataSet::RooDataSet(\"" << GetName() << "\") "
434 << "you are providing import data for the category state \"" << token
435 << "\", but the index category \"" << indexCat->GetName() << "\" has no such state!";
436 const std::string errorMsg = errorMsgStream.str();
437 coutE(InputArguments) << errorMsg << std::endl;
438 throw std::invalid_argument(errorMsg);
439 }
440
441 hmap[token] = static_cast<RooDataSet*>(*hiter);
442 ++hiter;
443 }
444 }
445
446 // process StoreError requests
447 if (errorSet) {
448 std::unique_ptr<RooArgSet> intErrorSet{_vars.selectCommon(*errorSet)};
449 intErrorSet->setAttribAll("StoreError") ;
450 for(RooAbsArg* arg : *intErrorSet) {
451 arg->attachToStore(*_dstore) ;
452 }
453 }
454 if (asymErrorSet) {
455 std::unique_ptr<RooArgSet> intAsymErrorSet{_vars.selectCommon(*asymErrorSet)};
456 intAsymErrorSet->setAttribAll("StoreAsymError") ;
457 for(RooAbsArg* arg : *intAsymErrorSet) {
458 arg->attachToStore(*_dstore) ;
459 }
460 }
461
462 // Initialize RooDataSet with optional weight variable
464
465 // Import one or more datasets
466 std::unique_ptr<RooFormulaVar> cutVarTmp;
467
468 if (indexCat) {
469 // Case 2 --- Import multiple RooDataSets as slices
470 loadValuesFromSlices(*indexCat, hmap, cutRange, cutVar, cutSpec);
471 } else if (impData) {
472 // Case 3 --- Import RooDataSet
473 std::unique_ptr<RooDataSet> impDataSet;
474
475 // If we are importing a RooDataHist, first convert it to a RooDataSet
476 if(impData->InheritsFrom(RooDataHist::Class())) {
477 impDataSet = makeDataSetFromDataHist(static_cast<RooDataHist const &>(*impData));
478 impData = impDataSet.get();
479 }
480 if (cutSpec) {
481 cutVarTmp = std::make_unique<RooFormulaVar>(cutSpec, cutSpec, *impData->get(), /*checkVariables=*/false);
482 cutVar = cutVarTmp.get();
483 }
484 _dstore->loadValues(impData->store(), cutVar, cutRange);
485
486 } else if (impTree || (fname && strlen(fname))) {
487 // Case 4 --- Import TTree from memory / file
488 std::unique_ptr<TFile> file;
489
490 if (impTree == nullptr) {
491 file.reset(TFile::Open(fname));
492 if (!file) {
493 std::stringstream ss;
494 ss << "RooDataSet::ctor(" << GetName() << ") ERROR file '" << fname
495 << "' cannot be opened or does not exist";
496 const std::string errMsg = ss.str();
497 coutE(InputArguments) << errMsg << std::endl;
498 throw std::invalid_argument(errMsg);
499 }
500
501 file->GetObject(tname, impTree);
502 if (!impTree) {
503 std::stringstream ss;
504 ss << "RooDataSet::ctor(" << GetName() << ") ERROR file '" << fname
505 << "' does not contain a TTree named '" << tname << "'";
506 const std::string errMsg = ss.str();
507 coutE(InputArguments) << errMsg << std::endl;
508 throw std::invalid_argument(errMsg);
509 }
510 }
511
512 if (cutSpec) {
513 cutVarTmp = std::make_unique<RooFormulaVar>(cutSpec, cutSpec, _vars, /*checkVariables=*/false);
514 cutVar = cutVarTmp.get();
515 }
516
517 if (tstore) {
518 tstore->loadValues(impTree, cutVar, cutRange);
519 } else {
521 tmpstore.loadValues(impTree, cutVar, cutRange);
522 _dstore->append(tmpstore);
523 }
524 }
525}
526
527////////////////////////////////////////////////////////////////////////////////
528/// Copy constructor
529
532{
533 initialize(other._wgtVar ? other._wgtVar->GetName() : nullptr);
535}
536
537////////////////////////////////////////////////////////////////////////////////
538/// Return an empty clone of this dataset. If vars is not null, only the variables in vars
539/// are added to the definition of the empty clone
540
541RooFit::OwningPtr<RooAbsData> RooDataSet::emptyClone(const char* newName, const char* newTitle, const RooArgSet* vars, const char* wgtVarName) const
542{
543 bool useOldWeight = _wgtVar && (wgtVarName == nullptr || strcmp(wgtVarName, _wgtVar->GetName()) == 0);
544
545 if(newName == nullptr) newName = GetName();
546 if(newTitle == nullptr) newTitle = GetTitle();
548
550 if(vars == nullptr) {
551 vars2.add(_vars);
552 } else {
553 for(RooAbsArg *var : *vars) {
554 // We should take the variables from the original dataset if
555 // available, such that we can query the "StoreError" and
556 // "StoreAsymError" attributes.
557 auto varInData = _vars.find(*var);
558 vars2.add(varInData ? *varInData : *var);
559 }
560 // We also need to add the weight variable of the original dataset if
561 // it's not added yet, again to query the error attributes correctly.
562 if(useOldWeight && !vars2.find(wgtVarName)) vars2.add(*_wgtVar);
563 }
564
565 RooArgSet errorSet;
567
568 for(RooAbsArg *var : vars2) {
569 if(var->getAttribute("StoreError")) errorSet.add(*var);
570 if(var->getAttribute("StoreAsymError")) asymErrorSet.add(*var);
571 }
572
573 using namespace RooFit;
574 return RooFit::makeOwningPtr<RooAbsData>(std::make_unique<RooDataSet>(
575 newName, newTitle, vars2, WeightVar(wgtVarName), StoreError(errorSet), StoreAsymError(asymErrorSet)));
576}
577
578
579
580////////////////////////////////////////////////////////////////////////////////
581/// Initialize the dataset. If wgtVarName is not null, interpret the observable
582/// with that name as event weight
583
585{
588 _wgtVar = nullptr ;
589 if (wgtVarName) {
591 if (!wgt) {
592 coutE(DataHandling) << "RooDataSet::RooDataSet(" << GetName() << "): designated weight variable "
593 << wgtVarName << " not found in set of variables, no weighting will be assigned" << std::endl ;
594 throw std::invalid_argument("RooDataSet::initialize() weight variable could not be initialised.");
595 } else if (!dynamic_cast<RooRealVar*>(wgt)) {
596 coutE(DataHandling) << "RooDataSet::RooDataSet(" << GetName() << "): designated weight variable "
597 << wgtVarName << " is not of type RooRealVar, no weighting will be assigned" << std::endl ;
598 throw std::invalid_argument("RooDataSet::initialize() weight variable could not be initialised.");
599 } else {
601 _wgtVar = static_cast<RooRealVar*>(wgt) ;
602 }
603 }
604}
605
606
607
608////////////////////////////////////////////////////////////////////////////////
609/// Implementation of RooAbsData virtual method that drives the RooAbsData::reduce() methods
610
611std::unique_ptr<RooAbsData> RooDataSet::reduceEng(const RooArgSet &varSubset, const RooFormulaVar *cutVar,
612 const char *cutRange, std::size_t nStart, std::size_t nStop) const
613{
614 checkInit();
615 RooArgSet tmp(varSubset);
616 if (_wgtVar) {
617 tmp.add(*_wgtVar);
618 }
619
620 auto createEmptyClone = [&]() { return emptyClone(GetName(), GetTitle(), &tmp); };
621
622 std::unique_ptr<RooAbsData> out{createEmptyClone()};
623
624 if (!cutRange || strchr(cutRange, ',') == nullptr) {
625 auto &ds = static_cast<RooDataSet &>(*out);
626 ds._dstore = _dstore->reduce(ds.GetName(), ds.GetTitle(), ds._vars, cutVar, cutRange, nStart, nStop);
627 ds._cachedVars.add(_dstore->cachedVars());
628 } else {
629 // Composite case: multiple ranges
630 auto tokens = ROOT::Split(cutRange, ",");
632 std::stringstream errMsg;
633 errMsg << "Error in RooAbsData::reduce! The ranges " << cutRange << " are overlapping!";
634 throw std::runtime_error(errMsg.str());
635 }
636 for (const auto &token : tokens) {
637 std::unique_ptr<RooAbsData> appendedData{createEmptyClone()};
638 auto &ds = static_cast<RooDataSet &>(*appendedData);
639 ds._dstore = _dstore->reduce(ds.GetName(), ds.GetTitle(), ds._vars, cutVar, token.c_str(), nStart, nStop);
640 ds._cachedVars.add(_dstore->cachedVars());
641 static_cast<RooDataSet &>(*out).append(ds);
642 }
643 }
644 return out;
645}
646
647
648
649////////////////////////////////////////////////////////////////////////////////
650/// Destructor
651
657
658
659
660////////////////////////////////////////////////////////////////////////////////
661/// Return binned clone of this dataset
662
664{
665 std::string title;
666 std::string name;
667 if (newName) {
668 name = newName ;
669 } else {
670 name = std::string(GetName()) + "_binned" ;
671 }
672 if (newTitle) {
673 title = newTitle ;
674 } else {
675 title = std::string(GetTitle()) + "_binned" ;
676 }
677
678 return RooFit::makeOwningPtr(std::make_unique<RooDataHist>(name,title,*get(),*this));
679}
680
681
682
683////////////////////////////////////////////////////////////////////////////////
684/// Return event weight of current event
685
686double RooDataSet::weight() const
687{
688 return store()->weight() ;
689}
690
691
692
693////////////////////////////////////////////////////////////////////////////////
694/// Return squared event weight of the current event. If this RooDataSet has no
695/// weight errors set, this will be the same as `weight() * weight()`, like
696/// expected for an unbinned dataset. When weight errors are set, it is assumed
697/// that the RooDataSet represents a weighted binned dataset and
698/// weightSquared() is the corresponding sum of weight squares for the bin.
699
701{
702 const double w = store()->weight();
703 const double e = weightError();
704 return e > 0.0 ? e * e : w * w;
705}
706
707
708////////////////////////////////////////////////////////////////////////////////
709/// \see RooAbsData::getWeightBatch().
710std::span<const double> RooDataSet::getWeightBatch(std::size_t first, std::size_t len, bool sumW2 /*=false*/) const {
711
712 std::size_t nEntries = this->numEntries(); // for the casting to std::size_t
713
714 if(first + len > nEntries) {
715 throw std::runtime_error("RooDataSet::getWeightBatch(): requested range not valid for dataset.");
716 }
717
718 std::span<const double> allWeights = _dstore->getWeightBatch(0, numEntries());
719 if(allWeights.empty()) return {};
720
721 if(!sumW2) return {&*(std::cbegin(allWeights) + first), len};
722
723 // Treat the sumW2 case with a result buffer, first reset buffer if the
724 // number of entries doesn't match with the dataset anymore
725 if(_sumW2Buffer && _sumW2Buffer->size() != nEntries) _sumW2Buffer.reset();
726
727 if (!_sumW2Buffer) {
728 _sumW2Buffer = std::make_unique<std::vector<double>>();
729 _sumW2Buffer->reserve(nEntries);
730
731 for (std::size_t i = 0; i < nEntries; ++i) {
732 get(i);
733 _sumW2Buffer->push_back(weightSquared());
734 }
735 }
736
737 return std::span<const double>(&*(_sumW2Buffer->begin() + first), len);
738}
739
740
741////////////////////////////////////////////////////////////////////////////////
742/// \copydoc RooAbsData::weightError(double&,double&,RooAbsData::ErrorType) const
743/// \param etype error type
744void RooDataSet::weightError(double& lo, double& hi, ErrorType etype) const
745{
746 store()->weightError(lo,hi,etype) ;
747}
748
749
750////////////////////////////////////////////////////////////////////////////////
751/// \copydoc RooAbsData::weightError(ErrorType)
752/// \param etype error type
754{
755 return store()->weightError(etype) ;
756}
757
758
759////////////////////////////////////////////////////////////////////////////////
760/// Return RooArgSet with coordinates of event 'index'
761
763{
765 return ret ? &_varsNoWgt : nullptr ;
766}
767
768
769////////////////////////////////////////////////////////////////////////////////
770
772{
773 return store()->sumEntries() ;
774}
775
776
777////////////////////////////////////////////////////////////////////////////////
778/// Return the sum of weights in all entries matching cutSpec (if specified)
779/// and in named range cutRange (if specified)
780
781double RooDataSet::sumEntries(const char* cutSpec, const char* cutRange) const
782{
783 // Setup RooFormulaVar for cutSpec if it is present
784 std::unique_ptr<RooFormula> select = nullptr ;
785 if (cutSpec && strlen(cutSpec) > 0) {
786 select = std::make_unique<RooFormula>("select",cutSpec,*get()) ;
787 }
788
789 // Shortcut for unweighted unselected datasets
790 if (!select && !cutRange && !isWeighted()) {
791 return numEntries() ;
792 }
793
794 // Otherwise sum the weights in the event
796 for (int i = 0 ; i<numEntries() ; i++) {
797 get(i) ;
798 if (select && select->eval()==0.) continue ;
799 if (cutRange && !_vars.allInRange(cutRange)) continue ;
800 sumw += weight();
801 }
802
803 return sumw.Sum() ;
804}
805
806
807
808
809////////////////////////////////////////////////////////////////////////////////
810/// Return true if dataset contains weighted events
811
813{
814 return store() ? store()->isWeighted() : false;
815}
816
817
818
819////////////////////////////////////////////////////////////////////////////////
820/// Returns true if histogram contains bins with entries with a non-integer weight
821
823{
824 // Return false if we have no weights
825 if (!_wgtVar) return false ;
826
827 // Now examine individual weights
828 for (int i=0 ; i<numEntries() ; i++) {
829 get(i) ;
830 if (std::abs(weight()-Int_t(weight()))>1e-10) return true ;
831 }
832 // If sum of weights is less than number of events there are negative (integer) weights
833 if (sumEntries()<numEntries()) return true ;
834
835 return false ;
836}
837
838
839
840
841////////////////////////////////////////////////////////////////////////////////
842/// Return a RooArgSet with the coordinates of the current event
843
845{
846 return &_varsNoWgt ;
847}
848
849
850
851////////////////////////////////////////////////////////////////////////////////
852/// Add a data point, with its coordinates specified in the 'data' argset, to the data set.
853/// Any variables present in 'data' but not in the dataset will be silently ignored.
854/// \param[in] data Data point.
855/// \param[in] wgt Event weight. Defaults to 1. The current value of the weight variable is
856/// ignored.
857/// \note To obtain weighted events, a variable must be designated `WeightVar` in the constructor.
858/// \param[in] wgtError Optional weight error.
859/// \note This requires including the weight variable in the set of `StoreError` variables when constructing
860/// the dataset.
861
862void RooDataSet::add(const RooArgSet& data, double wgt, double wgtError)
863{
864 checkInit() ;
865
866 const double oldW = _wgtVar ? _wgtVar->getVal() : 0.;
867
869
870 if (_wgtVar) {
871 _wgtVar->setVal(wgt) ;
872 if (wgtError!=0.) {
874 }
875 } else if ((wgt != 1. || wgtError != 0.) && _errorMsgCount < 5) {
876 ccoutE(DataHandling) << "An event weight/error was passed but no weight variable was defined"
877 << " in the dataset '" << GetName() << "'. The weight will be ignored." << std::endl;
879 }
880
882 && wgtError != 0.
883 && std::abs(wgt*wgt - wgtError)/wgtError > 1.E-15 //Exception for standard wgt^2 errors, which need not be stored.
884 && _errorMsgCount < 5 && !_wgtVar->getAttribute("StoreError")) {
885 coutE(DataHandling) << "An event weight error was passed to the RooDataSet '" << GetName()
886 << "', but the weight variable '" << _wgtVar->GetName()
887 << "' does not store errors. Check `StoreError` in the RooDataSet constructor." << std::endl;
889 }
890
891 fill();
892
893 // Restore weight state
894 if (_wgtVar) {
897 }
898}
899
900
901
902
903////////////////////////////////////////////////////////////////////////////////
904/// Add a data point, with its coordinates specified in the 'data' argset, to the data set.
905/// Any variables present in 'data' but not in the dataset will be silently ignored.
906/// \param[in] indata Data point.
907/// \param[in] inweight Event weight. The current value of the weight variable is ignored.
908/// \note To obtain weighted events, a variable must be designated `WeightVar` in the constructor.
909/// \param[in] weightErrorLo Asymmetric weight error.
910/// \param[in] weightErrorHi Asymmetric weight error.
911/// \note This requires including the weight variable in the set of `StoreAsymError` variables when constructing
912/// the dataset.
913
915{
916 checkInit() ;
917
918 const double oldW = _wgtVar ? _wgtVar->getVal() : 0.;
919
921 if (_wgtVar) {
924 } else if (inweight != 1. && _errorMsgCount < 5) {
925 ccoutE(DataHandling) << "An event weight was given but no weight variable was defined"
926 << " in the dataset '" << GetName() << "'. The weight will be ignored." << std::endl;
928 }
929
931 && _errorMsgCount < 5 && !_wgtVar->getAttribute("StoreAsymError")) {
932 coutE(DataHandling) << "An event weight error was passed to the RooDataSet '" << GetName()
933 << "', but the weight variable '" << _wgtVar->GetName()
934 << "' does not store errors. Check `StoreAsymError` in the RooDataSet constructor." << std::endl;
936 }
937
938 fill();
939
940 // Restore weight state
941 if (_wgtVar) {
944 }
945}
946
947
948
949
950
951////////////////////////////////////////////////////////////////////////////////
952/// Add a data point, with its coordinates specified in the 'data' argset, to the data set.
953/// \attention The order and type of the input variables are **assumed** to be the same as
954/// for the RooArgSet returned by RooDataSet::get(). Input values will just be written
955/// into the internal data columns by ordinal position.
956/// \param[in] data Data point.
957/// \param[in] wgt Event weight. Defaults to 1. The current value of the weight variable is
958/// ignored.
959/// \note To obtain weighted events, a variable must be designated `WeightVar` in the constructor.
960/// \param[in] wgtError Optional weight error.
961/// \note This requires including the weight variable in the set of `StoreError` variables when constructing
962/// the dataset.
963
964void RooDataSet::addFast(const RooArgSet& data, double wgt, double wgtError)
965{
966 checkInit() ;
967
968 const double oldW = _wgtVar ? _wgtVar->getVal() : 0.;
969
970 _varsNoWgt.assignFast(data,_dstore->dirtyProp());
971 if (_wgtVar) {
972 _wgtVar->setVal(wgt) ;
973 if (wgtError!=0.) {
975 }
976 } else if (wgt != 1. && _errorMsgCount < 5) {
977 ccoutE(DataHandling) << "An event weight was given but no weight variable was defined"
978 << " in the dataset '" << GetName() << "'. The weight will be ignored." << std::endl;
980 }
981
982 fill();
983
985 && wgtError != 0. && wgtError != wgt*wgt //Exception for standard weight error, which need not be stored
986 && _errorMsgCount < 5 && !_wgtVar->getAttribute("StoreError")) {
987 coutE(DataHandling) << "An event weight error was passed to the RooDataSet '" << GetName()
988 << "', but the weight variable '" << _wgtVar->GetName()
989 << "' does not store errors. Check `StoreError` in the RooDataSet constructor." << std::endl;
991 }
993 _doWeightErrorCheck = false;
994 }
995
996 if (_wgtVar) {
999 }
1000}
1001
1002
1003
1004////////////////////////////////////////////////////////////////////////////////
1005
1008{
1009 checkInit() ;
1011 if (data1) dsetList.push_back(data1) ;
1012 if (data2) dsetList.push_back(data2) ;
1013 if (data3) dsetList.push_back(data3) ;
1014 if (data4) dsetList.push_back(data4) ;
1015 if (data5) dsetList.push_back(data5) ;
1016 if (data6) dsetList.push_back(data6) ;
1017 return merge(dsetList) ;
1018}
1019
1020
1021
1022////////////////////////////////////////////////////////////////////////////////
1023/// Merge columns of supplied data set(s) with this data set. All
1024/// data sets must have equal number of entries. In case of
1025/// duplicate columns the column of the last dataset in the list
1026/// prevails
1027
1029{
1030
1031 checkInit() ;
1032 // Sanity checks: data sets must have the same size
1033 for (list<RooDataSet*>::iterator iter = dsetList.begin() ; iter != dsetList.end() ; ++iter) {
1034 if (numEntries()!=(*iter)->numEntries()) {
1035 coutE(InputArguments) << "RooDataSet::merge(" << GetName() << ") ERROR: datasets have different size" << std::endl ;
1036 return true ;
1037 }
1038 }
1039
1040 // Extend vars with elements of other dataset
1042 for (list<RooDataSet*>::iterator iter = dsetList.begin() ; iter != dsetList.end() ; ++iter) {
1043 _vars.addClone((*iter)->_vars,true) ;
1044 dstoreList.push_back((*iter)->store()) ;
1045 }
1046
1047 // Merge data stores
1049 mergedStore->SetName(_dstore->GetName()) ;
1050 mergedStore->SetTitle(_dstore->GetTitle()) ;
1051
1052 // Replace current data store with merged store
1053 _dstore.reset(mergedStore);
1054
1055 initialize(_wgtVar?_wgtVar->GetName():nullptr) ;
1056 return false ;
1057}
1058
1059
1060////////////////////////////////////////////////////////////////////////////////
1061/// Add all data points of given data set to this data set.
1062/// Observable in 'data' that are not in this dataset
1063/// with not be transferred
1064
1066{
1067 checkInit() ;
1068 _dstore->append(*data._dstore) ;
1069}
1070
1071
1072
1073////////////////////////////////////////////////////////////////////////////////
1074/// Add a column with the values of the given (function) argument
1075/// to this dataset. The function value is calculated for each
1076/// event using the observable values of each event in case the
1077/// function depends on variables with names that are identical
1078/// to the observable names in the dataset
1079
1081{
1082 checkInit() ;
1083 std::unique_ptr<RooAbsArg> ret{_dstore->addColumn(var,adjustRange)};
1084 RooAbsArg* retPtr = ret.get();
1085 _vars.addOwned(std::move(ret));
1086 initialize(_wgtVar?_wgtVar->GetName():nullptr) ;
1087 return retPtr;
1088}
1089
1090
1091////////////////////////////////////////////////////////////////////////////////
1092/// Special plot method for 'X-Y' datasets used in \f$ \chi^2 \f$ fitting.
1093/// For general plotting, see RooAbsData::plotOn().
1094///
1095/// These datasets
1096/// have one observable (X) and have weights (Y) and associated errors.
1097/// <table>
1098/// <tr><th> Contents options <th> Effect
1099/// <tr><td> YVar(RooRealVar& var) <td> Designate specified observable as 'y' variable
1100/// If not specified, the event weight will be the y variable
1101/// <tr><th> Histogram drawing options <th> Effect
1102/// <tr><td> DrawOption(const char* opt) <td> Select ROOT draw option for resulting TGraph object
1103/// <tr><td> LineStyle(Int_t style) <td> Select line style by ROOT line style code, default is solid
1104/// <tr><td> LineColor(Int_t color) <td> Select line color by ROOT color code, default is black
1105/// <tr><td> LineWidth(Int_t width) <td> Select line with in pixels, default is 3
1106/// <tr><td> MarkerStyle(Int_t style) <td> Select the ROOT marker style, default is 21
1107/// <tr><td> MarkerColor(Int_t color) <td> Select the ROOT marker color, default is black
1108/// <tr><td> MarkerSize(double size) <td> Select the ROOT marker size
1109/// <tr><td> Rescale(double factor) <td> Apply global rescaling factor to histogram
1110/// <tr><th> Misc. other options <th> Effect
1111/// <tr><td> Name(const chat* name) <td> Give curve specified name in frame. Useful if curve is to be referenced later
1112/// <tr><td> Invisible(bool flag) <td> Add curve to frame, but do not display. Useful in combination AddTo()
1113/// </table>
1114
1116 const RooCmdArg& arg3, const RooCmdArg& arg4,
1117 const RooCmdArg& arg5, const RooCmdArg& arg6,
1118 const RooCmdArg& arg7, const RooCmdArg& arg8) const
1119{
1120 checkInit() ;
1121
1122 RooLinkedList argList ;
1123 argList.Add((TObject*)&arg1) ; argList.Add((TObject*)&arg2) ;
1124 argList.Add((TObject*)&arg3) ; argList.Add((TObject*)&arg4) ;
1125 argList.Add((TObject*)&arg5) ; argList.Add((TObject*)&arg6) ;
1126 argList.Add((TObject*)&arg7) ; argList.Add((TObject*)&arg8) ;
1127
1128 // Process named arguments
1129 RooCmdConfig pc("RooDataSet::plotOnXY(" + std::string(GetName()) + ")");
1130 pc.defineString("drawOption","DrawOption",0,"P") ;
1131 pc.defineString("histName","Name",0,"") ;
1132 pc.defineInt("lineColor","LineColor",0,-999) ;
1133 pc.defineInt("lineStyle","LineStyle",0,-999) ;
1134 pc.defineInt("lineWidth","LineWidth",0,-999) ;
1135 pc.defineInt("markerColor","MarkerColor",0,-999) ;
1136 pc.defineInt("markerStyle","MarkerStyle",0,8) ;
1137 pc.defineDouble("markerSize","MarkerSize",0,-999) ;
1138 pc.defineInt("fillColor","FillColor",0,-999) ;
1139 pc.defineInt("fillStyle","FillStyle",0,-999) ;
1140 pc.defineInt("histInvisible","Invisible",0,0) ;
1141 pc.defineDouble("scaleFactor","Rescale",0,1.) ;
1142 pc.defineObject("xvar","XVar",0,nullptr) ;
1143 pc.defineObject("yvar","YVar",0,nullptr) ;
1144
1145
1146 // Process & check varargs
1147 pc.process(argList) ;
1148 if (!pc.ok(true)) {
1149 return frame ;
1150 }
1151
1152 // Extract values from named arguments
1153 const char* drawOptions = pc.getString("drawOption") ;
1154 Int_t histInvisible = pc.getInt("histInvisible") ;
1155 const char* histName = pc.getString("histName",nullptr,true) ;
1156 double scaleFactor = pc.getDouble("scaleFactor") ;
1157
1158 RooRealVar* xvar = static_cast<RooRealVar*>(_vars.find(frame->getPlotVar()->GetName())) ;
1159
1160 // Determine Y variable (default is weight, if present)
1161 RooRealVar* yvar = static_cast<RooRealVar*>(pc.getObject("yvar")) ;
1162
1163 // Sanity check. XY plotting only applies to weighted datasets if no YVar is specified
1164 if (!_wgtVar && !yvar) {
1165 coutE(InputArguments) << "RooDataSet::plotOnXY(" << GetName() << ") ERROR: no YVar() argument specified and dataset is not weighted" << std::endl ;
1166 return nullptr ;
1167 }
1168
1169 RooRealVar* dataY = yvar ? static_cast<RooRealVar*>(_vars.find(yvar->GetName())) : nullptr ;
1170 if (yvar && !dataY) {
1171 coutE(InputArguments) << "RooDataSet::plotOnXY(" << GetName() << ") ERROR on YVar() argument, dataset does not contain a variable named " << yvar->GetName() << std::endl ;
1172 return nullptr ;
1173 }
1174
1175
1176 // Make RooHist representing XY contents of data
1177 RooHist* graph = new RooHist ;
1178 if (histName) {
1179 graph->SetName(histName) ;
1180 } else {
1181 graph->SetName(("hxy_" + std::string(GetName())).c_str());
1182 }
1183
1184 for (int i=0 ; i<numEntries() ; i++) {
1185 get(i) ;
1186 double x = xvar->getVal() ;
1187 double exlo = xvar->getErrorLo() ;
1188 double exhi = xvar->getErrorHi() ;
1189 double y;
1190 double eylo;
1191 double eyhi;
1192 if (!dataY) {
1193 y = weight() ;
1195 } else {
1196 y = dataY->getVal() ;
1197 eylo = dataY->getErrorLo() ;
1198 eyhi = dataY->getErrorHi() ;
1199 }
1200 graph->addBinWithXYError(x,y,-1*exlo,exhi,-1*eylo,eyhi,scaleFactor) ;
1201 }
1202
1203 // Adjust style options according to named arguments
1204 Int_t lineColor = pc.getInt("lineColor") ;
1205 Int_t lineStyle = pc.getInt("lineStyle") ;
1206 Int_t lineWidth = pc.getInt("lineWidth") ;
1207 Int_t markerColor = pc.getInt("markerColor") ;
1208 Int_t markerStyle = pc.getInt("markerStyle") ;
1209 Size_t markerSize = pc.getDouble("markerSize") ;
1210 Int_t fillColor = pc.getInt("fillColor") ;
1211 Int_t fillStyle = pc.getInt("fillStyle") ;
1212
1213 if (lineColor!=-999) graph->SetLineColor(lineColor) ;
1214 if (lineStyle!=-999) graph->SetLineStyle(lineStyle) ;
1215 if (lineWidth!=-999) graph->SetLineWidth(lineWidth) ;
1216 if (markerColor!=-999) graph->SetMarkerColor(markerColor) ;
1217 if (markerStyle!=-999) graph->SetMarkerStyle(markerStyle) ;
1218 if (markerSize!=-999) graph->SetMarkerSize(markerSize) ;
1219 if (fillColor!=-999) graph->SetFillColor(fillColor) ;
1220 if (fillStyle!=-999) graph->SetFillStyle(fillStyle) ;
1221
1222 // Add graph to frame
1223 frame->addPlotable(graph,drawOptions,histInvisible) ;
1224
1225 return frame ;
1226}
1227
1228
1229
1230
1231////////////////////////////////////////////////////////////////////////////////
1232/// Read given list of ascii files, and construct a data set, using the given
1233/// ArgList as structure definition.
1234/// \param fileList Multiple file names, comma separated. Each
1235/// file is optionally prefixed with 'commonPath' if such a path is
1236/// provided
1237///
1238/// \param varList Specify the dimensions of the dataset to be built.
1239/// This list describes the order in which these dimensions appear in the
1240/// ascii files to be read.
1241/// Each line in the ascii file should contain N white-space separated
1242/// tokens, with N the number of args in `varList`. Any text beyond
1243/// N tokens will be ignored with a warning message.
1244/// (NB: This is the default output of RooArgList::writeToStream())
1245///
1246/// \param verbOpt `Q` be quiet, `D` debug mode (verbose)
1247///
1248/// \param commonPath All filenames in `fileList` will be prefixed with this optional path.
1249///
1250/// \param indexCatName Interpret the data as belonging to category `indexCatName`.
1251/// When multiple files are read, a RooCategory arg in `varList` can
1252/// optionally be designated to hold information about the source file
1253/// of each data point. This feature is enabled by giving the name
1254/// of the (already existing) category variable in `indexCatName`.
1255///
1256/// \attention If the value of any of the variables on a given line exceeds the
1257/// fit range associated with that dimension, the entire line will be
1258/// ignored. A warning message is printed in each case, unless the
1259/// `Q` verbose option is given. The number of events read and skipped
1260/// is always summarized at the end.
1261///
1262/// If no further information is given a label name 'fileNNN' will
1263/// be assigned to each event, where NNN is the sequential number of
1264/// the source file in `fileList`.
1265///
1266/// Alternatively, it is possible to override the default label names
1267/// of the index category by specifying them in the fileList string:
1268/// When instead of `file1.txt,file2.txt` the string
1269/// `file1.txt:FOO,file2.txt:BAR` is specified, a state named "FOO"
1270/// is assigned to the index category for each event originating from
1271/// file1.txt. The labels FOO,BAR may be predefined in the index
1272/// category via defineType(), but don't have to be.
1273///
1274/// Finally, one can also assign the same label to multiple files,
1275/// either by specifying `file1.txt:FOO,file2,txt:FOO,file3.txt:BAR`
1276/// or `file1.txt,file2.txt:FOO,file3.txt:BAR`.
1277///
1278
1280 const char *verbOpt, const char* commonPath,
1281 const char* indexCatName) {
1282 // Make working copy of variables list
1283 RooArgList variables(varList) ;
1284
1285 // Append blinding state category to variable list if not already there
1286 bool ownIsBlind(true) ;
1287 RooAbsArg* blindState = variables.find("blindState") ;
1288 if (!blindState) {
1289 blindState = new RooCategory("blindState","Blinding State") ;
1290 variables.add(*blindState) ;
1291 } else {
1292 ownIsBlind = false ;
1293 if (blindState->IsA()!=RooCategory::Class()) {
1294 oocoutE(nullptr,DataHandling) << "RooDataSet::read: ERROR: variable list already contains"
1295 << "a non-RooCategory blindState member" << std::endl ;
1296 return nullptr ;
1297 }
1298 oocoutW(nullptr,DataHandling) << "RooDataSet::read: WARNING: recycling existing "
1299 << "blindState category in variable list" << std::endl ;
1300 }
1301 RooCategory* blindCat = static_cast<RooCategory*>(blindState) ;
1302
1303 // Configure blinding state category
1304 blindCat->setAttribute("Dynamic") ;
1305 blindCat->defineType("Normal",0) ;
1306 blindCat->defineType("Blind",1) ;
1307
1308 // parse the option string
1310 opts.ToLower();
1311 bool verbose= !opts.Contains("q");
1312 bool debug= opts.Contains("d");
1313
1314 auto data = std::make_unique<RooDataSet>("dataset", fileList, variables);
1315 if (ownIsBlind) { variables.remove(*blindState) ; delete blindState ; }
1316 if(!data) {
1317 oocoutE(nullptr,DataHandling) << "RooDataSet::read: unable to create a new dataset"
1318 << std::endl;
1319 return nullptr;
1320 }
1321
1322 // Redirect blindCat to point to the copy stored in the data set
1323 blindCat = static_cast<RooCategory*>(data->_vars.find("blindState")) ;
1324
1325 // Find index category, if requested
1326 RooCategory *indexCat = nullptr;
1327 //RooCategory *indexCatOrig = 0;
1328 if (indexCatName) {
1329 RooAbsArg* tmp = nullptr;
1330 tmp = data->_vars.find(indexCatName) ;
1331 if (!tmp) {
1332 oocoutE(data.get(),DataHandling) << "RooDataSet::read: no index category named "
1333 << indexCatName << " in supplied variable list" << std::endl ;
1334 return nullptr;
1335 }
1336 if (tmp->IsA()!=RooCategory::Class()) {
1337 oocoutE(data.get(),DataHandling) << "RooDataSet::read: variable " << indexCatName
1338 << " is not a RooCategory" << std::endl ;
1339 return nullptr;
1340 }
1341 indexCat = static_cast<RooCategory*>(tmp);
1342
1343 // Prevent RooArgSet from attempting to read in indexCat
1344 indexCat->setAttribute("Dynamic") ;
1345 }
1346
1347
1348 Int_t outOfRange(0) ;
1349
1350 // Loop over all names in comma separated list
1351 Int_t fileSeqNum(0);
1352 for (const auto& filename : ROOT::Split(std::string(fileList), ", ")) {
1353 // Determine index category number, if this option is active
1354 if (indexCat) {
1355
1356 // Find and detach optional file category name
1357 const char *catname = strchr(filename.c_str(),':');
1358
1359 if (catname) {
1360 // Use user category name if provided
1361 catname++ ;
1362
1363 if (indexCat->hasLabel(catname)) {
1364 // Use existing category index
1365 indexCat->setLabel(catname);
1366 } else {
1367 // Register cat name
1368 indexCat->defineType(catname,fileSeqNum) ;
1369 indexCat->setIndex(fileSeqNum) ;
1370 }
1371 } else {
1372 // Assign autogenerated name
1373 char newLabel[128] ;
1374 snprintf(newLabel,128,"file%03d",fileSeqNum) ;
1375 if (indexCat->defineType(newLabel,fileSeqNum)) {
1376 oocoutE(data.get(), DataHandling) << "RooDataSet::read: Error, cannot register automatic type name " << newLabel
1377 << " in index category " << indexCat->GetName() << std::endl ;
1378 return nullptr ;
1379 }
1380 // Assign new category number
1381 indexCat->setIndex(fileSeqNum) ;
1382 }
1383 }
1384
1385 oocoutI(data.get(), DataHandling) << "RooDataSet::read: reading file " << filename << std::endl ;
1386
1387 // Prefix common path
1389 fullName.Append(filename) ;
1390 ifstream file(fullName) ;
1391
1392 if (!file.good()) {
1393 oocoutE(data.get(), DataHandling) << "RooDataSet::read: unable to open '"
1394 << filename << "'. Returning nullptr now." << std::endl;
1395 return nullptr;
1396 }
1397
1398 // double value;
1399 Int_t line(0) ;
1400 bool haveBlindString(false) ;
1401
1402 while(file.good() && !file.eof()) {
1403 line++;
1404 if(debug) oocxcoutD(data.get(),DataHandling) << "reading line " << line << std::endl;
1405
1406 // process comment lines
1407 if (file.peek() == '#') {
1408 if(debug) oocxcoutD(data.get(),DataHandling) << "skipping comment on line " << line << std::endl;
1409 } else {
1410 // Read single line
1411 bool readError = variables.readFromStream(file,true,verbose) ;
1412 data->_vars.assign(variables) ;
1413
1414 // Stop on read error
1415 if(!file.good()) {
1416 oocoutE(data.get(), DataHandling) << "RooDataSet::read(static): read error at line " << line << std::endl ;
1417 break;
1418 }
1419
1420 if (readError) {
1421 outOfRange++ ;
1422 } else {
1423 blindCat->setIndex(haveBlindString) ;
1424 data->fill(); // store this event
1425 }
1426 }
1427
1428 // Skip all white space (including empty lines).
1429 while (isspace(file.peek())) {
1430 char dummy;
1431 file >> std::noskipws >> dummy >> std::skipws;
1432 }
1433 }
1434
1435 file.close();
1436
1437 // get next file name
1438 fileSeqNum++ ;
1439 }
1440
1441 if (indexCat) {
1442 // Copy dynamically defined types from new data set to indexCat in original list
1443 assert(dynamic_cast<RooCategory*>(variables.find(indexCatName)));
1444 const auto origIndexCat = static_cast<RooCategory*>(variables.find(indexCatName));
1445 for (const auto& nameIdx : *indexCat) {
1446 origIndexCat->defineType(nameIdx.first, nameIdx.second);
1447 }
1448 }
1449 oocoutI(data.get(),DataHandling) << "RooDataSet::read: read " << data->numEntries()
1450 << " events (ignored " << outOfRange << " out of range events)" << std::endl;
1451
1452 return data.release();
1453}
1454
1455
1456
1457
1458////////////////////////////////////////////////////////////////////////////////
1459/// Write the contents of this dataset to an ASCII file with the specified name.
1460/// Each event will be written as a single line containing the written values
1461/// of each observable in the order they were declared in the dataset and
1462/// separated by whitespaces
1463
1464bool RooDataSet::write(const char* filename) const
1465{
1466 // Open file for writing
1467 ofstream ofs(filename) ;
1468 if (ofs.fail()) {
1469 coutE(DataHandling) << "RooDataSet::write(" << GetName() << ") cannot create file " << filename << std::endl ;
1470 return true ;
1471 }
1472
1473 // Write all lines as arglist in compact mode
1474 coutI(DataHandling) << "RooDataSet::write(" << GetName() << ") writing ASCII file " << filename << std::endl ;
1475 return write(ofs);
1476}
1477
1478////////////////////////////////////////////////////////////////////////////////
1479/// Write the contents of this dataset to the stream.
1480/// Each event will be written as a single line containing the written values
1481/// of each observable in the order they were declared in the dataset and
1482/// separated by whitespaces
1483
1484bool RooDataSet::write(ostream & ofs) const {
1485 checkInit();
1486
1487 for (Int_t i=0; i<numEntries(); ++i) {
1488 get(i)->writeToStream(ofs,true);
1489 }
1490
1491 if (ofs.fail()) {
1492 coutW(DataHandling) << "RooDataSet::write(" << GetName() << "): WARNING error(s) have occurred in writing" << std::endl ;
1493 }
1494
1495 return ofs.fail() ;
1496}
1497
1498
1499////////////////////////////////////////////////////////////////////////////////
1500/// Print info about this dataset to the specified output stream.
1501///
1502/// Standard: number of entries
1503/// Shape: list of variables we define & were generated with
1504
1505void RooDataSet::printMultiline(ostream& os, Int_t contents, bool verbose, TString indent) const
1506{
1507 checkInit() ;
1508 RooAbsData::printMultiline(os,contents,verbose,indent) ;
1509 if (_wgtVar) {
1510 os << indent << " Dataset variable \"" << _wgtVar->GetName() << "\" is interpreted as the event weight" << std::endl ;
1511 }
1512}
1513
1514
1515////////////////////////////////////////////////////////////////////////////////
1516/// Print value of the dataset, i.e. the sum of weights contained in the dataset
1517
1518void RooDataSet::printValue(ostream& os) const
1519{
1520 os << numEntries() << " entries" ;
1521 if (isWeighted()) {
1522 os << " (" << sumEntries() << " weighted)" ;
1523 }
1524}
1525
1526
1527
1528////////////////////////////////////////////////////////////////////////////////
1529/// Print argument of dataset, i.e. the observable names
1530
1531void RooDataSet::printArgs(ostream& os) const
1532{
1533 os << "[" ;
1534 bool first(true) ;
1535 for(RooAbsArg* arg : _varsNoWgt) {
1536 if (first) {
1537 first=false ;
1538 } else {
1539 os << "," ;
1540 }
1541 os << arg->GetName() ;
1542 }
1543 if (_wgtVar) {
1544 os << ",weight:" << _wgtVar->GetName() ;
1545 }
1546 os << "]" ;
1547}
1548
1549
1550
1551////////////////////////////////////////////////////////////////////////////////
1552/// Change the name of this dataset into the given name
1553
1554void RooDataSet::SetName(const char *name)
1555{
1556 if (_dir) _dir->GetList()->Remove(this);
1557 // We need to use the function from RooAbsData, because it already overrides TNamed::SetName
1559 if (_dir) _dir->GetList()->Add(this);
1560}
1561
1562
1563////////////////////////////////////////////////////////////////////////////////
1564/// Change the title of this dataset into the given name
1565
1566void RooDataSet::SetNameTitle(const char *name, const char* title)
1567{
1568 SetName(name);
1569 SetTitle(title);
1570}
1571
1572
1573////////////////////////////////////////////////////////////////////////////////
1574/// Stream an object of class RooDataSet.
1575
1577{
1578 if (R__b.IsReading()) {
1579
1580 UInt_t R__s;
1581 UInt_t R__c;
1582 Version_t R__v = R__b.ReadVersion(&R__s, &R__c);
1583
1584 if (R__v > 1) {
1585
1586 // Use new-style streaming for version >1
1587 R__b.ReadClassBuffer(RooDataSet::Class(), this, R__v, R__s, R__c);
1588
1589 } else {
1590
1591 // Legacy dataset conversion happens here. Legacy RooDataSet inherits from RooTreeData
1592 // which in turn inherits from RooAbsData. Manually stream RooTreeData contents on
1593 // file here and convert it into a RooTreeDataStore which is installed in the
1594 // new-style RooAbsData base class
1595
1596 // --- This is the contents of the streamer code of RooTreeData version 1 ---
1597 UInt_t R__s1;
1598 UInt_t R__c1;
1599 Version_t R__v1 = R__b.ReadVersion(&R__s1, &R__c1);
1600 if (R__v1) {
1601 }
1602
1604 TTree *X_tree(nullptr);
1605 R__b >> X_tree;
1607 X_truth.Streamer(R__b);
1609 X_blindString.Streamer(R__b);
1610 R__b.CheckByteCount(R__s1, R__c1, TClass::GetClass("RooTreeData"));
1611 // --- End of RooTreeData-v1 streamer
1612
1613 // Construct RooTreeDataStore from X_tree and complete initialization of new-style RooAbsData
1614 _dstore = std::make_unique<RooTreeDataStore>(X_tree, _vars);
1615 _dstore->SetName(GetName());
1616 _dstore->SetTitle(GetTitle());
1617 _dstore->checkInit();
1618
1619 // This is the contents of the streamer code of RooDataSet version 1
1622 R__b >> _wgtVar;
1623 R__b.CheckByteCount(R__s, R__c, RooDataSet::IsA());
1624 }
1625 } else {
1626 R__b.WriteClassBuffer(RooDataSet::Class(), this);
1627 }
1628}
1629
1630
1631
1632////////////////////////////////////////////////////////////////////////////////
1633/// Convert vector-based storage to tree-based storage. This implementation overrides the base class
1634/// implementation because the latter doesn't transfer weights.
1636{
1638 _dstore = std::make_unique<RooTreeDataStore>(GetName(), GetTitle(), _vars, *_dstore, nullptr, _wgtVar ? _wgtVar->GetName() : nullptr);
1640 }
1641}
1642
1643
1644namespace {
1645
1646 // Compile-time test if we can still use TStrings for the constructors of
1647 // RooDataClasses, either for both name and title or for only one of them.
1648 TString tstr = "tstr";
1649 const char * cstr = "cstr";
1650 RooRealVar x{"x", "x", 1.0};
1651 RooArgSet vars{x};
1652 RooDataSet d1(tstr, tstr, vars);
1653 RooDataSet d2(tstr, cstr, vars);
1654 RooDataSet d3(cstr, tstr, vars);
1655
1656} // namespace
1657
1658
1659void RooDataSet::loadValuesFromSlices(RooCategory &indexCat, std::map<std::string, RooAbsData *> const &slices,
1660 const char *rangeName, RooFormulaVar const *cutVar, const char *cutSpec)
1661{
1662
1663 if (cutVar && cutSpec) {
1664 throw std::invalid_argument("Only one of cutVar or cutSpec should be not a nullptr!");
1665 }
1666
1667 auto &indexCatInData = *static_cast<RooCategory *>(_vars.find(indexCat.GetName()));
1668
1669 for (auto const &item : slices) {
1670 std::unique_ptr<RooDataSet> sliceDataSet;
1671 RooAbsData* sliceData = item.second;
1672
1673 // If we are importing a RooDataHist, first convert it to a RooDataSet
1674 if(sliceData->InheritsFrom(RooDataHist::Class())) {
1676 sliceData = sliceDataSet.get();
1677 }
1678
1679 // Define state labels in index category (both in provided indexCat and in internal copy in dataset)
1680 if (!indexCat.hasLabel(item.first)) {
1681 indexCat.defineType(item.first);
1682 coutI(InputArguments) << "RooDataSet::ctor(" << GetName() << ") defining state \"" << item.first
1683 << "\" in index category " << indexCat.GetName() << std::endl;
1684 }
1685 if (!indexCatInData.hasLabel(item.first)) {
1686 indexCatInData.defineType(item.first);
1687 }
1688 indexCatInData.setLabel(item.first.c_str());
1689 std::unique_ptr<RooFormulaVar> cutVarTmp;
1690 if (cutSpec) {
1691 cutVarTmp = std::make_unique<RooFormulaVar>(cutSpec, cutSpec, *sliceData->get(), /*checkVariables=*/false);
1692 cutVar = cutVarTmp.get();
1693 }
1694 _dstore->loadValues(sliceData->store(), cutVar, rangeName);
1695 }
1696}
1697
1698/**
1699 * \brief Prints the contents of the RooDataSet to the specified output stream.
1700 *
1701 * This function iterates through all events (rows) of the dataset and prints
1702 * the value of each observable, along with the event's weight.
1703 * It is designed to be robust, handling empty or invalid datasets gracefully,
1704 * and works for datasets of any dimension.
1705 *
1706 * \param os The output stream (e.g., std::cout) to write the contents to.
1707 */
1708void RooDataSet::printContents(std::ostream& os) const
1709{
1710 os << "Contents of RooDataSet \"" << GetName() << "\"" << std::endl;
1711
1712 if (numEntries() == 0) {
1713 os << "(dataset is empty)" << std::endl;
1714 return;
1715 }
1716
1717 if (get() == nullptr || get()->empty()) {
1718 os << "(dataset has no observables)" << std::endl;
1719 return;
1720 }
1721
1722 for (int i = 0; i < numEntries(); ++i) {
1723 const RooArgSet* row = get(i); // reuses internal buffers
1724 os << " Entry " << i << ": ";
1725
1726 bool first = true;
1727 for (const auto* var : *row) {
1728 if (!first) os << ", ";
1729 first = false;
1730
1731 os << var->GetName() << "=";
1732 if (auto realVar = dynamic_cast<const RooRealVar*>(var)) {
1733 os << realVar->getVal();
1734 } else if (auto catVar = dynamic_cast<const RooCategory*>(var)) {
1735 os << catVar->getLabel();
1736 } else {
1737 os << "(unsupported type)"; //added as a precaution
1738 }
1739 }
1740
1741 os << ", weight=" << weight();
1742
1743 double lo, hi;
1744 weightError(lo, hi);
1745 if (lo != 0.0 || hi != 0.0) {
1746 os << " ±[" << lo << "," << hi << "]";
1747 }
1748
1749 os << std::endl;
1750 }
1751}
#define e(i)
Definition RSha256.hxx:103
ROOT::RRangeCast< T, false, Range_t > static_range_cast(Range_t &&coll)
#define coutI(a)
#define ccoutE(a)
#define oocoutW(o, a)
#define oocxcoutD(o, a)
#define coutW(a)
#define oocoutE(o, a)
#define oocoutI(o, a)
#define coutE(a)
#define TRACE_DESTROY
Definition RooTrace.h:24
#define TRACE_CREATE
Definition RooTrace.h:23
int Int_t
Signed integer 4 bytes (int)
Definition RtypesCore.h:59
float Size_t
Attribute size (float)
Definition RtypesCore.h:103
short Version_t
Class version identifier (short)
Definition RtypesCore.h:79
static void indent(ostringstream &buf, int indent_level)
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 data
Option_t Option_t TPoint TPoint const char GetTextMagnitude GetFillStyle GetLineColor GetLineWidth GetMarkerStyle GetTextAlign GetTextColor GetTextSize void char Point_t Rectangle_t WindowAttributes_t Float_t Float_t Float_t Int_t Int_t UInt_t UInt_t Rectangle_t Int_t Int_t Window_t TString Int_t GCValues_t GetPrimarySelectionOwner GetDisplay GetScreen GetColormap GetNativeEvent const char const char dpyName wid window const char font_name cursor keysym reg const char only_if_exist regb h Point_t winding char text const char depth char const char Int_t count const char ColorStruct_t color const char filename
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 const char GetTextMagnitude GetFillStyle GetLineColor GetLineWidth GetMarkerStyle GetTextAlign GetTextColor GetTextSize void char Point_t Rectangle_t WindowAttributes_t Float_t Float_t Float_t Int_t Int_t UInt_t UInt_t Rectangle_t Int_t Int_t Window_t TString Int_t GCValues_t GetPrimarySelectionOwner GetDisplay GetScreen GetColormap GetNativeEvent const char const char dpyName wid window const char font_name cursor keysym reg const char only_if_exist regb h Point_t winding char text const char depth char const char Int_t count const char ColorStruct_t color const char Pixmap_t Pixmap_t PictureAttributes_t attr const char char ret_data h unsigned char height h Atom_t Int_t ULong_t ULong_t unsigned char prop_list Atom_t Atom_t Atom_t Time_t UChar_t len
char name[80]
Definition TGX11.cxx:110
#define hi
#define snprintf
Definition civetweb.c:1579
The Kahan summation is a compensated summation algorithm, which significantly reduces numerical error...
Definition Util.h:141
const_iterator begin() const
const_iterator end() const
Common abstract base class for objects that represent a value and a "shape" in RooFit.
Definition RooAbsArg.h:76
void setAttribute(const Text_t *name, bool value=true)
Set (default) or clear a named boolean attribute of this object.
bool hasLabel(const std::string &label) const
Check if a state with name label exists.
virtual void removeAll()
Remove all arguments from our set, deleting them if we own them.
virtual bool remove(const RooAbsArg &var, bool silent=false, bool matchByNameOnly=false)
Remove the specified argument from our list.
bool allInRange(const char *rangeSpec) const
Return true if all contained object report to have their value inside the specified range.
void assignFast(const RooAbsCollection &other, bool setValDirty=true) const
Functional equivalent of assign() but assumes this and other collection have same layout.
virtual bool add(const RooAbsArg &var, bool silent=false)
Add the specified argument to list.
void assign(const RooAbsCollection &other) const
Sets the value, cache and constant attribute of any argument in our set that also appears in the othe...
virtual bool addOwned(RooAbsArg &var, bool silent=false)
Add an argument and transfer the ownership to the collection.
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.
Abstract base class for a data collection.
virtual bool isWeighted() const =0
virtual double sumEntries() const
virtual double weightError(RooAbsData::ErrorType etype=RooAbsData::Poisson) const =0
virtual double weight() const =0
Abstract base class for binned and unbinned datasets.
Definition RooAbsData.h:56
virtual const RooArgSet * get() const
Definition RooAbsData.h:100
void printMultiline(std::ostream &os, Int_t contents, bool verbose=false, TString indent="") const override
Interface for detailed printing of object.
void SetName(const char *name) override
Set the name of the TNamed.
RooAbsDataStore * store()
Definition RooAbsData.h:76
void checkInit() const
std::unique_ptr< RooAbsDataStore > _dstore
Data storage implementation.
Definition RooAbsData.h:358
virtual void fill()
RooArgSet _vars
Dimensions of this data set.
Definition RooAbsData.h:355
virtual Int_t numEntries() const
Return number of entries in dataset, i.e., count unweighted entries.
StorageType storageType
Definition RooAbsData.h:300
void Streamer(TBuffer &) override
Stream an object of class RooAbsData.
double getVal(const RooArgSet *normalisationSet=nullptr) const
Evaluate object.
Definition RooAbsReal.h:107
RooArgList is a container object that can hold multiple RooAbsArg objects.
Definition RooArgList.h:22
RooArgSet is a container object that can hold multiple RooAbsArg objects.
Definition RooArgSet.h:24
void Streamer(TBuffer &) override
Stream an object of class TObject.
Object to represent discrete states.
Definition RooCategory.h:28
bool setIndex(Int_t index, bool printError=true) override
Set value by specifying the index code of the desired state.
bool defineType(const std::string &label)
Define a state with given name.
bool setLabel(const char *label, bool printError=true) override
Set value by specifying the name of the desired state.
static TClass * Class()
Named container for two doubles, two integers two object points and three string pointers that can be...
Definition RooCmdArg.h:26
const char * getString(Int_t idx) const
Return string stored in slot idx.
Definition RooCmdArg.h:96
Configurable parser for RooCmdArg named arguments.
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'.
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...
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...
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.
Definition RooDataHist.h:40
static TClass * Class()
double weight(std::size_t i) const
Return weight of i-th bin.
double weightSquared(std::size_t i) const
Return squared weight sum of i-th bin.
const RooArgSet * get() const override
Get bin centre of current bin.
Definition RooDataHist.h:82
Container class to hold unbinned data.
Definition RooDataSet.h:32
RooFit::OwningPtr< RooAbsData > emptyClone(const char *newName=nullptr, const char *newTitle=nullptr, const RooArgSet *vars=nullptr, const char *wgtVarName=nullptr) const override
Return an empty clone of this dataset.
RooRealVar * _wgtVar
Pointer to weight variable (if set)
Definition RooDataSet.h:126
bool _doWeightErrorCheck
! When adding events with weights, check that weights can actually be stored.
Definition RooDataSet.h:134
static void cleanup()
RooArgSet _varsNoWgt
Vars without weight variable.
Definition RooDataSet.h:125
void loadValuesFromSlices(RooCategory &indexCat, std::map< std::string, RooAbsData * > const &slices, const char *rangeName, RooFormulaVar const *cutVar, const char *cutSpec)
RooFit::OwningPtr< RooDataHist > binnedClone(const char *newName=nullptr, const char *newTitle=nullptr) const
Return binned clone of this dataset.
void weightError(double &lo, double &hi, ErrorType etype=SumW2) const override
Return the asymmetric errors on the current weight.
const RooArgSet * get() const override
Return a RooArgSet with the coordinates of the current event.
void printContents(std::ostream &os=std::cout) const override
Print the contents of the dataset to the specified output stream.
virtual RooPlot * plotOnXY(RooPlot *frame, const RooCmdArg &arg1={}, const RooCmdArg &arg2={}, const RooCmdArg &arg3={}, const RooCmdArg &arg4={}, const RooCmdArg &arg5={}, const RooCmdArg &arg6={}, const RooCmdArg &arg7={}, const RooCmdArg &arg8={}) const
Special plot method for 'X-Y' datasets used in fitting.
void initialize(const char *wgtVarName)
Initialize the dataset.
void printArgs(std::ostream &os) const override
Print argument of dataset, i.e. the observable names.
void SetName(const char *name) override
Change the name of this dataset into the given name.
virtual void addFast(const RooArgSet &row, double weight=1.0, double weightError=0.0)
Add a data point, with its coordinates specified in the 'data' argset, to the data set.
bool merge(RooDataSet *data1, RooDataSet *data2=nullptr, RooDataSet *data3=nullptr, RooDataSet *data4=nullptr, RooDataSet *data5=nullptr, RooDataSet *data6=nullptr)
TClass * IsA() const override
Definition RooDataSet.h:138
virtual RooAbsArg * addColumn(RooAbsArg &var, bool adjustRange=true)
Add a column with the values of the given (function) argument to this dataset.
bool write(const char *filename) const
Write the contents of this dataset to an ASCII file with the specified name.
double sumEntries() const override
Return effective number of entries in dataset, i.e., sum all weights.
std::span< const double > getWeightBatch(std::size_t first, std::size_t len, bool sumW2) const override
~RooDataSet() override
Destructor.
bool isNonPoissonWeighted() const override
Returns true if histogram contains bins with entries with a non-integer weight.
void SetNameTitle(const char *name, const char *title) override
Change the title of this dataset into the given name.
void printValue(std::ostream &os) const override
Print value of the dataset, i.e. the sum of weights contained in the dataset.
void append(RooDataSet &data)
Add all data points of given data set to this data set.
RooDataSet()
Default constructor for persistence.
std::unique_ptr< std::vector< double > > _sumW2Buffer
! Buffer for sumW2 in case a batch of values is requested.
Definition RooDataSet.h:136
void Streamer(TBuffer &) override
Stream an object of class RooDataSet.
void add(const RooArgSet &row, double weight, double weightError)
Add one ore more rows of data.
unsigned short _errorMsgCount
! Counter to silence error messages when filling dataset.
Definition RooDataSet.h:133
static TClass * Class()
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.
void convertToTreeStore() override
Convert vector-based storage to tree-based storage.
void printMultiline(std::ostream &os, Int_t contents, bool verbose=false, TString indent="") const override
Print info about this dataset to the specified output stream.
double weightSquared() const override
Return squared event weight of the current event.
double weight() const override
Return event weight of current event.
static RooDataSet * read(const char *filename, const RooArgList &variables, const char *opts="", const char *commonPath="", const char *indexCatName=nullptr)
Read data from a text file and create a dataset from it.
bool isWeighted() const override
Return true if dataset contains weighted events.
Utility base class for RooFit objects that are to be attached to ROOT directories.
Definition RooDirItem.h:22
virtual void Streamer(TBuffer &)
void removeFromDir(TObject *obj)
Remove object from directory it was added to.
TDirectory * _dir
! Associated directory
Definition RooDirItem.h:33
A RooFormulaVar is a generic implementation of a real-valued object, which takes a RooArgList of serv...
Graphical representation of binned data based on the TGraphAsymmErrors class.
Definition RooHist.h:29
void addBinWithXYError(Axis_t binCenter, double n, double exlow, double exhigh, double eylow, double eyhigh, double scaleFactor=1.0)
Add a bin to this histogram with the specified bin contents and error.
Definition RooHist.cxx:497
Collection class for internal use, storing a collection of RooAbsArg pointers in a doubly linked list...
virtual void Add(TObject *arg)
Plot frame and a container for graphics objects within that frame.
Definition RooPlot.h:43
RooAbsRealLValue * getPlotVar() const
Definition RooPlot.h:137
void addPlotable(RooPlotable *plotable, Option_t *drawOptions="", bool invisible=false, bool refreshNorm=false)
Add the specified plotable object to our plot.
Definition RooPlot.cxx:475
Variable that can be changed from the outside.
Definition RooRealVar.h:37
void setVal(double value) override
Set value of variable to 'value'.
void setError(double value)
Definition RooRealVar.h:61
void removeAsymError()
Definition RooRealVar.h:66
void setAsymError(double lo, double hi)
Definition RooRealVar.h:67
void removeError()
Definition RooRealVar.h:62
The RooStringView is a wrapper around a C-style string that can also be constructed from a std::strin...
TTree-backed data storage.
virtual void SetFillColor(Color_t fcolor)
Set the fill area color.
Definition TAttFill.h:38
virtual void SetFillStyle(Style_t fstyle)
Set the fill area style.
Definition TAttFill.h:40
virtual void SetLineStyle(Style_t lstyle)
Set the line style.
Definition TAttLine.h:44
virtual void SetLineWidth(Width_t lwidth)
Set the line width.
Definition TAttLine.h:45
virtual void SetLineColor(Color_t lcolor)
Set the line color.
Definition TAttLine.h:42
virtual void SetMarkerColor(Color_t mcolor=1)
Set the marker color.
Definition TAttMarker.h:39
virtual void SetMarkerStyle(Style_t mstyle=1)
Set the marker style.
Definition TAttMarker.h:41
virtual void SetMarkerSize(Size_t msize=1)
Set the marker size.
Definition TAttMarker.h:46
Buffer base class used for serializing objects.
Definition TBuffer.h:43
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.
Definition TClass.cxx:2973
virtual TList * GetList() const
Definition TDirectory.h:223
static TFile * Open(const char *name, Option_t *option="", const char *ftitle="", Int_t compress=ROOT::RCompressionSetting::EDefaults::kUseCompiledDefault, Int_t netopt=0)
Create / open a file.
Definition TFile.cxx:3765
void SetName(const char *name="") override
Set graph name.
Definition TGraph.cxx:2426
virtual void SetTitle(const char *title="")
Set the title of the TNamed.
Definition TNamed.cxx:173
const char * GetName() const override
Returns name of object.
Definition TNamed.h:49
const char * GetTitle() const override
Returns title of object.
Definition TNamed.h:50
Mother of all ROOT objects.
Definition TObject.h:42
Basic string class.
Definition TString.h:138
A TTree represents a columnar dataset.
Definition TTree.h:89
TLine * line
RooCmdArg StoreError(const RooArgSet &aset)
RooCmdArg WeightVar(const char *name="weight", bool reinterpretAsWeight=false)
Double_t y[n]
Definition legend1.C:17
Double_t x[n]
Definition legend1.C:17
std::vector< std::string > Split(std::string_view str, std::string_view delims, bool skipEmpty=false)
Splits a string at each character in delims.
The namespace RooFit contains mostly switches that change the behaviour of functions of PDFs (or othe...
Definition CodegenImpl.h:71
T * OwningPtr
An alias for raw pointers for indicating that the return type of a RooFit function is an owning point...
Definition Config.h:35
OwningPtr< T > makeOwningPtr(std::unique_ptr< T > &&ptr)
Internal helper to turn a std::unique_ptr<T> into an OwningPtr.
Definition Config.h:40
bool checkIfRangesOverlap(RooArgSet const &observables, std::vector< std::string > const &rangeNames)
void initialize(typename Architecture_t::Matrix_t &A, EInitialization m)
Definition Functions.h:282
TLine l
Definition textangle.C:4