Root 4.08 TTree error related to bufsize

From: Mat Martin <msmartin_at_fnal.gov>
Date: Tue, 20 Jun 2006 19:41:07 -0500


Hi Folks,

               My observation is that in the code below, in the Branch(...) statements, if I don't supply the "bufsize" argument bigger than the default 64000 I can't create a tree bigger than about 7000 rows of the rather small structure given below.

There are 15 trees created by the code below, and 14 of them were fine when I looked at them in a separate root session. But the 15th, and largest (8900 entries appx) was garbage (gave me lots of :

Error in <TFile::ReadBuffer>: error reading all requested bytes from file pt_histos.root, got 0 of 25976
Error in <TFile::ReadBuffer>: error reading all requested bytes from file pt_histos.root, got 0 of 25976
Error in <TFile::ReadBuffer>: error reading all requested bytes from file pt_histos.root, got 0 of 25976
Error in <TFile::ReadBuffer>: error reading all requested bytes from file pt_histos.root, got 0 of 25976
Error in <TFile::ReadBuffer>: error reading all requested bytes from file pt_histos.root, got 0 of 25976
Error in <TFile::ReadBuffer>: error reading all requested bytes from file pt_histos.root, got 0 of 25976
Error in <TFile::ReadBuffer>: error reading all requested bytes from file pt_histos.root, got 0 of 25976
Error in <TFile::ReadBuffer>: error reading all requested bytes from file pt_histos.root, got 0 of 25976
Error in <TFile::ReadBuffer>: error r

When I supply the bufsize argument as 128000, as in the code below, the problem goes away. Am I missing something obvious? Shouldn't TTree know when to flush the buffer? Or is there a command to tell it to flush...?

cheers

Mat

#define makePt_histos_cxx
#include "makePt_histos.h"
#include <TH2.h>
#include <TStyle.h>
#include <TCanvas.h>
#include "TH1F.h"
#include <vector>
#include <fstream>
#include <iostream>

void makePt_histos::Loop()
{

//   In a ROOT session, you can do:
//      Root > .L makePt_histos.C
//      Root > makePt_histos t
//      Root > t.GetEntry(12); // Fill t data members with entry number 12
//      Root > t.Show();       // Show values of entry 12
//      Root > t.Show(16);     // Read and show values of entry 16
//      Root > t.Loop();       // Loop on all entries
//

//     This is the loop skeleton where:
//    jentry is the global entry number in the chain
//    ientry is the entry number in the current Tree
//  Note that the argument to GetEntry must be:
//    jentry for TChain::GetEntry
//    ientry for TTree::GetEntry and TBranch::GetEntry
//
//       To read only selected branches, Insert statements like:
// METHOD1:
//    fChain->SetBranchStatus("*",0);  // disable all branches
//    fChain->SetBranchStatus("branchname",1);  // activate branchname
// METHOD2: replace line
//    fChain->GetEntry(jentry);       //read all branches
//by b_branchname->GetEntry(ientry); //read only this branch

   if (fChain == 0) return;

   Int_t nentries = Int_t(fChain->GetEntriesFast());   

   Int_t nbins_hist = 48;
   Double_t bin_low = 4.6;
   Double_t bin_upp = 7.0;

   Int_t n_pt_bins = 15;

   Double_t pt_min = 0.0;
   Double_t pt_max = 30.0;

   Double_t pt_bin_width = (pt_max - pt_min)/n_pt_bins;

   std::cout<<"******************************"<<std::endl;
   std::cout<<"pt_bin_width: "<<pt_bin_width<<std::endl;
   std::cout<<"******************************"<<std::endl;

   std::vector<TH1F*> histo_vector;

   std::vector<TTree*> tree_vector;

   // TTree initialisations:

   std::vector<Float_t *>         LbF2mass_temp_vec;
   std::vector<Float_t *>         LbCt_temp_vec;
   std::vector<Float_t *>         LbCtErr_temp_vec;
   std::vector<Float_t *>         LbdCt_temp_vec;
   std::vector<Float_t *>         LcF2mass_temp_vec;
   std::vector<Float_t *>         LbF2pt_temp_vec;




   for(int i=0; i<n_pt_bins; i++){

     TString str_tmp("pt_hist_");

     TString str_tmp2("pt_tree_");

     char nos_str[3];
     sprintf(nos_str,"%i",i);
     TString nos_tstr(nos_str);

     TString title_str = str_tmp + nos_tstr;

     TString title_str2 = str_tmp2 + nos_tstr;

     TH1F * hist_temp = new TH1F(title_str.Data(),
                 title_str.Data(),
                 nbins_hist,
                 bin_low,
                 bin_upp);



     TTree * tree_temp = new TTree(title_str2.Data(),title_str2.Data());

    
     LbF2mass_temp_vec.push_back(new Float_t);
     LbCt_temp_vec.push_back(new Float_t);
     LbCtErr_temp_vec.push_back(new Float_t);
     LbdCt_temp_vec.push_back(new Float_t);
     LcF2mass_temp_vec.push_back(new Float_t);
     LbF2pt_temp_vec.push_back(new Float_t);



     tree_temp->Branch("LbF2mass", LbF2mass_temp_vec[i], 
"LbF2mass/F",128000);
     tree_temp->Branch("LbCt", LbCt_temp_vec[i], "LbCt/F",128000);
     tree_temp->Branch("LbCtErr", LbCtErr_temp_vec[i], "LbCtErr/F",128000);
     tree_temp->Branch("LbdCt", LbdCt_temp_vec[i], "LbdCt/F",128000);
     tree_temp->Branch("LcF2mass", LcF2mass_temp_vec[i], 
"LcF2mass/F",128000);
     tree_temp->Branch("LbF2pt", LbF2pt_temp_vec[i], "LbF2pt/F",128000);


    
     histo_vector.push_back(hist_temp);

     tree_vector.push_back(tree_temp);




   }//for

   Int_t nbytes = 0, nb = 0;
   for (Int_t jentry=0; jentry<nentries;jentry++) {

      Int_t ientry = LoadTree(jentry);
      if (ientry < 0) break;
      nb = fChain->GetEntry(jentry);   nbytes += nb;
      // if (Cut(ientry) < 0) continue;

      // Calculate which histogram to put the pt in:
      Double_t bin_float = (LbF2pt - pt_min) / pt_bin_width;

      // Truncate to integer (c++ numbering for bin)
      Int_t bin_int = bin_float;
     
      if(bin_int<n_pt_bins){


    (*LbF2mass_temp_vec[bin_int]) = LbF2mass;
    (*LbCt_temp_vec[bin_int]) = LbCt;
    (*LbCtErr_temp_vec[bin_int]) = LbCtErr;
    (*LbdCt_temp_vec[bin_int]) = LbdCt;

    (*LcF2mass_temp_vec[bin_int]) = LcF2mass;     (*LbF2pt_temp_vec[bin_int]) = LbF2pt;

    histo_vector[bin_int]->Fill(LbF2mass);     tree_vector[bin_int]->Fill();
      }//if

   }//for

   std::cout<<"After for loop"<<std::endl;

   // end debug section

   TFile fout("pt_histos.root","RECREATE");

   for(int i=0; i<histo_vector.size(); i++){      histo_vector[i]->Write();
   }//for

   for(int i=0; i<tree_vector.size(); i++){

       tree_vector[i]->Write();
   }//for

   fout.Close();

}//Loop

And my header file is:

//////////////////////////////////////////////////////////
// This class has been automatically generated on
// Tue Jun 20 14:18:49 2006 by ROOT version 4.00/08
// from TTree tree/Tree of events that pass cuts
// found on file: data_pthistos_with_cuts.root
//////////////////////////////////////////////////////////

#ifndef makePt_histos_h
#define makePt_histos_h

#include <TROOT.h>
#include <TChain.h>
#include <TFile.h>

class makePt_histos {
public :

   TTree          *fChain;   //!pointer to the analyzed TTree or TChain
   Int_t           fCurrent; //!current Tree number in a TChain

   // Declaration of leave types
   Float_t         LbF2mass;
   Float_t         LbCt;
   Float_t         LbCtErr;
   Float_t         LbdCt;
   Float_t         LcF2mass;
   Float_t         LbF2pt;

   // List of branches
   TBranch        *b_LbF2mass;   //!
   TBranch        *b_LbCt;   //!
   TBranch        *b_LbCtErr;   //!
   TBranch        *b_LbdCt;   //!
   TBranch        *b_LcF2mass;   //!
   TBranch        *b_LbF2pt;   //!

   makePt_histos(TTree *tree=0);
   ~makePt_histos();

   Int_t  Cut(Int_t entry);
   Int_t  GetEntry(Int_t entry);
   Int_t  LoadTree(Int_t entry);

   void Init(TTree *tree);
   void Loop();
   Bool_t Notify();
   void Show(Int_t entry = -1);
};

#endif

#ifdef makePt_histos_cxx

makePt_histos::makePt_histos(TTree *tree) {
// if parameter tree is not specified (or zero), connect the file // used to generate this class and read the Tree.

   if (tree == 0) {

      TFile *f =
(TFile*)gROOT->GetListOfFiles()->FindObject("data_pthistos_with_cuts.root");

      if (!f) {
    f = new TFile("data_pthistos_with_cuts.root","UPDATE");

      }
      tree = (TTree*)gDirectory->Get("tree");

   }
   Init(tree);
}

makePt_histos::~makePt_histos()
{

   if (!fChain) return;
   delete fChain->GetCurrentFile();
}

Int_t makePt_histos::GetEntry(Int_t entry) {
// Read contents of entry.

   if (!fChain) return 0;
   return fChain->GetEntry(entry);
}
Int_t makePt_histos::LoadTree(Int_t entry) {
// Set the environment to read one entry

   if (!fChain) return -5;
   Int_t centry = fChain->LoadTree(entry);    if (centry < 0) return centry;
   if (fChain->IsA() != TChain::Class()) return centry;    TChain *chain = (TChain*)fChain;
   if (chain->GetTreeNumber() != fCurrent) {

      fCurrent = chain->GetTreeNumber();
      Notify();

   }
   return centry;
}

void makePt_histos::Init(TTree *tree)
{

   // The Init() function is called when the selector needs to initialize
   // a new tree or chain. Typically here the branch addresses of the tree
   // will be set. It is normaly not necessary to make changes to the
   // generated code, but the routine can be extended by the user if needed.
   // Init() will be called many times when running with PROOF.

   // Set branch addresses
   if (tree == 0) return;
   fChain = tree;
   fCurrent = -1;
   fChain->SetMakeClass(1);

   fChain->SetBranchAddress("LbF2mass",&LbF2mass);
   fChain->SetBranchAddress("LbCt",&LbCt);
   fChain->SetBranchAddress("LbCtErr",&LbCtErr);
   fChain->SetBranchAddress("LbdCt",&LbdCt);
   fChain->SetBranchAddress("LcF2mass",&LcF2mass);
   fChain->SetBranchAddress("LbF2pt",&LbF2pt);
   Notify();
}

Bool_t makePt_histos::Notify()
{

   // The Notify() function is called when a new file is opened. This
   // can be either for a new TTree in a TChain or when when a new TTree
   // is started when using PROOF. Typically here the branch pointers
   // will be retrieved. It is normaly not necessary to make changes
   // to the generated code, but the routine can be extended by the
   // user if needed.

   // Get branch pointers

   b_LbF2mass = fChain->GetBranch("LbF2mass");
   b_LbCt = fChain->GetBranch("LbCt");
   b_LbCtErr = fChain->GetBranch("LbCtErr");
   b_LbdCt = fChain->GetBranch("LbdCt");
   b_LcF2mass = fChain->GetBranch("LcF2mass");
   b_LbF2pt = fChain->GetBranch("LbF2pt");

   return kTRUE;
}

void makePt_histos::Show(Int_t entry)
{
// Print contents of entry.
// If entry is not specified, print current entry

   if (!fChain) return;
   fChain->Show(entry);
}
Int_t makePt_histos::Cut(Int_t entry)
{

// This function may be called from Loop.
// returns  1 if entry is accepted.
// returns -1 otherwise.

   return 1;
}
#endif // #ifdef makePt_histos_cxx
Received on Wed Jun 21 2006 - 03:43:30 MEST

This archive was generated by hypermail 2.2.0 : Mon Jan 01 2007 - 16:31:59 MET