Logo ROOT   6.10/09
Reference Guide
ProofSimpleFile.C
Go to the documentation of this file.
1 /// \file
2 /// \ingroup tutorial_ProofSimpleFile
3 ///
4 /// Selector to fill a set of histograms and merging via file
5 ///
6 /// \macro_code
7 ///
8 /// \author Gerardo Ganis (gerardo.ganis@cern.ch)
9 
10 #define ProofSimpleFile_cxx
11 
12 #include "ProofSimpleFile.h"
13 #include <TCanvas.h>
14 #include <TFrame.h>
15 #include <TPaveText.h>
16 #include <TFormula.h>
17 #include <TF1.h>
18 #include <TH1F.h>
19 #include <TMath.h>
20 #include <TRandom3.h>
21 #include <TString.h>
22 #include <TStyle.h>
23 #include <TSystem.h>
24 #include <TParameter.h>
25 #include <TFile.h>
26 #include <TProofOutputFile.h>
27 
28 //_____________________________________________________________________________
29 ProofSimpleFile::ProofSimpleFile()
30 {
31  // Constructor
32 
33  fNhist = 16;
34  fHistTop = 0;
35  fHistDir = 0;
36  fRandom = 0;
37  fFile = 0;
38  fProofFile = 0;
39  fFileDir = 0;
40 }
41 
42 //_____________________________________________________________________________
43 ProofSimpleFile::~ProofSimpleFile()
44 {
45  // Destructor
46 
47  if (fRandom) delete fRandom;
48 }
49 
50 //_____________________________________________________________________________
51 Int_t ProofSimpleFile::CreateHistoArrays()
52 {
53  // Create the histogram arrays
54 
55  if (fNhist <= 0) {
56  Error("CreateHistoArrays", "fNhist must be positive!");
57  return -1;
58  }
59  // Histos array
60  fHistTop = new TH1F*[fNhist];
61  fHistDir = new TH1F*[fNhist];
62  // Done
63  return 0;
64 }
65 
66 //_____________________________________________________________________________
67 void ProofSimpleFile::Begin(TTree * /*tree*/)
68 {
69  // The Begin() function is called at the start of the query.
70  // When running with PROOF Begin() is only called on the client.
71  // The tree argument is deprecated (on PROOF 0 is passed).
72 
73  TString option = GetOption();
74 
75  // Number of histograms (needed in terminate)
76  Ssiz_t iopt = kNPOS;
77  if (fInput->FindObject("ProofSimpleFile_NHist")) {
79  dynamic_cast<TParameter<Long_t>*>(fInput->FindObject("ProofSimpleFile_NHist"));
80  fNhist = (p) ? (Int_t) p->GetVal() : fNhist;
81  } else if ((iopt = option.Index("nhist=")) != kNPOS) {
82  TString s;
83  Ssiz_t from = iopt + strlen("nhist=");
84  if (option.Tokenize(s, from, ";") && s.IsDigit()) fNhist = s.Atoi();
85  }
86 }
87 
88 //_____________________________________________________________________________
89 void ProofSimpleFile::SlaveBegin(TTree * /*tree*/)
90 {
91  // The SlaveBegin() function is called after the Begin() function.
92  // When running with PROOF SlaveBegin() is called on each slave server.
93  // The tree argument is deprecated (on PROOF 0 is passed).
94 
95  TString option = GetOption();
96 
97  // Number of histograms (needed in terminate)
98  Ssiz_t iopt = kNPOS;
99  if (fInput->FindObject("ProofSimpleFile_NHist")) {
100  TParameter<Long_t> *p =
101  dynamic_cast<TParameter<Long_t>*>(fInput->FindObject("ProofSimpleFile_NHist"));
102  fNhist = (p) ? (Int_t) p->GetVal() : fNhist;
103  } else if ((iopt = option.Index("nhist=")) != kNPOS) {
104  TString s;
105  Ssiz_t from = iopt + strlen("nhist=");
106  if (option.Tokenize(s, from, ";") && s.IsDigit()) fNhist = s.Atoi();
107  }
108 
109  // The file for merging
110  fProofFile = new TProofOutputFile("SimpleFile.root", "M");
111  TNamed *out = (TNamed *) fInput->FindObject("PROOF_OUTPUTFILE");
112  if (out) fProofFile->SetOutputFileName(out->GetTitle());
113  TDirectory *savedir = gDirectory;
114  fFile = fProofFile->OpenFile("RECREATE");
115  if (fFile && fFile->IsZombie()) SafeDelete(fFile);
116  savedir->cd();
117 
118  // Cannot continue
119  if (!fFile) {
120  TString amsg = TString::Format("ProofSimpleFile::SlaveBegin: could not create '%s':"
121  " instance is invalid!", fProofFile->GetName());
122  Abort(amsg, kAbortProcess);
123  return;
124  }
125 
126  // Histos arrays
127  if (CreateHistoArrays() != 0) {
128  Abort("ProofSimpleFile::SlaveBegin: could not create histograms", kAbortProcess);
129  return;
130  }
131 
132  // Create directory
133  if (!(fFileDir = fFile->mkdir("blue"))) {
134  Abort("ProofSimpleFile::SlaveBegin: could not create directory 'blue' in file!",
135  kAbortProcess);
136  return;
137  }
138 
139  // Create the histograms
140  for (Int_t i=0; i < fNhist; i++) {
141  fHistTop[i] = new TH1F(Form("ht%d",i), Form("ht%d",i), 100, -3., 3.);
142  fHistTop[i]->SetFillColor(kRed);
143  fHistTop[i]->SetDirectory(fFile);
144  fHistDir[i] = new TH1F(Form("hd%d",i), Form("hd%d",i), 100, -3., 3.);
145  fHistDir[i]->SetFillColor(kBlue);
146  fHistDir[i]->SetDirectory(fFileDir);
147  }
148 
149  // Set random seed
150  fRandom = new TRandom3(0);
151 }
152 
153 //_____________________________________________________________________________
154 Bool_t ProofSimpleFile::Process(Long64_t)
155 {
156  // The Process() function is called for each entry in the tree (or possibly
157  // keyed object in the case of PROOF) to be processed. The entry argument
158  // specifies which entry in the currently loaded tree is to be processed.
159  // It can be passed to either ProofSimpleFile::GetEntry() or TBranch::GetEntry()
160  // to read either all or the required parts of the data. When processing
161  // keyed objects with PROOF, the object is already loaded and is available
162  // via the fObject pointer.
163  //
164  // This function should contain the "body" of the analysis. It can contain
165  // simple or elaborate selection criteria, run algorithms on the data
166  // of the event and typically fill histograms.
167  //
168  // The processing can be stopped by calling Abort().
169  //
170  // Use fStatus to set the return value of TTree::Process().
171  //
172  // The return value is currently not used.
173 
174  for (Int_t i=0; i < fNhist; i++) {
175  if (fRandom && fHistTop[i] && fHistDir[i]) {
176  fHistTop[i]->Fill(fRandom->Gaus(0.,1.));
177  fHistDir[i]->Fill(fRandom->Gaus(0.,1.));
178  }
179  }
180 
181  return kTRUE;
182 }
183 
184 //_____________________________________________________________________________
185 void ProofSimpleFile::SlaveTerminate()
186 {
187  // The SlaveTerminate() function is called after all entries or objects
188  // have been processed. When running with PROOF SlaveTerminate() is called
189  // on each slave server.
190 
191  // Write histos to file
192  if (fFile) {
193  Bool_t cleanup = kTRUE;
194  TDirectory *savedir = gDirectory;
195  fFile->cd();
196  for (Int_t i=0; i < fNhist; i++) {
197  if (fHistTop[i] && fHistTop[i]->GetEntries() > 0) {
198  fHistTop[i]->Write();
199  fHistTop[i]->SetDirectory(0);
200  cleanup = kFALSE;
201  }
202  }
203  // Change to subdirectory
204  fFileDir->cd();
205  for (Int_t i=0; i < fNhist; i++) {
206  if (fHistDir[i] && fHistDir[i]->GetEntries() > 0) {
207  fHistDir[i]->Write();
208  fHistDir[i]->SetDirectory(0);
209  cleanup = kFALSE;
210  }
211  }
212  gDirectory = savedir;
213  fFile->Close();
214  // Cleanup or register
215  if (cleanup) {
216  Info("SlaveTerminate", "nothing to save: just cleanup everything ...");
217  TUrl uf(*(fFile->GetEndpointUrl()));
218  SafeDelete(fFile);
219  gSystem->Unlink(uf.GetFile());
220  SafeDelete(fProofFile);
221  } else {
222  Info("SlaveTerminate", "objects saved into '%s%s': sending related TProofOutputFile ...",
223  fProofFile->GetFileName(), fProofFile->GetOptionsAnchor());
224  fProofFile->Print();
225  fOutput->Add(fProofFile);
226  }
227  }
228 
229 }
230 
231 //_____________________________________________________________________________
232 void ProofSimpleFile::Terminate()
233 {
234  // The Terminate() function is the last function to be called during
235  // a query. It always runs on the client, it can be used to present
236  // the results graphically or save the results to file.
237 
238  // Get the histos from the file
239  if ((fProofFile =
240  dynamic_cast<TProofOutputFile*>(fOutput->FindObject("SimpleFile.root")))) {
241 
242  TString outputFile(fProofFile->GetOutputFileName());
243  TString outputName(fProofFile->GetName());
244  outputName += ".root";
245  Printf("outputFile: %s", outputFile.Data());
246 
247  // Read the ntuple from the file
248  if (!(fFile = TFile::Open(outputFile))) {
249  Error("Terminate", "could not open file: %s", outputFile.Data());
250  return;
251  }
252 
253  } else {
254  Error("Terminate", "TProofOutputFile not found");
255  return;
256  }
257 
258  // Histos arrays
259  if (CreateHistoArrays() != 0) {
260  Error("Terminate", "could not create histograms");
261  return;
262  }
263 
264  // Top histos
265  PlotHistos(0);
266  // Dir histos
267  PlotHistos(1);
268 }
269 
270 //_____________________________________________________________________________
271 void ProofSimpleFile::PlotHistos(Int_t opt)
272 {
273  // Plot the histograms ina dedicated canvas
274 
275  // Create a canvas, with fNhist pads
276  if (opt == 0) {
277  TCanvas *c1 = new TCanvas("c1","ProofSimpleFile top dir canvas",200,10,700,700);
278  Int_t nside = (Int_t)TMath::Sqrt((Float_t)fNhist);
279  nside = (nside*nside < fNhist) ? nside+1 : nside;
280  c1->Divide(nside,nside,0,0);
281 
282  for (Int_t i=0; i < fNhist; i++) {
283  fHistTop[i] = (TH1F *) fFile->Get(TString::Format("ht%d",i));
284  c1->cd(i+1);
285  if (fHistTop[i])
286  fHistTop[i]->Draw();
287  }
288 
289  // Final update
290  c1->cd();
291  c1->Update();
292  } else if (opt == 1) {
293  TCanvas *c2 = new TCanvas("c2","ProofSimpleFile 'blue' sub-dir canvas",400,60,700,700);
294  Int_t nside = (Int_t)TMath::Sqrt((Float_t)fNhist);
295  nside = (nside*nside < fNhist) ? nside+1 : nside;
296  c2->Divide(nside,nside,0,0);
297 
298  if ((fFileDir = (TDirectory *) fFile->Get("blue"))) {
299  for (Int_t i=0; i < fNhist; i++) {
300  fHistDir[i] = (TH1F *) fFileDir->Get(TString::Format("hd%d",i));
301  c2->cd(i+1);
302  if (fHistDir[i])
303  fHistDir[i]->Draw();
304  }
305  } else {
306  Error("PlotHistos", "directory 'blue' not found in output file");
307  }
308 
309  // Final update
310  c2->cd();
311  c2->Update();
312  } else {
313  Error("PlotHistos", "unknown option: %d", opt);
314  }
315 }
void Begin(Int_t type)
Random number generator class based on M.
Definition: TRandom3.h:27
long long Long64_t
Definition: RtypesCore.h:69
virtual void Draw(Option_t *option="")=0
Default Draw method for all objects.
float Float_t
Definition: RtypesCore.h:53
return c1
Definition: legend1.C:41
Definition: Rtypes.h:56
const Ssiz_t kNPOS
Definition: RtypesCore.h:115
This class represents a WWW compatible URL.
Definition: TUrl.h:35
THist< 1, float, THistStatContent, THistStatUncertainty > TH1F
Definition: THist.hxx:311
TVirtualPad * cd(Int_t subpadnumber=0)
Set current canvas & pad.
Definition: TCanvas.cxx:679
Ssiz_t Index(const char *pat, Ssiz_t i=0, ECaseCompare cmp=kExact) const
Definition: TString.h:587
Basic string class.
Definition: TString.h:129
tomato 1-D histogram with a float per channel (see TH1 documentation)}
Definition: TH1.h:551
int Int_t
Definition: RtypesCore.h:41
bool Bool_t
Definition: RtypesCore.h:59
static TFile * Open(const char *name, Option_t *option="", const char *ftitle="", Int_t compress=1, Int_t netopt=0)
Create / open a file.
Definition: TFile.cxx:3909
#define SafeDelete(p)
Definition: RConfig.h:499
virtual int Unlink(const char *name)
Unlink, i.e. remove, a file.
Definition: TSystem.cxx:1353
static TString Format(const char *fmt,...)
Static method which formats a string using a printf style format descriptor and return a TString...
Definition: TString.cxx:2345
The TNamed class is the base class for all named ROOT classes.
Definition: TNamed.h:29
void Info(const char *location, const char *msgfmt,...)
virtual void Close(Option_t *option="")
Delete all objects from memory and directory structure itself.
Definition: TDirectory.cxx:519
void Error(const char *location, const char *msgfmt,...)
Named parameter, streamable and storable.
Definition: TParameter.h:37
virtual TObject * FindObject(const char *name) const
Must be redefined in derived classes.
Definition: TObject.cxx:328
R__EXTERN TSystem * gSystem
Definition: TSystem.h:539
char * Form(const char *fmt,...)
Class to steer the merging of files produced on the workers.
#define Printf
Definition: TGeoToOCC.h:18
const Bool_t kFALSE
Definition: RtypesCore.h:92
int Ssiz_t
Definition: RtypesCore.h:63
The Canvas class.
Definition: TCanvas.h:31
TObjArray * Tokenize(const TString &delim) const
This function is used to isolate sequential tokens in a TString.
Definition: TString.cxx:2251
return c2
Definition: legend2.C:14
Describe directory structure in memory.
Definition: TDirectory.h:34
virtual Bool_t cd(const char *path=0)
Change current directory to "this" directory.
Definition: TDirectory.cxx:435
virtual void Divide(Int_t nx=1, Int_t ny=1, Float_t xmargin=0.01, Float_t ymargin=0.01, Int_t color=0)
Automatic pad generation by division.
Definition: TPad.cxx:1135
Selector to fill a set of histograms and merging via file.
Int_t Atoi() const
Return integer value of string.
Definition: TString.cxx:1975
Bool_t IsDigit() const
Returns true if all characters in string are digits (0-9) or white spaces, i.e.
Definition: TString.cxx:1817
A TTree object has a header with a name and a title.
Definition: TTree.h:78
const AParamType & GetVal() const
Definition: TParameter.h:65
#define gDirectory
Definition: TDirectory.h:211
Definition: Rtypes.h:56
Double_t Sqrt(Double_t x)
Definition: TMath.h:591
virtual void Update()
Update canvas pad buffers.
Definition: TCanvas.cxx:2208
const Bool_t kTRUE
Definition: RtypesCore.h:91
virtual const char * GetTitle() const
Returns title of object.
Definition: TNamed.h:48