]> git.uio.no Git - u/mrichter/AliRoot.git/blobdiff - MUON/AliMUONRefitter.cxx
Adapting to CORRFW changes (Chiara)
[u/mrichter/AliRoot.git] / MUON / AliMUONRefitter.cxx
index 9e038b044116407c8a95597c30d9ec142c9509c4..035f1d15ce2b307653ca14ccd356148ccd8dce0d 100644 (file)
@@ -25,6 +25,7 @@
 #include "AliMUONPreClusterFinderV2.h"
 #include "AliMUONPreClusterFinderV3.h"
 #include "AliMUONSimpleClusterServer.h"
+#include "AliMUONReconstructor.h"
 #include "AliMUONTrackReconstructor.h"
 #include "AliMUONTrackReconstructorK.h"
 #include "AliMUONRecoParam.h"
 #include "AliMUONVTrackStore.h"
 #include "AliMUONTrack.h"
 #include "AliMUONTracker.h"
+#include "AliMUONTrackParam.h"
 #include "AliLog.h"
 
 //-----------------------------------------------------------------------------
 /// \class AliMUONRefitter
 ///
-/// create new MUON object from ESD objects given as input (through the ESDInterface):
+/// This class has been developped to simplify the re-reconstruction of the MUON tracks
+/// stored into ESD with different recoParams and/or after having re-calibrated the digits.
+/// It creates new MUON object from ESD objects given as input (through the ESDInterface) then:
 ///
 /// - re-clusterize the ESD clusters using the attached ESD pads
 ///   (several new clusters can be reconstructed per ESD cluster)
@@ -59,17 +63,18 @@ ClassImp(AliMUONRefitter)
 /// \endcond
 
 //_____________________________________________________________________________
-AliMUONRefitter::AliMUONRefitter()
+AliMUONRefitter::AliMUONRefitter(const AliMUONRecoParam* recoParam)
 : TObject(),
+  fkRecoParam(recoParam),
+  fkESDInterface(0x0),
   fGeometryTransformer(0x0),
   fClusterServer(0x0),
-  fTracker(0x0),
-  fESDInterface(0x0)
+  fTracker(0x0)
 {
   /// Default constructor
   CreateGeometryTransformer();
   CreateClusterServer(*fGeometryTransformer);
-  if (fClusterServer) fTracker = AliMUONTracker::CreateTrackReconstructor(AliMUONReconstructor::GetRecoParam()->GetTrackingMode(),fClusterServer);
+  if (fClusterServer) fTracker = AliMUONTracker::CreateTrackReconstructor(recoParam,fClusterServer);
   if (!fClusterServer || !fTracker) {
     AliFatal("refitter initialization failed");
     exit(-1);
@@ -91,7 +96,7 @@ AliMUONVTrackStore* AliMUONRefitter::ReconstructFromDigits()
   /// re-reconstruct all tracks and attached clusters from the digits
   /// it is the responsability of the user to delete the returned store
   
-  if (!fESDInterface) {
+  if (!fkESDInterface) {
     AliError("the refitter must be connected to an ESDInterface containing the ESD event to reconstruct");
     return 0x0;
   }
@@ -101,11 +106,12 @@ AliMUONVTrackStore* AliMUONRefitter::ReconstructFromDigits()
   if (!newTrackStore) return 0x0;
   
   // loop over tracks and refit them (create new tracks)
-  Int_t nTracks = fESDInterface->GetNTracks();
-  for (Int_t iTrack = 0; iTrack < nTracks; iTrack++) {
-    AliMUONTrack *track = RetrackFromDigits(iTrack);
-    newTrackStore->Add(track);
-    delete track;
+  AliMUONTrack *track;
+  TIter next(fkESDInterface->CreateTrackIterator());
+  while ((track = static_cast<AliMUONTrack*>(next()))) {
+    AliMUONTrack *newTrack = RetrackFromDigits(*track);
+    if (newTrack) newTrackStore->Add(newTrack);
+    delete newTrack;
   }
   
   return newTrackStore;
@@ -117,7 +123,7 @@ AliMUONVTrackStore* AliMUONRefitter::ReconstructFromClusters()
   /// refit all tracks from the attached clusters
   /// it is the responsability of the user to delete the returned store
   
-  if (!fESDInterface) {
+  if (!fkESDInterface) {
     AliError("the refitter must be connected to an ESDInterface containing the ESD event to reconstruct");
     return 0x0;
   }
@@ -128,7 +134,7 @@ AliMUONVTrackStore* AliMUONRefitter::ReconstructFromClusters()
   
   // loop over tracks and refit them (create new tracks)
   AliMUONTrack *track;
-  TIter next(fESDInterface->CreateTrackIterator());
+  TIter next(fkESDInterface->CreateTrackIterator());
   while ((track = static_cast<AliMUONTrack*>(next()))) {
     AliMUONTrack* newTrack = newTrackStore->Add(*track);
     if (!fTracker->RefitTrack(*newTrack)) newTrackStore->Remove(*newTrack);
@@ -138,115 +144,35 @@ AliMUONVTrackStore* AliMUONRefitter::ReconstructFromClusters()
 }
 
 //_____________________________________________________________________________
-AliMUONTrack* AliMUONRefitter::RetrackFromDigits(Int_t iTrack)
+AliMUONTrack* AliMUONRefitter::RetrackFromDigits(UInt_t trackId)
 {
-  /// refit track "iTrack" from the digits (i.e. re-clusterized the attached clusters):
-  /// several new clusters may be reconstructed per initial ESD cluster:
-  /// -> all the combinations of clusters are considered to build the new tracks
-  /// -> return the best track (largest number of clusters or best chi2 in case of equality)
+  /// refit track "trackId" from the digits (i.e. re-clusterized the attached clusters)
   /// it is the responsability of the user to delete the returned track
   
-  if (!fESDInterface) {
+  if (!fkESDInterface) {
     AliError("the refitter must be connected to an ESDInterface containing the ESD event to reconstruct");
     return 0x0;
   }
   
   // get the track to refit
-  AliMUONTrack* track = fESDInterface->GetTrack(iTrack);
-  if (!track) return 0x0;
-  
-  // check if digits exist
-  if (fESDInterface->GetNDigits(iTrack) == 0) {
-    AliError(Form("no digit attached to track #%d",iTrack));
-    return 0x0;
-  }
-  
-  // prepare new track(s)
-  AliMUONVTrackStore* newTrackStore = AliMUONESDInterface::NewTrackStore();
-  if (!newTrackStore) return 0x0;
-  newTrackStore->Add(*track)->Clear("C");
-  
-  // prepare new cluster store
-  AliMUONVClusterStore* newClusterStore = AliMUONESDInterface::NewClusterStore();
-  if (!newClusterStore) {
-    delete newTrackStore;
-    return 0x0;
-  }
-  
-  // loop over clusters, re-clusterize and build new tracks
-  Int_t nClusters = track->GetNClusters();
-  for (Int_t iCluster = 0; iCluster < nClusters; iCluster++) {
-    
-    // reset the new cluster store
-    newClusterStore->Clear();
-    
-    // get the current cluster
-    AliMUONVCluster* cluster = fESDInterface->GetClusterFast(iTrack,iCluster);
-    
-    // re-clusterize current cluster
-    TIter next(fESDInterface->CreateDigitIterator(iTrack, iCluster));
-    fClusterServer->UseDigits(next);
-    Int_t nNewClusters = fClusterServer->Clusterize(cluster->GetChamberId(),*newClusterStore,AliMpArea());
-    
-    // check that re-clusterizing succeeded
-    if (nNewClusters == 0) {
-      AliWarning(Form("refit gave no cluster (chamber %d)",cluster->GetChamberId()));
-      AliInfo("initial ESD cluster:");
-      cluster->Print("FULL");
-      continue;
-    }
-    
-    // add the new cluster(s) to the tracks
-    AddClusterToTracks(*newClusterStore, *newTrackStore);
-    
-  }
-  
-  // refit the tracks and pick up the best one
-  AliMUONTrack *currentTrack, *bestTrack = 0x0;
-  Double_t currentChi2, bestChi2 = 1.e10;
-  Int_t currentNCluster, bestNClusters = 0;
-  TIter next(newTrackStore->CreateIterator());
-  while ((currentTrack = static_cast<AliMUONTrack*>(next()))) {
-    
-    // set the track parameters at first cluster if any (used as seed in original tracking)
-    AliMUONTrackParam* param = (AliMUONTrackParam*) currentTrack->GetTrackParamAtCluster()->First();
-    if (param) *param = *((AliMUONTrackParam*) track->GetTrackParamAtCluster()->First());
-    
-    // refit the track
-    if (!fTracker->RefitTrack(*currentTrack)) break;
-    
-    // find best track (the one with the higher number of cluster or the best chi2 in case of equality)
-    currentNCluster = currentTrack->GetNClusters();
-    currentChi2 = currentTrack->GetGlobalChi2();
-    if (currentNCluster > bestNClusters || (currentNCluster == bestNClusters && currentChi2 < bestChi2)) {
-      bestTrack = currentTrack;
-      bestNClusters = currentNCluster;
-      bestChi2 = currentChi2;
-    }
-    
-  }
+  AliMUONTrack* track = fkESDInterface->FindTrack(trackId);
   
-  // copy best track and free memory
-  AliMUONTrack* newTrack = bestTrack ? new AliMUONTrack(*bestTrack) : 0x0;
-  delete newClusterStore;
-  delete newTrackStore;
-  
-  return newTrack;
+  return track ? RetrackFromDigits(*track) : 0x0;
 }
 
 //_____________________________________________________________________________
-AliMUONTrack* AliMUONRefitter::RetrackFromClusters(Int_t iTrack)
+AliMUONTrack* AliMUONRefitter::RetrackFromClusters(UInt_t trackId)
 {
-  /// refit track "iTrack" form the clusters (i.e. do not re-clusterize)
+  /// refit track "trackId" from the clusters (i.e. do not re-clusterize)
   /// it is the responsability of the user to delete the returned track
   
-  if (!fESDInterface) {
+  if (!fkESDInterface) {
     AliError("the refitter must be connected to an ESDInterface containing the ESD event to reconstruct");
     return 0x0;
   }
   
   // get the track to refit
-  AliMUONTrack* track = fESDInterface->GetTrack(iTrack);
+  AliMUONTrack* track = fkESDInterface->FindTrack(trackId);
   if (!track) return 0x0;
   
   // refit the track (create a new one)
@@ -260,24 +186,24 @@ AliMUONTrack* AliMUONRefitter::RetrackFromClusters(Int_t iTrack)
 }
 
 //_____________________________________________________________________________
-AliMUONVClusterStore* AliMUONRefitter::ReClusterize(Int_t iTrack, Int_t iCluster)
+AliMUONVClusterStore* AliMUONRefitter::ReClusterize(UInt_t trackId, UInt_t clusterId)
 {
-  /// re-clusterize cluster numbered "iCluster" in track "iTrack"
+  /// re-clusterize cluster numbered "clusterId" in track "trackId"
   /// several new clusters may be reconstructed
   /// it is the responsability of the user to delete the returned store
   
-  if (!fESDInterface) {
+  if (!fkESDInterface) {
     AliError("the refitter must be connected to an ESDInterface containing the ESD event to reconstruct");
     return 0x0;
   }
   
   // get the cluster to re-clusterize
-  AliMUONVCluster* cluster = fESDInterface->GetCluster(iTrack,iCluster);
+  AliMUONVCluster* cluster = fkESDInterface->FindCluster(trackId,clusterId);
   if (!cluster) return 0x0;
   
   // check if digits exist
   if (cluster->GetNDigits() == 0) {
-    AliError(Form("no digit attached to cluster #%d in track %d",iCluster,iTrack));
+    AliError(Form("no digit attached to cluster #%d in track %d",clusterId,trackId));
     return 0x0;
   }
   
@@ -286,9 +212,9 @@ AliMUONVClusterStore* AliMUONRefitter::ReClusterize(Int_t iTrack, Int_t iCluster
   if (!clusterStore) return 0x0;
   
   // re-clusterize
-  TIter next(fESDInterface->CreateDigitIterator(iTrack, iCluster));
-  fClusterServer->UseDigits(next);
-  fClusterServer->Clusterize(cluster->GetChamberId(),*clusterStore,AliMpArea());
+  TIter next(fkESDInterface->CreateDigitIterator(trackId, clusterId));
+  fClusterServer->UseDigits(next,fkESDInterface->GetDigits());
+  fClusterServer->Clusterize(cluster->GetChamberId(),*clusterStore,AliMpArea(),fkRecoParam);
   
   return clusterStore;
 }
@@ -300,13 +226,13 @@ AliMUONVClusterStore* AliMUONRefitter::ReClusterize(UInt_t clusterId)
   /// several new clusters may be reconstructed
   /// it is the responsability of the user to delete the returned store
   
-  if (!fESDInterface) {
+  if (!fkESDInterface) {
     AliError("the refitter must be connected to an ESDInterface containing the ESD event to reconstruct");
     return 0x0;
   }
   
   // get the cluster to re-clusterize
-  AliMUONVCluster* cluster = fESDInterface->FindCluster(clusterId);
+  AliMUONVCluster* cluster = fkESDInterface->FindCluster(clusterId);
   if (!cluster) return 0x0;
   
   // check if digits exist
@@ -320,9 +246,9 @@ AliMUONVClusterStore* AliMUONRefitter::ReClusterize(UInt_t clusterId)
   if (!clusterStore) return 0x0;
   
   // re-clusterize
-  TIter next(fESDInterface->CreateDigitIteratorInCluster(clusterId));
-  fClusterServer->UseDigits(next);
-  fClusterServer->Clusterize(cluster->GetChamberId(),*clusterStore,AliMpArea());
+  TIter next(fkESDInterface->CreateDigitIteratorInCluster(clusterId));
+  fClusterServer->UseDigits(next,fkESDInterface->GetDigits());
+  fClusterServer->Clusterize(cluster->GetChamberId(),*clusterStore,AliMpArea(),fkRecoParam);
   
   return clusterStore;
 }
@@ -340,19 +266,117 @@ void AliMUONRefitter::CreateGeometryTransformer()
 void AliMUONRefitter::CreateClusterServer(AliMUONGeometryTransformer& transformer)
 {
   /// Create cluster server
-  AliMUONVClusterFinder* clusterFinder = AliMUONReconstructor::CreateClusterFinder(AliMUONReconstructor::GetRecoParam()->GetClusteringMode());
+  AliMUONVClusterFinder* clusterFinder = AliMUONReconstructor::CreateClusterFinder(fkRecoParam->GetClusteringMode());
   fClusterServer = clusterFinder ? new AliMUONSimpleClusterServer(clusterFinder,transformer) : 0x0;
 }
 
 //_____________________________________________________________________________
-void AliMUONRefitter::AddClusterToTracks(const AliMUONVClusterStore &clusterStore, AliMUONVTrackStore &trackStore)
+AliMUONTrack* AliMUONRefitter::RetrackFromDigits(const AliMUONTrack& track)
+{
+  /// refit the given track from the digits (i.e. re-clusterized the attached clusters):
+  /// several new clusters may be reconstructed per initial ESD cluster:
+  /// -> all the combinations of clusters are considered to build the new tracks
+  /// -> return the best track (largest number of clusters or best chi2 in case of equality)
+  
+  // check if digits exist
+  UInt_t trackId = track.GetUniqueID();
+  if (fkESDInterface->GetNDigits(trackId) == 0) {
+    AliError(Form("no digit attached to track #%d",trackId));
+    return 0x0;
+  }
+  
+  // prepare new track(s)
+  AliMUONVTrackStore* newTrackStore = AliMUONESDInterface::NewTrackStore();
+  if (!newTrackStore) return 0x0;
+  newTrackStore->Add(track)->Clear("C");
+  
+  // prepare new cluster store
+  AliMUONVClusterStore* newClusterStore = AliMUONESDInterface::NewClusterStore();
+  if (!newClusterStore) {
+    delete newTrackStore;
+    return 0x0;
+  }
+  
+  // loop over clusters, re-clusterize and build new tracks
+  AliMUONVCluster* cluster;
+  TIter nextCluster(fkESDInterface->CreateClusterIterator(trackId));
+  while ((cluster = static_cast<AliMUONVCluster*>(nextCluster()))) {
+    
+    // reset the new cluster store
+    newClusterStore->Clear();
+    
+    // re-clusterize current cluster
+    TIter nextDigit(fkESDInterface->CreateDigitIterator(trackId, cluster->GetUniqueID()));
+    fClusterServer->UseDigits(nextDigit,fkESDInterface->GetDigits());
+    Int_t nNewClusters = fClusterServer->Clusterize(cluster->GetChamberId(),*newClusterStore,AliMpArea(),fkRecoParam);
+    
+    // check that re-clusterizing succeeded
+    if (nNewClusters == 0) {
+      AliWarning(Form("refit gave no cluster (chamber %d)",cluster->GetChamberId()));
+      AliInfo("initial ESD cluster:");
+      cluster->Print("FULL");
+      continue;
+    }
+    
+    // add the new cluster(s) to the tracks
+    if (!AddClusterToTracks(*newClusterStore, *newTrackStore)) {
+      delete newClusterStore;
+      delete newTrackStore;
+      return 0x0;
+    }
+    
+  }
+  
+  if (newTrackStore->GetSize() > 1000) AliInfo(Form("%d tracks to refit... be patient!!",newTrackStore->GetSize()));
+                                              
+  // refit the tracks and pick up the best one
+  AliMUONTrack *currentTrack, *bestTrack = 0x0;
+  Double_t currentChi2, bestChi2 = AliMUONTrack::MaxChi2();
+  Int_t currentNCluster, bestNClusters = 0;
+  TIter next(newTrackStore->CreateIterator());
+  while ((currentTrack = static_cast<AliMUONTrack*>(next()))) {
+    
+    // set the track parameters at first cluster if any (used as seed in original tracking)
+    AliMUONTrackParam* param = (AliMUONTrackParam*) currentTrack->GetTrackParamAtCluster()->First();
+    if (param) *param = *((AliMUONTrackParam*) track.GetTrackParamAtCluster()->First());
+    
+    // refit the track
+    if (!fTracker->RefitTrack(*currentTrack)) continue;
+    
+    // find best track (the one with the higher number of cluster or the best chi2 in case of equality)
+    currentNCluster = currentTrack->GetNClusters();
+    currentChi2 = currentTrack->GetGlobalChi2();
+    if (currentNCluster > bestNClusters || (currentNCluster == bestNClusters && currentChi2 < bestChi2)) {
+      bestTrack = currentTrack;
+      bestNClusters = currentNCluster;
+      bestChi2 = currentChi2;
+    }
+    
+  }
+  
+  // copy best track and free memory
+  AliMUONTrack* newTrack = bestTrack ? new AliMUONTrack(*bestTrack) : 0x0;
+  delete newClusterStore;
+  delete newTrackStore;
+  
+  return newTrack;
+}
+
+//_____________________________________________________________________________
+Bool_t AliMUONRefitter::AddClusterToTracks(const AliMUONVClusterStore &clusterStore, AliMUONVTrackStore &trackStore)
 {
   /// add clusters to each of the given tracks
   /// duplicate the tracks if there are several clusters and add one cluster per copy
   
   // create new track store if there are more than 1 cluster to add per track
   Int_t nClusters = clusterStore.GetSize();
-  if (nClusters < 1) return;
+  if (nClusters < 1) return kTRUE;
+  
+  // check if we will exceed the maximum allowed number of tracks
+  if (nClusters * trackStore.GetSize() > fkRecoParam->GetMaxTrackCandidates()) {
+    AliError(Form("Too many track candidates (%d tracks). Stop refitting.", nClusters * trackStore.GetSize()));
+    return kFALSE;
+  }
   
   AliMUONTrackParam dummyParam;
   AliMUONTrack *currentTrack, *track;
@@ -369,7 +393,7 @@ void AliMUONRefitter::AddClusterToTracks(const AliMUONVClusterStore &clusterStor
     
     // add the new cluster(s) to the tracks
     // duplicate the tracks if there are several clusters
-    // the loop after loading the last cluster which is added to the current track
+    // stop the loop after loading the last cluster which is added to the current track
     iCluster = 0;
     TIter nextCluster(clusterStore.CreateIterator());
     while ((newCluster = static_cast<AliMUONVCluster*>(nextCluster())) && (iCluster < nClusters - 1)) {
@@ -397,5 +421,7 @@ void AliMUONRefitter::AddClusterToTracks(const AliMUONVClusterStore &clusterStor
     
   }
   
+  return kTRUE;
+  
 }