[ROOT] memory leak using TTree with TObjArray

From: Rene Brun (Rene.Brun@cern.ch)
Date: Wed Oct 23 2002 - 15:03:59 MEST


Following a suggestion by Sander, I am reposting a mail about memory leaks
with a different subject title. See below
I take once more this opportunity to repeat some very basic rules
when sending mails to roottalk:
- always specify a meaningfull subsject title. This facilitates the search
  with tools such as google, yahoo, etc.
- always specify the version of Root that you are using
- if you submit a problem, provide enough information such that it is not
   necessary to send another mail asking for more details.
- when submitting a problem, try to reproduce the problem in a small
  script. The time to solve the problem is often proportional to the size
  of the script.

Rene Brun


ORIGINAL MAIL ABOUT MEMORY LEAKS
================================
Hi Ruben,

Two solutions to your problem
 - solution1 (recommended)  in testwrite
   Set the ownership of your top level TObjArray.
     detectors = new TObjArray(nsens);
     detectors->SetOwner(kTRUE); //<======add this line

 - solution 2 (if you do not want to rewrite your data set) in testread

  for (int i=0;i<nev;i++) {
    // Read the branch for this detector
    branch->GetEntry(i);
    if (!(i%100)) {
      printf("Ev. %5d : %7s %7s
%s\n",i,"Sensor","NDigits","&TClonesArray");
      int nsens = detectors->GetLast()+1;
      for (int j=0;j<nsens;j++) {
        TClonesArray *arr = (TClonesArray*)detectors->At(j);
        printf("            %7d  %7d  %p |\n",j,arr->GetLast()+1,arr);
      }
    }
    detectors->Delete(); //<======add this line
  }

Rene Brun

 Ruben Shahoian wrote:
> 
> Hello,
> I need to write and read the branc of the tree, which constists of the
> TObjArray of TClonesArray (TObjArray being collector of data
> (TClonesArray) of different sensor).
> So, I do
> 
>   detectors = new TObjArray(nsens);
>   for (int i=0;i<nsens;i++) {
>     TClonesArray *arr = new TClonesArray("TObject",3000);
>     detectors->AddAt(arr,i);
>   }
>   file = new TFile("tree.root","RECREATE");
>   tree = new TTree("DataTree","Tree");
>   branch = tree->Branch("Det1","TObjArray",&detectors,32000,0);
> 
> It works fine for writing.
> But then, in the reading method, I do
>  TObjArray *detectors=0;
>   branch->SetAddress(&detectors);
>   ...
>   branch->GetEntry(i);
> 
> It reads back everything correctly but it appears that for each event
> it creates new TClonesArrays and attaches it to TObjArray (without even
> deleting the previous TClonesArrays, although, I would expect that they
> simply should be reused).
> I've tried both splitting the tree and setting SetAutoDelete(kTRUE),
> very soon it swallows up all RAM and starts swapping ...
> Is this normal behavoiur?
> I attach short macros (run .x testrw.C, demonstrating the problem)
> 
> Best regards,
>         Ruben

On Wed, 23 Oct 2002, Sander Klous wrote:

> Hi,
> Can you please resubmit this message to the mailing list with something 
> like 'memory leak using TTree with TObjArray' in the title?
> 
> http://root.cern.ch/root/roottalk/roottalk02/0444.html
> 
> As a courtesy to the people that encoutner this problem in the future...
> I could only find the mail after I solved the problem myself because of 
> the worthless title.
> Thanks,
> Sander
> 



This archive was generated by hypermail 2b29 : Sat Jan 04 2003 - 23:51:15 MET