Logo ROOT  
Reference Guide
RooAbsCategory.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 RooAbsCategory.cxx
19\class RooAbsCategory
20\ingroup Roofitcore
21
22RooAbsCategory is the base class for objects that represent a discrete value with a finite number of states.
23
24Each state is denoted by an integer and a name. Both can be used to retrieve and
25set states, but referring to states by index is more efficient. Conversion between
26index and name can be done using lookupName() or lookupIndex().
27It is possible to iterate through all defined states using begin() and end().
28
29For category classes deriving from RooAbsCategory, states can only be evaluated, *i.e.*, queried.
30Refer to RooAbsCategoryLValue and its derived classes for categories where states can also be set. The
31simplest category class whose states can be set, queried and saved in a dataset, refer to RooCategory.
32
33### Interface change in ROOT-6.22
34Category data were based in the class RooCatType, holding an index state and a category name truncated to 256
35characters. This wastes 64 bytes of storage space per entry, and prevents fast retrieval of category data.
36Since ROOT-6.22, categories are only represented by an integer. RooAbsCategory::lookupName() can be used to
37retrieve the corresponding state name. There is no limit for the length of the state name.
38
39To not break old code, the old RooCatType interfaces are still available. Whenever possible,
40the following replacements should be used:
41- lookupType() \f$ \rightarrow \f$ lookupName() / lookupIndex()
42- typeIterator() \f$ \rightarrow \f$ range-based for loop / begin() / end()
43- isValid(const RooCatType&) \f$ \rightarrow \f$ hasIndex() / hasLabel()
44**/
45
46#include "RooAbsCategory.h"
47
48#include "RooFit.h"
49#include "RooArgSet.h"
50#include "Roo1DTable.h"
51#include "RooCategory.h"
52#include "RooMsgService.h"
53#include "RooVectorDataStore.h"
55
56#include "Compression.h"
57#include "TString.h"
58#include "TH1.h"
59#include "TTree.h"
60#include "TLeaf.h"
61#include "ROOT/RMakeUnique.hxx"
62#include "TBranch.h"
63
64using namespace std;
65
67
68/// A category state to signify an invalid category. The category name is empty,
69/// the index is the minimal int.
71 static const decltype(RooAbsCategory::_stateNames)::value_type invalid{"", std::numeric_limits<value_type>::min()};
72 return invalid;
73}
74
75////////////////////////////////////////////////////////////////////////////////
76/// Constructor
77
78RooAbsCategory::RooAbsCategory(const char *name, const char *title) :
79 RooAbsArg(name,title), _currentIndex(0)
80{
83}
84
85
86
87////////////////////////////////////////////////////////////////////////////////
88/// Copy constructor, copies the registered category states from the original.
89
91 RooAbsArg(other,name), _currentIndex(other._currentIndex),
92 _stateNames(other._stateNames),
93 _insertionOrder(other._insertionOrder),
94 _treeVar(other._treeVar)
95{
98}
99
100
101
102////////////////////////////////////////////////////////////////////////////////
103/// Destructor
104
106{
107
108}
109
110
111
112////////////////////////////////////////////////////////////////////////////////
113/// Return index number of current state
114
116{
117 if (isValueDirty() || isShapeDirty()) {
119
121 }
122
123 return _currentIndex;
124}
125
126
127
128////////////////////////////////////////////////////////////////////////////////
129/// Return label string of current state.
130
132{
133 const auto index = getCurrentIndex();
134 for (const auto& item : stateNames()) {
135 if (item.second == index)
136 return item.first.c_str();
137 }
138
139 return "";
140}
141
142
143////////////////////////////////////////////////////////////////////////////////
144/// Equality operator with a integer (compares with state index number)
145
147{
148 return (index==getCurrentIndex()) ;
149}
150
151
152
153////////////////////////////////////////////////////////////////////////////////
154/// Equality operator with a string (compares with state label string)
155
156Bool_t RooAbsCategory::operator==(const char* label) const
157{
158 return strcmp(label, getCurrentLabel()) == 0;
159}
160
161
162
163////////////////////////////////////////////////////////////////////////////////
164/// Equality operator with another RooAbsArg. Only functional
165/// is also a RooAbsCategory, will return true if index is the same
166
168{
169 const RooAbsCategory* otherCat = dynamic_cast<const RooAbsCategory*>(&other) ;
170 return otherCat ? operator==(otherCat->getCurrentIndex()) : kFALSE ;
171}
172
173
174////////////////////////////////////////////////////////////////////////////////
175
176Bool_t RooAbsCategory::isIdentical(const RooAbsArg& other, Bool_t assumeSameType) const
177{
178 if (!assumeSameType) {
179 const RooAbsCategory* otherCat = dynamic_cast<const RooAbsCategory*>(&other) ;
180 return otherCat ? operator==(otherCat->getCurrentIndex()) : kFALSE ;
181 } else {
182 return getCurrentIndex() == static_cast<const RooAbsCategory&>(other).getCurrentIndex();
183 }
184}
185
186
187////////////////////////////////////////////////////////////////////////////////
188/// Check if a state with index `index` exists.
190{
191 for (const auto& item : stateNames()) {
192 if (item.second == index)
193 return true;
194 }
195
196 return false;
197}
198
199
200////////////////////////////////////////////////////////////////////////////////
201/// Look up the name corresponding to the given index.
202const std::string& RooAbsCategory::lookupName(value_type index) const {
203 for (const auto& item : stateNames()) {
204 if (item.second == index)
205 return item.first;
206 }
207
208 return invalidCategory().first;
209}
210
211////////////////////////////////////////////////////////////////////////////////
212/// Define a new state with given label. The next available
213/// integer is assigned as index value.
214const std::map<std::string, RooAbsCategory::value_type>::value_type& RooAbsCategory::defineState(const std::string& label)
215{
216 return defineState(label, nextAvailableStateIndex());
217}
218
219
220////////////////////////////////////////////////////////////////////////////////
221/// Internal version of defineState() that does not check if type
222/// already exists
224{
225 _stateNames.emplace(label, index);
226 _insertionOrder.push_back(label);
227
228 if (_stateNames.size() == 1)
229 _currentIndex = index;
230
232}
233
234
235
236////////////////////////////////////////////////////////////////////////////////
237/// Define new state with given name and index number.
238
239const std::map<std::string, RooAbsCategory::value_type>::value_type& RooAbsCategory::defineState(const std::string& label, RooAbsCategory::value_type index)
240{
241 auto& theStateNames = stateNames();
242
243 if (hasIndex(index)) {
244 coutE(InputArguments) << "RooAbsCategory::" << __func__ << "(" << GetName() << "): index "
245 << index << " already assigned" << endl ;
246 return invalidCategory();
247 }
248
249 if (hasLabel(label)) {
250 coutE(InputArguments) << "RooAbsCategory::" << __func__ << "(" << GetName() << "): label "
251 << label << " already assigned or not allowed" << endl ;
252 return invalidCategory();
253 }
254
255 const auto result = theStateNames.emplace(label, index);
256 _insertionOrder.push_back(label);
257
258 if (theStateNames.size() == 1)
259 _currentIndex = index;
260
262
263 return *(result.first);
264}
265
266
267
268////////////////////////////////////////////////////////////////////////////////
269/// Delete all currently defined states
270
272{
273 _stateNames.clear();
274 _insertionOrder.clear();
276 setShapeDirty() ;
277}
278
279
280////////////////////////////////////////////////////////////////////////////////
281/// Find the index number corresponding to the state name.
282/// \see hasLabel() for checking if a given label has been defined.
283/// \return Index of the category or std::numeric_limits<int>::min() on failure.
284RooAbsCategory::value_type RooAbsCategory::lookupIndex(const std::string& stateName) const {
285 const auto item = stateNames().find(stateName);
286 if (item != stateNames().end()) {
287 return item->second;
288 }
289
290 return invalidCategory().second;
291}
292
293////////////////////////////////////////////////////////////////////////////////
294/// Find our type that matches the specified type, or return 0 for no match.
295/// \deprecated RooCatType is not used, any more. This function will create one and let it leak.
296/// Use lookupIndex() (preferred) or lookupName() instead.
297const RooCatType* RooAbsCategory::lookupType(const RooCatType &other, Bool_t printError) const
298{
299 return lookupType(other.getVal(), printError);
300}
301
302
303
304////////////////////////////////////////////////////////////////////////////////
305/// Find our type corresponding to the specified index, or return nullptr for no match.
306/// \deprecated RooCatType is not used, any more. This function will create one and let it leak.
307/// Use lookupIndex() (preferred) or lookupName() instead.
309{
310 for (const auto& item : stateNames())
311 if (item.second == index) {
312 return retrieveLegacyState(index);
313 }
314
315 if (printError) {
316 coutE(InputArguments) << ClassName() << "::" << GetName() << ":lookupType: no match for index "
317 << index << endl;
318 }
319
320 return nullptr;
321}
322
323
324
325////////////////////////////////////////////////////////////////////////////////
326/// Find our type corresponding to the specified label, or return 0 for no match.
327/// \deprecated RooCatType is not used, any more. This function will create one and let it leak.
328/// Use lookupIndex() (preferred) or lookupName() instead.
329const RooCatType* RooAbsCategory::lookupType(const char* label, Bool_t printError) const
330{
331 for (const auto& type : stateNames()) {
332 if(type.first == label)
333 return retrieveLegacyState(type.second);
334 }
335
336 // Try if label represents integer number
337 char* endptr ;
338 RooAbsCategory::value_type idx=strtol(label,&endptr,10) ;
339 if (endptr==label+strlen(label)) {
340 return lookupType(idx);
341 }
342
343 if (printError) {
344 coutE(InputArguments) << ClassName() << "::" << GetName() << ":lookupType: no match for label "
345 << label << endl;
346 }
347 return nullptr;
348}
349
350
351////////////////////////////////////////////////////////////////////////////////
352/// Check if given state is defined for this object
353
355{
356 return hasIndex(value.getVal()) ;
357}
358
359
360
361////////////////////////////////////////////////////////////////////////////////
362/// Create a table matching the shape of this category
363
365{
366 return new Roo1DTable(GetName(),label,*this) ;
367}
368
369
370
371////////////////////////////////////////////////////////////////////////////////
372/// Read object contents from stream (dummy for now)
373
375{
376 return kFALSE ;
377}
378
379
380
381////////////////////////////////////////////////////////////////////////////////
382/// Write object contents to ostream
383
384void RooAbsCategory::writeToStream(ostream& os, Bool_t /* compact */) const
385{
386 os << getCurrentLabel() ;
387}
388
389
390
391////////////////////////////////////////////////////////////////////////////////
392/// Print value (label name)
393
394void RooAbsCategory::printValue(ostream& os) const
395{
396 os << getCurrentLabel() << "(idx = " << getCurrentIndex() << ")" << endl ;
397}
398
399
400
401////////////////////////////////////////////////////////////////////////////////
402/// Print info about this object to the specified stream. In addition to the info
403/// from RooAbsArg::printStream() we add:
404///
405/// Shape : label, index, defined types
406
408{
410
411 os << indent << "--- RooAbsCategory ---" << endl;
412 if (stateNames().empty()) {
413 os << indent << " ** No values defined **" << endl;
414 return;
415 }
416 os << indent << " Value = " << getCurrentIndex() << " \"" << getCurrentLabel() << ')' << endl;
417 os << indent << " Possible states:" << endl;
418 indent.Append(" ");
419 for (const auto& type : stateNames()) {
420 os << indent << type.first << '\t' << type.second << "\n";
421 }
422}
423
424
425
426////////////////////////////////////////////////////////////////////////////////
427/// Attach the category index and label to as branches to the given vector store
428
430{
431 RooVectorDataStore::CatVector* cv = vstore.addCategory(this) ;
433}
434
435
436
437
438////////////////////////////////////////////////////////////////////////////////
439/// Attach the category index and label as branches to the given
440/// TTree. The index field will be attached as integer with name
441/// `<name>_idx`. If a branch `<name>` exists, it attaches to this branch.
443{
444 // First check if there is an integer branch matching the category name
445 TString cleanName(cleanBranchName()) ;
446 TBranch* branch = t.GetBranch(cleanName) ;
447 if (!branch) {
448 cleanName += "_idx";
449 branch = t.GetBranch(cleanName);
450 }
451
452 if (branch) {
453 TString typeName(((TLeaf*)branch->GetListOfLeaves()->At(0))->GetTypeName()) ;
454 if (!typeName.CompareTo("Int_t")) {
455 // Imported TTree: attach only index field as branch
456
457 coutI(DataHandling) << "RooAbsCategory::attachToTree(" << GetName() << ") TTree branch " << GetName()
458 << " will be interpreted as category index" << endl ;
459
460 t.SetBranchAddress(cleanName, &_currentIndex) ;
461 setAttribute("INTIDXONLY_TREE_BRANCH",kTRUE) ;
462 _treeVar = true;
463 return ;
464 } else if (!typeName.CompareTo("UChar_t")) {
465 coutI(DataHandling) << "RooAbsReal::attachToTree(" << GetName() << ") TTree UChar_t branch " << GetName()
466 << " will be interpreted as category index" << endl ;
467 t.SetBranchAddress(cleanName,&_byteValue) ;
468 setAttribute("UCHARIDXONLY_TREE_BRANCH",kTRUE) ;
469 _treeVar = true;
470 return ;
471 }
472 } else {
473 TString format(cleanName);
474 format.Append("/I");
475 void* ptr = &_currentIndex;
476 t.Branch(cleanName, ptr, (const Text_t*)format, bufSize);
477 }
478}
479
480
481
482////////////////////////////////////////////////////////////////////////////////
483/// Fill tree branches associated with current object with current value
484
486{
487 TString idxName(GetName()) ;
488 idxName.Append("_idx") ;
489
490 // First determine if branch is taken
491 TBranch* idxBranch = t.GetBranch(idxName) ;
492 if (!idxBranch) {
493 coutF(DataHandling) << "RooAbsCategory::fillTreeBranch(" << GetName() << ") ERROR: not attached to tree" << endl ;
494 throw std::runtime_error("RooAbsCategory::fillTreeBranch(): Category is not attached to a tree.");
495 }
496
497 idxBranch->Fill() ;
498}
499
500
501
502////////////////////////////////////////////////////////////////////////////////
503/// (De)activate associate tree branch
504
506{
507 TBranch* branch = t.GetBranch(Form("%s_idx",GetName())) ;
508 if (branch) {
509 t.SetBranchStatus(Form("%s_idx",GetName()),active?1:0) ;
510 }
511}
512
513
514
515////////////////////////////////////////////////////////////////////////////////
516/// Explicitly synchronize RooAbsCategory internal cache
517
519{
521}
522
523
524
525////////////////////////////////////////////////////////////////////////////////
526/// Copy the cached value from given source and raise dirty flag.
527/// It is the callers responsibility to ensure that the sources
528/// cache is clean(valid) before this function is called, e.g. by
529/// calling syncCache() on the source.
530
531void RooAbsCategory::copyCache(const RooAbsArg *source, Bool_t /*valueOnly*/, Bool_t setValDirty)
532{
533 auto other = static_cast<const RooAbsCategory*>(source);
534 assert(dynamic_cast<const RooAbsCategory*>(source));
535
536 _currentIndex = other->_currentIndex;
537
538 if (setValDirty) {
540 }
541
542 if (!_treeVar)
543 return;
544
545 if (source->getAttribute("INTIDXONLY_TREE_BRANCH")) {
546 // Lookup cat state from other-index because label is missing
547 if (hasIndex(other->_currentIndex)) {
548 _currentIndex = other->_currentIndex;
549 } else {
550 coutE(DataHandling) << "RooAbsCategory::copyCache(" << GetName() << ") ERROR: index of source arg "
551 << source->GetName() << " is invalid (" << other->_currentIndex
552 << "), value not updated" << endl;
553 }
554 } else if (source->getAttribute("UCHARIDXONLY_TREE_BRANCH")) {
555 // Lookup cat state from other-index because label is missing
556 Int_t tmp = static_cast<int>(other->_byteValue);
557 if (hasIndex(tmp)) {
558 _currentIndex = tmp;
559 } else {
560 coutE(DataHandling) << "RooAbsCategory::copyCache(" << GetName() << ") ERROR: index of source arg "
561 << source->GetName() << " is invalid (" << tmp << "), value not updated" << endl;
562 }
563 }
564}
565
566////////////////////////////////////////////////////////////////////////////////
567/// Return name and index of the `n`th defined state. When states are defined using
568/// defineType() or operator[], the order of insertion is tracked, to mimic the behaviour
569/// before modernising the category classes.
570/// When directly manipulating the map with state names using states(), the order of insertion
571/// is not known, so alphabetical ordering as usual for std::map is used. The latter is faster.
572/// \param[in] n Number of state to be retrieved.
573/// \return A pair with name and index.
574const std::map<std::string, RooAbsCategory::value_type>::value_type& RooAbsCategory::getOrdinal(unsigned int n) const {
575 // Retrieve state names, trigger possible recomputation
576 auto& theStateNames = stateNames();
577
578 if (n >= theStateNames.size())
579 return invalidCategory();
580
581 if (theStateNames.size() != _insertionOrder.size())
582 return *std::next(theStateNames.begin(), n);
583
584 const auto item = theStateNames.find(_insertionOrder[n]);
585 if (item != theStateNames.end())
586 return *item;
587
588 return invalidCategory();
589}
590
591
592////////////////////////////////////////////////////////////////////////////////
593/// Return ordinal number of the current state.
595 // Retrieve state names, trigger possible recomputation
596 auto& theStateNames = stateNames();
597
598 const auto currentIndex = getCurrentIndex();
599
600 // If we don't have the full history if inserted state names, have to go by map ordering:
601 if (theStateNames.size() != _insertionOrder.size()) {
602 for (auto it = theStateNames.begin(); it != theStateNames.end(); ++it) {
603 if (it->second == currentIndex)
604 return std::distance(theStateNames.begin(), it);
605 }
606 }
607
608 // With full insertion history, find index of current label:
609 auto item = std::find(_insertionOrder.begin(), _insertionOrder.end(), getCurrentLabel());
610 assert(item != _insertionOrder.end());
611
612 return item - _insertionOrder.begin();
613}
614
615
616////////////////////////////////////////////////////////////////////////////////
617/// Create a RooCategory fundamental object with our properties.
618
620{
621 // Add and precalculate new category column
622 RooCategory *fund= new RooCategory(newname?newname:GetName(),GetTitle()) ;
623
624 // Copy states
625 for (const auto& type : stateNames()) {
626 fund->defineStateUnchecked(type.first, type.second);
627 }
628
629 return fund;
630}
631
632
633
634////////////////////////////////////////////////////////////////////////////////
635/// Determine if category has 2 or 3 states with index values -1,0,1
636
638{
639 const auto& theStateNames = stateNames();
640
641 if (theStateNames.size() > 3 || theStateNames.size() < 2) return false;
642 if (mustHaveZero && theStateNames.size() != 3) return false;
643
644 for (const auto& type : theStateNames) {
645 if (abs(type.second)>1)
646 return false;
647 }
648
649 return true;
650}
651
652/// \deprecated Use begin() and end() instead.
653/// \note Using this iterator creates useless RooCatType instances, which will leak
654/// unless deleted by the user.
657}
658
659const RooCatType* RooAbsCategory::defineType(const char* label) {
660 defineState(label);
661 return retrieveLegacyState(stateNames()[label]);
662}
663
664const RooCatType* RooAbsCategory::defineType(const char* label, int index) {
665 defineState(label, index);
666 return retrieveLegacyState(index);
667}
668
670 defineStateUnchecked(label, index);
671 return retrieveLegacyState(index);
672}
673
674/// Return the legacy RooCatType corresponding to `index`. If it doesn't exist, create one.
676 auto result = _legacyStates.find(index);
677 if (result == _legacyStates.end()) {
678 result = _legacyStates.emplace(index,
679 std::unique_ptr<RooCatType>(new RooCatType(lookupName(index).c_str(), index))).first;
680 }
681
682 return result->second.get();
683}
684
685
687 const auto& theStateNames = stateNames();
688
689 if (theStateNames.empty())
690 return 0;
691
692 return 1 + std::max_element(theStateNames.begin(), theStateNames.end(),
693 [](const std::map<std::string, value_type>::value_type& left,
694 const std::map<std::string, value_type>::value_type& right) {
695 return left.second < right.second; })->second;
696}
#define coutI(a)
Definition: RooMsgService.h:30
#define coutF(a)
Definition: RooMsgService.h:34
#define coutE(a)
Definition: RooMsgService.h:33
char Text_t
Definition: RtypesCore.h:60
const Bool_t kFALSE
Definition: RtypesCore.h:90
const Bool_t kTRUE
Definition: RtypesCore.h:89
#define ClassImp(name)
Definition: Rtypes.h:361
static void indent(ostringstream &buf, int indent_level)
char name[80]
Definition: TGX11.cxx:109
int type
Definition: TGX11.cxx:120
char * Form(const char *fmt,...)
Roo1DTable implements a one-dimensional table.
Definition: Roo1DTable.h:23
RooAbsArg is the common abstract base class for objects that represent a value (of arbitrary type) an...
Definition: RooAbsArg.h:73
void setShapeDirty()
Notify that a shape-like property (e.g. binning) has changed.
Definition: RooAbsArg.h:492
virtual void printMultiline(std::ostream &os, Int_t contents, Bool_t verbose=kFALSE, TString indent="") const
Implement multi-line detailed printing.
Definition: RooAbsArg.cxx:1359
Bool_t isShapeDirty() const
Definition: RooAbsArg.h:406
void setAttribute(const Text_t *name, Bool_t value=kTRUE)
Set (default) or clear a named boolean attribute of this object.
Definition: RooAbsArg.cxx:257
Bool_t isValueDirty() const
Definition: RooAbsArg.h:411
void clearValueDirty() const
Definition: RooAbsArg.h:547
void setValueDirty()
Mark the element dirty. This forces a re-evaluation when a value is requested.
Definition: RooAbsArg.h:487
TString cleanBranchName() const
Construct a mangled name from the actual name that is free of any math symbols that might be interpre...
Definition: RooAbsArg.cxx:1830
Bool_t getAttribute(const Text_t *name) const
Check if a named attribute is set. By default, all attributes are unset.
Definition: RooAbsArg.cxx:280
RooAbsCategory is the base class for objects that represent a discrete value with a finite number of ...
virtual value_type getCurrentIndex() const
Return index number of current state.
virtual void copyCache(const RooAbsArg *source, Bool_t valueOnly=kFALSE, Bool_t setValueDirty=kTRUE)
Copy the cached value from given source and raise dirty flag.
virtual bool isValid() const
WVE (08/21/01) Probably obsolete now.
unsigned int getCurrentOrdinalNumber() const
Return ordinal number of the current state.
bool hasLabel(const std::string &label) const
Check if a state with name label exists.
virtual const char * getCurrentLabel() const
Return label string of current state.
const std::string & lookupName(value_type index) const
Get the name corresponding to the given index.
TIterator * typeIterator() const
virtual void fillTreeBranch(TTree &t)
Fill tree branches associated with current object with current value.
RooCatType * retrieveLegacyState(value_type index) const
Return the legacy RooCatType corresponding to index. If it doesn't exist, create one.
value_type _currentIndex
Bool_t operator==(value_type index) const
Equality operator with a integer (compares with state index number)
virtual void attachToVStore(RooVectorDataStore &vstore)
Attach the category index and label to as branches to the given vector store.
Roo1DTable * createTable(const char *label) const
Create a table matching the shape of this category.
void defineStateUnchecked(const std::string &label, value_type index)
Internal version of defineState() that does not check if type already exists.
virtual ~RooAbsCategory()
Destructor.
const RooCatType * defineTypeUnchecked(const char *label, value_type index)
virtual void attachToTree(TTree &t, Int_t bufSize=32000)
Attach the category index and label as branches to the given TTree.
value_type nextAvailableStateIndex() const
virtual Bool_t isIdentical(const RooAbsArg &other, Bool_t assumeSameType=kFALSE) const
RooAbsArg * createFundamental(const char *newname=0) const
Create a RooCategory fundamental object with our properties.
std::map< std::string, value_type >::const_iterator end() const
Iterator for category state names. Points to pairs of index and name.
virtual void writeToStream(std::ostream &os, Bool_t compact) const
Write object contents to ostream.
virtual const std::map< std::string, RooAbsCategory::value_type >::value_type & defineState(const std::string &label)
Define a new state with given label.
virtual void setTreeBranchStatus(TTree &t, Bool_t active)
(De)activate associate tree branch
virtual value_type evaluate() const =0
Evaluate the category state and return.
virtual void printMultiline(std::ostream &os, Int_t contents, Bool_t verbose=kFALSE, TString indent="") const
Print info about this object to the specified stream.
const std::map< std::string, value_type >::value_type & getOrdinal(unsigned int n) const
Return name and index of the nth defined state.
const RooCatType * lookupType(value_type index, Bool_t printError=kFALSE) const
Find our type corresponding to the specified index, or return nullptr for no match.
UChar_t _byteValue
Keeps track in which order state numbers have been inserted. Make sure this is updated in recomputeSh...
std::map< value_type, std::unique_ptr< RooCatType, std::function< void(RooCatType *)> > > _legacyStates
Transient cache for byte values from tree branches.
bool hasIndex(value_type index) const
Check if a state with index index exists.
virtual void syncCache(const RooArgSet *set=0)
Explicitly synchronize RooAbsCategory internal cache.
std::vector< std::string > _insertionOrder
Map state names to index numbers. Make sure state names are updated in recomputeShape().
std::map< std::string, value_type > _stateNames
Current category state.
const RooCatType * defineType(const char *label)
Bool_t isSignType(Bool_t mustHaveZero=kFALSE) const
Determine if category has 2 or 3 states with index values -1,0,1.
const std::map< std::string, value_type > & stateNames() const
Access the map of state names to index numbers.
virtual void printValue(std::ostream &os) const
Print value (label name)
static const decltype(_stateNames) ::value_type & invalidCategory()
Is this category attached to a tree?
value_type lookupIndex(const std::string &stateName) const
Find the index number corresponding to the state name.
virtual Bool_t readFromStream(std::istream &is, Bool_t compact, Bool_t verbose=kFALSE)
Read object contents from stream (dummy for now)
bool _treeVar
Map holding pointers to RooCatType instances. Only for legacy interface. Don't use if possible.
void clearTypes()
Delete all currently defined states.
RooArgSet is a container object that can hold multiple RooAbsArg objects.
Definition: RooArgSet.h:28
RooCatType is an auxilary class for RooAbsCategory and defines a a single category state.
Int_t getVal() const
RooCategory is an object to represent discrete states.
Definition: RooCategory.h:23
void setBuffer(RooAbsCategory::value_type *newBuf)
RooVectorDataStore is the abstract base class for data collection that use a TTree as internal storag...
CatVector * addCategory(RooAbsCategory *cat)
A TTree is a list of TBranches.
Definition: TBranch.h:91
TObjArray * GetListOfLeaves()
Definition: TBranch.h:245
Int_t Fill()
Definition: TBranch.h:203
Iterator abstract base class.
Definition: TIterator.h:30
A TLeaf describes individual elements of a TBranch See TBranch structure in TTree.
Definition: TLeaf.h:49
virtual const char * GetTitle() const
Returns title of object.
Definition: TNamed.h:48
virtual const char * GetName() const
Returns name of object.
Definition: TNamed.h:47
TObject * At(Int_t idx) const
Definition: TObjArray.h:166
virtual const char * ClassName() const
Returns name of class to which the object belongs.
Definition: TObject.cxx:128
Basic string class.
Definition: TString.h:131
int CompareTo(const char *cs, ECaseCompare cmp=kExact) const
Compare a string to char *cs2.
Definition: TString.cxx:418
TString & Append(const char *cs)
Definition: TString.h:559
A TTree represents a columnar dataset.
Definition: TTree.h:78
virtual TBranch * GetBranch(const char *name)
Return pointer to the branch with the given name in this tree or its friends.
Definition: TTree.cxx:5209
virtual Int_t SetBranchAddress(const char *bname, void *add, TBranch **ptr=0)
Change branch address, dealing with clone trees properly.
Definition: TTree.cxx:8237
TBranch * Branch(const char *name, T *obj, Int_t bufsize=32000, Int_t splitlevel=99)
Add a new branch, and infer the data type from the type of obj being passed.
Definition: TTree.h:348
virtual void SetBranchStatus(const char *bname, Bool_t status=1, UInt_t *found=0)
Set branch status to Process or DoNotProcess.
Definition: TTree.cxx:8386
const Int_t n
Definition: legend1.C:16
@ DataHandling
Definition: RooGlobalFunc.h:69
@ InputArguments
Definition: RooGlobalFunc.h:68