Object I/O of a user-defined class containing TVector3

Dear ROOT developers and users,

I am trying to write a class object contaning TVector3 object as a data member,
but failed with a run-time error.
Please take a look at the class definition in event.hh and event.cc in the attached archive.
The class “Event” has a pointer to a TClonesArray object, in which the pointers of “Track” objects are stored.

Here’s the procedure to build an executable to generate a ROOT file, and the result.

[kameoka@amd02] make g++ -g -Wall -fPIC `root-config --cflags` -c event.cc rootcint -f event_dict.cc -c event.hh LinkDef.h g++ -g -Wall -fPIC `root-config --cflags` -c event_dict.cc g++ -shared -O event.o event_dict.o -o libevent.so -L/opt/heplib/root/pro/lib -lPhysics g++ -g -Wall `root-config --libs` libevent.so main.o -o main [kameoka@amd02] ./main

*** Break *** segmentation violation
Generating stack trace…
0x0000002a958d2488 in int TStreamerInfo::WriteBufferAux<char**>(TBuffer&, char** const&, int, int, int, int) + 0xaa8 from /opt/heplib/root/pro/lib/libCore.so.4.02
0x0000002a958cda3f in TStreamerInfo::WriteBufferClones(TBuffer&, TClonesArray*, int, int, int) + 0x5f from /opt/heplib/root/pro/lib/libCore.so.4.02
0x0000002a96da74c3 in TBranchElement::FillLeaves(TBuffer&) + 0x2c3 from /opt/heplib/root/pro/lib/libTree.so.4.02
0x0000002a96d9fb3b in TBranch::Fill() + 0x42b from /opt/heplib/root/pro/lib/libTree.so.4.02
0x0000002a96da7836 in TBranchElement::Fill() + 0x116 from /opt/heplib/root/pro/lib/libTree.so.4.02
0x0000002a96da77f9 in TBranchElement::Fill() + 0xd9 from /opt/heplib/root/pro/lib/libTree.so.4.02
0x0000002a96da77f9 in TBranchElement::Fill() + 0xd9 from /opt/heplib/root/pro/lib/libTree.so.4.02
0x0000002a96dc6b45 in TTree::Fill() + 0x65 from /opt/heplib/root/pro/lib/libTree.so.4.02
0x0000000000401807 in main + 0x40f from ./main
0x0000002a97e0eacd in __libc_start_main + 0xfd from /lib64/tls/libc.so.6
0x000000000040135a in TFile::TFile(char const*, char const*, char const*, int) + 0x42 from ./main
zsh: 20494 abort ./main

If I use not the pointer to which TVector3 object is dynamically allocated,
but the TVector3 object itself as a data member,
the program runs.
In that case, however, on a ROOT session, member function such as TVector3::Mag() cannot be used through TTree::Draw,
although the data members are accessible.

I would appreciate any suggestion.


Kame
test.tar.gz (1.49 KB)

In your main.cc, replace
Track *tk = new(a[i]) Track(j, chi2, x, y, z);
by
Track *tk = new(a[j]) Track(j, chi2, x, y, z);

also replace
Track() {}
by
Track() {v=0;}

Rene

Hi Rene,
Thank you for the reply.

I am sorry. It was just a careless mistake!
Now it works.

I have another question related to object I/O.

I defined a static data member which points the TClonesArray object in Event class
to make sure that the object is created only once,
following the example in $ROOTSYS/test.

TClonesArray *tks;
static TClonesArray *_tks;

But this seems unnecessary
since the Event object is created only once in the main program.
If that static pointer is required,
it means the constructor of Event class can be implicitly called
in another place(?).
Am I correct?


Kame

If you create the Event object once only you do not need the static member. In the Event example at $ROOTSYS/test we show an implementation where the Event object may be recreated at each event.

Rene

I see. Thanks.
May I ask you two more questions?

  1. If so, it seems natural for me to make the constructor create the TClonesArray object like

Event::Event() : tks(new TClonesArray(“Track”, 10)) {} .

But the users guide tells not to allocate any objects in default constructor.
Is this okay if only one Event object is created throughout the program ?

  1. If one want a class to have a non-simple type object as a data member,
    does it always need to be dynamically allocated?

I mean

class Event {

TVector3 v; // TVector3 object as a data member

}

or

class Event {

TVector3 *v; // TVector3 object will be allocated

}

The first case did not work when I tried.
In the second case, do I need to add “//->” in the comment field?


Kame