Write 2d variable size arrays into TTree

Hi,
is there a way of storing 2d array with variable dimensions into the TTree?

If no, is there any workaround for that?

cheers


ROOT Version: 6.18

For 1 variable and 1 fixed there are several options. For 2 variables dimensions use std::vector<std::vector<type_name>>

Dear pcanal.
I doubt this works.
I have tried the following example. Which does not find any good constructor for a branch with 2 vectors.

error: no matching member function for call to 'Branch'

int test(){
    int nParticles;
    vector<int> nTracks;
    vector<vector<double>> trackPosition;

    TFile file("test.root", "RECREATE");
    TTree tree("test", "test");
    tree.Branch("nParticles", &nParticles, "nParticles/I");
    tree.Branch("nTracks", nTracks, "nTracks[nParticles]/I");
    tree.Branch("trackPosition", trackPosition,"trackPosition[nParticles][nTracks]/D");

    //Assume 2 particles
    nParticles = 2;
    //1st has 2 traks
    nTracks.push_back(2);
    //2nd has 3 tracks
    nTracks.push_back(3);

    //Fill positions of each track for 1st particle
    vector<double> temp1;
    for (size_t i = 0; i < 2; i++) temp1.push_back((i+1)*10);
    trackPosition.push_back(temp1);

    //Fill positions of each track for 2st particle
    vector<double> temp2;
    for (size_t i = 0; i < 3; i++) temp2.push_back((i+1)*100);
    trackPosition.push_back(temp2);

    tree.Fill();
    file.Write();
return 0;
}

I also tried this with variable arrays like this:

int test(){
    int nParticles;
    int nTracks[100];
    Double_t trackPosition[100][100];

    TFile file("test.root", "RECREATE");
    TTree tree("test", "test");
    tree.Branch("nParticles", &nParticles, "nParticles/I");
    tree.Branch("nTracks", nTracks, "nTracks[nParticles]/I");
    tree.Branch("trackPosition", trackPosition,"trackPosition[nParticles][nTracks]/D");

    //Assume 2 particles
    nParticles = 2;
    //1st has 2 traks
    nTracks[0] = 2;
    //2nd has 3 tracks
    nTracks[1] = 3;

    //Fill positions of each track for 1st particle
    for (size_t i = 0; i < 2; i++) trackPosition[0][i] = (i+1)*10.;

    //Fill positions of each track for 2st particle
    for (size_t i = 0; i < 3; i++) trackPosition[1][i] = (i+1)*100.;

    tree.Fill();
    file.Write();
    return 0;
}

But trackPosition values in the written file are all 0.

It only works if I put 2nd dimension as constant. But then it stores too much of empty_space information.

I looked at TBranch source file and it doesn’t seem to be implemented yet.
Is it correct? Is there a hope that it will be implemented soon? Or are there any workaround for this without storing a lot of empty data and complicating future analysis.

cheers,
Bohdan

You cannot do that with plain “C style” arrays. Only one dimension can be variable.

You might be able to do it with nested std::vectors. But then you each of the outer array elements can be an independent length, unless you constrain them in your filling code.

Dear all, thanks for the replies.

All works, I just realized I need to use another Branch method.

Doesn’t work:

    vector<int> nTracks;
    vector<vector<double>> trackPosition;
    tree.Branch("nTracks", nTracks, "nTracks[nParticles]/I");
    tree.Branch("trackPosition", trackPosition,"trackPosition[nParticles][nTracks]/D");

Works fine:

    vector<int> nTracks;
    vector<vector<double>> trackPosition;
    tree->Branch("nTracks", &nTracks);
    tree->Branch("trackPosition", &trackPosition);

I leave it here in case if someone finds it helpful

1 Like

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