Copying TH1F from TFile

Hi everyone,

I am working with a TFile that contains a lot of TH1F objects. Each TH1F is a histogram of 2048 points. I am trying to open the file, read a particular TH1F (Histo1 in this example), and then write it to another TFile as a TLeaf in a TBranch in a TTree. I am trying to use the code below, but it segfaults.

The declaration of a branch is the bit that breaks it. If I remove the & from wf, the code runs, but it just fills TH1F inside the branch with 2048 points of rubbish pointer addresses. I have checked the contents of wf using wf->GetBinContent(), and wf contains the correct values.

Any help with getting this to run will be appreciated!

TFile *rootin = TFile::Open("Data.root");
TFile rootout("Test.root", "recreate");
TTree* fevent = new TTree("array", "array");

TH1F* wf = (TH1F*)rootin->Get("Histo1");

fevent->Branch("data", &wf, "wf[2048]/F");

fisevent->Fill();
rootout.Write();

wf is the address of the histogram itself, i.e. its metadata, not the address data stored in the histogram! (actually, &wf it is even the address of the pointer (on the stack) to the histogram metadata!)

You could use histogram->GetArray to get the underlying data array (but consider underflow/overflow bins as well). Also, what is fisevent in your code? What do you want to fill? It might be cleaner to copy the data from the histogram into a separate array.

1 Like

My apologies, fisevent was meant to be fevent, this is an artefact of trying to create a skeleton code to demonstrate what I do here.

I can extract the 2048 values stored in Histo1 correctly. I want to fill the branch with TH1F wf. Ultimately, I want the following structure:

rootout->fevent->data->TH1F Histo1 with 2048 data points

Understood. And I already gave the solution. Use GetArray.

root [0] auto h = new TH1F("h", "h", 10, 0, 10);
root [1] for (int i = 0; i < 10; ++i) h->Fill(i, i*i);
root [2] TFile outfile("/tmp/histoarray.root", "recreate");
root [3] auto tree = new TTree("array", "array");
root [4] tree->Branch("data", h->GetArray() + 1, "wf[10]/F");
root [5] tree->Fill();
root [6] tree->Write();
root [7] outfile.Close();

Note: array is a bad name for the tree since std::array is a type.
The +1 is to skip the underflow bin.

1 Like

Thank you, that solves it!

This topic was automatically closed 14 days after the last reply. New replies are no longer allowed.