Creating a Branch that each element is an Array

Hi,

I have some digital data to analyze and I want to use the Tree structure. However I end up with some problems.

Let’s say that I have some channels storing data, each one gives me an output of a histogram for every event in my experiment. What I want to do is storing each event of the same channel in the same branch as a Leaf. Therefore, if the experiment has 100 events:

channel 0 will have 100 leafs
channel 1 will have 100 leafs
channel 2 will have 100 leafs
and so on.

Since the Tree Viewer cannot support Histograms I have changed them into arrays. The problem that I hace is that I cannot fill the tree properly, I cannot see every event so just a value of each one of them.

This is the code that I used:

[code]hfile = new TFile(“prova.root”,“recreate”);
mytree = new TTree(“Mytree”,“Mytree”);

mytree->Branch(“canals”,&i,“i/I”);
mytree->Branch(“hola”, ch0A, “ch0A[i]/F”);

for(i = 0 ; i < 1024; i++){ //every histogram has 1024 values
ch0A[i]=ch[1]->GetBinContent(i);
}
mytree->Fill();

mytree->Write();
hfile->Close();[/code]

Does anyone has some clue in how to solve it?

Thanks in advance!

The branch name should not contain the letter i, but the number of entries 1024.
Also, you should define the array before defining the branch. Use the correct type for your data. Below I assumed it is a float. I do not believe that you need to store the channel number is the tree as it is already part of the index for ch0A.

hfile = new TFile("prova.root","recreate");
mytree = new TTree("Mytree","Mytree");

Float_t ch0A[1024];
mytree->Branch("hola", ch0A, "ch0A[1024]/F");

  for(i = 0 ; i < 1024; i++){          //every histogram has 1024 values     
ch0A[i]=ch[1]->GetBinContent(i);
}
    mytree->Fill(); 

mytree->Write();
hfile->Close();

[quote]What I want to do is storing each event of the same channel in the same branch as a Leaf. [/quote]That is contrary to the usual semantic of a TTree where instead you store each event of the same channel as an [b]entry{/b] in the same branch as a single leaf.

Philippe.

@ksmith: thanks for the reply. I had already this line:

Float_t ch0A[1024]

@pcanal: I don’t really understand your reply. The thing is that my events are not single values, but a full histogram/array.

Anyhow, now I see that when I scan the data it is well done analyzed, but what I would like to do is to split the branch, as far as I know I cannot do a splitlevel when I defined the branch with an array. Is there a way to split the branch with the array, let’s say:

I tried that but it gave me an error. Does someone knows how to do it?

Thanks,

psc

[quote]@pcanal: I don’t really understand your reply. The thing is that my events are not single values, but a full histogram/array.[/quote]Yes, so indeed you need an array. However what was confusing in your expression is the (likely) confusion between the term leaf and entry/event in your original text. For example:[quote] Therefore, if the experiment has 100 events:
channel 0 will have 100 leafs[/quote]What you do want in this case is for ‘channel 0’ to have 100 entries(/events). On the other hand, if [quote]Is there a way to split the branch with the array, let’s say:[/quote]was possible, it would lead to the branch “hola” to have 1024 leaves.

No, TTree does not support split an array into one leaf per element of the array. So if you wanted to do so you would have to do it by hand:for (int i=0; i<1024; ++i) { mytree->Branch(TString::Format("hola%d",i),&(ch0A)); }.

One significant difference between the 2 case is how easy it is to Draw/Scan across all the values. If you use the array form you can do both:mytree->Draw("ch0A"); // plot together all the triggers for all events mytree->Draw("ch0A[3]","ch0A[4]>0"); // plot a single trigger with a cut on another onewhile with the hand split making the first plot is much harder:mytree->Draw("ch0A_0"); mytree->Draw("ch0A_1","","SAME"); etc... mytree->Draw("ch0A_3","ch0A_4>0"); // plot a single trigger with a cut on another onebut the resulting file might be more compact (better compression) and each individual trigger would be readable without having to read all the other trigger (potential performance gain).

So, I was wondering what was your goal is splitting the array.

Cheers,
Philippe.

Hi Philippe,

you are right, indeed. What I would like to have is to have 100 entries made of 1024 values each one.

Somehow, I had manage to have a branch with everything inside:

So, when I scan I obtain:

  • Row * Instance * hola *

    1 *        2 *        -2 *
  •    1 *        3 *         1 *
    
  •    1 *        4 *         8 *
    
  •    1 *        5 *         4 *
    
  •    1 *        6 *        -6 *
    
  •    1 *        7 *        -2 *
    
  •    1 *        8 *         9 *
    
  •    1 *        9 *         5 *
    
  •    1 *       10 *        -2 *
    
  •    1 *       11 *        -7 *
    
  •    1 *       12 *         5 *
    
  •    1 *       13 *         8 *
    
  •    1 *       14 *         0 *
    
  •    1 *       15 *        -5 *
    
  •    1 *       16 *        -2 *
    
  •    1 *       17 *         7 *
    
  •    1 *       18 *         7 *
    
  •    1 *       19 *        -2 *
    
  •    1 *       20 *        -3 *
    
  •    1 *       21 *         1 *
    
  •    1 *       22 *         8 *
    
  •    1 *       23 *        -1 *
    
  •    1 *       24 *        -5 *
    

the problem that I have now is that I cannot read a single row at once, even not using the comand:

Scan->hola[][1] if I would like to read row 1, for instance.

Do you know why?

Thanks

Hi,

To read a single row (entry) when using Scan, you need to use the following syntax:mytree->Scan("hola[]","","",1,234);// Reading 1 entry starting at entry number 234
To read the single value for one of the trigger for one entry:mytree->Scan("hola[23]","","",1,234);// Reading the value of 23rd trigger for 1 entry starting at entry number 234

Cheers,
Philippe.