]> git.uio.no Git - u/mrichter/AliRoot.git/blame - PHOS/AliPHOSTrackSegmentMakerv2.cxx
Updated QA classes (Yves)
[u/mrichter/AliRoot.git] / PHOS / AliPHOSTrackSegmentMakerv2.cxx
CommitLineData
861b23c3 1/**************************************************************************
2 * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
3 * *
4 * Author: The ALICE Off-line Project. *
5 * Contributors are mentioned in the code where appropriate. *
6 * *
7 * Permission to use, copy, modify and distribute this software and its *
8 * documentation strictly for non-commercial purposes is hereby granted *
9 * without fee, provided that the above copyright notice appears in all *
10 * copies and that both the copyright notice and this permission notice *
11 * appear in the supporting documentation. The authors make no claims *
12 * about the suitability of this software for any purpose. It is *
13 * provided "as is" without express or implied warranty. *
14 **************************************************************************/
15/* $Id$ */
16
17/* History of cvs commits:
18 *
19 * $Log$
a5fa6165 20 * Revision 1.5 2007/07/11 13:43:30 hristov
21 * New class AliESDEvent, backward compatibility with the old AliESD (Christian)
22 *
af885e0f 23 * Revision 1.4 2007/05/04 14:49:29 policheh
24 * AliPHOSRecPoint inheritance from AliCluster
25 *
9ee9f78d 26 * Revision 1.3 2007/04/25 19:39:42 kharlov
27 * Track extracpolation improved
28 *
c978a69b 29 * Revision 1.2 2007/04/01 19:16:52 kharlov
30 * D.P.: Produce EMCTrackSegments using TPC/ITS tracks (no CPV)
31 *
861b23c3 32 *
33 */
34
35//_________________________________________________________________________
36// Implementation version 2 of algorithm class to construct PHOS track segments
37// Track segment for PHOS is list of
38// EMC RecPoint + (possibly) projection of TPC track
39// To find TrackSegments we do the following:
40// for each EMC RecPoints we look at
41// TPC projections radius fRtpc.
42// If there is such a track
43// we make "Link" it is just indexes of EMC and TPC track and distance
44// between them in the PHOS plane.
45// Then we sort "Links" and starting from the
46// least "Link" pointing to the unassined EMC and TPC assing them to
47// new TrackSegment.
48// If there is no TPC track we make TrackSegment
49// consisting from EMC alone. There is no TrackSegments without EMC RecPoint.
50//// In principle this class should be called from AliPHOSReconstructor, but
51// one can use it as well in standalone mode.
52// Use case:
53// root [0] AliPHOSTrackSegmentMakerv2 * t = new AliPHOSTrackSegmentMaker("galice.root", "tracksegmentsname", "recpointsname")
54// Warning in <TDatabasePDG::TDatabasePDG>: object already instantiated
55// // reads gAlice from header file "galice.root", uses recpoints stored in the branch names "recpointsname" (default = "Default")
56// // and saves recpoints in branch named "tracksegmentsname" (default = "recpointsname")
57// root [1] t->ExecuteTask()
58// root [3] t->SetTrackSegmentsBranch("max distance 5 cm")
59// root [4] t->ExecuteTask("deb all time")
60//
61//*-- Author: Dmitri Peressounko (RRC Ki & SUBATECH) & Yves Schutz (SUBATECH)
62//
63
64// --- ROOT system ---
4b598bb1 65#include "TFile.h"
861b23c3 66#include "TTree.h"
67#include "TBenchmark.h"
68
69// --- Standard library ---
70#include "Riostream.h"
71// --- AliRoot header files ---
72#include "AliPHOSGeometry.h"
73#include "AliPHOSTrackSegmentMakerv2.h"
74#include "AliPHOSTrackSegment.h"
75#include "AliPHOSLink.h"
76#include "AliPHOSGetter.h"
a5fa6165 77
af885e0f 78#include "AliESDEvent.h"
861b23c3 79#include "AliESDtrack.h"
80
81ClassImp( AliPHOSTrackSegmentMakerv2)
82
83
84//____________________________________________________________________________
85AliPHOSTrackSegmentMakerv2::AliPHOSTrackSegmentMakerv2() :
86 AliPHOSTrackSegmentMaker(),
87 fDefaultInit(kTRUE),
88 fWrite(kFALSE),
89 fNTrackSegments(0),
90 fRtpc(0.f),
c978a69b 91 fVtx(0.,0.,0.),
861b23c3 92 fLinkUpArray(0),
c978a69b 93 fTPCtracks(),
861b23c3 94 fEmcFirst(0),
95 fEmcLast(0),
96 fModule(0),
97 fTrackSegmentsInRun(0)
861b23c3 98{
99 // default ctor (to be used mainly by Streamer)
100 InitParameters() ;
861b23c3 101}
102
103//____________________________________________________________________________
104AliPHOSTrackSegmentMakerv2::AliPHOSTrackSegmentMakerv2(const TString & alirunFileName, const TString & eventFolderName) :
105 AliPHOSTrackSegmentMaker(alirunFileName, eventFolderName),
106 fDefaultInit(kFALSE),
107 fWrite(kFALSE),
108 fNTrackSegments(0),
109 fRtpc(0.f),
c978a69b 110 fVtx(0.,0.,0.),
861b23c3 111 fLinkUpArray(0),
c978a69b 112 fTPCtracks(),
861b23c3 113 fEmcFirst(0),
114 fEmcLast(0),
115 fModule(0),
116 fTrackSegmentsInRun(0)
117{
118 // ctor
119 InitParameters() ;
120 Init() ;
121 fESD = 0;
122}
123
124//____________________________________________________________________________
125AliPHOSTrackSegmentMakerv2::AliPHOSTrackSegmentMakerv2(const AliPHOSTrackSegmentMakerv2 & tsm) :
126 AliPHOSTrackSegmentMaker(tsm),
127 fDefaultInit(kFALSE),
128 fWrite(kFALSE),
129 fNTrackSegments(0),
130 fRtpc(0.f),
c978a69b 131 fVtx(0.,0.,0.),
861b23c3 132 fLinkUpArray(0),
c978a69b 133 fTPCtracks(),
861b23c3 134 fEmcFirst(0),
135 fEmcLast(0),
136 fModule(0),
137 fTrackSegmentsInRun(0)
138{
139 // cpy ctor: no implementation yet
140 // requested by the Coding Convention
141 Fatal("cpy ctor", "not implemented") ;
142}
143
144
145//____________________________________________________________________________
146 AliPHOSTrackSegmentMakerv2::~AliPHOSTrackSegmentMakerv2()
147{
148 // dtor
149 // fDefaultInit = kTRUE if TrackSegmentMaker created by default ctor (to get just the parameters)
150 if (!fDefaultInit)
151 delete fLinkUpArray ;
861b23c3 152}
153
154//____________________________________________________________________________
155const TString AliPHOSTrackSegmentMakerv2::BranchName() const
156{
157
158 return GetName() ;
159}
160
161//____________________________________________________________________________
162void AliPHOSTrackSegmentMakerv2::FillOneModule()
163{
164 // Finds first and last indexes between which
165 // clusters from one PHOS module are
166
167 AliPHOSGetter * gime = AliPHOSGetter::Instance() ;
168 const AliPHOSGeometry * geom = gime->PHOSGeometry() ;
169
170 TObjArray * emcRecPoints = gime->EmcRecPoints() ;
171
172 //First EMC clusters
173 Int_t totalEmc = emcRecPoints->GetEntriesFast() ;
174 for(fEmcFirst = fEmcLast; (fEmcLast < totalEmc) &&
175 ((dynamic_cast<AliPHOSRecPoint *>(emcRecPoints->At(fEmcLast)))->GetPHOSMod() == fModule );
176 fEmcLast ++) ;
177
178 //Now TPC tracks
4b598bb1 179 if(fESD){
180 //Do it ones, only first time
181 if(fModule==1){
182 Int_t nTracks = fESD->GetNumberOfTracks();
c978a69b 183
184 Int_t nPHOSmod = geom->GetNModules() ;
185 if(fTPCtracks[0].size()<(UInt_t)nTracks){
186 for(Int_t i=0; i<nPHOSmod; i++)
187 fTPCtracks[i].resize(nTracks) ;
188 }
189 for(Int_t i=0; i<5; i++)fNtpcTracks[i]=0 ;
4b598bb1 190 TVector3 inPHOS ;
191
192 //In this particular case we use fixed vertex position at zero
193 Double_t vtx[3]={0.,0.,0.} ;
194 AliESDtrack *track;
195 Double_t xyz[3] ;
4b598bb1 196 Double_t rEMC = geom->GetIPtoCrystalSurface() ; //Use here ideal geometry
197 for (Int_t iTrack=0; iTrack<nTracks; iTrack++) {
198 track = fESD->GetTrack(iTrack);
c978a69b 199 for(Int_t iTestMod=1; iTestMod<=nPHOSmod; iTestMod++){
200 Double_t modAngle=270.+geom->GetPHOSAngle(iTestMod) ;
201 modAngle*=TMath::Pi()/180. ;
202 track->Rotate(modAngle);
203 if (!track->GetXYZAt(rEMC, fESD->GetMagneticField(), xyz))
204 continue; //track coord on the cylinder of PHOS radius
205 if ((TMath::Abs(xyz[0])+TMath::Abs(xyz[1])+TMath::Abs(xyz[2]))<=0)
206 continue;
207 //Check if this track hits PHOS
208 inPHOS.SetXYZ(xyz[0],xyz[1],xyz[2]);
209 Int_t modNum ;
210 Double_t x,z ;
211 geom->ImpactOnEmc(vtx, inPHOS.Theta(), inPHOS.Phi(), modNum, z, x) ;
212 if(modNum==iTestMod){
213 //Mark this track as one belonging to module
214 TrackInPHOS_t &t = fTPCtracks[modNum-1][fNtpcTracks[modNum-1]++] ;
215 t.track = track ;
216 t.x = x ;
217 t.z = z ;
218 break ;
219 }
4b598bb1 220 }
221 }
861b23c3 222 }
223 }
4b598bb1 224
861b23c3 225}
226
227//____________________________________________________________________________
228void AliPHOSTrackSegmentMakerv2::GetDistanceInPHOSPlane(AliPHOSEmcRecPoint * emcClu,
229 AliESDtrack *track,
230 Float_t &dx, Float_t &dz) const
231{
232 // Calculates the distance between the EMC RecPoint and the CPV RecPoint
233 // Clusters are sorted in "rows" and "columns" of width 1 cm
234
235 const AliPHOSGeometry * geom = AliPHOSGeometry::GetInstance() ;
c978a69b 236 TVector3 emcGlobal; // Global position of the EMC recpoint
9ee9f78d 237 geom->GetGlobalPHOS((AliPHOSRecPoint*)emcClu,emcGlobal);
4b598bb1 238
c978a69b 239 //Calculate actual distance to the PHOS surface
240 Double_t modAngle=270.+geom->GetPHOSAngle(emcClu->GetPHOSMod()) ;
241 modAngle*=TMath::Pi()/180. ;
242 Double_t rEMC = emcGlobal.X()*TMath::Cos(modAngle)+emcGlobal.Y()*TMath::Sin(modAngle) ;
243 track->Rotate(modAngle);
861b23c3 244 Double_t xyz[3] ;
c978a69b 245 if(!track->GetXYZAt(rEMC, fESD->GetMagneticField(), xyz)){
246 dx=999. ;
247 dz=999. ;
248 return ; //track coord on the cylinder of PHOS radius
861b23c3 249 }
c978a69b 250 if((TMath::Abs(xyz[0])+TMath::Abs(xyz[1])+TMath::Abs(xyz[2]))<=0){
861b23c3 251 dx=999. ;
252 dz=999. ;
c978a69b 253 return ;
254 }
255
256 dx=(emcGlobal.X()-xyz[0])*TMath::Sin(modAngle)-(emcGlobal.Y()-xyz[1])*TMath::Cos(modAngle) ;
257 dx=TMath::Sign(dx,(Float_t)(emcGlobal.X()-xyz[0])) ; //set direction
258 dz=emcGlobal.Z()-xyz[2] ;
861b23c3 259
260 return ;
261}
262//____________________________________________________________________________
263void AliPHOSTrackSegmentMakerv2::Init()
264{
265 // Make all memory allocations that are not possible in default constructor
266
267 AliPHOSGetter* gime = AliPHOSGetter::Instance();
268 if(!gime)
269 gime = AliPHOSGetter::Instance(GetTitle(), fEventFolderName.Data());
270
271 fLinkUpArray = new TClonesArray("AliPHOSLink", 1000);
272 if ( !gime->TrackSegmentMaker() ) {
273 gime->PostTrackSegmentMaker(this);
274 }
861b23c3 275}
276
277//____________________________________________________________________________
278void AliPHOSTrackSegmentMakerv2::InitParameters()
279{
280 //Initializes parameters
281 fRtpc = 4. ;
282 fEmcFirst = 0 ;
283 fEmcLast = 0 ;
284 fLinkUpArray = 0 ;
285 fWrite = kTRUE ;
286 fTrackSegmentsInRun = 0 ;
287 SetEventRange(0,-1) ;
288}
289
290
291//____________________________________________________________________________
c978a69b 292void AliPHOSTrackSegmentMakerv2::MakeLinks()
861b23c3 293{
294 // Finds distances (links) between all EMC and CPV clusters,
295 // which are not further apart from each other than fRcpv
296 // and sort them in accordance with this distance
297
298 AliPHOSGetter * gime = AliPHOSGetter::Instance() ;
299 TObjArray * emcRecPoints = gime->EmcRecPoints() ;
300
301 fLinkUpArray->Clear() ;
302
303 AliPHOSEmcRecPoint * emcclu ;
304
305 Int_t iLinkUp = 0 ;
306
307 Int_t iEmcRP;
308 for(iEmcRP = fEmcFirst; iEmcRP < fEmcLast; iEmcRP++ ) {
309 emcclu = dynamic_cast<AliPHOSEmcRecPoint *>(emcRecPoints->At(iEmcRP)) ;
c978a69b 310 TVector3 vecEmc ;
311 emcclu->GetLocalPosition(vecEmc) ;
861b23c3 312 Int_t mod=emcclu->GetPHOSMod() ;
c978a69b 313 for(Int_t itr=0; itr<fNtpcTracks[mod-1] ; itr++){
314 TrackInPHOS_t &t = fTPCtracks[mod-1][itr] ;
315 //calculate raw distance
316 Double_t rawdx = t.x - vecEmc.X() ;
317 Double_t rawdz = t.z - vecEmc.Z() ;
318 if(TMath::Sqrt(rawdx*rawdx+rawdz*rawdz)<fRtpc){
319 Float_t dx,dz ;
320 //calculate presize difference accounting misalignment
321 GetDistanceInPHOSPlane(emcclu, t.track, dx,dz) ;
322 Int_t itrack = t.track->GetID() ;
861b23c3 323 new ((*fLinkUpArray)[iLinkUp++]) AliPHOSLink(dx, dz, iEmcRP, itrack, -1) ;
324 }
325 }
326 }
861b23c3 327 fLinkUpArray->Sort() ; //first links with smallest distances
328}
329
330//____________________________________________________________________________
331void AliPHOSTrackSegmentMakerv2::MakePairs()
332{
333 // Using the previously made list of "links", we found the smallest link - i.e.
334 // link with the least distance between EMC and CPV and pointing to still
335 // unassigned RecParticles. We assign these RecPoints to TrackSegment and
336 // remove them from the list of "unassigned".
337
338 AliPHOSGetter * gime = AliPHOSGetter::Instance() ;
339
340 TObjArray * emcRecPoints = gime->EmcRecPoints() ;
341 TClonesArray * trackSegments = gime->TrackSegments();
342
343 //Make arrays to mark clusters already chosen
344 Int_t * emcExist = 0;
345 if(fEmcLast > fEmcFirst)
346 emcExist = new Int_t[fEmcLast-fEmcFirst] ;
347
348 Int_t index;
349 for(index = 0; index <fEmcLast-fEmcFirst; index ++)
350 emcExist[index] = 1 ;
351
352
c978a69b 353 Bool_t * tpcExist = 0;
354 Int_t nTracks = fESD->GetNumberOfTracks();
861b23c3 355 if(nTracks>0)
c978a69b 356 tpcExist = new Bool_t[nTracks] ;
861b23c3 357
358 for(index = 0; index <nTracks; index ++)
359 tpcExist[index] = 1 ;
360
361
362 // Finds the smallest links and makes pairs of CPV and EMC clusters with smallest distance
363 TIter nextUp(fLinkUpArray) ;
364
365 AliPHOSLink * linkUp ;
366
367 AliPHOSCpvRecPoint * nullpointer = 0 ;
368
369 while ( (linkUp = static_cast<AliPHOSLink *>(nextUp()) ) ){
370
371 if(emcExist[linkUp->GetEmc()-fEmcFirst] != -1){
372
373 if(tpcExist[linkUp->GetCpv()]){ //Track still exist
374 Float_t dx,dz ;
375 linkUp->GetXZ(dx,dz) ;
376 new ((* trackSegments)[fNTrackSegments])
377 AliPHOSTrackSegment(dynamic_cast<AliPHOSEmcRecPoint *>(emcRecPoints->At(linkUp->GetEmc())) ,
378 nullpointer,
379 linkUp->GetTrack(),dx,dz) ;
861b23c3 380 (dynamic_cast<AliPHOSTrackSegment *>(trackSegments->At(fNTrackSegments)))->SetIndexInList(fNTrackSegments);
381 fNTrackSegments++ ;
382 emcExist[linkUp->GetEmc()-fEmcFirst] = -1 ; //Mark emc that Cpv was found
383 //mark track as already used
384 tpcExist[linkUp->GetCpv()] = kFALSE ;
385 } //if CpvUp still exist
386 }
387 }
388
389 //look through emc recPoints left without CPV
390 if(emcExist){ //if there is emc rec point
391 Int_t iEmcRP ;
392 for(iEmcRP = 0; iEmcRP < fEmcLast-fEmcFirst ; iEmcRP++ ){
393 if(emcExist[iEmcRP] > 0 ){
394 new ((*trackSegments)[fNTrackSegments])
395 AliPHOSTrackSegment(dynamic_cast<AliPHOSEmcRecPoint *>(emcRecPoints->At(iEmcRP+fEmcFirst)),
396 nullpointer) ;
397 (dynamic_cast<AliPHOSTrackSegment *>(trackSegments->At(fNTrackSegments)))->SetIndexInList(fNTrackSegments);
398 fNTrackSegments++;
399 }
400 }
401 }
402 delete [] emcExist ;
403 delete [] tpcExist ;
404}
405
406//____________________________________________________________________________
407void AliPHOSTrackSegmentMakerv2::Exec(Option_t *option)
408{
409 // Steering method to perform track segment construction for events
410 // in the range from fFirstEvent to fLastEvent.
411 // This range is optionally set by SetEventRange().
412 // if fLastEvent=-1 (by default), then process events until the end.
413
414 if(strstr(option,"tim"))
415 gBenchmark->Start("PHOSTSMaker");
416
417 if(strstr(option,"print")) {
418 Print() ;
419 return ;
420 }
421
422 AliPHOSGetter * gime = AliPHOSGetter::Instance() ;
423
424 const AliPHOSGeometry * geom = gime->PHOSGeometry() ;
425
426 if (fLastEvent == -1)
427 fLastEvent = gime->MaxEvent() - 1 ;
428 else
429 fLastEvent = TMath::Min(fFirstEvent,gime->MaxEvent());
430 Int_t nEvents = fLastEvent - fFirstEvent + 1;
431
432 Int_t ievent ;
433 for (ievent = fFirstEvent; ievent <= fLastEvent; ievent++) {
434 gime->Event(ievent,"DR") ;
435 //Make some initializations
436 fNTrackSegments = 0 ;
437 fEmcFirst = 0 ;
438 fEmcLast = 0 ;
439
440 gime->TrackSegments()->Clear();
441
861b23c3 442 // if(!ReadRecPoints(ievent)) continue; //reads RecPoints for event ievent
443
444 for(fModule = 1; fModule <= geom->GetNModules() ; fModule++ ) {
445 FillOneModule() ;
446 MakeLinks() ;
447 MakePairs() ;
448 }
449
450 WriteTrackSegments() ;
451
452 if(strstr(option,"deb"))
453 PrintTrackSegments(option);
454
455 //increment the total number of track segments per run
456 fTrackSegmentsInRun += gime->TrackSegments()->GetEntriesFast() ;
457 }
458
459 if(strstr(option,"tim")){
460 gBenchmark->Stop("PHOSTSMaker");
461 Info("Exec", "took %f seconds for making TS %f seconds per event",
462 gBenchmark->GetCpuTime("PHOSTSMaker"),
463 gBenchmark->GetCpuTime("PHOSTSMaker")/nEvents) ;
464 }
465 if(fWrite) //do not unload in "on flight" mode
466 Unload();
467}
468//____________________________________________________________________________
861b23c3 469void AliPHOSTrackSegmentMakerv2::Unload()
470{
471 // Unloads the task from the folder
472 AliPHOSGetter * gime = AliPHOSGetter::Instance() ;
473 gime->PhosLoader()->UnloadRecPoints() ;
474 gime->PhosLoader()->UnloadTracks() ;
475}
476
477//____________________________________________________________________________
478void AliPHOSTrackSegmentMakerv2::Print(const Option_t *)const
479{
480 // Print TrackSegmentMaker parameters
481
482 TString message("") ;
483 if( strcmp(GetName(), "") != 0 ) {
484 message = "\n======== AliPHOSTrackSegmentMakerv2 ========\n" ;
485 message += "Making Track segments\n" ;
486 message += "with parameters:\n" ;
487 message += " Maximal EMC - TPC distance (cm) %f\n" ;
488 message += "============================================\n" ;
489 Info("Print", message.Data(),fRtpc) ;
490 }
491 else
492 Info("Print", "AliPHOSTrackSegmentMakerv2 not initialized ") ;
493}
494
495//____________________________________________________________________________
496void AliPHOSTrackSegmentMakerv2::WriteTrackSegments()
497{
498 // Writes found TrackSegments to TreeR. Creates branches
499 // "PHOSTS" and "AliPHOSTrackSegmentMaker" with the same title.
500 // In the former branch found TrackSegments are stored, while
501 // in the latter all parameters, with which TS were made.
502 // ROOT does not allow overwriting existing branches, therefore
503 // first we check, if branches with the same title already exist.
504 // If yes - exits without writing.
505
506 AliPHOSGetter *gime = AliPHOSGetter::Instance() ;
507
508 TClonesArray * trackSegments = gime->TrackSegments() ;
509 trackSegments->Expand(trackSegments->GetEntriesFast()) ;
510
511 if(fWrite){ //We write TreeT
512 TTree * treeT = gime->TreeT();
513
514 //First TS
515 Int_t bufferSize = 32000 ;
516 TBranch * tsBranch = treeT->Branch("PHOSTS",&trackSegments,bufferSize);
517 tsBranch->Fill() ;
518
519 gime->WriteTracks("OVERWRITE");
520 gime->WriteTrackSegmentMaker("OVERWRITE");
521 }
522}
523
524
525//____________________________________________________________________________
526void AliPHOSTrackSegmentMakerv2::PrintTrackSegments(Option_t * option)
527{
528 // option deb - prints # of found TrackSegments
529 // option deb all - prints as well indexed of found RecParticles assigned to the TS
530
531 TClonesArray * trackSegments = AliPHOSGetter::Instance()->TrackSegments() ;
532
533 Info("PrintTrackSegments", "Results from TrackSegmentMaker:") ;
534 printf("nevent: %d\n", gAlice->GetEvNumber()) ;
535 printf(" Found %d TrackSegments\n", trackSegments->GetEntriesFast() );
536
537 if(strstr(option,"all")) { // printing found TS
538 printf("TrackSegment # EMC RP# CPV RP#\n") ;
539 Int_t index;
540 for (index = 0 ; index <trackSegments->GetEntriesFast() ; index++) {
541 AliPHOSTrackSegment * ts = (AliPHOSTrackSegment * )trackSegments->At(index) ;
542 printf(" %d %d %d \n", ts->GetIndexInList(), ts->GetEmcIndex(), ts->GetTrackIndex() ) ;
543 }
544 }
545}