43 Error(
"TClonesReader::GetCA()",
"Read error in TBranchProxy.");
72 Error(
"TSTLReader::GetCP()",
"Read error in TBranchProxy.");
76 Error(
"TSTLReader::GetCP()",
"Logic error, proxy object not set in TBranchProxy.");
85 if (!myCollectionProxy)
return 0;
86 return myCollectionProxy->
Size();
91 if (!myCollectionProxy)
return 0;
93 return *(
void**)myCollectionProxy->
At(idx);
96 return myCollectionProxy->
At(idx);
108 if (!proxy->
Read()) {
110 Error(
"TCollectionLessSTLReader::GetCP()",
"Read error in TBranchProxy.");
114 Error(
"TCollectionLessSTLReader::GetCP()",
"Logic error, proxy object not set in TBranchProxy.");
118 return fLocalCollection;
123 if (!myCollectionProxy)
return 0;
125 return myCollectionProxy->
Size();
130 if (!myCollectionProxy)
return 0;
133 return *(
void**)myCollectionProxy->
At(idx);
135 return myCollectionProxy->
At(idx);
145 Int_t fBasicTypeSize;
147 TObjectArrayReader() : fBasicTypeSize(-1) { }
148 ~TObjectArrayReader() {}
152 Error(
"TObjectArrayReader::GetCP()",
"Read error in TBranchProxy.");
160 if (!myCollectionProxy)
return 0;
161 return myCollectionProxy->
Size();
164 if (!proxy->
Read())
return 0;
167 void *array = (
void*)proxy->
GetStart();
169 if (fBasicTypeSize == -1){
172 Error(
"TObjectArrayReader::At()",
"Cannot get class info from branch proxy.");
178 objectSize = fBasicTypeSize;
180 return (
void*)((
Byte_t*)array + (objectSize * idx));
183 void SetBasicTypeSize(
Int_t size){
184 fBasicTypeSize = size;
188 template <
class BASE>
189 class TUIntOrIntReader:
public BASE {
192 std::unique_ptr<TTreeReaderValueBase> fSizeReader;
193 bool fIsUnsigned =
false;
202 template <
class...
ARGS>
203 TUIntOrIntReader(
TTreeReader *treeReader,
const char *leafName,
205 BASE(std::forward<ARGS>(args)...)
207 if (
TLeaf* sizeLeaf = treeReader->
GetTree()->FindLeaf(leafName)) {
208 fIsUnsigned = sizeLeaf->IsUnsigned();
219 return *GetSizeReader<UInt_t>();
220 return *GetSizeReader<Int_t>();
224 class TArrayParameterSizeReader:
public TUIntOrIntReader<TObjectArrayReader> {
227 TUIntOrIntReader<TObjectArrayReader>(treeReader,
branchName) {}
231 class TArrayFixedSizeReader :
public TObjectArrayReader {
236 TArrayFixedSizeReader(
Int_t sizeArg) : fSize(sizeArg) {}
243 ~TBasicTypeArrayReader() {}
248 Error(
"TBasicTypeArrayReader::GetCP()",
"Read error in TBranchProxy.");
257 if (!myCollectionProxy)
return 0;
258 return myCollectionProxy->
Size();
263 if (!myCollectionProxy)
return 0;
268 class TBasicTypeClonesReader :
public TClonesReader {
272 TBasicTypeClonesReader(
Int_t offsetArg) : fOffset(offsetArg) {}
276 if (!myClonesArray)
return 0;
277 return (
Byte_t*)myClonesArray->
At(idx) + fOffset;
286 TLeafReader(
TTreeReaderValueBase *valueReaderArg) : fValueReader(valueReaderArg), fElementSize(-1) {}
290 return myLeaf ? myLeaf->
GetLen() : 0;
296 if (fElementSize == -1){
298 if (!myLeaf)
return 0;
301 return (
Byte_t*)address + (fElementSize * idx);
310 class TLeafParameterSizeReader:
public TUIntOrIntReader<TLeafReader> {
312 TLeafParameterSizeReader(
TTreeReader *treeReader,
const char *leafName,
314 TUIntOrIntReader<TLeafReader>(treeReader, leafName, valueReaderArg) {}
318 return TUIntOrIntReader<TLeafReader>::GetSize(proxy);
339 fSetupStatus = kSetupInternalError;
341 Error(
"TTreeReaderArrayBase::CreateProxy()",
"TTreeReader object not set / available for branch %s!",
343 fSetupStatus = kSetupTreeDestructed;
348 const char* brDataType =
"{UNDETERMINED}";
351 brDataType = GetBranchDataType(br, dictUnused);
353 Error(
"TTreeReaderArrayBase::CreateProxy()",
"The template argument type T of %s accessing branch %s (which contains data of type %s) is not known to ROOT. You will need to create a dictionary for it.",
354 GetDerivedTypeName(), fBranchName.Data(), brDataType);
355 fSetupStatus = kSetupMissingDictionary;
366 TLeaf *myLeaf =
nullptr;
367 if (!GetBranchAndLeaf(branch, myLeaf, branchActualType))
371 Error(
"TTreeReaderArrayBase::CreateProxy()",
372 "No dictionary for branch %s.", fBranchName.Data());
379 fSetupStatus = kSetupMatch;
381 SetImpl(branch, myLeaf);
390 fSetupStatus = kSetupMatch;
392 Error(
"TTreeReaderArrayBase::CreateProxy()",
393 "Type ambiguity (want %s, have %s) for branch %s.",
400 bool isTopLevel = branch->
GetMother() == branch;
402 membername = strrchr(branch->
GetName(),
'.');
403 if (membername.IsNull()) {
404 membername = branch->
GetName();
407 namedProxy =
new TNamedBranchProxy(fTreeReader->fDirector, branch, fBranchName, membername);
408 fTreeReader->AddProxy(namedProxy);
411 fSetupStatus = kSetupMatch;
413 fSetupStatus = kSetupMismatch;
417 TString branchActualTypeName;
418 const char* nonCollTypeName = GetBranchContentDataType(branch, branchActualTypeName, branchActualType);
419 if (nonCollTypeName) {
420 Error(
"TTreeReaderArrayBase::CreateContentProxy()",
"The branch %s contains data of type %s, which should be accessed through a TTreeReaderValue< %s >.",
421 fBranchName.Data(), nonCollTypeName, nonCollTypeName);
422 if (fSetupStatus == kSetupInternalError)
423 fSetupStatus = kSetupNotACollection;
427 if (!branchActualType) {
428 if (branchActualTypeName.IsNull()) {
429 Error(
"TTreeReaderArrayBase::CreateContentProxy()",
"Cannot determine the type contained in the collection of branch %s. That's weird - please report!",
432 Error(
"TTreeReaderArrayBase::CreateContentProxy()",
"The branch %s contains data of type %s, which does not have a dictionary.",
433 fBranchName.Data(), branchActualTypeName.Data());
434 if (fSetupStatus == kSetupInternalError)
435 fSetupStatus = kSetupMissingDictionary;
441 if (fDict != branchActualType) {
442 Error(
"TTreeReaderArrayBase::CreateContentProxy()",
"The branch %s contains data of type %s. It cannot be accessed by a TTreeReaderArray<%s>",
443 fBranchName.Data(), branchActualType->
GetName(), fDict->GetName());
444 if (fSetupStatus == kSetupInternalError || fSetupStatus >= 0)
445 fSetupStatus = kSetupMismatch;
457 SetImpl(branch, myLeaf);
466 branch = fTreeReader->
GetTree()->GetBranch(fBranchName);
470 if (!fBranchName.Contains(
".")) {
471 Error(
"TTreeReaderArrayBase::GetBranchAndLeaf()",
"The tree does not have a branch called %s. You could check with TTree::Print() for available branches.", fBranchName.Data());
472 fSetupStatus = kSetupMissingBranch;
477 TRegexp leafNameExpression (
"\\.[a-zA-Z0-9_]+$");
478 TString leafName (fBranchName(leafNameExpression));
479 TString
branchName = fBranchName(0, fBranchName.Length() - leafName.Length());
480 branch = fTreeReader->
GetTree()->GetBranch(branchName);
482 Error(
"TTreeReaderArrayBase::GetBranchAndLeaf()",
"The tree does not have a branch called %s. You could check with TTree::Print() for available branches.", fBranchName.Data());
483 fSetupStatus = kSetupMissingBranch;
488 myLeaf = branch->GetLeaf(TString(leafName(1, leafName.Length())));
490 Error(
"TTreeReaderArrayBase::GetBranchAndLeaf()",
"The tree does not have a branch, nor a sub-branch called %s. You could check with TTree::Print() for available branches.", fBranchName.Data());
491 fSetupStatus = kSetupMissingBranch;
498 Error(
"TTreeReaderArrayBase::GetBranchAndLeaf()",
"Failed to get the dictionary for %s.", myLeaf->
GetTypeName());
499 fSetupStatus = kSetupMissingDictionary;
506 branchActualType = fDict;
509 fLeafName = leafName(1, leafName.Length());
510 fHaveLeaf = (fLeafName.Length() > 0);
511 fSetupStatus = kSetupMatchLeaf;
514 Error(
"TTreeReaderArrayBase::GetBranchAndLeaf()",
"Leaf of type %s cannot be read by TTreeReaderValue<%s>.", myLeaf->
GetTypeName(), fDict->GetName());
516 fSetupStatus = kSetupMismatch;
542 fImpl =
new TLeafReader(
this);
548 fImpl =
new TLeafParameterSizeReader(fTreeReader, leafFullName.Data(),
this);
550 fSetupStatus = kSetupMatchLeaf;
564 if (fSetupStatus == kSetupInternalError)
565 fSetupStatus = kSetupMatch;
567 fImpl =
new TSTLReader();
573 fImpl =
new TClonesReader();
584 fImpl =
new TBasicTypeArrayReader();
587 fImpl =
new TBasicTypeClonesReader(element->
GetOffset());
591 ((TObjectArrayReader*)fImpl)->SetBasicTypeSize(((
TDataType*)fDict)->
Size());
596 ((TArrayParameterSizeReader*)fImpl)->SetBasicTypeSize(((
TDataType*)fDict)->
Size());
599 fImpl =
new TClonesReader();
601 Error(
"TTreeReaderArrayBase::SetImpl()",
602 "Cannot read branch %s: unhandled streamer element type %s",
603 fBranchName.Data(), element->IsA()->
GetName());
604 fSetupStatus = kSetupInternalError;
615 Error(
"TTreeReaderArrayBase::SetImpl",
"Failed to get the top leaf from the branch");
616 fSetupStatus = kSetupMissingBranch;
621 if (fSetupStatus == kSetupInternalError)
622 fSetupStatus = kSetupMatch;
624 fImpl =
new TArrayFixedSizeReader(size);
627 fImpl =
new TArrayParameterSizeReader(fTreeReader, sizeLeaf->
GetName());
629 ((TObjectArrayReader*)fImpl)->SetBasicTypeSize(((
TDataType*)fDict)->
Size());
631 Error(
"TTreeReaderArrayBase::SetImpl",
"Support for branches of type TBranchClones not implemented");
632 fSetupStatus = kSetupInternalError;
634 Error(
"TTreeReaderArrayBase::SetImpl",
"Support for branches of type TBranchObject not implemented");
635 fSetupStatus = kSetupInternalError;
637 Error(
"TTreeReaderArrayBase::SetImpl",
"Support for branches of type TBranchSTL not implemented");
638 fImpl =
new TSTLReader();
639 fSetupStatus = kSetupInternalError;
641 Error(
"TTreeReaderArrayBase::SetImpl",
"Support for branches of type TBranchRef not implemented");
642 fSetupStatus = kSetupInternalError;
657 TString& contentTypeName,
661 contentTypeName =
"";
665 || brElement->
GetType() == 3) {
670 Error(
"TTreeReaderArrayBase::GetBranchContentDataType()",
"Could not get value class.");
679 if (brElement->
GetType() == 3) {
688 Error(
"TTreeReaderArrayBase::GetBranchContentDataType()",
"Cannot determine STL collection type of %s stored in branch %s", brElement->
GetClassName(), branch->
GetName());
693 if (isMap) contentTypeName =
"std::pair< ";
694 contentTypeName += splitType.fElements[1];
696 contentTypeName += splitType.fElements[2];
697 contentTypeName +=
" >";
702 }
else if (brElement->
GetType() == 31
703 || brElement->
GetType() == 41) {
708 if (ExpectedTypeRet == 0) {
714 Error(
"TTreeReaderArrayBase::GetBranchContentDataType()",
"The branch %s contains a data type %d for which the dictionary cannot be retrieved.",
715 branch->
GetName(), (int)dtData);
720 }
else if (ExpectedTypeRet == 1) {
721 int brID = brElement->
GetID();
724 Error(
"TTreeReaderArrayBase::GetBranchContentDataType()",
"The branch %s contains data of type %s for which the dictionary does not exist. It's needed.",
739 return "{CANNOT DETERMINE TBranchElement DATA TYPE}";
751 Error(
"TTreeReaderArrayBase::GetBranchDataType()",
"Could not get class from branch element.");
755 if (!myCollectionProxy){
756 Error(
"TTreeReaderArrayBase::GetBranchDataType()",
"Could not get collection proxy from STL class");
764 Error(
"TTreeReaderArrayBase::GetBranchDataType()",
"Could not get valueClass from collectionProxy.");
767 contentTypeName = dict->
GetName();
771 if (!fProxy->Setup() || !fProxy->Read()){
772 Error(
"TTreeReaderArrayBase::GetBranchContentDataType()",
"Failed to get type from proxy, unable to check type");
773 contentTypeName =
"UNKNOWN";
775 return contentTypeName;
779 contentTypeName = dict->
GetName();
793 contentTypeName =
"TClonesArray";
794 Warning(
"TTreeReaderArrayBase::GetBranchContentDataType()",
"Not able to check type correctness, ignoring check");
796 fSetupStatus = kSetupNoCheck;
803 if (dict) contentTypeName = dict->
GetName();
808 contentTypeName = dict->
GetName();
819 if ((!dataTypeName || !dataTypeName[0])
832 Error(
"TTreeReaderArrayBase::GetBranchContentDataType()",
"The branch %s was created using a leaf list and cannot be represented as a C++ type. Please access one of its siblings using a TTreeReaderArray:", branch->
GetName());
835 while ((leaf = (
TLeaf*) iLeaves())) {
836 Error(
"TTreeReaderArrayBase::GetBranchContentDataType()",
" %s.%s", branch->
GetName(), leaf->GetName());
842 Warning(
"TTreeReaderArrayBase::GetBranchContentDataType()",
"Not able to check type correctness, ignoring check");
844 fSetupStatus = kSetupNoCheck;
850 return "TClonesArray";
853 Error(
"TTreeReaderArrayBase::GetBranchContentDataType()",
"The branch %s is a TBranchRef and cannot be represented as a C++ type.", branch->
GetName());
856 Error(
"TTreeReaderArrayBase::GetBranchContentDataType()",
"The branch %s is of type %s - something that is not handled yet.", branch->
GetName(), branch->IsA()->
GetName());
Describe Streamer information for one class version.
virtual const char * GetName() const
Returns name of object.
virtual const char * GetClassName() const
Return the name of the user class whose content is stored in this branch, if any. ...
A TLeaf describes individual elements of a TBranch See TBranch structure in TTree.
static TDataType * GetDataType(EDataType type)
Given a EDataType type, get the TDataType* that represents it.
TVirtualCollectionProxy * GetCollectionProxy()
Return the collection proxy describing the branch content, if any.
const char * GetBranchContentDataType(TBranch *branch, TString &contentTypeName, TDictionary *&dict)
Access a branch's collection content (not the collection itself) through a proxy. ...
TString GetTypeName()
Get basic type of typedef, e,g.
Int_t GetSplitLevel() const
virtual Int_t GetExpectedType(TClass *&clptr, EDataType &type)
Fill expectedClass and expectedType with information on the data type of the object/values contained ...
TTreeReader is a simple, robust and fast interface to read values from a TTree, TChain or TNtuple...
virtual TClass * GetValueClass() const =0
TStreamerElement * GetElement(Int_t id) const
virtual const char * GetTypeName() const
virtual TLeaf * GetLeafCounter(Int_t &countval) const
Return a pointer to the counter of this leaf.
Regular expression class.
virtual void CreateProxy()
Create the proxy object for our branch.
static TDictionary * GetDictionary(const char *name)
TStreamerInfo * GetInfo() const
Get streamer info for the branch class.
TVirtualCollectionProxy * GetCollectionProxy() const
Return the proxy describing the collection (if any).
virtual void * GetStart(UInt_t=0)
Int_t GetArrayLength() const
EReadStatus ProxyRead()
Try to read the value from the TBranchProxy, returns the status of the read.
Type GetType(const std::string &Name)
TObject * At(Int_t idx) const
virtual EDataType GetType() const =0
void SetContentDict(TDictionary *dict)
TBranchElement * GetBranchCount() const
const Detail::TBranchProxy * GetProxy() const
virtual TLeaf * GetLeaf(const char *name) const
Return pointer to the 1st Leaf named name in thisBranch.
int IsSTLCont(int testAlloc=0) const
type : type name: vector<list<classA,allocator>,allocator> testAlloc: if true, we test allocator...
virtual Int_t GetLenType() const
TDictionary * GetContentDict() const
Extracts data from a TTree.
virtual const char * GetClonesName() const
TTreeReaderValueBase::EReadStatus fReadStatus
bool GetBranchAndLeaf(TBranch *&branch, TLeaf *&myLeaf, TDictionary *&branchActualType)
Determine the branch / leaf and its type; reset fProxy / fSetupStatus on error.
virtual Int_t GetLen() const
Return the number of effective elements of this leaf.
virtual const char * GetTypeName() const
Return type name of element in the branch.
Basic data type descriptor (datatype information is obtained from CINT).
This class defines an abstract interface that must be implemented by all classes that contain diction...
virtual Bool_t HasPointers() const =0
virtual TLeaf * GetLeafCount() const
TClass * GetCurrentClass()
Return a pointer to the current type of the data member corresponding to branch element.
void * GetAddress()
Returns the memory address of the object being read.
The ROOT global object gROOT contains a list of all defined classes.
void Warning(const char *location, const char *msgfmt,...)
A Branch for the case of an object.
TObject * UncheckedAt(Int_t i) const
TVirtualCollectionProxy * GetCollection()
virtual const char * GetClassName() const
Return the name of the user class whose content is stored in this branch, if any. ...
virtual void * At(UInt_t idx)=0
TObjArray * GetListOfLeaves()
TClass * GetClass() const
TLeaf * GetLeaf()
If we are reading a leaf, return the corresponding TLeaf.
Int_t GetClassSize() const
TObjArray * GetElements() const
virtual UInt_t Size() const =0
An array of clone (identical) objects.
const char * GetTypeName() const
virtual ~TVirtualCollectionReader()
virtual TClass * GetClass() const
Int_t GetEntries() const
Return the number of objects in array (i.e.
virtual void * At(Detail::TBranchProxy *, size_t)=0
Base class for all the proxy object.
TBranch * GetBranch() const
A TTree is a list of TBranches.
TBranch * GetMother() const
Get our top-level parent branch in the tree.
void Error(ErrorHandler_t func, int code, const char *va_(fmt),...)
Write error message and call a handler, if required.
TClass * GetClass() const
void SetImpl(TBranch *branch, TLeaf *myLeaf)
Create the TVirtualCollectionReader object for our branch.
virtual size_t GetSize(Detail::TBranchProxy *)=0