--- /dev/null
+/**************************************************************************
+ * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
+ * *
+ * Author: The ALICE Off-line Project. *
+ * Contributors are mentioned in the code where appropriate. *
+ * *
+ * Permission to use, copy, modify and distribute this software and its *
+ * documentation strictly for non-commercial purposes is hereby granted *
+ * without fee, provided that the above copyright notice appears in all *
+ * copies and that both the copyright notice and this permission notice *
+ * appear in the supporting documentation. The authors make no claims *
+ * about the suitability of this software for any purpose. It is *
+ * provided "as is" without express or implied warranty. *
+ **************************************************************************/
+
+
+////////////////////////////////////////////////////////////////////////
+// //
+// Class for the Selection of Non-Heavy-Flavour-Electrons trought //
+// the invariant mass method. The selection can be done from two //
+// diferent algorithms, which can be choosed calling the function //
+// "SetAlgorithm(TString Algorithm)". //
+// //
+// Author: Elienos Pereira de Oliveira Filho //
+// (University of São Paulo) //
+// //
+////////////////////////////////////////////////////////////////////////
+
+#include "TH1F.h"
+#include "TMath.h"
+#include "TLorentzVector.h"
+
+#include "AliESDEvent.h"
+#include "AliESDtrackCuts.h"
+#include "AliESDtrack.h"
+
+#include "AliSelectNonHFE.h"
+#include "AliKFParticle.h"
+#include "AliLog.h"
+#include "stdio.h"
+#include "iostream"
+#include "fstream"
+
+ClassImp(AliSelectNonHFE)
+//________________________________________________________________________
+AliSelectNonHFE::AliSelectNonHFE(const char *name, const Char_t *title)
+: TNamed(name, title)
+ ,fTrackCuts(0)
+ ,fAlgorithm("MA")
+ ,fAngleCut(999)
+ ,fdcaCut(999)
+ ,fdEdxMin(62)
+ ,fdEdxMax(100)
+ ,fMassCut(0.5)
+ ,fChi2OverNDFCut(999)
+ ,fIsLS(kFALSE)
+ ,fIsULS(kFALSE)
+ ,fNLS(0)
+ ,fNULS(0)
+ ,fLSPartner(0)
+ ,fULSPartner(0)
+ ,fHistMass(0)
+ ,fHistMassBack(0)
+ ,fHistDCA(0)
+ ,fHistDCABack(0)
+ ,fHistAngle(0)
+ ,fHistAngleBack(0)
+{
+ //
+ // Constructor
+ //
+
+ fTrackCuts = new AliESDtrackCuts();
+ //Configure Default Track Cuts
+ fTrackCuts->SetAcceptKinkDaughters(kFALSE);
+ fTrackCuts->SetRequireTPCRefit(kTRUE);
+ fTrackCuts->SetEtaRange(-0.9,0.9);
+ fTrackCuts->SetRequireSigmaToVertex(kTRUE);
+ fTrackCuts->SetMaxChi2PerClusterTPC(4.0);
+ fTrackCuts->SetMinNClustersTPC(50);
+ fTrackCuts->SetPtRange(0.3,1e10);
+
+
+}
+
+//________________________________________________________________________
+AliSelectNonHFE::AliSelectNonHFE()
+ : TNamed()
+ ,fTrackCuts(0)
+ ,fAlgorithm("MA")
+ ,fAngleCut(999)
+ ,fdcaCut(999)
+ ,fdEdxMin(62)
+ ,fdEdxMax(100)
+ ,fMassCut(0.5)
+ ,fChi2OverNDFCut(999)
+ ,fIsLS(kFALSE)
+ ,fIsULS(kFALSE)
+ ,fNLS(0)
+ ,fNULS(0)
+ ,fLSPartner(0)
+ ,fULSPartner(0)
+ ,fHistMass(0)
+ ,fHistMassBack(0)
+ ,fHistDCA(0)
+ ,fHistDCABack(0)
+ ,fHistAngle(0)
+ ,fHistAngleBack(0)
+{
+ //
+ // Constructor
+ //
+
+ fTrackCuts = new AliESDtrackCuts();
+ //Configure Default Track Cuts
+ fTrackCuts->SetAcceptKinkDaughters(kFALSE);
+ fTrackCuts->SetRequireTPCRefit(kTRUE);
+ fTrackCuts->SetEtaRange(-0.9,0.9);
+ fTrackCuts->SetRequireSigmaToVertex(kTRUE);
+ fTrackCuts->SetMaxChi2PerClusterTPC(4.0);
+ fTrackCuts->SetMinNClustersTPC(50);
+ fTrackCuts->SetPtRange(0.3,1e10);
+
+
+}
+
+//_________________________________________
+AliSelectNonHFE::~AliSelectNonHFE()
+{
+ //
+ // Destructor
+ //
+
+ if(fTrackCuts) delete fTrackCuts;
+ if(fLSPartner) delete [] fLSPartner;
+ if(fULSPartner) delete [] fULSPartner;
+
+
+}
+
+//__________________________________________
+void AliSelectNonHFE::FindNonHFE(Int_t iTrack1, AliESDtrack *track1, AliESDEvent *fESD)
+{
+ //
+ // Find non HFE electrons
+ //
+
+
+ //Magnetic Field
+ Double_t bfield = fESD->GetMagneticField();
+
+ //Second Track loop
+
+ fIsULS = kFALSE; //Non-HFE Unlike signal Flag
+ fIsLS = kFALSE; //Non-HFE like signal Flag
+ fNULS = 0; //Non-HFE Unlike signal Flag
+ fNLS = 0; //Non-HFE like signal Flag
+
+ if(fLSPartner) delete [] fLSPartner;
+ if(fULSPartner) delete [] fULSPartner;
+ fLSPartner = new int [100]; //store the partners index
+ fULSPartner = new int [100]; //store the partners index
+
+ for(Int_t iTrack2 = iTrack1+1; iTrack2 < fESD->GetNumberOfTracks(); iTrack2++)
+ {
+ AliESDtrack* track2 = fESD->GetTrack(iTrack2);
+ if (!track2)
+ {
+ printf("ERROR: Could not receive track %d\n", iTrack2);
+ continue;
+ }
+
+ //Second track cuts
+ Double_t dEdx2 = track2->GetTPCsignal();
+ if(dEdx2<fdEdxMin || dEdx2>fdEdxMax) continue;
+ if(!fTrackCuts->AcceptTrack(track2)) continue;
+
+ if(fAlgorithm=="MA")
+ {
+ //Variables
+ Double_t p1[3];
+ Double_t p2[3];
+ Double_t xt1; //radial position track 1 at the DCA point
+ Double_t xt2; //radial position track 2 at the DCA point
+ //DCA track1-track2
+ Double_t dca12 = track2->GetDCA(track1,bfield,xt2,xt1);
+
+ //Momento of the track extrapolated to DCA track-track
+ //Track1
+ Bool_t hasdcaT1 = track1->GetPxPyPzAt(xt1,bfield,p1);
+ //Track2
+ Bool_t hasdcaT2 = track2->GetPxPyPzAt(xt2,bfield,p2);
+
+ if(!hasdcaT1 || !hasdcaT2) AliWarning("It could be a problem in the extrapolation");
+
+ //track1-track2 Invariant Mass
+ Double_t eMass = 0.000510998910; //Electron mass in GeV
+ Double_t pP1 = sqrt(p1[0]*p1[0]+p1[1]*p1[1]+p1[2]*p1[2]); //Track 1 momentum
+ Double_t pP2 = sqrt(p2[0]*p2[0]+p2[1]*p2[1]+p2[2]*p2[2]); //Track 1 momentum
+
+ //Double_t E1 = sqrt(eMass*eMass+pP1*pP1);
+ //Double_t E2 = sqrt(eMass*eMass+pP2*pP2);
+ //Double_t imass = sqrt(2*eMass*eMass+2*(E1*E2-(p1[0]*p2[0]+p1[1]*p2[1]+p1[2]*p2[2])));
+ //Double_t angle = TMath::ACos((p1[0]*p2[0]+p1[1]*p2[1]+p1[2]*p2[2])/(pP1*pP2));
+
+ TLorentzVector v1(p1[0],p1[1],p1[2],sqrt(eMass*eMass+pP1*pP1));
+ TLorentzVector v2(p2[0],p2[1],p2[2],sqrt(eMass*eMass+pP2*pP2));
+ Double_t imass = (v1+v2).M(); //Invariant Mass
+ Double_t angle = v1.Angle(v2.Vect()); //Opening Angle (Total Angle)
+
+ Float_t fCharge1 = track1->Charge();
+ Float_t fCharge2 = track2->Charge();
+
+ if(imass<fMassCut && angle<fAngleCut && dca12<fdcaCut)
+ {
+ if(fCharge1*fCharge2<0)
+ {
+ fIsULS=kTRUE;
+ fULSPartner[fNULS] = iTrack2;
+ fNULS++;
+ }
+ if(fCharge1*fCharge2>0)
+ {
+ fIsLS=kTRUE;
+ fLSPartner[fNLS] = iTrack2;
+ fNLS++;
+ }
+ }
+
+ //Fill some histograms
+ if(fCharge1*fCharge2<0 && fHistMass) fHistMass->Fill(imass);
+ if(fCharge1*fCharge2>0 && fHistMassBack) fHistMassBack->Fill(imass);
+
+ if(fCharge1*fCharge2<0 && fHistDCA) fHistDCA->Fill(dca12);
+ if(fCharge1*fCharge2>0 && fHistDCABack) fHistDCABack->Fill(dca12);
+
+ if(fCharge1*fCharge2<0 && fHistAngle) fHistAngle->Fill(angle);
+ if(fCharge1*fCharge2>0 && fHistAngleBack) fHistAngleBack->Fill(angle);
+
+ }
+ else if(fAlgorithm=="KF")
+ {
+ Int_t fPDGtrack1 = 11;
+ Int_t fPDGtrack2 = 11;
+
+ Float_t fCharge1 = track1->Charge();
+ Float_t fCharge2 = track2->Charge();
+
+ if(fCharge1>0) fPDGtrack1 = -11;
+ if(fCharge2>0) fPDGtrack2 = -11;
+
+ AliKFParticle fKFtrack1(*track1, fPDGtrack1);
+ AliKFParticle fKFtrack2(*track2, fPDGtrack2);
+ AliKFParticle fRecoGamma(fKFtrack1, fKFtrack2);
+
+ //Reconstruction Cuts
+ if(fRecoGamma.GetNDF()<1) continue;
+ Double_t chi2OverNDF = fRecoGamma.GetChi2()/fRecoGamma.GetNDF();
+ if(TMath::Sqrt(TMath::Abs(chi2OverNDF))>fChi2OverNDFCut) continue;
+
+ //Invariant Mass
+ Double_t imass;
+ Double_t width;
+ fRecoGamma.GetMass(imass,width);
+
+ //Opening Angle (Total Angle)
+ Double_t angle = fKFtrack1.GetAngle(fKFtrack2);
+
+ //Fill some histograms
+ if(fCharge1*fCharge2<0 && fHistAngle) fHistAngle->Fill(angle);
+ if(fCharge1*fCharge2>0 && fHistAngleBack) fHistAngleBack->Fill(angle);
+
+ if(angle<fAngleCut) continue;
+
+ if(imass<fMassCut)
+ {
+ if(fCharge1*fCharge2<0)
+ {
+ fIsULS=kTRUE;
+ fULSPartner[fNULS] = iTrack2;
+ fNULS++;
+ }
+ if(fCharge1*fCharge2>0)
+ {
+ fIsLS=kTRUE;
+ fLSPartner[fNLS] = iTrack2;
+ fNLS++;
+ }
+ }
+
+ //Fill some histograms
+ if(fCharge1*fCharge2<0 && fHistMass) fHistMass->Fill(imass);
+ if(fCharge1*fCharge2>0 && fHistMassBack) fHistMassBack->Fill(imass);
+
+ }
+ else
+ {
+ AliError( Form("Error: %s is not a valid algorithm option.",(const char*)fAlgorithm));
+ return;
+ }
+
+ }
+
+ return;
+}
--- /dev/null
+#ifndef ALISELECTNONHFE_H
+#define ALISELECTNONHFE_H
+
+/* Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
+ * See cxx source for full Copyright notice */
+
+////////////////////////////////////////////////////////////////////////
+// //
+// Task for the Selection of Non-Heavy-Flavour-Electrons //
+// //
+// Author: Elienos Pereira de Oliveira Filho //
+// (University of São Paulo) //
+// //
+////////////////////////////////////////////////////////////////////////
+
+#ifndef ROOT_TNamed
+#include <TNamed.h>
+#endif
+
+class TH1F;
+class TH2F;
+class AliESDEvent;
+class AliESDtrack;
+class AliESDtrackCuts;
+
+
+class AliSelectNonHFE : public TNamed {
+ public:
+ AliSelectNonHFE();
+ AliSelectNonHFE(const char *name, const Char_t *title);
+ virtual ~AliSelectNonHFE();
+ Int_t GetNLS() const {return fNLS;};
+ Int_t GetNULS() const {return fNULS;};
+ Int_t* GetPartnersLS() const {return fLSPartner;};
+ Int_t* GetPartnersULS() const {return fULSPartner;};
+ Bool_t IsLS() const {return fIsLS;};
+ Bool_t IsULS() const {return fIsULS;};
+ void FindNonHFE(Int_t iTrack, AliESDtrack *track1, AliESDEvent *fESD);
+ void SetAlgorithm(TString Algorithm) {fAlgorithm = Algorithm;};
+ void SetChi2OverNDFCut(Double_t Chi2OverNDFCut) {fChi2OverNDFCut = Chi2OverNDFCut;};
+ void SetDCACut(Double_t dcaCut) {fdcaCut = dcaCut;};
+ void SetHistAngleBack(TH1F *HistAngleBack) {fHistAngleBack = HistAngleBack;};
+ void SetHistAngle(TH1F *HistAngle) {fHistAngle = HistAngle;};
+ void SetHistDCABack(TH1F *HistDCABack) {fHistDCABack = HistDCABack;};
+ void SetHistDCA(TH1F *HistDCA) {fHistDCA = HistDCA;};
+ void SetHistMassBack(TH1F *HistMassBack) {fHistMassBack = HistMassBack;};
+ void SetHistMass(TH1F *HistMass) {fHistMass = HistMass;};
+ void SetInvariantMassCut(Double_t MassCut) {fMassCut = MassCut;};
+ void SetOpeningAngleCut(Double_t AngleCut) {fAngleCut = AngleCut;};
+ void SetTrackCuts(Double_t dEdxMin, Double_t dEdxMax) {fdEdxMin = dEdxMin; fdEdxMax = dEdxMax;};
+ void SetTrackCuts(Double_t dEdxMin, Double_t dEdxMax, AliESDtrackCuts* TrackCuts)
+ {fdEdxMin = dEdxMin; fdEdxMax = dEdxMax; fTrackCuts = TrackCuts;};
+
+ private:
+ AliESDtrackCuts *fTrackCuts; //! Track quality
+ TString fAlgorithm; //Algorithm choice: "MA" (Manual Algorithm) or "KF" (Kalman Filter Algorithm)
+ Double_t fAngleCut; //Maximum opening angle between the tracks
+ Double_t fdcaCut; //Maximum dca between the tracks
+ Double_t fdEdxMin; //Minimum partner dEdx value
+ Double_t fdEdxMax; //Maximum partner dEdx value
+ Double_t fMassCut; //Maximum Invariant Mass Value for Non-HF-Electrons
+ Double_t fChi2OverNDFCut; //Maximum value of Chi2 over NDF in the case of KF Algorithm
+ Bool_t fIsLS; //Unlike signal pairs Flag
+ Bool_t fIsULS; //like signal pairs Flag
+ Int_t fNLS; //Number of Unlike signal pairs
+ Int_t fNULS; //Number of like signal pairs
+ Int_t *fLSPartner; //! Pointer for the LS partners index
+ Int_t *fULSPartner; //! Pointer for the ULS partners index
+ TH1F *fHistMass; //! Invariant mass histogram for Unlike sign pairs
+ TH1F *fHistMassBack; //! Invariant mass histogram for like sign pairs
+ TH1F *fHistDCA; //! DCA histogram for Unlike sign pairs
+ TH1F *fHistDCABack; //! DCA histogram for like sign pairs
+ TH1F *fHistAngle; //! Opening Angle histogram for Unlike sign pairs
+ TH1F *fHistAngleBack; //! Opening Angle histogram for like sign pairs
+
+ AliSelectNonHFE(const AliSelectNonHFE&); // not implemented
+ AliSelectNonHFE& operator=(const AliSelectNonHFE&); // not implemented
+
+ ClassDef(AliSelectNonHFE, 1); //!example of analysis
+};
+
+#endif