/*****************************************************************************
* Project: RooFit *
* Package: RooFitCore *
* File: $Id: RooCategory.cc,v 1.28 2005/06/23 15:08:56 wverkerke Exp $
* Authors: *
* WV, Wouter Verkerke, UC Santa Barbara, verkerke@slac.stanford.edu *
* DK, David Kirkby, UC Irvine, dkirkby@uci.edu *
* *
* Copyright (c) 2000-2005, Regents of the University of California *
* and Stanford University. All rights reserved. *
* *
* Redistribution and use in source and binary forms, *
* with or without modification, are permitted according to the terms *
* listed in LICENSE (http://roofit.sourceforge.net/license.txt) *
*****************************************************************************/
// -- CLASS DESCRIPTION [CAT] --
// RooCategory represents a fundamental (non-derived) discrete value object. The class
// has a public interface to define the possible value states.
#include "RooFit.h"
#include "Riostream.h"
#include "Riostream.h"
#include <stdlib.h>
#include <string.h>
#include "TTree.h"
#include "TString.h"
#include "TH1.h"
#include "RooCategory.h"
#include "RooArgSet.h"
#include "RooStreamParser.h"
ClassImp(RooCategory)
;
RooCategory::RooCategory(const char *name, const char *title) :
RooAbsCategoryLValue(name,title)
{
// Constructor. Types must be defined using defineType() before variable can be used
setValueDirty() ;
setShapeDirty() ;
}
RooCategory::RooCategory(const RooCategory& other, const char* name) :
RooAbsCategoryLValue(other, name)
{
// Copy constructor
// Copy ranges
TIterator* iter = other._altRanges.MakeIterator() ;
TList* origTypeList ;
while((origTypeList=(TList*)iter->Next())) {
TList* typeList = new TList ;
typeList->SetName(origTypeList->GetName()) ;
TIterator* iter2 = origTypeList->MakeIterator() ;
RooCatType* state ;
while((state=(RooCatType*)iter2->Next())) {
typeList->Add(const_cast<RooCatType*>(lookupType(state->GetName()))) ;
}
delete iter2 ;
_altRanges.Add(typeList) ;
}
delete iter ;
}
RooCategory::~RooCategory()
{
// Destructor
// Delete ranges
_altRanges.Delete() ;
}
Bool_t RooCategory::setIndex(Int_t index, Bool_t printError)
{
// Set value by specifying the index code of the desired state.
// If printError is set, a message will be printed if
// the specified index does not represent a valid state.
const RooCatType* type = lookupType(index,printError) ;
if (!type) return kTRUE ;
_value = *type ;
setValueDirty() ;
return kFALSE ;
}
Bool_t RooCategory::setLabel(const char* label, Bool_t printError)
{
// Set value by specifying the name of the desired state
// If printError is set, a message will be printed if
// the specified label does not represent a valid state.
const RooCatType* type = lookupType(label,printError) ;
if (!type) return kTRUE ;
_value = *type ;
setValueDirty() ;
return kFALSE ;
}
Bool_t RooCategory::defineType(const char* label)
{
// Define a state with given name, the lowest available
// positive integer is assigned as index. Category
// state labels may not contain semicolons.
// Error status is return if state with given name
// is already defined
if (TString(label).Contains(";")) {
cout << "RooCategory::defineType(" << GetName()
<< "): semicolons not allowed in label name" << endl ;
return kTRUE ;
}
return RooAbsCategory::defineType(label)?kFALSE:kTRUE ;
}
Bool_t RooCategory::defineType(const char* label, Int_t index)
{
// Define a state with given name and index. Category
// state labels may not contain semicolons
// Error status is return if state with given name
// or index is already defined
if (TString(label).Contains(";")) {
cout << "RooCategory::defineType(" << GetName()
<< "): semicolons not allowed in label name" << endl ;
return kTRUE ;
}
return RooAbsCategory::defineType(label,index)?kFALSE:kTRUE ;
}
Bool_t RooCategory::readFromStream(istream& is, Bool_t /*compact*/, Bool_t verbose)
{
// Read object contents from given stream
// Read single token
RooStreamParser parser(is) ;
TString token = parser.readToken() ;
return setLabel(token,verbose) ;
}
void RooCategory::writeToStream(ostream& os, Bool_t compact) const
{
// compact only at the moment
if (compact) {
os << getIndex() ;
} else {
os << getLabel() ;
}
}
void RooCategory::clearRange(const char* name, Bool_t silent)
{
// Check that both input arguments are not null pointers
if (!name) {
cout << "RooCategory::clearRange(" << GetName() << ") ERROR: must specificy valid range name" << endl ;
return ;
}
// Find the list that represents this range
TList* rangeNameList = static_cast<TList*>(_altRanges.FindObject(name)) ;
// If it exists, clear it
if (rangeNameList) {
rangeNameList->Clear() ;
} else if (!silent) {
cout << "RooCategory::clearRange(" << GetName() << ") ERROR: range '" << name << "' does not exist" << endl ;
}
}
void RooCategory::setRange(const char* name, const char* stateNameList)
{
clearRange(name,kTRUE) ;
addToRange(name,stateNameList) ;
}
void RooCategory::addToRange(const char* name, const char* stateNameList)
{
// Check that both input arguments are not null pointers
if (!name || !stateNameList) {
cout << "RooCategory::setRange(" << GetName() << ") ERROR: must specificy valid name and state name list" << endl ;
return ;
}
// Find the list that represents this range
TList* rangeNameList = static_cast<TList*>(_altRanges.FindObject(name)) ;
// If it does not exist, create it on the fly
if (!rangeNameList) {
cout << "RooCategory::setRange(" << GetName()
<< ") new range named '" << name << "' created with state list " << stateNameList << endl ;
rangeNameList = new TList ;
rangeNameList->SetName(name) ;
_altRanges.Add(rangeNameList) ;
}
// Parse list of state names, verify that each is valid and add them to the list
char* buf = new char[strlen(stateNameList)+1] ;
strcpy(buf,stateNameList) ;
char* token = strtok(buf,",") ;
while(token) {
const RooCatType* state = lookupType(token,kFALSE) ;
if (state && !rangeNameList->FindObject(token)) {
rangeNameList->Add(const_cast<RooCatType*>(state)) ;
} else {
cout << "RooCategory::setRange(" << GetName() << ") WARNING: Ignoring invalid state name '"
<< token << "' in state name list" << endl ;
}
token = strtok(0,",") ;
}
delete[] buf ;
}
Bool_t RooCategory::isStateInRange(const char* rangeName, const char* stateName) const
{
// Check that both input arguments are not null pointers
if (!rangeName||!stateName) {
cout << "RooCategory::isStateInRange(" << GetName() << ") ERROR: must specificy valid range name and state name" << endl ;
return kFALSE ;
}
// Find the list that represents this range
TList* rangeNameList = static_cast<TList*>(_altRanges.FindObject(rangeName)) ;
// If the range doesn't exist create range with all valid states included
if (rangeNameList) {
return rangeNameList->FindObject(stateName) ? kTRUE : kFALSE ;
}
// Range does not exists -- create it on the fly with full set of states (analoguous to RooRealVar)
return kTRUE ;
}
ROOT page - Class index - Class Hierarchy - Top of the page
This page has been automatically generated. If you have any comments or suggestions about the page layout send a mail to ROOT support, or contact the developers with any questions or problems regarding ROOT.