]> git.uio.no Git - u/mrichter/AliRoot.git/commitdiff
Migration of PWG2/FEMTOSCOPY to PWGCF/FEMTOSCOPY
authorakisiel <akisiel@f7af4fe6-9843-0410-8265-dc069ae4e863>
Mon, 30 Jan 2012 16:35:12 +0000 (16:35 +0000)
committerakisiel <akisiel@f7af4fe6-9843-0410-8265-dc069ae4e863>
Mon, 30 Jan 2012 16:35:12 +0000 (16:35 +0000)
280 files changed:
PWGCF/CMakelibPWGCFFEMTOSCOPYAOD.pkg [new file with mode: 0644]
PWGCF/CMakelibPWGCFfemtoscopy.pkg [new file with mode: 0644]
PWGCF/CMakelibPWGCFfemtoscopyUser.pkg [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliAnalysisTaskFemto.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliAnalysisTaskFemto.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoAODTrackCut.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoAODTrackCut.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoAnalysis.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoAnalysisAzimuthal.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoAnalysisAzimuthal.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoAnalysisCollection.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoAnalysisReactionPlane.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoAnalysisReactionPlane.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoBPLCMS3DCorrFctn.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoBPLCMS3DCorrFctn.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoBasicEventCut.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoBasicEventCut.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoBasicTrackCut.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoBasicTrackCut.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCorrFctn.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCorrFctn.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCorrFctn3DLCMSSym.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCorrFctn3DLCMSSym.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCorrFctn3DSpherical.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCorrFctn3DSpherical.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCorrFctnCollection.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCorrFctnNonIdDR.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCorrFctnNonIdDR.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCoulomb.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCoulomb.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCutMonitor.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCutMonitor.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCutMonitorCollection.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCutMonitorEventMult.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCutMonitorEventMult.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCutMonitorEventVertex.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCutMonitorEventVertex.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCutMonitorHandler.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCutMonitorHandler.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCutMonitorParticlePID.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCutMonitorParticlePID.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCutMonitorParticleVertPos.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCutMonitorParticleVertPos.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCutMonitorParticleYPt.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCutMonitorParticleYPt.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoDummyPairCut.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoDummyPairCut.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEnumeration.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEvent.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEvent.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventCut.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventCutEstimators.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventCutEstimators.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReader.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReader.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReaderAOD.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReaderAOD.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReaderAODChain.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReaderAODChain.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReaderESD.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReaderESD.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReaderESDChain.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReaderESDChain.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReaderESDChainKine.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReaderESDChainKine.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReaderKinematicsChain.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReaderKinematicsChain.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReaderStandard.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReaderStandard.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventWriter.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventWriterCollection.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoFsiTools.F [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoFsiWeightLednicky.F [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoHelix.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoHiddenInfo.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoKTPairCut.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoKTPairCut.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoKink.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoKink.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoKinkCollection.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoKinkCut.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoLikeSignAnalysis.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoLikeSignAnalysis.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoLikeSignCorrFctn.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoLorentzVector.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoLorentzVectorD.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoMCTrackCut.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoMCTrackCut.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoManager.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoManager.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelCorrFctn.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelCorrFctn.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelFreezeOutGenerator.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelFreezeOutGenerator.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelGausLCMSFreezeOutGenerator.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelGausLCMSFreezeOutGenerator.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelGlobalHiddenInfo.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelGlobalHiddenInfo.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelHiddenInfo.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelHiddenInfo.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelManager.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelManager.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelWeightGenerator.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelWeightGenerator.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelWeightGeneratorBasic.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelWeightGeneratorBasic.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelWeightGeneratorLednicky.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelWeightGeneratorLednicky.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoPair.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoPair.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoPairCut.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoParticle.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoParticle.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoParticleCollection.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoParticleCut.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoPicoEvent.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoPicoEvent.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoPicoEventCollection.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoPicoEventCollectionVector.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoPicoEventCollectionVectorHideAway.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoPicoEventCollectionVectorHideAway.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoQinvCorrFctn.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoQinvCorrFctn.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoSimpleAnalysis.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoSimpleAnalysis.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoString.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoThreeVector.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoThreeVectorD.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoTrack.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoTrack.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoTrackCollection.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoTrackCut.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoTypes.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoV0.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoV0.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoV0Collection.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoV0Cut.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoVector.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoVertexAnalysis.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoVertexAnalysis.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoVertexMultAnalysis.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoVertexMultAnalysis.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoXi.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoXi.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoXiCollection.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFemtoXiCut.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFmHelix.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFmHelix.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFmHelixD.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFmLorentzVector.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFmLorentzVectorD.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFmPhysicalHelix.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFmPhysicalHelix.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFmPhysicalHelixD.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFmThreeVector.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFmThreeVectorD.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliFmThreeVectorF.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliTwoTrackRes.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/AliTwoTrackRes.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/PhysicalConstants.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/SystemOfUnits.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/TpcLocalTransform.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/TpcLocalTransform.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemto/phys_constants.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoBPLCMS3DCorrFctnEMCIC.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoBPLCMS3DCorrFctnEMCIC.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoChi2CorrFctn.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoChi2CorrFctn.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCorrFctn3DSphericalEMCIC.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCorrFctn3DSphericalEMCIC.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCorrFctnDEtaDPhi.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCorrFctnDEtaDPhi.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCorrFctnDirectYlm.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCorrFctnDirectYlm.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCorrFctnGammaMonitor.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCorrFctnGammaMonitor.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCorrFctnTPCNcls.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCorrFctnTPCNcls.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCutMonitorParticleEtCorr.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCutMonitorParticleEtCorr.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCutMonitorParticleMomRes.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCutMonitorParticleMomRes.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCutMonitorParticlePtPDG.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCutMonitorParticlePtPDG.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCutMonitorTrackTPCchiNdof.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCutMonitorTrackTPCchiNdof.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCutMonitorTrackTPCncls.cxx [new file with mode: 0755]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCutMonitorTrackTPCncls.h [new file with mode: 0755]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoESDTrackCut.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoESDTrackCut.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoEventReaderESDKine.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoEventReaderESDKine.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelAllHiddenInfo.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelAllHiddenInfo.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelBPLCMSCorrFctn.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelBPLCMSCorrFctn.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctn3DLCMSSpherical.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctn3DLCMSSpherical.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctn3DSpherical.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctn3DSpherical.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctnDEtaDPhi.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctnDEtaDPhi.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctnDirectYlm.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctnDirectYlm.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctnNonIdDR.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctnNonIdDR.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctnSource.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctnSource.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctnTrueQ.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctnTrueQ.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelGausRinvFreezeOutGenerator.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelGausRinvFreezeOutGenerator.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoPairCutAntiGamma.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoPairCutAntiGamma.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoPairCutPt.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoPairCutPt.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoPairCutRadialDistance.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoPairCutRadialDistance.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoQAEventCut.cxx [new file with mode: 0755]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoQAEventCut.h [new file with mode: 0755]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoQATrackCut.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoQATrackCut.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoQPairCut.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoQPairCut.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoQinvCorrFctnEMCIC.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoQinvCorrFctnEMCIC.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoShareQualityCorrFctn.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoShareQualityCorrFctn.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoShareQualityKTPairCut.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoShareQualityKTPairCut.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoShareQualityPairCut.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoShareQualityPairCut.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoShareQualityQAPairCut.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoShareQualityQAPairCut.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoShareQualityTPCEntranceSepPairCut.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoShareQualityTPCEntranceSepPairCut.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoShareQualityTPCEntranceSepQAPairCut.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoShareQualityTPCEntranceSepQAPairCut.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoTPCInnerCorrFctn.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoTPCInnerCorrFctn.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoYlm.cxx [new file with mode: 0644]
PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoYlm.h [new file with mode: 0644]
PWGCF/FEMTOSCOPY/Documentation/AliFemto.pdf [new file with mode: 0644]
PWGCF/FEMTOSCOPY/Documentation/AliFemto.tex [new file with mode: 0755]
PWGCF/FEMTOSCOPY/Documentation/AliFemtoTitle.pdf [new file with mode: 0644]
PWGCF/FEMTOSCOPY/Documentation/Analysis.pdf [new file with mode: 0644]
PWGCF/FEMTOSCOPY/Documentation/ExampleMacro1.pdf [new file with mode: 0644]
PWGCF/FEMTOSCOPY/Documentation/ExampleMacro2.pdf [new file with mode: 0644]
PWGCF/FEMTOSCOPY/Documentation/ExampleMacro3.pdf [new file with mode: 0644]
PWGCF/FEMTOSCOPY/Documentation/ExampleMacro4.pdf [new file with mode: 0644]
PWGCF/FEMTOSCOPY/Documentation/ExampleMacro5.pdf [new file with mode: 0644]
PWGCF/FEMTOSCOPY/Documentation/TopLevelUML.pdf [new file with mode: 0644]
PWGCF/FEMTOSCOPY/macros/AddTaskFemto.C [new file with mode: 0644]
PWGCF/FEMTOSCOPY/macros/Batch/ConfigFemtoAnalysis.C [new file with mode: 0644]
PWGCF/FEMTOSCOPY/macros/Batch/runBatch.C [new file with mode: 0644]
PWGCF/FEMTOSCOPY/macros/BatchMC/runBatch.C [new file with mode: 0644]
PWGCF/FEMTOSCOPY/macros/ConfigFemtoAnalysis.C [new file with mode: 0644]
PWGCF/FEMTOSCOPY/macros/Local/AliFemtoSplittingMergingQA.C [new file with mode: 0644]
PWGCF/FEMTOSCOPY/macros/Local/runLocal.C [new file with mode: 0644]
PWGCF/FEMTOSCOPY/macros/Proof/runProof.C [new file with mode: 0644]
PWGCF/FEMTOSCOPY/macros/Train/AddTaskFemto.C [new file with mode: 0644]
PWGCF/FEMTOSCOPY/macros/Train/DEtaDPhi/ConfigFemtoAnalysis.C [new file with mode: 0644]
PWGCF/FEMTOSCOPY/macros/Train/DEtaDPhiKaons/ConfigFemtoAnalysis.C [new file with mode: 0644]
PWGCF/FEMTOSCOPY/macros/Train/DEtaDPhiNoPID/ConfigFemtoAnalysis.C [new file with mode: 0644]
PWGCF/FEMTOSCOPY/macros/Train/DataTrain1/ConfigFemtoAnalysis.C [new file with mode: 0644]
PWGCF/FEMTOSCOPY/macros/Train/PWG2FemtoExercise1/ConfigFemtoAnalysis.C [new file with mode: 0644]
PWGCF/FEMTOSCOPY/macros/Train/PWG2FemtoExercise1/runBatch.C [new file with mode: 0644]
PWGCF/FEMTOSCOPY/macros/Train/PWG2FemtoExercise1/runLocal.C [new file with mode: 0644]
PWGCF/FEMTOSCOPY/macros/Train/PWG2Train2/ConfigFemtoAnalysis.C [new file with mode: 0644]
PWGCF/FEMTOSCOPY/macros/Train/PWG2TrainLHC10a6/ConfigFemtoAnalysis.C [new file with mode: 0644]
PWGCF/FEMTOSCOPY/macros/Train/PionsFemtoscopy/ConfigFemtoAnalysis.C [new file with mode: 0644]
PWGCF/FEMTOSCOPY/macros/Train/ProtonFemtoscopy/ConfigFemtoAnalysis.C [new file with mode: 0644]
PWGCF/FEMTOSCOPY/macros/Train/ProtonFemtoscopy/runBatch.C [new file with mode: 0644]
PWGCF/FEMTOSCOPY/macros/Train/Train3/ConfigFemtoAnalysis.C [new file with mode: 0644]
PWGCF/FEMTOSCOPY/macros/Train/TwoTrackQA/ConfigFemtoAnalysis.C [new file with mode: 0644]
PWGCF/FEMTOSCOPY/macros/Train/TwoTrackQA/ConfigFemtoAnalysisCentral.C [new file with mode: 0644]
PWGCF/FEMTOSCOPY/macros/Train/TwoTrackQA/FemtoQAPlots.C [new file with mode: 0644]
PWGCF/PWGCFFEMTOSCOPYAODLinkDef.h [new file with mode: 0644]
PWGCF/PWGCFfemtoscopyLinkDef.h [new file with mode: 0644]
PWGCF/PWGCFfemtoscopyUserLinkDef.h [new file with mode: 0644]

diff --git a/PWGCF/CMakelibPWGCFFEMTOSCOPYAOD.pkg b/PWGCF/CMakelibPWGCFFEMTOSCOPYAOD.pkg
new file mode 100644 (file)
index 0000000..3d03438
--- /dev/null
@@ -0,0 +1,48 @@
+# -*- mode: CMake -*-
+#-----------------------------------------------------------------------#
+# Package File for PWGCFAOD                                              #
+# Author : Johny Jose (johny.jose@cern.ch)                              #
+# Variables Defined :                                                   #
+#                                                                       #
+# SRCS - C++ source files                                               #
+# HDRS - C++ header files                                               #
+# DHDR - ROOT Dictionary Linkdef header file                            #
+# CSRCS - C source files                                                #
+# CHDRS - C header files                                                #
+# EINCLUDE - Include directories                                        #
+# EDEFINE - Compiler definitions                                        #
+# ELIBS - Extra libraries to link                                       #
+# ELIBSDIR - Extra library directories                                  #
+# PACKFFLAGS - Fortran compiler flags for package                       #
+# PACKCXXFLAGS - C++ compiler flags for package                         #
+# PACKCFLAGS - C compiler flags for package                             #
+# PACKSOFLAGS - Shared library linking flags                            #
+# PACKLDFLAGS - Module linker flags                                     #
+# PACKBLIBS - Libraries to link (Executables only)                      #
+# EXPORT - Header files to be exported                                  #
+# CINTHDRS - Dictionary header files                                    #
+# CINTAUTOLINK - Set automatic dictionary generation                    #
+# ARLIBS - Archive Libraries and objects for linking (Executables only) #
+# SHLIBS - Shared Libraries and objects for linking (Executables only)  #
+#-----------------------------------------------------------------------#
+
+set ( SRCS  
+    FEMTOSCOPYAOD/AliPWG2AODTrack.cxx 
+    FEMTOSCOPYAOD/AliAnalysisTaskPWG2ESDfilter.cxx 
+    FEMTOSCOPYAOD/AliAnalysisTaskPWG2AODUpdate.cxx 
+    )
+
+string ( REPLACE ".cxx" ".h" HDRS "${SRCS}" )
+
+set ( DHDR PWGCFFEMTOSCOPYAODLinkDef.h)
+
+set ( EXPORT )
+
+set ( EINCLUDE  PYTHIA6 PWGCF/FEMTOSCOPYAOD STEER/AOD STEER/STEERBase)
+
+install (FILES centraltrain/AnalysisTrainPWGCF.C 
+         DESTINATION PWGCF/centraltrain)
+
+#
+# EOF
+#
diff --git a/PWGCF/CMakelibPWGCFfemtoscopy.pkg b/PWGCF/CMakelibPWGCFfemtoscopy.pkg
new file mode 100644 (file)
index 0000000..a132088
--- /dev/null
@@ -0,0 +1,152 @@
+# -*- mode: CMake -*-
+#------------------------------------------------------------------------#
+# Package File for PWG2femtoscopy                                        #
+# Author : Johny Jose (johny.jose@cern.ch)                               #
+# Variables Defined :                                                    #
+#                                                                        #
+# SRCS - C++ source files                                                #
+# HDRS - C++ header files                                                #
+# DHDR - ROOT Dictionary Linkdef header file                             #
+# CSRCS - C source files                                                 #
+# CHDRS - C header files                                                 #
+# EINCLUDE - Include directories                                         #
+# EDEFINE - Compiler definitions                                         #
+# ELIBS - Extra libraries to link                                        #
+# ELIBSDIR - Extra library directories                                   #
+# PACKFFLAGS - Fortran compiler flags for package                        #
+# PACKCXXFLAGS - C++ compiler flags for package                          #
+# PACKCFLAGS - C compiler flags for package                              #
+# PACKSOFLAGS - Shared library linking flags                             #
+# PACKLDFLAGS - Module linker flags                                      #
+# PACKBLIBS - Libraries to link (Executables only)                       #
+# EXPORT - Header files to be exported                                   #
+# CINTHDRS - Dictionary header files                                     #
+# CINTAUTOLINK - Set automatic dictionary generation                     #
+# ARLIBS - Archive Libraries and objects for linking (Executables only)  #
+# SHLIBS - Shared Libraries and objects for linking (Executables only)   #
+#------------------------------------------------------------------------#
+
+set ( SRCS  
+    FEMTOSCOPY/AliFemto/AliFemtoSimpleAnalysis.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoLikeSignAnalysis.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoVertexAnalysis.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoVertexMultAnalysis.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoAnalysisAzimuthal.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoAnalysisReactionPlane.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoBPLCMS3DCorrFctn.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoCorrFctn3DLCMSSym.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoQinvCorrFctn.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoBasicEventCut.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoEventCutEstimators.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoBasicTrackCut.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoDummyPairCut.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoCoulomb.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoCutMonitorHandler.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoEvent.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoKink.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoManager.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoPair.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoParticle.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoPicoEvent.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoPicoEventCollectionVectorHideAway.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoTrack.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoV0.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoXi.cxx 
+    FEMTOSCOPY/AliFemto/AliFmHelix.cxx 
+    FEMTOSCOPY/AliFemto/AliFmPhysicalHelix.cxx 
+    FEMTOSCOPY/AliFemto/TpcLocalTransform.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoEventReader.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoEventReaderStandard.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoEventReaderESD.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoEventReaderESDChain.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoEventReaderESDChainKine.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoModelHiddenInfo.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoModelGlobalHiddenInfo.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoModelGausLCMSFreezeOutGenerator.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoModelWeightGenerator.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoModelWeightGeneratorBasic.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoModelManager.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoModelCorrFctn.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoModelFreezeOutGenerator.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoModelWeightGeneratorLednicky.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoCutMonitorParticleYPt.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoCutMonitorParticleVertPos.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoCutMonitorParticlePID.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoCutMonitorEventMult.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoCutMonitorEventVertex.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoKTPairCut.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoCorrFctnNonIdDR.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoCorrFctn3DSpherical.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoEventReaderAOD.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoEventReaderAODChain.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoAODTrackCut.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoCutMonitor.cxx 
+    FEMTOSCOPY/AliFemto/AliFemtoCorrFctn.cxx 
+    FEMTOSCOPY/AliFemto/AliAnalysisTaskFemto.cxx 
+    FEMTOSCOPY/AliFemto/AliTwoTrackRes.cxx
+    FEMTOSCOPY/AliFemto/AliFemtoMCTrackCut.cxx
+    FEMTOSCOPY/AliFemto/AliFemtoEventReaderKinematicsChain.cxx
+    )
+
+string ( REPLACE ".cxx" ".h" HDRS "${SRCS}" )
+
+set ( HDRS ${HDRS}  
+    FEMTOSCOPY/AliFemto/AliFmThreeVector.h 
+    FEMTOSCOPY/AliFemto/AliFmThreeVectorF.h 
+    FEMTOSCOPY/AliFemto/AliFmThreeVectorD.h 
+    FEMTOSCOPY/AliFemto/AliFmPhysicalHelixD.h 
+    FEMTOSCOPY/AliFemto/AliFmHelixD.h 
+    FEMTOSCOPY/AliFemto/AliFmLorentzVectorD.h 
+    FEMTOSCOPY/AliFemto/AliFemtoV0Cut.h 
+    FEMTOSCOPY/AliFemto/AliFemtoKinkCut.h 
+    FEMTOSCOPY/AliFemto/AliFemtoXiCut.h 
+    FEMTOSCOPY/AliFemto/AliFemtoAnalysisCollection.h 
+    FEMTOSCOPY/AliFemto/AliFemtoAnalysis.h 
+    FEMTOSCOPY/AliFemto/AliFemtoCorrFctnCollection.h 
+    FEMTOSCOPY/AliFemto/AliFemtoEnumeration.h 
+    FEMTOSCOPY/AliFemto/AliFemtoHelix.h 
+    FEMTOSCOPY/AliFemto/AliFemtoHiddenInfo.h 
+    FEMTOSCOPY/AliFemto/AliFemtoLikeSignCorrFctn.h 
+    FEMTOSCOPY/AliFemto/AliFemtoLorentzVector.h 
+    FEMTOSCOPY/AliFemto/AliFemtoString.h 
+    FEMTOSCOPY/AliFemto/AliFemtoThreeVectorD.h 
+    FEMTOSCOPY/AliFemto/AliFemtoThreeVector.h 
+    FEMTOSCOPY/AliFemto/AliFemtoTypes.h 
+    FEMTOSCOPY/AliFemto/AliFemtoVector.h 
+    FEMTOSCOPY/AliFemto/AliFmLorentzVector.h 
+    FEMTOSCOPY/AliFemto/phys_constants.h 
+    FEMTOSCOPY/AliFemto/PhysicalConstants.h 
+    FEMTOSCOPY/AliFemto/SystemOfUnits.h 
+    FEMTOSCOPY/AliFemto/AliFemtoPairCut.h 
+    FEMTOSCOPY/AliFemto/AliFemtoEventCut.h 
+    FEMTOSCOPY/AliFemto/AliFemtoParticleCut.h 
+    FEMTOSCOPY/AliFemto/AliFemtoTrackCollection.h 
+    FEMTOSCOPY/AliFemto/AliFemtoV0Collection.h 
+    FEMTOSCOPY/AliFemto/AliFemtoXiCollection.h 
+    FEMTOSCOPY/AliFemto/AliFemtoKinkCollection.h 
+    FEMTOSCOPY/AliFemto/AliFemtoPicoEventCollection.h 
+    FEMTOSCOPY/AliFemto/AliFemtoParticleCollection.h 
+    FEMTOSCOPY/AliFemto/AliFemtoCutMonitorCollection.h 
+    FEMTOSCOPY/AliFemto/AliFemtoTrackCut.h 
+    FEMTOSCOPY/AliFemto/AliFemtoPicoEventCollectionVector.h 
+    FEMTOSCOPY/AliFemto/AliFemtoEventWriter.h 
+    FEMTOSCOPY/AliFemto/AliFemtoEventWriterCollection.h 
+    FEMTOSCOPY/AliFemto/AliFemtoMCTrackCut.h
+    FEMTOSCOPY/AliFemto/AliFemtoEventReaderKinematicsChain.h
+    )
+
+set ( FSRCS  FEMTOSCOPY/AliFemto/AliFemtoFsiTools.F FEMTOSCOPY/AliFemto/AliFemtoFsiWeightLednicky.F)
+
+set ( DHDR  PWGCFfemtoscopyLinkDef.h)
+
+set ( EXPORT )
+
+set ( EINCLUDE  PWGCF/FEMTOSCOPY/AliFemto PWGCF/AOD PWGCF/FORWARD/analysis STEER/AOD STEER/ESD STEER/STEERBase)
+
+install (DIRECTORY FEMTOSCOPY/macros
+         DESTINATION PWGCF/FEMTOSCOPY 
+         PATTERN .svn EXCLUDE)
+
+#
+# EOF
+#
diff --git a/PWGCF/CMakelibPWGCFfemtoscopyUser.pkg b/PWGCF/CMakelibPWGCFfemtoscopyUser.pkg
new file mode 100644 (file)
index 0000000..e800172
--- /dev/null
@@ -0,0 +1,41 @@
+#--------------------------------------------------------------------------------#
+# Package File for PWGCFfemtoscopyUser                                            #
+# Author : Johny Jose (johny.jose@cern.ch)                                       #
+# Variables Defined :                                                            #
+#                                                                                #
+# SRCS - C++ source files                                                        #
+# HDRS - C++ header files                                                        #
+# DHDR - ROOT Dictionary Linkdef header file                                     #
+# CSRCS - C source files                                                         #
+# CHDRS - C header files                                                         #
+# EINCLUDE - Include directories                                                 #
+# EDEFINE - Compiler definitions                                                 #
+# ELIBS - Extra libraries to link                                                #
+# ELIBSDIR - Extra library directories                                           #
+# PACKFFLAGS - Fortran compiler flags for package                                #
+# PACKCXXFLAGS - C++ compiler flags for package                                  #
+# PACKCFLAGS - C compiler flags for package                                      #
+# PACKSOFLAGS - Shared library linking flags                                     #
+# PACKLDFLAGS - Module linker flags                                              #
+# PACKBLIBS - Libraries to link (Executables only)                               #
+# EXPORT - Header files to be exported                                           #
+# CINTHDRS - Dictionary header files                                             #
+# CINTAUTOLINK - Set automatic dictionary generation                             #
+# ARLIBS - Archive Libraries and objects for linking (Executables only)          #
+# SHLIBS - Shared Libraries and objects for linking (Executables only)           #
+#--------------------------------------------------------------------------------#
+
+set ( SRCS  FEMTOSCOPY/AliFemtoUser/AliFemtoShareQualityPairCut.cxx FEMTOSCOPY/AliFemtoUser/AliFemtoShareQualityKTPairCut.cxx FEMTOSCOPY/AliFemtoUser/AliFemtoShareQualityTPCEntranceSepPairCut.cxx FEMTOSCOPY/AliFemtoUser/AliFemtoESDTrackCut.cxx FEMTOSCOPY/AliFemtoUser/AliFemtoTPCInnerCorrFctn.cxx FEMTOSCOPY/AliFemtoUser/AliFemtoChi2CorrFctn.cxx FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctnSource.cxx FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctnDEtaDPhi.cxx FEMTOSCOPY/AliFemtoUser/AliFemtoModelBPLCMSCorrFctn.cxx FEMTOSCOPY/AliFemtoUser/AliFemtoModelGausRinvFreezeOutGenerator.cxx FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctnTrueQ.cxx FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctnNonIdDR.cxx FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctn3DSpherical.cxx FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctn3DLCMSSpherical.cxx FEMTOSCOPY/AliFemtoUser/AliFemtoCutMonitorParticleMomRes.cxx FEMTOSCOPY/AliFemtoUser/AliFemtoModelAllHiddenInfo.cxx FEMTOSCOPY/AliFemtoUser/AliFemtoCutMonitorTrackTPCchiNdof.cxx FEMTOSCOPY/AliFemtoUser/AliFemtoQATrackCut.cxx FEMTOSCOPY/AliFemtoUser/AliFemtoQAEventCut.cxx FEMTOSCOPY/AliFemtoUser/AliFemtoCutMonitorTrackTPCncls.cxx FEMTOSCOPY/AliFemtoUser/AliFemtoShareQualityTPCEntranceSepQAPairCut.cxx FEMTOSCOPY/AliFemtoUser/AliFemtoShareQualityQAPairCut.cxx FEMTOSCOPY/AliFemtoUser/AliFemtoShareQualityCorrFctn.cxx FEMTOSCOPY/AliFemtoUser/AliFemtoYlm.cxx FEMTOSCOPY/AliFemtoUser/AliFemtoCorrFctnDirectYlm.cxx FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctnDirectYlm.cxx FEMTOSCOPY/AliFemtoUser/AliFemtoCutMonitorParticlePtPDG.cxx FEMTOSCOPY/AliFemtoUser/AliFemtoCorrFctnTPCNcls.cxx FEMTOSCOPY/AliFemtoUser/AliFemtoCorrFctnDEtaDPhi.cxx FEMTOSCOPY/AliFemtoUser/AliFemtoCorrFctnGammaMonitor.cxx FEMTOSCOPY/AliFemtoUser/AliFemtoQinvCorrFctnEMCIC.cxx FEMTOSCOPY/AliFemtoUser/AliFemtoCorrFctn3DSphericalEMCIC.cxx FEMTOSCOPY/AliFemtoUser/AliFemtoBPLCMS3DCorrFctnEMCIC.cxx FEMTOSCOPY/AliFemtoUser/AliFemtoPairCutAntiGamma.cxx FEMTOSCOPY/AliFemtoUser/AliFemtoCutMonitorParticleEtCorr.cxx FEMTOSCOPY/AliFemtoUser/AliFemtoPairCutRadialDistance.cxx FEMTOSCOPY/AliFemtoUser/AliFemtoPairCutPt.cxx)
+
+string ( REPLACE ".cxx" ".h" HDRS "${SRCS}" )
+
+set ( DHDR  PWGCFfemtoscopyUserLinkDef.h)
+
+set ( EXPORT )
+
+set ( EINCLUDE  PWGCF/FEMTOSCOPYAOD PWGCF/FEMTOSCOPY/AliFemto PWGCF/FEMTOSCOPY/AliFemtoUser)
+if( ALICE_TARGET STREQUAL "win32gcc")
+       
+               set ( PACKSOFLAGS  ${SOFLAGS} -L${ALICE_ROOT}/lib/tgt_${ALICE_TARGET} -lPWGCFAOD -lPWGCFfemtoscopy)
+
+endif( ALICE_TARGET STREQUAL "win32gcc")
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliAnalysisTaskFemto.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliAnalysisTaskFemto.cxx
new file mode 100644 (file)
index 0000000..fe3e52b
--- /dev/null
@@ -0,0 +1,516 @@
+//------------------------------------------------------
+// AliAnalysisTaskFemto - A task for the analysis framework
+// from the FEMTOSCOPY analysis of PWG2. Creates the necessary
+// connection between the ESD or AOD input and the femtoscopic
+// code.
+// Author: Adam Kisiel, OSU; Adam.Kisiel@cern.ch
+//------------------------------------------------------
+#include "TROOT.h"
+#include "TChain.h"
+#include "TH1.h"
+#include "TCanvas.h"
+#include "TSystem.h"
+#include "TFile.h"
+#include "TInterpreter.h"
+
+#include "AliAnalysisTask.h"
+
+#include "AliESDEvent.h"
+
+#include "AliFemtoAnalysis.h"
+#include "AliAnalysisTaskFemto.h"
+#include "AliVHeader.h"
+#include "AliGenEventHeader.h"
+#include "AliGenHijingEventHeader.h"
+#include "AliGenCocktailEventHeader.h"
+
+ClassImp(AliAnalysisTaskFemto)
+
+// Default name for the setup macro of femto analysis  
+// This function MUST be defined in the separate file !!!
+// extern AliFemtoManager *ConfigFemtoAnalysis();
+
+//________________________________________________________________________
+AliAnalysisTaskFemto::AliAnalysisTaskFemto(const char *name, const char *aConfigMacro, const char *aConfigParams):
+    AliAnalysisTask(name,""), 
+    fESD(0), 
+    fESDpid(0),
+    fAOD(0),
+    fAODpidUtil(0),
+    fStack(0),
+    fOutputList(0), 
+    fReader(0x0),
+    fManager(0x0),
+    fAnalysisType(0),
+    fConfigMacro(0),
+    fConfigParams(0)
+{
+  // Constructor.
+  // Input slot #0 works with an Ntuple
+  DefineInput(0, TChain::Class());
+  // Output slot #0 writes into a TH1 container
+  DefineOutput(0, TList::Class());
+  fConfigMacro = (char *) malloc(sizeof(char) * strlen(aConfigMacro));
+  strcpy(fConfigMacro, aConfigMacro);
+  fConfigParams = (char *) malloc(sizeof(char) * strlen(aConfigParams));
+  strcpy(fConfigParams, aConfigParams);
+}
+//________________________________________________________________________
+AliAnalysisTaskFemto::AliAnalysisTaskFemto(const char *name, const char *aConfigMacro="ConfigFemtoAnalysis.C"): 
+    AliAnalysisTask(name,""), 
+    fESD(0), 
+    fESDpid(0),
+    fAOD(0),
+    fAODpidUtil(0),
+    fStack(0),
+    fOutputList(0), 
+    fReader(0x0),
+    fManager(0x0),
+    fAnalysisType(0),
+    fConfigMacro(0),
+    fConfigParams(0)
+{
+  // Constructor.
+  // Input slot #0 works with an Ntuple
+  DefineInput(0, TChain::Class());
+  // Output slot #0 writes into a TH1 container
+  DefineOutput(0, TList::Class());
+  fConfigMacro = (char *) malloc(sizeof(char) * strlen(aConfigMacro));
+  strcpy(fConfigMacro, aConfigMacro);
+  fConfigParams = (char *) malloc(sizeof(char) * 2);
+  strcpy(fConfigParams, "");
+}
+
+AliAnalysisTaskFemto::AliAnalysisTaskFemto(const AliAnalysisTaskFemto& aFemtoTask):
+    AliAnalysisTask(aFemtoTask), 
+    fESD(0), 
+    fESDpid(0),
+    fAOD(0),
+    fAODpidUtil(0),
+    fStack(0),
+    fOutputList(0), 
+    fReader(0x0),
+    fManager(0x0),
+    fAnalysisType(0),
+    fConfigMacro(0),
+    fConfigParams(0)
+{
+  // copy constructor
+  fESD = aFemtoTask.fESD; 
+  fESDpid = aFemtoTask.fESDpid; 
+  fAOD = aFemtoTask.fAOD; 
+  fAODpidUtil = aFemtoTask.fAODpidUtil;
+  fStack = aFemtoTask.fStack;
+  fOutputList = aFemtoTask.fOutputList;   
+  fReader = aFemtoTask.fReader;       
+  fManager = aFemtoTask.fManager;      
+  fAnalysisType = aFemtoTask.fAnalysisType; 
+  fConfigMacro = (char *) malloc(sizeof(char) * strlen(aFemtoTask.fConfigMacro));
+  strcpy(fConfigMacro, aFemtoTask.fConfigMacro);
+  fConfigParams = (char *) malloc(sizeof(char) * strlen(aFemtoTask.fConfigParams));
+  strcpy(fConfigParams, aFemtoTask.fConfigParams);
+}
+
+
+AliAnalysisTaskFemto& AliAnalysisTaskFemto::operator=(const AliAnalysisTaskFemto& aFemtoTask){
+  // assignment operator
+  if (this == &aFemtoTask)
+    return *this;
+
+  fESD = aFemtoTask.fESD; 
+  fESDpid = aFemtoTask.fESDpid;
+  fAOD = aFemtoTask.fAOD; 
+  fAODpidUtil = aFemtoTask.fAODpidUtil;
+  fStack = aFemtoTask.fStack;
+  fOutputList = aFemtoTask.fOutputList;   
+  fReader = aFemtoTask.fReader;       
+  fManager = aFemtoTask.fManager;      
+  fAnalysisType = aFemtoTask.fAnalysisType; 
+  if (fConfigMacro) free(fConfigMacro);
+  fConfigMacro = (char *) malloc(sizeof(char) * strlen(aFemtoTask.fConfigMacro));
+  strcpy(fConfigMacro, aFemtoTask.fConfigMacro);
+  if (fConfigParams) free(fConfigParams);
+  fConfigParams = (char *) malloc(sizeof(char) * strlen(aFemtoTask.fConfigParams));
+  strcpy(fConfigParams, aFemtoTask.fConfigParams);
+
+  return *this;
+}
+
+AliAnalysisTaskFemto::~AliAnalysisTaskFemto() 
+{
+  if (fConfigMacro) free(fConfigMacro);
+  if (fConfigParams) free(fConfigParams);
+}
+
+
+//________________________________________________________________________
+void AliAnalysisTaskFemto::ConnectInputData(Option_t *) {
+  AliInfo(Form("   ConnectInputData %s\n", GetName()));
+
+  fESD = 0;
+  fESDpid = 0;
+  fAOD = 0;
+  fAODpidUtil = 0;
+  fAnalysisType = 0;
+
+  TTree* tree = dynamic_cast<TTree*> (GetInputData(0));
+  if (!tree) {
+    AliWarning("Could not read chain from input slot 0");
+    return;
+  } 
+
+  AliFemtoEventReaderESDChain *femtoReader = dynamic_cast<AliFemtoEventReaderESDChain *> (fReader);
+  if ((dynamic_cast<AliFemtoEventReaderESDChain *> (fReader))) {
+    AliESDInputHandler *esdH = dynamic_cast<AliESDInputHandler*> (AliAnalysisManager::GetAnalysisManager()->GetInputEventHandler());
+    
+    if(esdH) {
+      AliInfo("Selected ESD analysis");
+      fAnalysisType = 1;
+      
+//       if (!esdH) {
+//     AliWarning("Could not get ESDInputHandler");
+//       } 
+//       else {
+       fESD = esdH->GetEvent();
+        fESDpid = esdH->GetESDpid();
+        femtoReader->SetESDPid(fESDpid);
+//       }
+    }
+}
+  else if ((dynamic_cast<AliFemtoEventReaderKinematicsChain *> (fReader))) {
+    AliESDInputHandler *esdH = dynamic_cast<AliESDInputHandler*> (AliAnalysisManager::GetAnalysisManager()->GetInputEventHandler());
+    
+    if(esdH) {
+      AliInfo("Selected ESD analysis");
+      fAnalysisType = 1;
+      
+//       if (!esdH) {
+//     AliWarning("Could not get ESDInputHandler");
+//       } 
+//       else {
+       fESD = esdH->GetEvent();
+        //fESDpid = esdH->GetESDpid();
+        //femtoReader->SetESDPid(fESDpid);
+//       }
+    }
+  }
+
+
+  AliFemtoEventReaderESDChainKine *femtoReaderESDKine = dynamic_cast<AliFemtoEventReaderESDChainKine *> (fReader);
+  if ((dynamic_cast<AliFemtoEventReaderESDChainKine *> (fReader))) {
+    AliESDInputHandler *esdH = dynamic_cast<AliESDInputHandler*> (AliAnalysisManager::GetAnalysisManager()->GetInputEventHandler());
+    
+    if(esdH) {
+      AliInfo("Selected ESD analysis");
+      fAnalysisType = 1;
+      
+//       if (!esdH) {
+//     AliWarning("Could not get ESDInputHandler");
+//       } 
+//       else {
+       fESD = esdH->GetEvent();
+        fESDpid = esdH->GetESDpid();
+        femtoReaderESDKine->SetESDPid(fESDpid);
+//       }
+    }
+}
+
+  //  AliFemtoEventReaderKinematicsChain *femtoReaderKine = dynamic_cast<AliFemtoEventReaderKinematicsChain *> (fReader);
+  if ((dynamic_cast<AliFemtoEventReaderKinematicsChain *> (fReader))) {
+    AliESDInputHandler *esdH = dynamic_cast<AliESDInputHandler*> (AliAnalysisManager::GetAnalysisManager()->GetInputEventHandler());
+    
+    if(esdH) {
+      AliInfo("Selected ESD analysis");
+      fAnalysisType = 1;
+      
+      //       if (!esdH) {
+      //       AliWarning("Could not get ESDInputHandler");
+      //       } 
+      //       else {
+      fESD = esdH->GetEvent();
+      //fESDpid = esdH->GetESDpid();
+      //femtoReader->SetESDPid(fESDpid);
+      //       }
+    }
+  }
+  
+  
+  AliFemtoEventReaderAODChain *femtoReaderAOD = dynamic_cast<AliFemtoEventReaderAODChain *> (fReader);
+  if (dynamic_cast<AliFemtoEventReaderAODChain *> (fReader)) {
+    AliAODInputHandler *aodH = dynamic_cast<AliAODInputHandler*> (AliAnalysisManager::GetAnalysisManager()->GetInputEventHandler());
+    
+    if (!aodH) {
+      TObject *handler = AliAnalysisManager::GetAnalysisManager()->GetOutputEventHandler();
+      AliInfo("Has output handler ");
+      if( handler && handler->InheritsFrom("AliAODHandler") ) {
+       AliInfo("Selected AOD analysis");
+       
+       fAOD = ((AliAODHandler*)handler)->GetAOD();
+       fAnalysisType = 2;
+      }
+      else {
+       AliWarning("Selected AOD reader but no AOD handler found");
+      }
+    } 
+    else {
+      AliInfo("Selected AOD analysis");
+      fAnalysisType = 2;
+      
+      fAOD = aodH->GetEvent();
+
+      fAODpidUtil = aodH->GetAODpidUtil();
+      //      printf("aodH->GetAODpidUtil(): %x",aodH->GetAODpidUtil());
+      femtoReaderAOD->SetAODpidUtil(fAODpidUtil);
+    }
+  }
+
+  if ((!fAOD) && (!fESD)) {
+    AliWarning("Wrong analysis type: Only ESD and AOD types are allowed!");
+  }
+}
+
+//________________________________________________________________________
+void AliAnalysisTaskFemto::CreateOutputObjects() {
+  AliInfo("Creating Femto Analysis objects\n");
+
+  gSystem->SetIncludePath("-I$ROOTSYS/include -I./STEERBase/ -I./ESD/ -I./AOD/ -I./ANALYSIS/ -I./ANALYSISalice/ -I./PWG2AOD/AOD -I./PWG2femtoscopy/FEMTOSCOPY/AliFemto -I./PWG2femtoscopyUser/FEMTOSCOPY/AliFemtoUser");
+  //  char fcm[2000];
+//   sprintf(fcm, "%s++", fConfigMacro);
+//   gROOT->LoadMacro(fcm);
+  gROOT->LoadMacro(fConfigMacro);
+  //  fJetFinder = (AliJetFinder*) gInterpreter->ProcessLine("ConfigJetAnalysis()");
+  if (!fConfigParams)
+    SetFemtoManager((AliFemtoManager *) gInterpreter->ProcessLine("ConfigFemtoAnalysis()"));
+  else
+    SetFemtoManager((AliFemtoManager *) gInterpreter->ProcessLine(Form("ConfigFemtoAnalysis(%s)", fConfigParams)));
+
+  TList *tOL;
+  fOutputList = fManager->Analysis(0)->GetOutputList();
+
+  for (unsigned int ian = 1; ian<fManager->AnalysisCollection()->size(); ian++) {
+    tOL = fManager->Analysis(ian)->GetOutputList();
+
+    TIter nextListCf(tOL);
+    while (TObject *obj = nextListCf()) {
+      fOutputList->Add(obj);
+    }
+
+    delete tOL;
+  }
+
+  PostData(0, fOutputList);
+}
+
+//________________________________________________________________________
+void AliAnalysisTaskFemto::Exec(Option_t *) {
+  // Task making a femtoscopic analysis.
+
+  if (fAnalysisType==1) {
+    if (!fESD) {
+      AliWarning("fESD not available");
+      return;
+    }
+
+    //Get MC data
+    AliMCEventHandler*    mctruth = (AliMCEventHandler*) 
+      ((AliAnalysisManager::GetAnalysisManager())->GetMCtruthEventHandler());
+    
+    AliGenHijingEventHeader *hdh = 0;
+    if(mctruth) {
+      fStack = mctruth->MCEvent()->Stack();
+
+      AliGenCocktailEventHeader *hd = dynamic_cast<AliGenCocktailEventHeader *> (mctruth->MCEvent()->GenEventHeader());
+      
+      if (hd) {
+       
+       //      AliInfo ("Got MC cocktail event header %p\n", (void *) hd);
+       TList *lhd = hd->GetHeaders();
+       //      AliInfo ("Got list of headers %d\n", lhd->GetEntries());
+       
+       for (int iterh=0; iterh<lhd->GetEntries(); iterh++) 
+         {
+           hdh = dynamic_cast<AliGenHijingEventHeader *> (lhd->At(iterh));
+           //      AliInfo ("HIJING header at %i is %p\n", iterh, (void *) hdh);
+         }
+      }    
+    }
+
+    // Get ESD
+    AliESDInputHandler *esdH = dynamic_cast<AliESDInputHandler*> (AliAnalysisManager::GetAnalysisManager()->GetInputEventHandler());
+    
+    if (!esdH) {
+      AliWarning("Could not get ESDInputHandler");
+      return;
+    } 
+    else {
+      fESD = esdH->GetEvent();
+      fESDpid = esdH->GetESDpid();   
+    }
+
+    AliInfo(Form("Tracks in ESD: %d \n",fESD->GetNumberOfTracks()));
+
+    if (fESD->GetNumberOfTracks() >= 0) {
+    
+      if (!fReader) {
+       AliWarning("No ESD reader for ESD analysis !\n");
+      }
+      
+      AliFemtoEventReaderESDChain* fesdc = dynamic_cast<AliFemtoEventReaderESDChain *> (fReader);
+      if (fesdc)
+       {
+         // Process the event with no Kine information
+         fesdc->SetESDSource(fESD);
+         fManager->ProcessEvent();
+       }
+
+       AliFemtoEventReaderKinematicsChain* fkinec = dynamic_cast<AliFemtoEventReaderKinematicsChain *> (fReader);
+      if (fkinec)
+       {
+         // Process the event with Kine information only
+         fkinec->SetStackSource(fStack);
+         fManager->ProcessEvent();
+       }
+
+
+      AliFemtoEventReaderESDChainKine* fesdck = dynamic_cast<AliFemtoEventReaderESDChainKine *> (fReader);
+      if (fesdck) 
+       {
+         // Process the event with Kine information
+         fesdck->SetESDSource(fESD);
+         fesdck->SetStackSource(fStack);
+         
+         fesdck->SetGenEventHeader(hdh);
+         fManager->ProcessEvent();
+       }
+      AliFemtoEventReaderStandard* fstd = dynamic_cast<AliFemtoEventReaderStandard *> (fReader);
+      if (fstd) 
+       {
+         // Process the event with Kine information
+         fstd->SetESDSource(fESD);
+         if (mctruth) {
+           fstd->SetStackSource(fStack);
+           fstd->SetGenEventHeader(hdh);
+           fstd->SetInputType(AliFemtoEventReaderStandard::kESDKine);
+         }
+         else
+           fstd->SetInputType(AliFemtoEventReaderStandard::kESD);
+         fManager->ProcessEvent();
+       }
+    } 
+
+    // Post the output histogram list
+    PostData(0, fOutputList);
+  }
+
+  if (fAnalysisType==2) {    
+    if (!fAOD) {
+      AliWarning("fAOD not available");
+      return;
+    }
+
+    // Get AOD
+//     AliAODInputHandler *aodH = dynamic_cast<AliAODInputHandler*> (AliAnalysisManager::GetAnalysisManager()->GetInputEventHandler());
+      
+//     if (!aodH) {
+//       AliWarning("Could not get AODInputHandler");
+//       return;
+//     } 
+//     else {
+
+//       fAOD = aodH->GetEvent();
+//     }
+
+    AliInfo(Form("Tracks in AOD: %d \n",fAOD->GetNumberOfTracks()));
+    
+    if (fAOD->GetNumberOfTracks() > 0) {
+      if (!fReader) {
+       AliWarning("No AOD reader for AOD analysis! \n");
+      }
+      else {
+       AliFemtoEventReaderAODChain* faodc = dynamic_cast<AliFemtoEventReaderAODChain *> (fReader);
+
+       if (faodc) {
+         // Process the event
+         faodc->SetAODSource(fAOD);
+         fManager->ProcessEvent();
+       }
+       AliFemtoEventReaderStandard* fstd = dynamic_cast<AliFemtoEventReaderStandard *> (fReader);
+
+       if (fstd) {
+         // Process the event
+         fstd->SetAODSource(fAOD);
+         fstd->SetInputType(AliFemtoEventReaderStandard::kAOD);
+         fManager->ProcessEvent();
+       }
+      }
+    } 
+
+    // Post the output histogram list
+    PostData(0, fOutputList);
+  }
+}      
+
+//________________________________________________________________________
+void AliAnalysisTaskFemto::Terminate(Option_t *) {
+  // Do the final processing
+  if (fManager) {
+    fManager->Finish();
+  }
+}
+//________________________________________________________________________
+void AliAnalysisTaskFemto:: FinishTaskOutput() {
+  // Do the final processing
+  if (fManager) {
+    fManager->Finish();
+  }
+}
+//________________________________________________________________________
+void AliAnalysisTaskFemto::SetFemtoReaderESD(AliFemtoEventReaderESDChain *aReader)
+{
+  AliInfo("Selecting Femto reader for ESD\n");
+  fReader = aReader;
+}
+//________________________________________________________________________
+void AliAnalysisTaskFemto::SetFemtoReaderESDKine(AliFemtoEventReaderESDChainKine *aReader)
+{
+  AliInfo("Selecting Femto reader for ESD with Kinematics information\n");
+  fReader = aReader;
+}
+//________________________________________________________________________
+void AliAnalysisTaskFemto::SetFemtoReaderAOD(AliFemtoEventReaderAODChain *aReader)
+{
+  AliInfo("Selecting Femto reader for AOD\n");
+  fReader = aReader;
+}
+void AliAnalysisTaskFemto::SetFemtoReaderStandard(AliFemtoEventReaderStandard *aReader)
+{
+  AliInfo("Selecting Standard all-purpose Femto reader\n");
+  fReader = aReader;
+}
+void AliAnalysisTaskFemto::SetFemtoReaderKinematics(AliFemtoEventReaderKinematicsChain *aReader)
+{
+  printf("Selecting Femto reader for Kinematics (Monte Carlo) information\n");
+  fReader = aReader;
+}
+//________________________________________________________________________
+void AliAnalysisTaskFemto::SetFemtoManager(AliFemtoManager *aManager)
+{
+  fManager = aManager;
+  AliInfo(Form("Got reader %p\n", (void *) aManager->EventReader()));
+  AliFemtoEventReaderESDChain     *tReaderESDChain     = dynamic_cast<AliFemtoEventReaderESDChain *> (aManager->EventReader());
+  AliFemtoEventReaderESDChainKine *tReaderESDChainKine = dynamic_cast<AliFemtoEventReaderESDChainKine *> (aManager->EventReader());
+  AliFemtoEventReaderAODChain     *tReaderAODChain     = dynamic_cast<AliFemtoEventReaderAODChain *> (aManager->EventReader());
+  AliFemtoEventReaderStandard     *tReaderStandard     = dynamic_cast<AliFemtoEventReaderStandard *> (aManager->EventReader());
+  AliFemtoEventReaderKinematicsChain *tReaderKineChain = dynamic_cast<AliFemtoEventReaderKinematicsChain *> (aManager->EventReader());
+
+ if ((!tReaderESDChain) && (!tReaderESDChainKine) && (!tReaderAODChain) && (!tReaderStandard) && (!tReaderKineChain)) {
+    AliWarning("No AliFemto event reader created. Will not run femto analysis.\n");
+    return;
+  }
+  if (tReaderESDChain) SetFemtoReaderESD(tReaderESDChain);
+  if (tReaderESDChainKine) SetFemtoReaderESDKine(tReaderESDChainKine);
+  if (tReaderAODChain) SetFemtoReaderAOD(tReaderAODChain);
+  if (tReaderStandard) SetFemtoReaderStandard(tReaderStandard);
+  if (tReaderKineChain) SetFemtoReaderKinematics(tReaderKineChain);
+}
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliAnalysisTaskFemto.h b/PWGCF/FEMTOSCOPY/AliFemto/AliAnalysisTaskFemto.h
new file mode 100644 (file)
index 0000000..711f450
--- /dev/null
@@ -0,0 +1,78 @@
+//------------------------------------------------------
+// AliAnalysisTaskFemto - A task for the analysis framework
+// from the FEMTOSCOPY analysis of PWG2. Creates the necessary
+// connection between the ESD or AOD input and the femtoscopic
+// code.
+// Author: Adam Kisiel, OSU; Adam.Kisiel@cern.ch
+//------------------------------------------------------
+#ifndef ALIANALYSISTASKFEMTO_H
+#define ALIANALYSISTASKFEMTO_H
+
+#include "TH1.h"
+
+#include "AliESDInputHandler.h"
+#include "AliAODHandler.h"
+#include "AliAODInputHandler.h"
+#include "AliMCEventHandler.h"
+#include "AliESDEvent.h"
+#include "AliAODEvent.h"
+#include "AliMCEvent.h"
+
+#include "AliAnalysisTask.h"
+#include "AliAnalysisManager.h"
+#include "AliAnalysisDataContainer.h"
+
+#include "AliFemtoEventReaderESDChain.h"
+#include "AliFemtoEventReaderESDChainKine.h"
+#include "AliFemtoEventReaderAODChain.h"
+#include "AliFemtoEventReaderStandard.h"
+#include "AliFemtoEventReaderKinematicsChain.h"
+#include "AliFemtoManager.h"
+
+#include "AliESDpid.h"
+#include "AliAODpidUtil.h"
+
+
+class AliAnalysisTaskFemto : public AliAnalysisTask {
+ public:
+  AliAnalysisTaskFemto() : AliAnalysisTask(), fESD(0), fESDpid(0), fAOD(0), fAODpidUtil(0), fStack(0), fOutputList(0), fReader(0x0), fManager(0x0), fAnalysisType(0), fConfigMacro(0), fConfigParams(0) {}
+  AliAnalysisTaskFemto(const char *name, const char *aConfigMacro, const char *aConfigParams);
+  AliAnalysisTaskFemto(const char *name, const char *aConfigMacro);
+  AliAnalysisTaskFemto(const AliAnalysisTaskFemto& aFemtoTask);
+  virtual ~AliAnalysisTaskFemto();
+  
+  AliAnalysisTaskFemto& operator=(const AliAnalysisTaskFemto& aFemtoTask);
+
+  virtual void   ConnectInputData(Option_t *);
+  virtual void   CreateOutputObjects();
+  virtual void   Exec(Option_t *option);
+  virtual void   Terminate(Option_t *);
+  virtual void   FinishTaskOutput();
+
+  void SetFemtoReaderESD(AliFemtoEventReaderESDChain *aReader);
+  void SetFemtoReaderESDKine(AliFemtoEventReaderESDChainKine *aReader);
+  void SetFemtoReaderAOD(AliFemtoEventReaderAODChain *aReader);
+  void SetFemtoReaderStandard(AliFemtoEventReaderStandard *aReader);
+  void SetFemtoManager(AliFemtoManager *aManager);
+  void SetFemtoReaderKinematics(AliFemtoEventReaderKinematicsChain *aReader);
+
+ private:
+  AliESDEvent                 *fESD;          //! ESD object
+  AliESDpid                   *fESDpid;       //! ESDpid object
+  AliAODEvent                 *fAOD;          //! AOD object
+  AliAODpidUtil               *fAODpidUtil;   // AliAODpidUtil object
+
+  AliStack                    *fStack;        //! Stack from Kinematics
+  TList                       *fOutputList;   //  AliFemto results list
+  AliFemtoEventReader         *fReader;       //! Reference to the reader
+  AliFemtoManager             *fManager;      //! AliFemto top-level manager 
+  int                          fAnalysisType; //  Mark ESD of AOD analysis
+  char                        *fConfigMacro;  //  Config macro location
+  char                        *fConfigParams; //  Config macro parameters
+
+
+  ClassDef(AliAnalysisTaskFemto, 3); // example of analysis
+};
+
+#endif
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoAODTrackCut.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoAODTrackCut.cxx
new file mode 100644 (file)
index 0000000..2c60d50
--- /dev/null
@@ -0,0 +1,374 @@
+/***************************************************************************
+ *
+ * $Id: AliFemtoAODTrackCut.cxx 23733 2008-02-05 16:51:41Z akisiel $ 
+ *
+ * 
+ ***************************************************************************
+ *
+ * 
+ *              
+ *
+ ***************************************************************************
+ *
+ * $Log$
+ * Revision 1.3  2007/05/22 09:01:42  akisiel
+ * Add the possibiloity to save cut settings in the ROOT file
+ *
+ * Revision 1.2  2007/05/21 10:38:25  akisiel
+ * More coding rule conformance
+ *
+ * Revision 1.1  2007/05/16 10:25:06  akisiel
+ * Making the directory structure of AliFemtoUser flat. All files go into one common directory
+ *
+ * Revision 1.4  2007/05/03 09:46:10  akisiel
+ * Fixing Effective C++ warnings
+ *
+ * Revision 1.3  2007/04/27 07:25:59  akisiel
+ * Make revisions needed for compilation from the main AliRoot tree
+ *
+ * Revision 1.1.1.1  2007/04/25 15:38:41  panos
+ * Importing the HBT code dir
+ *
+ * Revision 1.4  2007-04-03 16:00:08  mchojnacki
+ * Changes to iprove memory managing
+ *
+ * Revision 1.3  2007/03/13 15:30:03  mchojnacki
+ * adding reader for simulated data
+ *
+ * Revision 1.2  2007/03/08 14:58:03  mchojnacki
+ * adding some alice stuff
+ *
+ * Revision 1.1.1.1  2007/03/07 10:14:49  mchojnacki
+ * First version on CVS
+ *
+ **************************************************************************/
+
+#include "AliFemtoAODTrackCut.h"
+#include <cstdio>
+
+#ifdef __ROOT__ 
+ClassImp(AliFemtoAODTrackCut)
+#endif
+
+
+// electron
+// 0.13 - 1.8
+// 0       7.594129e-02    8.256141e-03
+// 1       -5.535827e-01   8.170825e-02
+// 2       1.728591e+00    3.104210e-01
+// 3       -2.827893e+00   5.827802e-01
+// 4       2.503553e+00    5.736207e-01
+// 5       -1.125965e+00   2.821170e-01
+// 6       2.009036e-01    5.438876e-02
+
+// pion
+// 0.13 - 2.0
+// 0       1.063457e+00    8.872043e-03
+// 1       -4.222208e-01   2.534402e-02
+// 2       1.042004e-01    1.503945e-02
+
+// kaon
+// 0.18 - 2.0
+// 0       -7.289406e-02   1.686074e-03
+// 1       4.415666e-01    1.143939e-02
+// 2       -2.996790e-01   1.840964e-02
+// 3       6.704652e-02    7.783990e-03
+
+// proton
+// 0.26 - 2.0
+// 0       -3.730200e-02   2.347311e-03
+// 1       1.163684e-01    1.319316e-02
+// 2       8.354116e-02    1.997948e-02
+// 3       -4.608098e-02   8.336400e-03
+
+
+AliFemtoAODTrackCut::AliFemtoAODTrackCut() :
+    fCharge(0),
+    fLabel(0),
+    fMaxchiNdof(1000.0),
+    fMaxSigmaToVertex(1000.0),
+    fNTracksPassed(0),
+    fNTracksFailed(0),
+    fMostProbable(0)
+{
+  // Default constructor
+  fNTracksPassed = fNTracksFailed = 0;
+  fCharge = 0;  // takes both charges 0
+  fPt[0]=0.0;              fPt[1] = 100.0;//100
+  fRapidity[0]=-2;       fRapidity[1]=2;//-2 2
+  fPidProbElectron[0]=-1;fPidProbElectron[1]=2;
+  fPidProbPion[0]=-1;    fPidProbPion[1]=2;
+  fPidProbKaon[0]=-1;fPidProbKaon[1]=2;
+  fPidProbProton[0]=-1;fPidProbProton[1]=2;
+  fPidProbMuon[0]=-1;fPidProbMuon[1]=2;
+  fLabel=false;
+}
+//------------------------------
+AliFemtoAODTrackCut::~AliFemtoAODTrackCut(){
+  /* noop */
+}
+//------------------------------
+bool AliFemtoAODTrackCut::Pass(const AliFemtoTrack* track)
+{
+  // test the particle and return 
+  // true if it meets all the criteria
+  // false if it doesn't meet at least one of the criteria
+  float tMost[5];
+  
+  if (((track->ITSchi2() + track->TPCchi2())/(track->ITSncls() + track->TPCncls())) > fMaxchiNdof) {
+    return false;
+  }
+
+  if (fMaxSigmaToVertex < track->SigmaToVertex()) {
+    return false;
+  }
+  
+  if (fLabel)
+    {
+      //cout<<"labels"<<endl;
+      if(track->Label()<0)
+       {
+         fNTracksFailed++;
+         //   cout<<"No Go Through the cut"<<endl;
+         //  cout<<fLabel<<" Label="<<track->Label()<<endl;
+         return false;
+       }    
+    }
+  if (fCharge!=0)
+    {              
+      //cout<<"AliFemtoESD  cut ch "<<endl;
+      //cout<<fCharge<<" Charge="<<track->Charge()<<endl;
+      if (track->Charge()!= fCharge)   
+       {
+         fNTracksFailed++;
+         //  cout<<"No Go Through the cut"<<endl;
+         // cout<<fCharge<<" Charge="<<track->Charge()<<endl;
+         return false;
+       }
+    }
+  float tEnergy = ::sqrt(track->P().Mag2()+fMass*fMass);
+  float tRapidity = 0.5*::log((tEnergy+track->P().z())/(tEnergy-track->P().z()));
+  float tPt = ::sqrt((track->P().x())*(track->P().x())+(track->P().y())*(track->P().y()));
+  if ((tRapidity<fRapidity[0])||(tRapidity>fRapidity[1]))
+    {
+      fNTracksFailed++;
+      //cout<<"No Go Through the cut"<<endl;   
+      //cout<<fRapidity[0]<<" < Rapidity ="<<tRapidity<<" <"<<fRapidity[1]<<endl;
+      return false;
+    }
+  if ((tPt<fPt[0])||(tPt>fPt[1]))
+    {
+      fNTracksFailed++;
+      //cout<<"No Go Through the cut"<<endl;
+      //cout<<fPt[0]<<" < Pt ="<<Pt<<" <"<<fPt[1]<<endl;
+      return false;
+    }
+
+    
+  if ((track->PidProbElectron()<fPidProbElectron[0])||(track->PidProbElectron()>fPidProbElectron[1]))
+    {
+      fNTracksFailed++;
+      //cout<<"No Go Through the cut"<<endl;
+      //cout<<fPidProbElectron[0]<<" < e ="<<track->PidProbElectron()<<" <"<<fPidProbElectron[1]<<endl;
+      return false;
+    }
+  if ((track->PidProbPion()<fPidProbPion[0])||(track->PidProbPion()>fPidProbPion[1]))
+    {
+      fNTracksFailed++;
+      //cout<<"No Go Through the cut"<<endl;
+      //cout<<fPidProbPion[0]<<" < pi ="<<track->PidProbPion()<<" <"<<fPidProbPion[1]<<endl;
+      return false;
+    }
+  if ((track->PidProbKaon()<fPidProbKaon[0])||(track->PidProbKaon()>fPidProbKaon[1]))
+    {
+      fNTracksFailed++;
+      //cout<<"No Go Through the cut"<<endl;
+      //cout<<fPidProbKaon[0]<<" < k ="<<track->PidProbKaon()<<" <"<<fPidProbKaon[1]<<endl;
+      return false;
+    }
+  if ((track->PidProbProton()<fPidProbProton[0])||(track->PidProbProton()>fPidProbProton[1]))
+    {
+      fNTracksFailed++;
+      //cout<<"No Go Through the cut"<<endl;
+      //cout<<fPidProbProton[0]<<" < p  ="<<track->PidProbProton()<<" <"<<fPidProbProton[1]<<endl;
+      return false;
+    }
+  if ((track->PidProbMuon()<fPidProbMuon[0])||(track->PidProbMuon()>fPidProbMuon[1]))
+    {
+      fNTracksFailed++;
+      //cout<<"No Go Through the cut"<<endl;
+      //cout<<fPidProbMuon[0]<<" <  mi="<<track->PidProbMuon()<<" <"<<fPidProbMuon[1]<<endl;
+      return false;
+    }
+
+  if (fMostProbable) {
+    tMost[0] = track->PidProbElectron()*PidFractionElectron(track->P().Mag());
+    tMost[1] = 0.0;
+    tMost[2] = track->PidProbPion()*PidFractionPion(track->P().Mag());
+    tMost[3] = track->PidProbKaon()*PidFractionKaon(track->P().Mag());
+    tMost[4] = track->PidProbProton()*PidFractionProton(track->P().Mag());
+    int imost=0;
+    float ipidmax = 0.0;
+    for (int ip=0; ip<5; ip++)
+      if (tMost[ip] > ipidmax) { ipidmax = tMost[ip]; imost = ip; };
+    if (imost != fMostProbable) return false;
+  }
+  
+  // cout<<"Go Through the cut"<<endl;
+  // cout<<fLabel<<" Label="<<track->Label()<<endl;
+  // cout<<fCharge<<" Charge="<<track->Charge()<<endl;
+  // cout<<fPt[0]<<" < Pt ="<<Pt<<" <"<<fPt[1]<<endl;
+  //cout<<fRapidity[0]<<" < Rapidity ="<<tRapidity<<" <"<<fRapidity[1]<<endl;
+  //cout<<fPidProbElectron[0]<<" <  e="<<track->PidProbElectron()<<" <"<<fPidProbElectron[1]<<endl;
+  //cout<<fPidProbPion[0]<<" <  pi="<<track->PidProbPion()<<" <"<<fPidProbPion[1]<<endl;
+  //cout<<fPidProbKaon[0]<<" <  k="<<track->PidProbKaon()<<" <"<<fPidProbKaon[1]<<endl;
+  //cout<<fPidProbProton[0]<<" <  p="<<track->PidProbProton()<<" <"<<fPidProbProton[1]<<endl;
+  //cout<<fPidProbMuon[0]<<" <  mi="<<track->PidProbMuon()<<" <"<<fPidProbMuon[1]<<endl;
+  fNTracksPassed++ ;
+  return true;
+    
+    
+}
+//------------------------------
+AliFemtoString AliFemtoAODTrackCut::Report()
+{
+  // Prepare report from the execution
+  string tStemp;
+  char tCtemp[100];
+  snprintf(tCtemp , 100, "Particle mass:\t%E\n",this->Mass());
+  tStemp=tCtemp;
+  snprintf(tCtemp , 100, "Particle charge:\t%d\n",fCharge);
+  tStemp+=tCtemp;
+  snprintf(tCtemp , 100, "Particle pT:\t%E - %E\n",fPt[0],fPt[1]);
+  tStemp+=tCtemp;
+  snprintf(tCtemp , 100, "Particle rapidity:\t%E - %E\n",fRapidity[0],fRapidity[1]);
+  tStemp+=tCtemp;
+  snprintf(tCtemp , 100, "Number of tracks which passed:\t%ld  Number which failed:\t%ld\n",fNTracksPassed,fNTracksFailed);
+  tStemp += tCtemp;
+  AliFemtoString returnThis = tStemp;
+  return returnThis;
+}
+TList *AliFemtoAODTrackCut::ListSettings()
+{
+  // return a list of settings in a writable form
+  TList *tListSetttings = new TList();
+  char buf[200];
+  snprintf(buf, 200, "AliFemtoAODTrackCut.mass=%f", this->Mass());
+  tListSetttings->AddLast(new TObjString(buf));
+
+  snprintf(buf, 200, "AliFemtoAODTrackCut.charge=%i", fCharge);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoAODTrackCut.pidprobpion.minimum=%f", fPidProbPion[0]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoAODTrackCut.pidprobpion.maximum=%f", fPidProbPion[1]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoAODTrackCut.pidprobkaon.minimum=%f", fPidProbKaon[0]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoAODTrackCut.pidprobkaon.maximum=%f", fPidProbKaon[1]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoAODTrackCut.pidprobproton.minimum=%f", fPidProbProton[0]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoAODTrackCut.pidprobproton.maximum=%f", fPidProbProton[1]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoAODTrackCut.pidprobelectron.minimum=%f", fPidProbElectron[0]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoAODTrackCut.pidprobelectron.maximum=%f", fPidProbElectron[1]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoAODTrackCut.pidprobMuon.minimum=%f", fPidProbMuon[0]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoAODTrackCut.pidprobMuon.maximum=%f", fPidProbMuon[1]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoAODTrackCut.pt.minimum=%f", fPt[0]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoAODTrackCut.pt.maximum=%f", fPt[1]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoAODTrackCut.rapidity.minimum=%f", fRapidity[0]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoAODTrackCut.rapidity.maximum=%f", fRapidity[1]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoAODTrackCut.maxchindof=%f", fMaxchiNdof);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoAODTrackCut.maxsigmatovertex=%f", fMaxSigmaToVertex);
+  tListSetttings->AddLast(new TObjString(buf));
+  if (fMostProbable) {
+    if (fMostProbable == 2)
+      snprintf(buf, 200, "AliFemtoAODTrackCut.mostprobable=%s", "Pion");
+    if (fMostProbable == 3)
+      snprintf(buf, 200, "AliFemtoAODTrackCut.mostprobable=%s", "Kaon");
+    if (fMostProbable == 4)
+      snprintf(buf, 200, "AliFemtoAODTrackCut.mostprobable=%s", "Proton");
+    tListSetttings->AddLast(new TObjString(buf));
+  }
+  return tListSetttings;
+}
+                           // electron
+// 0.13 - 1.8
+// 0       7.594129e-02    8.256141e-03
+// 1       -5.535827e-01   8.170825e-02
+// 2       1.728591e+00    3.104210e-01
+// 3       -2.827893e+00   5.827802e-01
+// 4       2.503553e+00    5.736207e-01
+// 5       -1.125965e+00   2.821170e-01
+// 6       2.009036e-01    5.438876e-02
+float AliFemtoAODTrackCut::PidFractionElectron(float mom) const
+{
+  // Provide a parameterized fraction of electrons dependent on momentum
+  if (mom<0.13) return 0.0;
+  if (mom>1.8) return 0.0;
+  return (7.594129e-02 
+         -5.535827e-01*mom        
+         +1.728591e+00*mom*mom    
+         -2.827893e+00*mom*mom*mom 
+         +2.503553e+00*mom*mom*mom*mom    
+         -1.125965e+00*mom*mom*mom*mom*mom      
+         +2.009036e-01*mom*mom*mom*mom*mom*mom);   
+}
+
+// pion
+// 0.13 - 2.0
+// 0       1.063457e+00    8.872043e-03
+// 1       -4.222208e-01   2.534402e-02
+// 2       1.042004e-01    1.503945e-02
+float AliFemtoAODTrackCut::PidFractionPion(float mom) const
+{
+  // Provide a parameterized fraction of pions dependent on momentum
+  if (mom<0.13) return 0.0;
+  if (mom>2.0) return 0.0;
+  return ( 1.063457e+00
+          -4.222208e-01*mom
+          +1.042004e-01*mom*mom);
+}
+
+// kaon
+// 0.18 - 2.0
+// 0       -7.289406e-02   1.686074e-03
+// 1       4.415666e-01    1.143939e-02
+// 2       -2.996790e-01   1.840964e-02
+// 3       6.704652e-02    7.783990e-03
+float AliFemtoAODTrackCut::PidFractionKaon(float mom) const
+{
+  // Provide a parameterized fraction of kaons dependent on momentum
+  if (mom<0.18) return 0.0;
+  if (mom>2.0) return 0.0;
+  return (-7.289406e-02
+         +4.415666e-01*mom        
+         -2.996790e-01*mom*mom    
+         +6.704652e-02*mom*mom*mom);
+}
+
+// proton
+// 0.26 - 2.0
+// 0       -3.730200e-02   2.347311e-03
+// 1       1.163684e-01    1.319316e-02
+// 2       8.354116e-02    1.997948e-02
+// 3       -4.608098e-02   8.336400e-03
+float AliFemtoAODTrackCut::PidFractionProton(float mom) const
+{
+  // Provide a parameterized fraction of protons dependent on momentum
+  if (mom<0.26) return  0.0;
+  if (mom>2.0) return 0.0;
+  return (-3.730200e-02  
+         +1.163684e-01*mom           
+         +8.354116e-02*mom*mom       
+         -4.608098e-02*mom*mom*mom);  
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoAODTrackCut.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoAODTrackCut.h
new file mode 100644 (file)
index 0000000..4d7454c
--- /dev/null
@@ -0,0 +1,94 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFemtoAODTrackCut: A basic track cut that used information from     //
+// ALICE AOD to accept or reject the track.                              //  
+// Enables the selection on charge, transverse momentum, rapidity,       //
+// pid probabilities, number of ITS and TPC clusters                     //
+// Author: Adam Kisiel (WUT, OSU), Adam.Kisiel@cern.ch                   //
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+
+#ifndef ALIFEMTOAODTRACKCUT_H
+#define ALIFEMTOAODTRACKCUT_H
+
+//#ifndef StMaker_H
+//#include "StMaker.h"
+//#endif
+
+#include "AliFemtoTrackCut.h"
+
+class AliFemtoAODTrackCut : public AliFemtoTrackCut 
+{
+
+ public:
+  AliFemtoAODTrackCut();
+  virtual ~AliFemtoAODTrackCut();
+
+  virtual bool Pass(const AliFemtoTrack* aTrack);
+
+  virtual AliFemtoString Report();
+  virtual TList *ListSettings();
+  virtual AliFemtoParticleType Type(){return hbtTrack;}
+
+  void SetPt(const float& lo, const float& hi);
+  void SetRapidity(const float& lo, const float& hi);
+  void SetCharge(const int& ch);
+  void SetPidProbElectron(const float& lo, const float& hi);
+  void SetPidProbPion(const float& lo, const float& hi);
+  void SetPidProbKaon(const float& lo, const float& hi);
+  void SetPidProbProton(const float& lo, const float& hi);
+  void SetPidProbMuon(const float& lo, const float& hi);
+  void SetLabel(const bool& flag);
+  void SetMaxChiNdof(const float& maxchi);
+  void SetMaxSigmaToVertex(const float& maxsig);
+  void SetMostProbablePion();
+  void SetMostProbableKaon();
+  void SetMostProbableProton();
+  void SetNoMostProbable(); 
+
+ private:   // here are the quantities I want to cut on...
+
+  int               fCharge;             // particle charge
+  float             fPt[2];              // bounds for transverse momentum
+  float             fRapidity[2];        // bounds for rapidity
+  float             fPidProbElectron[2]; // bounds for electron probability
+  float             fPidProbPion[2];     // bounds for pion probability
+  float             fPidProbKaon[2];     // bounds for kaon probability
+  float             fPidProbProton[2];   // bounds for proton probability
+  float             fPidProbMuon[2];     // bounds for muon probability 
+  bool              fLabel;              // if true label<0 will not pass throught 
+  float             fMaxchiNdof;         // maximum allowed chi2/ndof for TPC clusters
+  float             fMaxSigmaToVertex;   // maximum allowed sigma to primary vertex
+  long              fNTracksPassed;      // passed tracks count
+  long              fNTracksFailed;      // failed tracks count
+  int               fMostProbable;       // this particle type is required to be most probable
+
+  float PidFractionElectron(float mom) const;
+  float PidFractionPion(float mom) const;
+  float PidFractionKaon(float mom) const;
+  float PidFractionProton(float mom) const;
+
+#ifdef __ROOT__ 
+  ClassDef(AliFemtoAODTrackCut, 1)
+#endif
+    };
+
+
+inline void AliFemtoAODTrackCut::SetPt(const float& lo, const float& hi){fPt[0]=lo; fPt[1]=hi;}
+inline void AliFemtoAODTrackCut::SetRapidity(const float& lo,const float& hi){fRapidity[0]=lo; fRapidity[1]=hi;}
+inline void AliFemtoAODTrackCut::SetCharge(const int& ch){fCharge = ch;}
+inline void AliFemtoAODTrackCut::SetPidProbElectron(const float& lo,const float& hi){fPidProbElectron[0]=lo; fPidProbElectron[1]=hi;}
+inline void AliFemtoAODTrackCut::SetPidProbPion(const float& lo,const float& hi){fPidProbPion[0]=lo; fPidProbPion[1]=hi;}
+inline void AliFemtoAODTrackCut::SetPidProbKaon(const float& lo,const float& hi){fPidProbKaon[0]=lo; fPidProbKaon[1]=hi;}
+inline void AliFemtoAODTrackCut::SetPidProbProton(const float& lo,const float& hi){fPidProbProton[0]=lo; fPidProbProton[1]=hi;}
+inline void AliFemtoAODTrackCut::SetPidProbMuon(const float& lo,const float& hi){fPidProbMuon[0]=lo; fPidProbMuon[1]=hi;}
+inline void AliFemtoAODTrackCut::SetLabel(const bool& flag){fLabel=flag;}
+inline void AliFemtoAODTrackCut::SetMostProbablePion() { fMostProbable = 2; }
+inline void AliFemtoAODTrackCut::SetMostProbableKaon() { fMostProbable = 3; }
+inline void AliFemtoAODTrackCut::SetMostProbableProton() { fMostProbable = 4; }
+inline void AliFemtoAODTrackCut::SetNoMostProbable() { fMostProbable = 0; }
+inline void AliFemtoAODTrackCut::SetMaxChiNdof(const float& maxchi) { fMaxchiNdof = maxchi; }
+inline void AliFemtoAODTrackCut::SetMaxSigmaToVertex(const float& maxsig) { fMaxSigmaToVertex = maxsig; }
+
+#endif
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoAnalysis.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoAnalysis.h
new file mode 100644 (file)
index 0000000..8a98627
--- /dev/null
@@ -0,0 +1,32 @@
+////////////////////////////////////////////////////////////////////////////////
+/// AliFemtoAnalysis - the pure virtual base class for femto analysis        ///
+/// All analysis classes must inherit from this one                          ///
+////////////////////////////////////////////////////////////////////////////////
+#ifndef AliFemtoAnalysis_hh
+#define AliFemtoAnalysis_hh
+
+#include "AliFemtoTypes.h"
+#include <TList.h>
+#include <TObjString.h>
+
+class AliFemtoEvent;
+
+class AliFemtoAnalysis{
+
+public:
+
+  AliFemtoAnalysis() { /* noop */ };
+  virtual ~AliFemtoAnalysis() { /* noop */ };
+
+  
+  virtual AliFemtoString Report() = 0;       //! returns reports of all cuts applied and correlation functions being done
+  virtual TList* ListSettings() = 0;         // return list of cut settings for the analysis
+
+  virtual TList* GetOutputList() = 0;        // Return a TList of objects to be written as output
+  virtual void ProcessEvent(const AliFemtoEvent* aEventToAnalyze) = 0;
+
+  virtual void Finish() = 0;
+
+};
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoAnalysisAzimuthal.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoAnalysisAzimuthal.cxx
new file mode 100644 (file)
index 0000000..38cf4d2
--- /dev/null
@@ -0,0 +1,469 @@
+////////////////////////////////////////////////////////////////////////////
+//                                                                        //
+// AliFemtoAnalysisReactionPlane - Femtoscopic analysis which mixes event //
+// with respect to the z position of the primary vertex and event total   //
+// multiplicity and uses only events in certain reaction plane angle bin  //
+//                                                                        //
+////////////////////////////////////////////////////////////////////////////
+
+#include "AliFemtoAnalysisAzimuthal.h"
+#include <TMath.h>
+#include <string>
+#include <cstdio>
+#include "AliFemtoParticleCollection.h"
+#include "AliFemtoTrackCut.h"
+#include "AliFemtoV0Cut.h"
+#include "AliFemtoPairCut.h"
+#include "TVector2.h"
+#include "AliFemtoKinkCut.h"
+#include "AliFemtoPicoEventCollectionVector.h"
+#include "AliFemtoPicoEventCollectionVectorHideAway.h"
+
+#ifdef __ROOT__ 
+ClassImp(AliFemtoAnalysisAzimuthal)
+#endif
+
+extern void FillHbtParticleCollection(AliFemtoParticleCut*         partCut,
+                                     AliFemtoEvent*               hbtEvent,
+                                     AliFemtoParticleCollection*  partCollection);
+
+
+//____________________________
+AliFemtoAnalysisAzimuthal::AliFemtoAnalysisAzimuthal(unsigned int binsVertex, double minVertex, double maxVertex,
+                                                      unsigned int binsMult, double minMult, double maxMult, unsigned short binsRP) 
+  : 
+  fFemtoParticleCut(0),
+  fFlowParticleCut(0),
+  fVertexZBins(binsVertex), 
+  fOverFlowVertexZ(0), 
+  fUnderFlowVertexZ(0),
+  fMultBins(binsMult) ,
+  fOverFlowMult(0),    
+  fUnderFlowMult(0),
+  fRPBins(binsRP),
+  fPsi(0)
+{
+  //  mControlSwitch     = 0;
+  fCorrFctnCollection= 0;
+  fCorrFctnCollection = new AliFemtoCorrFctnCollection;
+  fVertexZ[0] = minVertex;
+  fVertexZ[1] = maxVertex;
+  fMult[0] = minMult;
+  fMult[1] = maxMult;
+  if (fMixingBuffer) delete fMixingBuffer;
+  fPicoEventCollectionVectorHideAway = new AliFemtoPicoEventCollectionVectorHideAway(fVertexZBins,fVertexZ[0],fVertexZ[1],
+                                                                                    fMultBins,fMult[0],fMult[1],
+                                                                                    fRPBins,0.0,TMath::Pi());
+}
+
+//____________________________
+
+AliFemtoAnalysisAzimuthal::AliFemtoAnalysisAzimuthal(const AliFemtoAnalysisAzimuthal& a) : 
+  AliFemtoSimpleAnalysis(),
+  fFemtoParticleCut(0),
+  fFlowParticleCut(0),
+  fVertexZBins(a.fVertexZBins), 
+  fOverFlowVertexZ(0), 
+  fUnderFlowVertexZ(0),
+  fMultBins(a.fMultBins) ,
+  fOverFlowMult(0),    
+  fUnderFlowMult(0),
+  fRPBins(a.fRPBins),
+  fPsi(0)
+
+{
+  fCorrFctnCollection= 0;
+  fCorrFctnCollection = new AliFemtoCorrFctnCollection;
+  fVertexZ[0] = a.fVertexZ[0]; 
+  fVertexZ[1] = a.fVertexZ[1];
+  fMult[0] = a.fMult[0]; 
+  fMult[1] = a.fMult[1];
+  if (fMixingBuffer) delete fMixingBuffer;
+  fPicoEventCollectionVectorHideAway = new AliFemtoPicoEventCollectionVectorHideAway(fVertexZBins,fVertexZ[0],fVertexZ[1],
+                                                                                    fMultBins,fMult[0],fMult[1],
+                                                                                    fRPBins,0.0,TMath::Pi());
+  // find the right event cut
+  fEventCut = a.fEventCut->Clone();
+  // find the right femto particle cut
+  fFemtoParticleCut = a.fFemtoParticleCut->Clone();
+  // find the right flow particle cut
+  fFlowParticleCut = a.fFlowParticleCut->Clone();
+  // find the right pair cut
+  fPairCut = a.fPairCut->Clone();
+  
+  if ( fEventCut ) {
+      SetEventCut(fEventCut); // this will set the myAnalysis pointer inside the cut
+      cout << " AliFemtoAnalysisAzimuthal::AliFemtoAnalysisAzimuthal(const AliFemtoAnalysisAzimuthal& a) - event cut set " << endl;
+  }
+  if ( fFemtoParticleCut ) {
+      SetFirstParticleCut(fFemtoParticleCut); // this will set the myAnalysis pointer inside the cut
+      cout << " AliFemtoAnalysisAzimuthal::AliFemtoAnalysisAzimuthal(const AliFemtoAnalysisAzimuthal& a) - femto particle cut set " << endl;
+  }
+  if ( fFlowParticleCut ) {
+      SetSecondParticleCut(fFlowParticleCut); // this will set the myAnalysis pointer inside the cut
+      cout << " AliFemtoAnalysisAzimuthal::AliFemtoAnalysisAzimuthal(const AliFemtoAnalysisAzimuthal& a) - flow particle cut set " << endl;
+  }
+  if ( fPairCut ) {
+      SetPairCut(fPairCut); // this will set the myAnalysis pointer inside the cut
+      cout << " AliFemtoAnalysisAzimuthal::AliFemtoAnalysisAzimuthal(const AliFemtoAnalysisAzimuthal& a) - pair cut set " << endl;
+  }
+
+  AliFemtoCorrFctnIterator iter;
+  for (iter=a.fCorrFctnCollection->begin(); iter!=a.fCorrFctnCollection->end();iter++){
+    cout << " AliFemtoAnalysisAzimuthal::AliFemtoAnalysisAzimuthal(const AliFemtoAnalysisAzimuthal& a) - looking for correlation functions " << endl;
+    AliFemtoCorrFctn* fctn = (*iter)->Clone();
+    if (fctn) AddCorrFctn(fctn);
+    else cout << " AliFemtoAnalysisAzimuthal::AliFemtoAnalysisAzimuthal(const AliFemtoAnalysisAzimuthal& a) - correlation function not found " << endl;
+  }
+  fNumEventsToMix = a.fNumEventsToMix;
+  cout << " AliFemtoAnalysisAzimuthal::AliFemtoAnalysisAzimuthal(const AliFemtoAnalysisAzimuthal& a) - analysis copied " << endl;
+}
+
+AliFemtoAnalysisAzimuthal& AliFemtoAnalysisAzimuthal::operator=(const AliFemtoAnalysisAzimuthal& a)
+{
+  // Assignment operator
+  if (this == &a)
+    return *this;
+
+  fCorrFctnCollection= 0;
+  fCorrFctnCollection = new AliFemtoCorrFctnCollection;
+  fVertexZ[0] = a.fVertexZ[0]; 
+  fVertexZ[1] = a.fVertexZ[1];
+  fMult[0] = a.fMult[0]; 
+  fMult[1] = a.fMult[1];
+  if (fMixingBuffer) delete fMixingBuffer;
+  fPicoEventCollectionVectorHideAway = new AliFemtoPicoEventCollectionVectorHideAway(fVertexZBins,fVertexZ[0],fVertexZ[1],
+                                                                                    fMultBins,fMult[0],fMult[1],
+                                                                                    fRPBins,0.0,TMath::Pi());
+  // find the right event cut
+  fEventCut = a.fEventCut->Clone();
+  // find the right femto particle cut
+  fFemtoParticleCut = a.fFemtoParticleCut->Clone();
+  // find the right flow particle cut
+  fFlowParticleCut = a.fFlowParticleCut->Clone();
+  // find the right pair cut
+  fPairCut = a.fPairCut->Clone();
+  
+  if ( fEventCut ) {
+      SetEventCut(fEventCut); // this will set the myAnalysis pointer inside the cut
+      cout << " AliFemtoAnalysisAzimuthal::AliFemtoAnalysisAzimuthal(const AliFemtoAnalysisAzimuthal& a) - event cut set " << endl;
+  }
+  if ( fFemtoParticleCut ) {
+      SetFirstParticleCut(fFemtoParticleCut); // this will set the myAnalysis pointer inside the cut
+      cout << " AliFemtoAnalysisAzimuthal::AliFemtoAnalysisAzimuthal(const AliFemtoAnalysisAzimuthal& a) - femto particle cut set " << endl;
+  }
+  if ( fFlowParticleCut ) {
+      SetSecondParticleCut(fFlowParticleCut); // this will set the myAnalysis pointer inside the cut
+      cout << " AliFemtoAnalysisAzimuthal::AliFemtoAnalysisAzimuthal(const AliFemtoAnalysisAzimuthal& a) - flow particle cut set " << endl;
+  }
+  if ( fPairCut ) {
+      SetPairCut(fPairCut); // this will set the myAnalysis pointer inside the cut
+      cout << " AliFemtoAnalysisAzimuthal::AliFemtoAnalysisAzimuthal(const AliFemtoAnalysisAzimuthal& a) - pair cut set " << endl;
+  }
+
+  AliFemtoCorrFctnIterator iter;
+  for (iter=a.fCorrFctnCollection->begin(); iter!=a.fCorrFctnCollection->end();iter++){
+    cout << " AliFemtoAnalysisAzimuthal::AliFemtoAnalysisAzimuthal(const AliFemtoAnalysisAzimuthal& a) - looking for correlation functions " << endl;
+    AliFemtoCorrFctn* fctn = (*iter)->Clone();
+    if (fctn) AddCorrFctn(fctn);
+    else cout << " AliFemtoAnalysisAzimuthal::AliFemtoAnalysisAzimuthal(const AliFemtoAnalysisAzimuthal& a) - correlation function not found " << endl;
+  }
+  fNumEventsToMix = a.fNumEventsToMix;
+  cout << " AliFemtoAnalysisAzimuthal::AliFemtoAnalysisAzimuthal(const AliFemtoAnalysisAzimuthal& a) - analysis copied " << endl;
+
+  return *this;
+  
+}
+
+//____________________________
+AliFemtoAnalysisAzimuthal::~AliFemtoAnalysisAzimuthal(){
+  // now delete every PicoEvent in the EventMixingBuffer and then the Buffer itself
+  delete fPicoEventCollectionVectorHideAway;
+}
+
+//_________________________
+void AliFemtoAnalysisAzimuthal::ProcessEvent(const AliFemtoEvent* hbtEvent) {
+  // Perform event processing in bins of z vertex, multiplicity and Reaction Plane angle
+  // cout << " AliFemtoAnalysisAzimuthal::ProcessEvent(const AliFemtoEvent* hbtEvent) " << endl;
+
+  //****from AliFemtoSimpleAnalysis****
+
+  fPicoEvent=0; // we will get a new pico event, if not prevent corr. fctn to access old pico event
+  fNeventsProcessed++;
+
+  // startup for EbyE 
+  fFemtoParticleCut->EventBegin(hbtEvent);
+  fFlowParticleCut->EventBegin(hbtEvent);
+  fPairCut->EventBegin(hbtEvent);
+
+  for (AliFemtoCorrFctnIterator iter=fCorrFctnCollection->begin(); iter!=fCorrFctnCollection->end();iter++){
+    (*iter)->EventBegin(hbtEvent);
+  }
+
+  // event cut and event cut monitor
+  bool tmpPassEvent = fEventCut->Pass(hbtEvent);
+  if (!tmpPassEvent) 
+    fEventCut->FillCutMonitor(hbtEvent, tmpPassEvent);
+  if (tmpPassEvent) {
+    fPicoEvent = new AliFemtoPicoEvent; // this is what we will make pairs from and put in Mixing Buffer, no memory leak. we will delete picoevents when they come out of the mixing buffer
+    FillHbtParticleCollection(fFemtoParticleCut,(AliFemtoEvent*)hbtEvent,fPicoEvent->FirstParticleCollection());
+    FillHbtParticleCollection(fFlowParticleCut,(AliFemtoEvent*)hbtEvent,fPicoEvent->SecondParticleCollection());
+    
+      // get right mixing buffer
+  double vertexZ = hbtEvent->PrimVertPos().z();
+  double mult = hbtEvent->UncorrectedNumberOfPrimaries();
+  TVector2 tQ = GetQVector(fPicoEvent->SecondParticleCollection());
+  double tPsi=tQ.Phi()/2.;
+  if (tPsi > TMath::Pi()) tPsi -= TMath::Pi();
+      
+   fMixingBuffer = fPicoEventCollectionVectorHideAway->PicoEventCollection(vertexZ,mult,fPsi); 
+  if (!fMixingBuffer) {
+    if ( vertexZ < fVertexZ[0] ) fUnderFlowVertexZ++;
+    if ( vertexZ > fVertexZ[1] ) fOverFlowVertexZ++;
+    if ( mult < fMult[0] ) fUnderFlowMult++;
+    if ( mult > fMult[1] ) fOverFlowMult++;
+    return;
+  }   
+    
+    //cout << "#particles in Collection: " << fPicoEvent->FirstParticleCollection()->size() << endl;
+    
+    //switch which allows only using events with ParticleCollections containing a minimum number of entries
+    if (fPicoEvent->FirstParticleCollection()->size() >= fMinSizePartCollection ) {
+      fEventCut->FillCutMonitor(hbtEvent, tmpPassEvent);
+    }
+
+      //------ Make real pairs (assume identical) ------//
+      MakePairs("real", fPicoEvent->FirstParticleCollection() );
+      //cout << "AliFemtoAnalysisAzimuthal::ProcessEvent() - reals done ";
+
+      //---- Make pairs for mixed events, looping over events in mixingBuffer ----//
+      AliFemtoPicoEvent* storedEvent;
+      AliFemtoPicoEventIterator fPicoEventIter;
+      for (fPicoEventIter=MixingBuffer()->begin();fPicoEventIter!=MixingBuffer()->end();fPicoEventIter++){
+        storedEvent = *fPicoEventIter;
+        MakePairs("mixed",fPicoEvent->FirstParticleCollection(),
+                            storedEvent->FirstParticleCollection() );
+      }
+      //cout << " - mixed done   " << endl;
+
+      //--------- If mixing buffer is full, delete oldest event ---------//
+      if ( MixingBufferFull() ) {
+        delete MixingBuffer()->back();
+        MixingBuffer()->pop_back();
+      }
+
+      //-------- Add current event (fPicoEvent) to mixing buffer --------//
+      MixingBuffer()->push_front(fPicoEvent);
+
+    }  // if ParticleCollections are big enough (mal jun2002)
+    else{
+      fEventCut->FillCutMonitor(hbtEvent, !tmpPassEvent);
+      delete fPicoEvent;
+    }
+
+  // if currentEvent is accepted by currentAnalysis cleanup for EbyE 
+  fFemtoParticleCut->EventEnd(hbtEvent);
+  fFlowParticleCut->EventEnd(hbtEvent);
+  fPairCut->EventEnd(hbtEvent);
+  for (AliFemtoCorrFctnIterator iter=fCorrFctnCollection->begin(); iter!=fCorrFctnCollection->end();iter++){
+    (*iter)->EventEnd(hbtEvent);
+  } 
+}
+
+//_______________________________________________________________________________
+void AliFemtoAnalysisAzimuthal::MakePairs(const char* typeIn, AliFemtoParticleCollection *partCollection1,
+                                      AliFemtoParticleCollection *partCollection2){
+// Build pairs, check pair cuts, and call CFs' AddRealPair() or AddMixedPair() methods. 
+// If no second particle collection is specfied, make pairs within first particle collection.
+
+  string type = typeIn;
+
+  //  int swpart = ((long int) partCollection1) % 2;
+  int swpart = fNeventsProcessed % 2;
+
+  AliFemtoPair* tPair = new AliFemtoPair;
+  AliFemtoCorrFctnIterator tCorrFctnIter;
+  AliFemtoParticleIterator tPartIter1, tPartIter2;
+
+  AliFemtoParticleIterator tStartOuterLoop = partCollection1->begin();  // always
+  AliFemtoParticleIterator tEndOuterLoop   = partCollection1->end();    // will be one less if identical
+  AliFemtoParticleIterator tStartInnerLoop;
+  AliFemtoParticleIterator tEndInnerLoop;
+  if (partCollection2) {                         //   Two collections:
+    tStartInnerLoop = partCollection2->begin();  //   Full inner & outer loops
+    tEndInnerLoop   = partCollection2->end();    
+  }
+  else {                                         //   One collection:
+    tEndOuterLoop--;                             //   Outer loop goes to next-to-last particle
+    tEndInnerLoop = partCollection1->end() ;     //   Inner loop goes to last particle
+  }
+  for (tPartIter1=tStartOuterLoop;tPartIter1!=tEndOuterLoop;tPartIter1++) {
+    if (!partCollection2){
+      tStartInnerLoop = tPartIter1;
+      tStartInnerLoop++;
+    }
+    tPair->SetTrack1(*tPartIter1);
+    for (tPartIter2 = tStartInnerLoop; tPartIter2!=tEndInnerLoop;tPartIter2++) {
+      tPair->SetTrack2(*tPartIter2);
+
+//For getting the pair angle wrt EP
+  if (type == "real"){
+       TVector2 tQ, tQVector;
+       float tPsi=0, mQx=0, mQy=0, PairAngleEP=0;
+       tQ = GetQVector(partCollection1);
+
+       mQx = tQ.X() - cos(2*(tPair->Track1()->FourMomentum().Phi()))*(tPair->Track1()->Track()->Pt()) - cos(2*(tPair->Track2()->FourMomentum().Phi()))*(tPair->Track2()->Track()->Pt());
+       mQy = tQ.Y() - sin(2*(tPair->Track1()->FourMomentum().Phi()))*(tPair->Track1()->Track()->Pt()) - sin(2*(tPair->Track2()->FourMomentum().Phi()))*(tPair->Track2()->Track()->Pt());
+  
+       tQVector.Set(mQx,mQy);
+
+       tPsi=tQVector.Phi()/2.;
+       if (tPsi > TMath::Pi()) tPsi -= TMath::Pi();
+
+       PairAngleEP = (tPair->EmissionAngle() - tPsi);
+       tPair->SetPairAngleEP(PairAngleEP);
+  }
+
+  if (type == "mixed"){
+       float tPsi1=0, tPsi2=0, mQx1=0, mQx2=0,mQy1=0, mQy2=0, px1=0, px2=0, py1=0, py2=0, PairAngleEP=0;
+       TVector2 tQ1, tQ2, tQVector1, tQVector2, tP;
+
+       tQ1 = GetQVector(partCollection1);
+       tQ2 = GetQVector(partCollection2);
+
+       mQx1 = tQ1.X() - cos(2*(tPair->Track1()->FourMomentum().Phi()))*(tPair->Track1()->Track()->Pt());
+       mQx2 = tQ2.X() - cos(2*(tPair->Track2()->FourMomentum().Phi()))*(tPair->Track2()->Track()->Pt());
+       mQy1 = tQ1.Y() - sin(2*(tPair->Track1()->FourMomentum().Phi()))*(tPair->Track1()->Track()->Pt());
+       mQy2 = tQ2.Y() - sin(2*(tPair->Track2()->FourMomentum().Phi()))*(tPair->Track2()->Track()->Pt());
+  
+       tQVector1.Set(mQx1,mQy1);
+       tQVector2.Set(mQx2,mQy2);
+
+       tPsi1=tQVector1.Phi()/2.;
+       if (tPsi1 > TMath::Pi()) tPsi1 -= TMath::Pi();
+
+       tPsi2=tQVector2.Phi()/2.;
+       if (tPsi2 > TMath::Pi()) tPsi2 -= TMath::Pi();
+
+       px1 = (tPair->Track1()->Track()->Pt())*cos(tPair->Track1()->FourMomentum().Phi() - tPsi1);
+       px2 = (tPair->Track2()->Track()->Pt())*cos(tPair->Track2()->FourMomentum().Phi() - tPsi2);
+       py1 = (tPair->Track1()->Track()->Pt())*sin(tPair->Track1()->FourMomentum().Phi() - tPsi1);
+       py2 = (tPair->Track2()->Track()->Pt())*sin(tPair->Track2()->FourMomentum().Phi() - tPsi2);
+
+       tP.Set(px1+px2, py1+py2);
+       PairAngleEP = tP.Phi();
+
+       tPair->SetPairAngleEP(PairAngleEP);
+  }
+
+      // The following lines have to be uncommented if you want pairCutMonitors
+      // they are not in for speed reasons
+      // bool tmpPassPair = fPairCut->Pass(tPair);
+      // fPairCut->FillCutMonitor(tPair, tmpPassPair);
+      // if ( tmpPassPair )
+
+      //---- If pair passes cut, loop over CF's and add pair to real/mixed ----//
+
+      if (!partCollection2) {
+       if (swpart) {
+         tPair->SetTrack1(*tPartIter2);
+         tPair->SetTrack2(*tPartIter1);
+         swpart = 0;
+       }
+       else {
+         tPair->SetTrack1(*tPartIter1);
+         tPair->SetTrack2(*tPartIter2);
+         swpart = 1;
+       }
+      }
+
+
+      if (fPairCut->Pass(tPair)){
+        for (tCorrFctnIter=fCorrFctnCollection->begin();
+             tCorrFctnIter!=fCorrFctnCollection->end();tCorrFctnIter++){
+          AliFemtoCorrFctn* tCorrFctn = *tCorrFctnIter;
+          if(type == "real")
+            tCorrFctn->AddRealPair(tPair);
+         else if(type == "mixed")
+            tCorrFctn->AddMixedPair(tPair);
+          else
+            cout << "Problem with pair type, type = " << type.c_str() << endl;
+        }
+      }
+    }    // loop over second particle
+  }      // loop over first particle
+
+  delete tPair;
+}
+
+//_____________________________________________
+TVector2 AliFemtoAnalysisAzimuthal::GetQVector(AliFemtoParticleCollection* particlecollection){
+  
+  TVector2 mQ;
+  float mQx=0, mQy=0;
+
+  if (!particlecollection) {
+    mQ.Set(0.0, 0.0);
+    return mQ;
+  }
+
+  AliFemtoParticle* flowparticle;
+  AliFemtoParticleIterator pIter;
+  AliFemtoParticleIterator startLoop = particlecollection->begin();
+  AliFemtoParticleIterator endLoop   = particlecollection->end();
+  for (pIter=startLoop;pIter!=endLoop;pIter++){
+    flowparticle = *pIter;
+    mQx += (cos(2*flowparticle->FourMomentum().Phi()))*(flowparticle->Track()->Pt());
+    mQy += (sin(2*flowparticle->FourMomentum().Phi()))*(flowparticle->Track()->Pt());
+  }
+  
+  mQ.Set(mQx,mQy);
+  return mQ;
+}
+
+//__________________________________________________
+double AliFemtoAnalysisAzimuthal::GetCurrentReactionPlane()
+{
+  return fPsi;
+}
+
+//_________________________
+TList* AliFemtoAnalysisAzimuthal::GetOutputList()
+{
+  // Collect the list of output objects to be written
+
+  TList *tOutputList = new TList();
+  TList *p1Cut = fFemtoParticleCut->GetOutputList();
+
+  TListIter nextp1(p1Cut);
+  while (TObject *obj = nextp1.Next()) {
+    tOutputList->Add(obj);
+  }
+
+  TList *pairCut = fPairCut->GetOutputList();
+
+  TIter nextpair(pairCut);
+  while (TObject *obj = nextpair()) {
+    tOutputList->Add(obj);
+  }
+
+  TList *eventCut = fEventCut->GetOutputList();
+
+  TIter nextevent(eventCut);
+  while (TObject *obj = nextevent()) {
+    tOutputList->Add(obj);
+  }
+
+  AliFemtoCorrFctnIterator iter;
+  for (iter=fCorrFctnCollection->begin(); iter!=fCorrFctnCollection->end();iter++){
+    TList *tListCf = (*iter)->GetOutputList();
+    
+    TIter nextListCf(tListCf);
+    while (TObject *obj = nextListCf()) {
+      tOutputList->Add(obj);
+    }
+  }
+
+  return tOutputList;
+  
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoAnalysisAzimuthal.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoAnalysisAzimuthal.h
new file mode 100644 (file)
index 0000000..d806651
--- /dev/null
@@ -0,0 +1,67 @@
+////////////////////////////////////////////////////////////////////////////
+//                                                                        //
+// AliFemtoAnalysisReactionPlane - Femtoscopic analysis which mixes event //
+// with respect to the z position of the primary vertex and event total   //
+// multiplicity and uses only events in certain reaction plane angle bin  //
+//                                                                        //
+////////////////////////////////////////////////////////////////////////////
+
+#ifndef ALIFEMTOANALYSISAZIMUTHAL_H
+#define ALIFEMTOANALYSISAZIMUTHAL_H
+
+#include "AliFemtoSimpleAnalysis.h"        // base analysis class
+
+class TVector2;
+
+class AliFemtoAnalysisAzimuthal : public AliFemtoSimpleAnalysis {
+
+public:
+
+  AliFemtoAnalysisAzimuthal(unsigned int binsVertex=10, double minVertex=-100., double maxVertex=+100., unsigned int binsMult=10, double minMult=-1.e9, double maxMult=+1.e9, unsigned short binsRP=10);
+  AliFemtoAnalysisAzimuthal(const AliFemtoAnalysisAzimuthal& TheOriginalAnalysis);  // copy constructor
+
+  AliFemtoAnalysisAzimuthal& operator=(const AliFemtoAnalysisAzimuthal& aAna);
+
+  virtual void ProcessEvent(const AliFemtoEvent* ProcessThisEvent);
+  virtual ~AliFemtoAnalysisAzimuthal();
+  virtual unsigned int OverflowVertexZ() const { return fOverFlowVertexZ;}
+  virtual unsigned int UnderflowVertexZ() const { return fUnderFlowVertexZ;}
+  virtual unsigned int OverflowMult() const { return fOverFlowMult;}
+  virtual unsigned int UnderflowMult() const { return fUnderFlowMult;}
+  double GetCurrentReactionPlane();
+  TVector2 GetQVector(AliFemtoParticleCollection* particlecollection);
+  virtual void MakePairs(const char* typeIn, AliFemtoParticleCollection *partCollection1, AliFemtoParticleCollection *partCollection2=0);
+  virtual TList* GetOutputList();
+
+ // Get the particle cuts
+  virtual AliFemtoParticleCut*   FemtoParticleCut() {return fFemtoParticleCut;}
+  virtual AliFemtoParticleCut*   FlowParticleCut() {return fFlowParticleCut;}
+ // Set the cuts
+  void SetFemtoParticleCut(AliFemtoParticleCut* x) {fFemtoParticleCut = x; x->SetAnalysis((AliFemtoAnalysis*)this);}
+  void SetFlowParticleCut(AliFemtoParticleCut* x) {fFlowParticleCut = x; x->SetAnalysis((AliFemtoAnalysis*)this);}
+  void SetEventCut(AliFemtoEventCut* x) {fEventCut = x; x->SetAnalysis((AliFemtoAnalysis*)this);}
+  void SetPairCut(AliFemtoPairCut* x) {fPairCut = x; x->SetAnalysis((AliFemtoAnalysis*)this);}
+
+protected:
+
+  AliFemtoParticleCut*                 fFemtoParticleCut;    //  select particles of type #1 
+  AliFemtoParticleCut*         fFlowParticleCut;   //  select particles of type #2 
+
+  double fVertexZ[2];                 /* min/max z-vertex position allowed to be processed */
+  unsigned int fVertexZBins;          /* number of VERTEX mixing bins in z-vertex in EventMixing Buffer */
+  unsigned int fOverFlowVertexZ;      /* number of events encountered which had too large z-vertex */
+  unsigned int fUnderFlowVertexZ;     /* number of events encountered which had too small z-vertex */
+  double fMult[2];                    /* min/max multiplicity allowed for event to be processed */
+  unsigned int fMultBins;             /* number of MULTIPLICITY mixing bins in z-vertex in EventMixing Buffer */
+  unsigned int fOverFlowMult;         /* number of events encountered which had too large multiplicity */
+  unsigned int fUnderFlowMult;        /* number of events encountered which had too small multiplicity */
+  unsigned short fRPBins;             // Number of reaction plane angle orientation bins
+  double fPsi;                         // Reaction plane angle of the current event
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoAnalysisAzimuthal, 0)
+#endif
+    
+};
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoAnalysisCollection.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoAnalysisCollection.h
new file mode 100644 (file)
index 0000000..2ef52b4
--- /dev/null
@@ -0,0 +1,54 @@
+/***************************************************************************
+ *
+ * $Id$
+ *
+ * Author: Mike Lisa, Ohio State, lisa@mps.ohio-state.edu
+ ***************************************************************************
+ *
+ * Description: part of STAR HBT Framework: AliFemtoMaker package
+ *  The AnalysisCollection is pointed to by the Manager, and holds pointers
+ *  to all Analysis objects currently active
+ *
+ ***************************************************************************
+ *
+ * $Log$
+ * Revision 1.1  2007/05/16 10:22:11  akisiel
+ * Making the directory structure of AliFemto flat. All files go into one common directory
+ *
+ * Revision 1.1.1.1  2007/04/25 15:38:41  panos
+ * Importing the HBT code dir
+ *
+ * Revision 1.1.1.1  2007/03/07 10:14:49  mchojnacki
+ * First version on CVS
+ *
+ * Revision 1.3  2000/03/17 17:23:05  laue
+ * Roberts new three particle correlations implemented.
+ *
+ * Revision 1.2  2000/02/01 00:33:31  laue
+ * namespaces changed to run on the new Solaris Compiler CC5
+ * since we can use member templates in franks1Histo.h we are doing it
+ *
+ * Revision 1.1.1.1  1999/06/29 16:02:57  lisa
+ * Installation of AliFemtoMaker
+ *
+ **************************************************************************/
+
+#ifndef AliFemtoAnalysisCollection_hh
+#define AliFemtoAnalysisCollection_hh
+
+
+#include <list>
+#if !defined(ST_NO_NAMESPACES)
+using std::list;
+#endif
+class AliFemtoAnalysis;
+
+#ifdef ST_NO_TEMPLATE_DEF_ARGS
+typedef list<AliFemtoAnalysis*, allocator<AliFemtoAnalysis*> >            AliFemtoAnalysisCollection;
+typedef list<AliFemtoAnalysis*, allocator<AliFemtoAnalysis*> >::iterator  AliFemtoSimpleAnalysisIterator;
+#else
+typedef list<AliFemtoAnalysis*>            AliFemtoAnalysisCollection;
+typedef list<AliFemtoAnalysis*>::iterator  AliFemtoSimpleAnalysisIterator;
+#endif
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoAnalysisReactionPlane.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoAnalysisReactionPlane.cxx
new file mode 100644 (file)
index 0000000..11fbdbd
--- /dev/null
@@ -0,0 +1,255 @@
+////////////////////////////////////////////////////////////////////////////
+//                                                                        //
+// AliFemtoAnalysisReactionPlane - Femtoscopic analysis which mixes event //
+// with respect to the z position of the primary vertex and event total   //
+// multiplicity and uses only events in certain reaction plane angle bin  //
+//                                                                        //
+////////////////////////////////////////////////////////////////////////////
+
+#include <TMath.h>
+#include "AliFemtoAnalysisReactionPlane.h"
+#include "AliFemtoParticleCollection.h"
+#include "AliFemtoTrackCut.h"
+#include "AliFemtoV0Cut.h"
+#include "AliFemtoKinkCut.h"
+#include "AliFemtoPicoEventCollectionVector.h"
+#include "AliFemtoPicoEventCollectionVectorHideAway.h"
+
+#ifdef __ROOT__ 
+ClassImp(AliFemtoAnalysisReactionPlane)
+#endif
+
+extern void FillHbtParticleCollection(AliFemtoParticleCut*         partCut,
+                                     AliFemtoEvent*               hbtEvent,
+                                     AliFemtoParticleCollection*  partCollection);
+
+
+//____________________________
+AliFemtoAnalysisReactionPlane::AliFemtoAnalysisReactionPlane(unsigned int binsVertex, double minVertex, double maxVertex,
+                                                      unsigned int binsMult, double minMult, double maxMult, unsigned short binsRP) 
+  : 
+  fVertexZBins(binsVertex), 
+  fOverFlowVertexZ(0), 
+  fUnderFlowVertexZ(0),
+  fMultBins(binsMult) ,
+  fOverFlowMult(0),    
+  fUnderFlowMult(0),
+  fRPBins(binsRP),
+  fCurrentRP(0)
+{
+  //  mControlSwitch     = 0;
+  fEventCut          = 0;
+  fFirstParticleCut  = 0;
+  fSecondParticleCut = 0;
+  fPairCut           = 0;
+  fCorrFctnCollection= 0;
+  fCorrFctnCollection = new AliFemtoCorrFctnCollection;
+  fVertexZ[0] = minVertex;
+  fVertexZ[1] = maxVertex;
+  fUnderFlowVertexZ = 0; 
+  fOverFlowVertexZ = 0; 
+  fMult[0] = minMult;
+  fMult[1] = maxMult;
+  fUnderFlowMult = 0; 
+  fOverFlowMult = 0; 
+  if (fMixingBuffer) delete fMixingBuffer;
+  fPicoEventCollectionVectorHideAway = new AliFemtoPicoEventCollectionVectorHideAway(fVertexZBins,fVertexZ[0],fVertexZ[1],
+                                                                                    fMultBins,fMult[0],fMult[1],
+                                                                                    fRPBins,0.0,TMath::Pi());
+}
+//____________________________
+
+AliFemtoAnalysisReactionPlane::AliFemtoAnalysisReactionPlane(const AliFemtoAnalysisReactionPlane& a) : 
+  AliFemtoSimpleAnalysis(),
+  fVertexZBins(a.fVertexZBins), 
+  fOverFlowVertexZ(0), 
+  fUnderFlowVertexZ(0),
+  fMultBins(a.fMultBins) ,
+  fOverFlowMult(0),    
+  fUnderFlowMult(0),
+  fRPBins(a.fRPBins),
+  fCurrentRP(0)
+{
+  //AliFemtoAnalysisReactionPlane();
+  fEventCut          = 0;
+  fFirstParticleCut  = 0;
+  fSecondParticleCut = 0;
+  fPairCut           = 0;
+  fCorrFctnCollection= 0;
+  fCorrFctnCollection = new AliFemtoCorrFctnCollection;
+  fVertexZ[0] = a.fVertexZ[0]; 
+  fVertexZ[1] = a.fVertexZ[1];
+  fUnderFlowVertexZ = 0; 
+  fOverFlowVertexZ = 0; 
+  fMult[0] = a.fMult[0]; 
+  fMult[1] = a.fMult[1];
+  fUnderFlowMult = 0; 
+  fOverFlowMult = 0; 
+  if (fMixingBuffer) delete fMixingBuffer;
+  fPicoEventCollectionVectorHideAway = new AliFemtoPicoEventCollectionVectorHideAway(fVertexZBins,fVertexZ[0],fVertexZ[1],
+                                                                                    fMultBins,fMult[0],fMult[1],
+                                                                                    fRPBins,0.0,TMath::Pi());
+
+  // find the right event cut
+  fEventCut = a.fEventCut->Clone();
+  // find the right first particle cut
+  fFirstParticleCut = a.fFirstParticleCut->Clone();
+  // find the right second particle cut
+  if (a.fFirstParticleCut==a.fSecondParticleCut) 
+    SetSecondParticleCut(fFirstParticleCut); // identical particle hbt
+  else
+  fSecondParticleCut = a.fSecondParticleCut->Clone();
+
+  fPairCut = a.fPairCut->Clone();
+  
+  if ( fEventCut ) {
+      SetEventCut(fEventCut); // this will set the myAnalysis pointer inside the cut
+      cout << " AliFemtoAnalysisReactionPlane::AliFemtoAnalysisReactionPlane(const AliFemtoAnalysisReactionPlane& a) - event cut set " << endl;
+  }
+  if ( fFirstParticleCut ) {
+      SetFirstParticleCut(fFirstParticleCut); // this will set the myAnalysis pointer inside the cut
+      cout << " AliFemtoAnalysisReactionPlane::AliFemtoAnalysisReactionPlane(const AliFemtoAnalysisReactionPlane& a) - first particle cut set " << endl;
+  }
+  if ( fSecondParticleCut ) {
+      SetSecondParticleCut(fSecondParticleCut); // this will set the myAnalysis pointer inside the cut
+      cout << " AliFemtoAnalysisReactionPlane::AliFemtoAnalysisReactionPlane(const AliFemtoAnalysisReactionPlane& a) - second particle cut set " << endl;
+  }  if ( fPairCut ) {
+      SetPairCut(fPairCut); // this will set the myAnalysis pointer inside the cut
+      cout << " AliFemtoAnalysisReactionPlane::AliFemtoAnalysisReactionPlane(const AliFemtoAnalysisReactionPlane& a) - pair cut set " << endl;
+  }
+
+  AliFemtoCorrFctnIterator iter;
+  for (iter=a.fCorrFctnCollection->begin(); iter!=a.fCorrFctnCollection->end();iter++){
+    cout << " AliFemtoAnalysisReactionPlane::AliFemtoAnalysisReactionPlane(const AliFemtoAnalysisReactionPlane& a) - looking for correlation functions " << endl;
+    AliFemtoCorrFctn* fctn = (*iter)->Clone();
+    if (fctn) AddCorrFctn(fctn);
+    else cout << " AliFemtoAnalysisReactionPlane::AliFemtoAnalysisReactionPlane(const AliFemtoAnalysisReactionPlane& a) - correlation function not found " << endl;
+  }
+
+  fNumEventsToMix = a.fNumEventsToMix;
+
+  cout << " AliFemtoAnalysisReactionPlane::AliFemtoAnalysisReactionPlane(const AliFemtoAnalysisReactionPlane& a) - analysis copied " << endl;
+
+}
+AliFemtoAnalysisReactionPlane& AliFemtoAnalysisReactionPlane::operator=(const AliFemtoAnalysisReactionPlane& TheOriginalAnalysis)
+{
+  if (this != &TheOriginalAnalysis) {
+
+    //AliFemtoAnalysisReactionPlane();
+    fVertexZ[0] = TheOriginalAnalysis.fVertexZ[0]; 
+    fVertexZ[1] = TheOriginalAnalysis.fVertexZ[1];
+    fUnderFlowVertexZ = 0; 
+    fOverFlowVertexZ = 0; 
+    fMult[0] = TheOriginalAnalysis.fMult[0]; 
+    fMult[1] = TheOriginalAnalysis.fMult[1];
+    fUnderFlowMult = 0; 
+    fOverFlowMult = 0; 
+    if (fMixingBuffer) delete fMixingBuffer;
+    fVertexZBins = TheOriginalAnalysis.fVertexZBins;
+    fMultBins = TheOriginalAnalysis.fMultBins;
+    fRPBins = TheOriginalAnalysis.fRPBins;
+    fCurrentRP = 0;
+    
+    if (fEventCut) delete fEventCut;
+    fEventCut = TheOriginalAnalysis.fEventCut->Clone();
+    
+    if (fFirstParticleCut) delete fFirstParticleCut;
+    fFirstParticleCut = TheOriginalAnalysis.fFirstParticleCut->Clone();
+    
+    if (fSecondParticleCut) delete fSecondParticleCut;
+    if (TheOriginalAnalysis.fFirstParticleCut==TheOriginalAnalysis.fSecondParticleCut) 
+      SetSecondParticleCut(fFirstParticleCut); // identical particle hbt
+    else
+      fSecondParticleCut = TheOriginalAnalysis.fSecondParticleCut->Clone();
+    
+    if (fPairCut) delete fPairCut;
+    fPairCut = TheOriginalAnalysis.fPairCut->Clone();
+    
+    if ( fEventCut ) {
+      SetEventCut(fEventCut); // this will set the myAnalysis pointer inside the cut
+    }
+    if ( fFirstParticleCut ) {
+      SetFirstParticleCut(fFirstParticleCut); // this will set the myAnalysis pointer inside the cut
+    }
+    if ( fSecondParticleCut ) {
+      SetSecondParticleCut(fSecondParticleCut); // this will set the myAnalysis pointer inside the cut
+    }  if ( fPairCut ) {
+      SetPairCut(fPairCut); // this will set the myAnalysis pointer inside the cut
+    }
+    
+    if (fPicoEventCollectionVectorHideAway) delete fPicoEventCollectionVectorHideAway;
+    fPicoEventCollectionVectorHideAway = new AliFemtoPicoEventCollectionVectorHideAway(fVertexZBins,fVertexZ[0],fVertexZ[1],
+                                                                                      fMultBins,fMult[0],fMult[1],
+                                                                                      fRPBins,0.0,TMath::Pi());
+    
+    AliFemtoCorrFctnIterator iter;
+    for (iter=TheOriginalAnalysis.fCorrFctnCollection->begin(); iter!=TheOriginalAnalysis.fCorrFctnCollection->end();iter++){
+      AliFemtoCorrFctn* fctn = (*iter)->Clone();
+      if (fctn) AddCorrFctn(fctn);
+    }
+    
+    fNumEventsToMix = TheOriginalAnalysis.fNumEventsToMix;
+
+  }
+
+  return *this;
+}
+
+//____________________________
+AliFemtoAnalysisReactionPlane::~AliFemtoAnalysisReactionPlane(){
+  // now delete every PicoEvent in the EventMixingBuffer and then the Buffer itself
+  delete fPicoEventCollectionVectorHideAway;
+}
+
+//____________________________
+AliFemtoString AliFemtoAnalysisReactionPlane::Report()
+{
+  // Prepare a report of the execution
+  cout << "AliFemtoAnalysisReactionPlane - constructing Report..."<<endl;
+  char ctemp[200];
+  AliFemtoString temp = "-----------\nHbt AliFemtoAnalysisReactionPlane Report:\n";
+  snprintf(ctemp , 200, "Events are mixed in %d VertexZ bins in the range %E cm to %E cm.\n",fVertexZBins,fVertexZ[0],fVertexZ[1]);
+  temp += ctemp;
+  snprintf(ctemp , 200, "Events underflowing: %d\n",fUnderFlowVertexZ);
+  temp += ctemp;
+  snprintf(ctemp , 200, "Events overflowing: %d\n",fOverFlowVertexZ);
+  temp += ctemp;
+  snprintf(ctemp , 200, "Events are mixed in %d Mult bins in the range %E cm to %E cm.\n",fMultBins,fMult[0],fMult[1]);
+  temp += ctemp;
+  snprintf(ctemp , 200, "Events underflowing: %d\n",fUnderFlowMult);
+  temp += ctemp;
+  snprintf(ctemp , 200, "Events overflowing: %d\n",fOverFlowMult);
+  temp += ctemp;
+  snprintf(ctemp , 200, "Now adding AliFemtoSimpleAnalysis(base) Report\n");
+  temp += ctemp;
+  temp += AliFemtoSimpleAnalysis::Report();
+  AliFemtoString returnThis=temp;
+  return returnThis;
+}
+//_________________________
+void AliFemtoAnalysisReactionPlane::ProcessEvent(const AliFemtoEvent* hbtEvent) {
+  // Perform event processing
+  // in bins of z vertex and multiplicity
+
+  // cout << " AliFemtoAnalysisReactionPlane::ProcessEvent(const AliFemtoEvent* hbtEvent) " << endl;
+  // get right mixing buffer
+  double vertexZ = hbtEvent->PrimVertPos().z();
+  double mult = hbtEvent->UncorrectedNumberOfPrimaries();
+  fCurrentRP = hbtEvent->ReactionPlaneAngle();
+  
+  fMixingBuffer = fPicoEventCollectionVectorHideAway->PicoEventCollection(vertexZ,mult,fCurrentRP); 
+  if (!fMixingBuffer) {
+    if ( vertexZ < fVertexZ[0] ) fUnderFlowVertexZ++;
+    if ( vertexZ > fVertexZ[1] ) fOverFlowVertexZ++;
+    if ( mult < fMult[0] ) fUnderFlowMult++;
+    if ( mult > fMult[1] ) fOverFlowMult++;
+    return;
+  }
+  // call ProcessEvent() from AliFemtoSimpleAnalysis-base
+  AliFemtoSimpleAnalysis::ProcessEvent(hbtEvent);
+}
+
+double AliFemtoAnalysisReactionPlane::GetCurrentReactionPlane()
+{
+  return fCurrentRP;
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoAnalysisReactionPlane.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoAnalysisReactionPlane.h
new file mode 100644 (file)
index 0000000..2283efb
--- /dev/null
@@ -0,0 +1,47 @@
+////////////////////////////////////////////////////////////////////////////
+//                                                                        //
+// AliFemtoAnalysisReactionPlane - Femtoscopic analysis which mixes event //
+// with respect to the z position of the primary vertex and event total   //
+// multiplicity and uses only events in certain reaction plane angle bin  //
+//                                                                        //
+////////////////////////////////////////////////////////////////////////////
+
+#ifndef ALIFEMTOANALYSISREACTIONPLANE_H
+#define ALIFEMTOANALYSISREACTIONPLANE_H
+
+#include "AliFemtoSimpleAnalysis.h"        // base analysis class
+
+class AliFemtoAnalysisReactionPlane : public AliFemtoSimpleAnalysis {
+
+public:
+
+  AliFemtoAnalysisReactionPlane(unsigned int binsVertex=10, double minVertex=-100., double maxVertex=+100., unsigned int binsMult=10, double minMult=-1.e9, double maxMult=+1.e9, unsigned short binsRP=10);
+  AliFemtoAnalysisReactionPlane(const AliFemtoAnalysisReactionPlane& TheOriginalAnalysis);  // copy constructor
+  AliFemtoAnalysisReactionPlane& operator=(const AliFemtoAnalysisReactionPlane& TheOriginalAnalysis); 
+  virtual void ProcessEvent(const AliFemtoEvent* ProcessThisEvent);
+  virtual ~AliFemtoAnalysisReactionPlane();
+  virtual AliFemtoString Report();       //! returns reports of all cuts applied and correlation functions being done
+  virtual unsigned int OverflowVertexZ() const { return fOverFlowVertexZ;}
+  virtual unsigned int UnderflowVertexZ() const { return fUnderFlowVertexZ;}
+  virtual unsigned int OverflowMult() const { return fOverFlowMult;}
+  virtual unsigned int UnderflowMult() const { return fUnderFlowMult;}
+  double GetCurrentReactionPlane();
+
+protected:
+  double fVertexZ[2];                 /* min/max z-vertex position allowed to be processed */
+  unsigned int fVertexZBins;          /* number of VERTEX mixing bins in z-vertex in EventMixing Buffer */
+  unsigned int fOverFlowVertexZ;      /* number of events encountered which had too large z-vertex */
+  unsigned int fUnderFlowVertexZ;     /* number of events encountered which had too small z-vertex */
+  double fMult[2];                    /* min/max multiplicity allowed for event to be processed */
+  unsigned int fMultBins;             /* number of MULTIPLICITY mixing bins in z-vertex in EventMixing Buffer */
+  unsigned int fOverFlowMult;         /* number of events encountered which had too large multiplicity */
+  unsigned int fUnderFlowMult;        /* number of events encountered which had too small multiplicity */
+  unsigned short fRPBins;             // Number of reaction plane angle orientation bins
+  double fCurrentRP;                  // Reaction plane angle of the current event
+#ifdef __ROOT__
+  ClassDef(AliFemtoAnalysisReactionPlane, 0)
+#endif
+    
+};
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoBPLCMS3DCorrFctn.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoBPLCMS3DCorrFctn.cxx
new file mode 100644 (file)
index 0000000..77900c3
--- /dev/null
@@ -0,0 +1,461 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFemtoBPLCMS3DCorrFctn: a class to calculate 3D correlation         //
+// for pairs of identical particles.                                     //
+// It also stored the weighted qinv per bin histogram for the coulomb    //
+// correction.                                                           //
+// In analysis the function should be first created in a macro, then     //
+// added to the analysis, and at the end of the macro the procedure to   //
+// write out histograms should be called.                                //
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+
+#include "AliFemtoBPLCMS3DCorrFctn.h"
+#include "AliFemtoKTPairCut.h"
+#include "AliFemtoAnalysisReactionPlane.h"
+//#include "AliFemtoHisto.h"
+#include <cstdio>
+
+#ifdef __ROOT__ 
+ClassImp(AliFemtoBPLCMS3DCorrFctn)
+#endif
+
+//____________________________
+AliFemtoBPLCMS3DCorrFctn::AliFemtoBPLCMS3DCorrFctn(char* title, const int& nbins, const float& QLo, const float& QHi)
+  :
+  AliFemtoCorrFctn(),
+//   fIDNumHisto(0),
+//   fIDDenHisto(0),
+//   fIDRatHisto(0),
+//   fSMNumHisto(0),
+//   fSMDenHisto(0),
+//   fSMRatHisto(0),
+//   fCorrectionHisto(0),
+//   fCorrCFHisto(0),
+  fNumerator(0),
+  fDenominator(0),
+  fRatio(0),
+  fQinvHisto(0),
+  fLambda(0),
+  fRout2(0),
+  fRside2(0),
+  fRlong2(0),
+  fQinvNormLo(0),
+  fQinvNormHi(0),
+  fNumRealsNorm(0),
+  fNumMixedNorm(0),
+  fUseRPSelection(0)
+{
+  // Basic constructor
+  // set some stuff...
+  fQinvNormLo = (QHi-QLo)*0.8;
+  fQinvNormHi = (QHi-QLo)*0.8;
+  fNumRealsNorm = 0;
+  fNumMixedNorm = 0;
+  //  fCorrection = 0;  // pointer to Coulomb Correction object
+
+  //  fSmearPair = 0; // no resolution correction unless user sets SmearPair
+
+  // set up numerator
+  char tTitNum[101] = "Num";
+  strncat(tTitNum,title, 100);
+  fNumerator = new TH3D(tTitNum,title,nbins,-QHi,QHi,nbins,-QHi,QHi,nbins,-QHi,QHi);
+  // set up denominator
+  char tTitDen[101] = "Den";
+  strncat(tTitDen,title, 100);
+  fDenominator = new TH3D(tTitDen,title,nbins,-QHi,QHi,nbins,-QHi,QHi,nbins,-QHi,QHi);
+  // set up uncorrected denominator
+  char tTitDenUncoul[101] = "DenNoCoul";
+  strncat(tTitDenUncoul,title, 100);
+  //  fUncorrectedDenominator = new TH3D(tTitDenUncoul,title,nbins,-QHi,QHi,nbins,-QHi,QHi,nbins,-QHi,QHi);
+  // set up ratio
+  char tTitRat[101] = "Rat";
+  strncat(tTitRat,title, 100);
+  fRatio = new TH3D(tTitRat,title,nbins,-QHi,QHi,nbins,-QHi,QHi,nbins,-QHi,QHi);
+  // set up ave qInv
+  char tTitQinv[101] = "Qinv";
+  strncat(tTitQinv,title, 100);
+  fQinvHisto = new TH3D(tTitQinv,title,nbins,-QHi,QHi,nbins,-QHi,QHi,nbins,-QHi,QHi);
+
+  // to enable error bar calculation...
+  fNumerator->Sumw2();
+  fDenominator->Sumw2();
+  //  fUncorrectedDenominator->Sumw2();
+  fRatio->Sumw2();
+
+//   // Following histos are for the momentum resolution correction
+//   // they are filled only if a AliFemtoSmear object is plugged in
+//   // here comes the "idea" numerator and denominator and ratio...
+//   char tTitNumID[101] = "IDNum";
+//   strncat(tTitNumID,title, 100);
+//   fIDNumHisto = new TH3D(tTitNumID,title,nbins,-QHi,QHi,nbins,-QHi,QHi,nbins,-QHi,QHi);
+//   char tTitDenID[101] = "IDDen";
+//   strncat(tTitDenID,title, 100);
+//   fIDDenHisto = new TH3D(tTitDenID,title,nbins,-QHi,QHi,nbins,-QHi,QHi,nbins,-QHi,QHi);
+//   char tTitRatID[101] = "IDRat";
+//   strncat(tTitRatID,title, 100);
+//   fIDRatHisto = new TH3D(tTitRatID,title,nbins,-QHi,QHi,nbins,-QHi,QHi,nbins,-QHi,QHi);
+
+//   fIDNumHisto->Sumw2();
+//   fIDDenHisto->Sumw2();
+//   fIDRatHisto->Sumw2();
+
+//   //
+//   // here comes the "smeared" numerator and denominator...
+//   char tTitNumSM[101] = "SMNum";
+//   strncat(tTitNumSM,title, 100);
+//   fSMNumHisto = new TH3D(tTitNumSM,title,nbins,-QHi,QHi,nbins,-QHi,QHi,nbins,-QHi,QHi);
+//   char tTitDenSM[101] = "SMDen";
+//   strncat(tTitDenSM,title, 100);
+//   fSMDenHisto = new TH3D(tTitDenSM,title,nbins,-QHi,QHi,nbins,-QHi,QHi,nbins,-QHi,QHi);
+//   char tTitRatSM[101] = "SMRat";
+//   strncat(tTitRatSM,title, 100);
+//   fSMRatHisto = new TH3D(tTitRatSM,title,nbins,-QHi,QHi,nbins,-QHi,QHi,nbins,-QHi,QHi);
+//   //
+//   fSMNumHisto->Sumw2();
+//   fSMDenHisto->Sumw2();
+//   fSMRatHisto->Sumw2();
+//   //
+//   // here comes the correction factor (which is just ratio of ideal ratio to smeared ratio)
+//   char tTitCorrection[101] = "CorrectionFactor";
+//   strncat(tTitCorrection,title, 100);
+//   fCorrectionHisto = new TH3D(tTitCorrection,title,nbins,-QHi,QHi,nbins,-QHi,QHi,nbins,-QHi,QHi);  
+//   fCorrectionHisto->Sumw2();
+//   // here comes the fully corrected correlation function
+//   char tTitCorrCF[101] = "CorrectedCF";
+//   strncat(tTitCorrCF,title, 100);
+//   fCorrCFHisto = new TH3D(tTitCorrCF,title,nbins,-QHi,QHi,nbins,-QHi,QHi,nbins,-QHi,QHi);
+//   fCorrCFHisto->Sumw2();
+
+  // user can (and should) override these defaults...
+  fLambda = 0.6;
+  fRout2 = 6.0*6.0;
+  fRside2 = 6.0*6.0;
+  fRlong2 = 7.0*7.0;
+
+}
+
+AliFemtoBPLCMS3DCorrFctn::AliFemtoBPLCMS3DCorrFctn(const AliFemtoBPLCMS3DCorrFctn& aCorrFctn) :
+  AliFemtoCorrFctn(aCorrFctn),
+//   fIDNumHisto(0),
+//   fIDDenHisto(0),
+//   fIDRatHisto(0),
+//   fSMNumHisto(0),
+//   fSMDenHisto(0),
+//   fSMRatHisto(0),
+//   fCorrectionHisto(0),
+//   fCorrCFHisto(0),
+  fNumerator(0),
+  fDenominator(0),
+  fRatio(0),
+  fQinvHisto(0),
+  fLambda(0),
+  fRout2(0),
+  fRside2(0),
+  fRlong2(0),
+  fQinvNormLo(0),
+  fQinvNormHi(0),
+  fNumRealsNorm(0),
+  fNumMixedNorm(0),
+  fUseRPSelection(0)
+{
+  // Copy constructor
+//   fIDNumHisto = new TH3D(*aCorrFctn.fIDNumHisto);
+//   fIDDenHisto = new TH3D(*aCorrFctn.fIDDenHisto);
+//   fIDRatHisto = new TH3D(*aCorrFctn.fIDRatHisto);
+//   fSMNumHisto = new TH3D(*aCorrFctn.fSMNumHisto);
+//   fSMDenHisto = new TH3D(*aCorrFctn.fSMDenHisto);
+//   fSMRatHisto = new TH3D(*aCorrFctn.fSMRatHisto);
+//   fCorrectionHisto = new TH3D(*aCorrFctn.fCorrectionHisto);
+//   fCorrCFHisto = new TH3D(*aCorrFctn.fCorrCFHisto);
+  fNumerator = new TH3D(*aCorrFctn.fNumerator);
+  fDenominator = new TH3D(*aCorrFctn.fDenominator);
+  fRatio = new TH3D(*aCorrFctn.fRatio);
+  fQinvHisto = new TH3D(*aCorrFctn.fQinvHisto);
+  fLambda = aCorrFctn.fLambda;
+  fRout2 = aCorrFctn.fRout2;
+  fRside2 = aCorrFctn.fRside2;
+  fRlong2 = aCorrFctn.fRlong2;
+  fQinvNormLo = aCorrFctn.fQinvNormLo;
+  fQinvNormHi = aCorrFctn.fQinvNormHi;
+  fNumRealsNorm = aCorrFctn.fNumRealsNorm;
+  fNumMixedNorm = aCorrFctn.fNumMixedNorm;
+  fUseRPSelection = aCorrFctn.fUseRPSelection;
+}
+//____________________________
+AliFemtoBPLCMS3DCorrFctn::~AliFemtoBPLCMS3DCorrFctn(){
+  // Destructor
+  delete fNumerator;
+  delete fDenominator;
+  delete fRatio;
+  delete fQinvHisto;
+//   delete fIDNumHisto;
+//   delete fIDDenHisto;
+//   delete fIDRatHisto;
+//   delete fSMNumHisto;
+//   delete fSMDenHisto;
+//   delete fSMRatHisto;
+//   delete fCorrectionHisto;
+//   delete fCorrCFHisto;
+}
+//_________________________
+AliFemtoBPLCMS3DCorrFctn& AliFemtoBPLCMS3DCorrFctn::operator=(const AliFemtoBPLCMS3DCorrFctn& aCorrFctn)
+{
+  // assignment operator
+  if (this == &aCorrFctn)
+    return *this;
+//   if (fIDNumHisto) delete fIDNumHisto;
+//   fIDNumHisto = new TH3D(*aCorrFctn.fIDNumHisto);
+//   if (fIDDenHisto) delete fIDDenHisto;
+//   fIDDenHisto = new TH3D(*aCorrFctn.fIDDenHisto);
+//   if (fIDRatHisto) delete fIDRatHisto;
+//   fIDRatHisto = new TH3D(*aCorrFctn.fIDRatHisto);
+//   if (fSMNumHisto) delete fSMNumHisto;
+//   fSMNumHisto = new TH3D(*aCorrFctn.fSMNumHisto);
+//   if (fSMDenHisto) delete fSMDenHisto;
+//   fSMDenHisto = new TH3D(*aCorrFctn.fSMDenHisto);
+//   if (fSMRatHisto) delete fSMRatHisto;
+//   fSMRatHisto = new TH3D(*aCorrFctn.fSMRatHisto);
+
+//   if (fCorrectionHisto) delete fCorrectionHisto;
+//   fCorrectionHisto = new TH3D(*aCorrFctn.fCorrectionHisto);
+//   if (fCorrCFHisto) delete fCorrCFHisto;
+//   fCorrCFHisto = new TH3D(*aCorrFctn.fCorrCFHisto);
+  if (fNumerator) delete fNumerator;
+  fNumerator = new TH3D(*aCorrFctn.fNumerator);
+  if (fDenominator) delete fDenominator;
+  fDenominator = new TH3D(*aCorrFctn.fDenominator);
+  if (fRatio) delete fRatio;
+  fRatio = new TH3D(*aCorrFctn.fRatio);
+  if (fQinvHisto) delete fQinvHisto;
+  fQinvHisto = new TH3D(*aCorrFctn.fQinvHisto);
+
+  fLambda = aCorrFctn.fLambda;
+  fRout2 = aCorrFctn.fRout2;
+  fRside2 = aCorrFctn.fRside2;
+  fRlong2 = aCorrFctn.fRlong2;
+  fQinvNormLo = aCorrFctn.fQinvNormLo;
+  fQinvNormHi = aCorrFctn.fQinvNormHi;
+  fNumRealsNorm = aCorrFctn.fNumRealsNorm;
+  fNumMixedNorm = aCorrFctn.fNumMixedNorm;
+  fUseRPSelection = aCorrFctn.fUseRPSelection;
+
+  return *this;
+}
+
+//_________________________
+void AliFemtoBPLCMS3DCorrFctn::WriteOutHistos(){
+  // Write out all histograms to file
+  fNumerator->Write();
+  fDenominator->Write();
+  //  fUncorrectedDenominator->Write();
+  fRatio->Write();
+  fQinvHisto->Write();
+
+  /*
+    if (fSmearPair){
+    fIDNumHisto->Write();
+    fIDDenHisto->Write();
+    fIDRatHisto->Write();
+    //
+    fSMNumHisto->Write();
+    fSMDenHisto->Write();
+    fSMRatHisto->Write();
+    //
+    fCorrectionHisto->Write();
+    fCorrCFHisto->Write();
+    }
+  */
+}
+//______________________________
+TList* AliFemtoBPLCMS3DCorrFctn::GetOutputList()
+{
+  // Prepare the list of objects to be written to the output
+  TList *tOutputList = new TList();
+
+  tOutputList->Add(fNumerator); 
+  tOutputList->Add(fDenominator);  
+  tOutputList->Add(fQinvHisto);  
+
+  return tOutputList;
+}
+
+//_________________________
+void AliFemtoBPLCMS3DCorrFctn::Finish(){
+  // here is where we should normalize, fit, etc...
+  double tNumFact,tDenFact;
+  if ((fNumRealsNorm !=0) && (fNumMixedNorm !=0)){
+    tNumFact = double(fNumRealsNorm);
+    tDenFact = double(fNumMixedNorm);
+  }
+  // can happen that the fNumRealsNorm and fNumMixedNorm = 0 if you do non-standard
+  //   things like making a new CorrFctn and just setting the Numerator and Denominator
+  //   from OTHER CorrFctns which you read in (like when doing parallel processing) 
+  else{
+    cout << "Warning! - no normalization constants defined - I do the best I can..." << endl;
+    int nbins = fNumerator->GetNbinsX();
+    int half_way = nbins/2;
+    tNumFact = fNumerator->Integral(half_way,nbins,half_way,nbins,half_way,nbins);
+    tDenFact = fDenominator->Integral(half_way,nbins,half_way,nbins,half_way,nbins);
+  }
+
+  fRatio->Divide(fNumerator,fDenominator,tDenFact,tNumFact);
+  //  fQinvHisto->Divide(fUncorrectedDenominator);
+  fQinvHisto->Divide(fDenominator);
+
+  /*
+  // now do all the resolution correction stuff..
+  if (fSmearPair){  // but only do it if we have been working with a SmearPair
+  fIDRatHisto->Divide(fIDNumHisto,fIDDenHisto);
+  fSMRatHisto->Divide(fSMNumHisto,fSMDenHisto);
+  fCorrectionHisto->Divide(fIDRatHisto,fSMRatHisto);
+  fCorrCFHisto->Multiply(fRatio,fCorrectionHisto);
+  }
+  */
+
+}
+
+//____________________________
+AliFemtoString AliFemtoBPLCMS3DCorrFctn::Report(){
+  // Construct the report
+  string stemp = "LCMS Frame Bertsch-Pratt 3D Correlation Function Report:\n";
+  char ctemp[100];
+  snprintf(ctemp , 100, "Number of entries in numerator:\t%E\n",fNumerator->GetEntries());
+  stemp += ctemp;
+  snprintf(ctemp , 100, "Number of entries in denominator:\t%E\n",fDenominator->GetEntries());
+  stemp += ctemp;
+  snprintf(ctemp , 100, "Number of entries in ratio:\t%E\n",fRatio->GetEntries());
+  stemp += ctemp;
+  snprintf(ctemp , 100, "Normalization region in Qinv was:\t%E\t%E\n",fQinvNormLo,fQinvNormHi);
+  stemp += ctemp;
+  snprintf(ctemp , 100, "Number of pairs in Normalization region was:\n");
+  stemp += ctemp;
+  snprintf(ctemp , 100, "In numerator:\t%lu\t In denominator:\t%lu\n",fNumRealsNorm,fNumMixedNorm);
+  stemp += ctemp;
+  /*  if (fCorrection)
+      {
+      float radius = fCorrection->GetRadius();
+      snprintf(ctemp , 100, "Coulomb correction used radius of\t%E\n",radius);
+      }
+      else
+      {
+      snprintf(ctemp , 100, "No Coulomb Correction applied to this CorrFctn\n");
+      }
+      stemp += ctemp;
+  */
+
+  if (fPairCut){
+    snprintf(ctemp , 100, "Here is the PairCut specific to this CorrFctn\n");
+    stemp += ctemp;
+    stemp += fPairCut->Report();
+  }
+  else{
+    snprintf(ctemp , 100, "No PairCut specific to this CorrFctn\n");
+    stemp += ctemp;
+  }
+
+  //  
+  AliFemtoString returnThis = stemp;
+  return returnThis;
+}
+//____________________________
+void AliFemtoBPLCMS3DCorrFctn::AddRealPair( AliFemtoPair* pair){
+  // perform operations on real pairs
+  if (fPairCut){
+    if (fUseRPSelection) {
+      AliFemtoKTPairCut *ktc = dynamic_cast<AliFemtoKTPairCut *>(fPairCut);
+      if (!ktc) { 
+       cout << "RP aware cut requested, but not connected to the CF" << endl;
+       if (!(fPairCut->Pass(pair))) return;
+      }
+      else {
+       AliFemtoAnalysisReactionPlane *arp = dynamic_cast<AliFemtoAnalysisReactionPlane *> (HbtAnalysis());
+       if (!arp) {
+         cout << "RP aware cut requested, but not connected to the CF" << endl;
+         if (!(fPairCut->Pass(pair))) return;
+       }
+       else if (!(ktc->Pass(pair, arp->GetCurrentReactionPlane()))) return;
+      }
+    }
+    else
+      if (!(fPairCut->Pass(pair))) return;
+  }
+
+  double tQinv = fabs(pair->QInv());   // note - qInv() will be negative for identical pairs...
+  if ((tQinv < fQinvNormHi) && (tQinv > fQinvNormLo)) fNumRealsNorm++;
+  double qOut = (pair->QOutCMS());
+  double qSide = (pair->QSideCMS());
+  double qLong = (pair->QLongCMS());
+
+  fNumerator->Fill(qOut,qSide,qLong);
+}
+//____________________________
+void AliFemtoBPLCMS3DCorrFctn::AddMixedPair( AliFemtoPair* pair){
+  // perform operations on mixed pairs
+//   if (fPairCut){
+//     if (!(fPairCut->Pass(pair))) return;
+//   }
+  if (fPairCut){
+    if (fUseRPSelection) {
+      AliFemtoKTPairCut *ktc = dynamic_cast<AliFemtoKTPairCut *>(fPairCut);
+      if (!ktc) { 
+       cout << "RP aware cut requested, but not connected to the CF" << endl;
+       if (!(fPairCut->Pass(pair))) return;
+      }
+      else {
+       AliFemtoAnalysisReactionPlane *arp = dynamic_cast<AliFemtoAnalysisReactionPlane *> (HbtAnalysis());
+       if (!arp) {
+         cout << "RP aware cut requested, but not connected to the CF" << endl;
+         if (!(fPairCut->Pass(pair))) return;
+       }
+       else if (!(ktc->Pass(pair, arp->GetCurrentReactionPlane()))) return;
+      }
+    }
+    else
+      if (!(fPairCut->Pass(pair))) return;
+  }
+
+  //  double CoulombWeight = (fCorrection ? fCorrection->CoulombCorrect(pair) : 1.0);
+  double tCoulombWeight = 1.0;
+
+  double tQinv = fabs(pair->QInv());   // note - qInv() will be negative for identical pairs...
+  if ((tQinv < fQinvNormHi) && (tQinv > fQinvNormLo)) fNumMixedNorm++;
+  double qOut = (pair->QOutCMS());
+  double qSide = (pair->QSideCMS());
+  double qLong = (pair->QLongCMS());
+
+  fDenominator->Fill(qOut,qSide,qLong,tCoulombWeight);
+  //  fUncorrectedDenominator->Fill(qOut,qSide,qLong,1.0);
+  fQinvHisto->Fill(qOut,qSide,qLong,tQinv);
+
+  /*
+  // now for the momentum resolution stuff...
+  if (fSmearPair){
+      double CorrWeight =  1.0 + 
+      fLambda*exp((-qOut*qOut*fRout2 -qSide*qSide*fRside2 -qLong*qLong*fRlong2)/0.038936366329);
+    CorrWeight *= CoulombWeight;  // impt.
+
+    fIDNumHisto->Fill(qOut,qSide,qLong,CorrWeight);
+    fIDDenHisto->Fill(qOut,qSide,qLong,CoulombWeight);
+
+    fSmearPair->SetUnsmearedPair(pair);
+    double qOut_prime = fabs(fSmearPair->SmearedPair().qOutCMS());
+    double qSide_prime = fabs(fSmearPair->SmearedPair().qSideCMS());
+    double qLong_prime = fabs(fSmearPair->SmearedPair().qLongCMS());
+
+    fSMNumHisto->Fill(qOut_prime,qSide_prime,qLong_prime,CorrWeight);
+
+    double SmearedCoulombWeight = ( fCorrection ? 
+                                   fCorrection->CoulombCorrect(&(fSmearPair->SmearedPair())) : 
+                                   1.0);
+
+    fSMDenHisto->Fill(qOut_prime,qSide_prime,qLong_prime,SmearedCoulombWeight);
+  }
+  */
+}
+
+
+void AliFemtoBPLCMS3DCorrFctn::SetUseRPSelection(unsigned short aRPSel)
+{
+  fUseRPSelection = aRPSel;
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoBPLCMS3DCorrFctn.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoBPLCMS3DCorrFctn.h
new file mode 100644 (file)
index 0000000..053eb8c
--- /dev/null
@@ -0,0 +1,121 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFemtoBPLCMS3DCorrFctn: a class to calculate 3D correlation         //
+// for pairs of identical particles.                                     //
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+
+#ifndef ALIFEMTOBPLCMS3DCORRFCTN_H
+#define ALIFEMTOBPLCMS3DCORRFCTN_H
+
+#include "AliFemtoCorrFctn.h"
+//#include "AliFemtoCoulomb.h"
+#include "AliFemtoPairCut.h"
+//#include "AliFemtoHisto.h"
+#include "TH3D.h"
+//#include "AliFemtoSmearPair.h"
+
+class AliFemtoBPLCMS3DCorrFctn : public AliFemtoCorrFctn {
+public:
+  AliFemtoBPLCMS3DCorrFctn(char* title, const int& nbins, const float& QLo, const float& QHi);
+  AliFemtoBPLCMS3DCorrFctn(const AliFemtoBPLCMS3DCorrFctn& aCorrFctn);
+  virtual ~AliFemtoBPLCMS3DCorrFctn();
+
+  AliFemtoBPLCMS3DCorrFctn& operator=(const AliFemtoBPLCMS3DCorrFctn& aCorrFctn);
+
+  virtual AliFemtoString Report();
+  virtual void AddRealPair( AliFemtoPair* aPair);
+  virtual void AddMixedPair( AliFemtoPair* aPair);
+
+  virtual void Finish();
+
+  TH3D* Numerator();
+  TH3D* Denominator();
+  TH3D* Ratio();
+  TH3D* QinvHisto();
+
+  // here are get and set for the range over which the correlation function 
+  // is normalized (in Qinv).  The range is set to 0.15..0.18 in the constuctor
+  // by default, but the Set's below override this
+  void SetNormRangeLo(float qLo);
+  void SetNormRangeHi(float qHi);
+  float GetNormRangeLo() const;
+  float GetNormRangeHi() const;
+
+  void WriteOutHistos();
+  virtual TList* GetOutputList();
+
+  //  void SetCoulombCorrection(AliFemtoCoulomb* Correction);
+
+  void SetUseRPSelection(unsigned short aRPSel);
+
+  //  void SetSmearPair(AliFemtoSmearPair*);
+  void SetRout(double guess);
+  void SetRside(double guess);
+  void SetRlong(double guess);
+  void SetLambda(double guess);
+
+private:
+/*   // here are a whole bunch of histos that get filled if we do resolution correction */
+/*   TH3D* fIDNumHisto;        // true pairs numerator   */
+/*   TH3D* fIDDenHisto;        // true pairs denominator */
+/*   TH3D* fIDRatHisto;        // true pairs ratio       */
+/*   //  */
+/*   TH3D* fSMNumHisto;        // mixed pairs numerator   */
+/*   TH3D* fSMDenHisto;            // mixed pairs denominator */
+/*   TH3D* fSMRatHisto;            // mixed pairs ratio       */
+/*   // */
+/*   TH3D* fCorrectionHisto;   // correction histogram */
+/*   TH3D* fCorrCFHisto;       // Corrected CF */
+
+  TH3D* fNumerator;         // numerator
+  TH3D* fDenominator;       // denominator
+  //  TH3D* fUncorrectedDenominator;
+  TH3D* fRatio;             // ratio - the correlation function
+  TH3D* fQinvHisto;         // Qinv weights
+
+  // for resolution correction
+  //  AliFemtoSmearPair* fSmearPair; //!
+  double fLambda;           // lambda for smearing correction
+  double fRout2;            // Rout for smearing correction
+  double fRside2;           // Rside for smearing correction
+  double fRlong2;           // Rlong for smearing correction
+
+  // upper and lower bounds of Qinv region where to do normalization
+  float fQinvNormLo;        // Lower bound of Qinv normalization range
+  float fQinvNormHi;        // Upper bound of Qinv normalization range
+
+  // and here are the number of pairs in that region...
+  unsigned long int fNumRealsNorm; // pairs in numerator in Qinv normalization range
+  unsigned long int fNumMixedNorm; // pairs in denominator in Qinv normalization range
+
+ protected:
+  unsigned short fUseRPSelection;  // The pair cut uses RP selection
+
+  //  AliFemtoCoulomb* fCorrection; //!
+  
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoBPLCMS3DCorrFctn, 1)
+#endif
+};
+
+inline  TH3D* AliFemtoBPLCMS3DCorrFctn::Numerator(){return fNumerator;}
+inline  TH3D* AliFemtoBPLCMS3DCorrFctn::Denominator(){return fDenominator;}
+//inline  TH3D* AliFemtoBPLCMS3DCorrFctn::UncorrectedDenominator(){return fUncorrectedDenominator;}
+inline  TH3D* AliFemtoBPLCMS3DCorrFctn::Ratio(){return fRatio;}
+inline  TH3D* AliFemtoBPLCMS3DCorrFctn::QinvHisto(){return fQinvHisto;}
+inline  void AliFemtoBPLCMS3DCorrFctn::SetNormRangeLo(float qLo){fQinvNormLo = qLo;}
+inline  void AliFemtoBPLCMS3DCorrFctn::SetNormRangeHi(float qHi){fQinvNormHi = qHi;}
+inline  float AliFemtoBPLCMS3DCorrFctn::GetNormRangeLo() const{return fQinvNormLo;}
+inline  float AliFemtoBPLCMS3DCorrFctn::GetNormRangeHi() const{return fQinvNormHi;}
+//inline  void AliFemtoBPLCMS3DCorrFctn::SetCoulombCorrection(AliFemtoCoulomb* Correction){fCorrection = Correction;}
+//inline  void AliFemtoBPLCMS3DCorrFctn::SetSmearPair(AliFemtoSmearPair* sp){fSmearPair = sp;}
+
+inline  void AliFemtoBPLCMS3DCorrFctn::SetRout(double r){fRout2 = r*r;}
+inline  void AliFemtoBPLCMS3DCorrFctn::SetRside(double r){fRside2 = r*r;}
+inline  void AliFemtoBPLCMS3DCorrFctn::SetRlong(double r){fRlong2 = r*r;}
+inline  void AliFemtoBPLCMS3DCorrFctn::SetLambda(double l){fLambda = l;}
+
+#endif
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoBasicEventCut.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoBasicEventCut.cxx
new file mode 100644 (file)
index 0000000..149a99c
--- /dev/null
@@ -0,0 +1,87 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoBasicEventCut - the basic cut for events.                          //
+// Only cuts on event multiplicity and z-vertex position                      //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+
+#include "AliFemtoBasicEventCut.h"
+//#include <cstdio>
+
+#ifdef __ROOT__
+ClassImp(AliFemtoBasicEventCut)
+#endif
+
+AliFemtoBasicEventCut::AliFemtoBasicEventCut() :
+  AliFemtoEventCut(),
+  fEventMult(),
+  fVertZPos(),
+  fAcceptBadVertex(false), 
+  fNEventsPassed(0), 
+  fNEventsFailed(0),
+  fAcceptOnlyPhysics(true),
+  fSelectTrigger(0)
+{
+  // Default constructor
+  fEventMult[0] = 0;
+  fEventMult[1] = 100000;
+  fVertZPos[0] = -100.0;
+  fVertZPos[1] = 100.0;
+} 
+//------------------------------
+AliFemtoBasicEventCut::~AliFemtoBasicEventCut(){
+  // Default destructor
+}
+//------------------------------
+bool AliFemtoBasicEventCut::Pass(const AliFemtoEvent* event){
+  // Pass events if they fall within the multiplicity and z-vertex
+  // position range. Fail otherwise
+  //  int mult =  event->NumberOfTracks();
+  int mult = (int) event->UncorrectedNumberOfPrimaries();
+  double vertexZPos = event->PrimVertPos().z();
+//   cout << "AliFemtoBasicEventCut:: mult:       " << fEventMult[0] << " < " << mult << " < " << fEventMult[1] << endl;
+//   cout << "AliFemtoBasicEventCut:: VertexZPos: " << fVertZPos[0] << " < " << vertexZPos << " < " << fVertZPos[1] << endl;
+//   cout << "AliFemtoBasicEventCut:: VertexZErr: " << event->PrimVertCov()[4] << endl;
+  bool goodEvent =
+    ((mult >= fEventMult[0]) && 
+     (mult <= fEventMult[1]) && 
+     (vertexZPos > fVertZPos[0]) &&
+     (vertexZPos < fVertZPos[1]) &&
+     ((!fAcceptBadVertex) || (event->ZDCParticipants() > 1.0)) &&
+     ((!fAcceptOnlyPhysics) || (event->IsCollisionCandidate())) &&
+     ((!fSelectTrigger) || (event->TriggerCluster() == fSelectTrigger)));
+  goodEvent ? fNEventsPassed++ : fNEventsFailed++ ;
+//   cout << "AliFemtoBasicEventCut:: return : " << goodEvent << endl;
+//     (fAcceptBadVertex || (event->PrimVertCov()[4] > -1000.0)) &&
+  return (goodEvent);
+}
+//------------------------------
+AliFemtoString AliFemtoBasicEventCut::Report(){
+  // Prepare report
+  string stemp;
+  char ctemp[100];
+  snprintf(ctemp , 100, "\nMultiplicity:\t %d-%d",fEventMult[0],fEventMult[1]);
+  stemp = ctemp;
+  snprintf(ctemp , 100, "\nVertex Z-position:\t %E-%E",fVertZPos[0],fVertZPos[1]);
+  stemp += ctemp;
+  snprintf(ctemp , 100, "\nNumber of events which passed:\t%ld  Number which failed:\t%ld",fNEventsPassed,fNEventsFailed);
+  stemp += ctemp;
+  AliFemtoString returnThis = stemp;
+  return returnThis;
+}
+void AliFemtoBasicEventCut::SetAcceptBadVertex(bool b)
+{
+  fAcceptBadVertex = b;
+}
+bool AliFemtoBasicEventCut::GetAcceptBadVertex()
+{
+  return fAcceptBadVertex;
+}
+void AliFemtoBasicEventCut::SetAcceptOnlyPhysics(bool b)
+{
+  fAcceptOnlyPhysics = b;
+}
+bool AliFemtoBasicEventCut::GetAcceptOnlyPhysics()
+{
+  return fAcceptOnlyPhysics;
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoBasicEventCut.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoBasicEventCut.h
new file mode 100644 (file)
index 0000000..f991459
--- /dev/null
@@ -0,0 +1,84 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoBasicEventCut - the basic cut for events.                          //
+// Only cuts on event multiplicity and z-vertex position                      //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+
+#ifndef ALIFEMTOBASICEVENTCUT_H
+#define ALIFEMTOBASICEVENTCUT_H
+
+// do I need these lines ?
+//#ifndef StMaker_H
+//#include "StMaker.h"
+//#endif
+
+#include "AliFemtoEventCut.h"
+
+class AliFemtoBasicEventCut : public AliFemtoEventCut {
+
+public:
+
+  AliFemtoBasicEventCut();
+  AliFemtoBasicEventCut(AliFemtoBasicEventCut& c);
+  virtual ~AliFemtoBasicEventCut();
+  AliFemtoBasicEventCut& operator=(AliFemtoBasicEventCut& c);
+
+  void SetEventMult(const int& lo,const int& hi);
+  void SetVertZPos(const float& lo, const float& hi);
+  void SetAcceptBadVertex(bool b);
+  void SetAcceptOnlyPhysics(bool b);
+  int NEventsPassed() const;
+  int NEventsFailed() const;
+  bool GetAcceptBadVertex();
+  bool GetAcceptOnlyPhysics();
+  void SetTriggerSelection(int trig);
+
+  virtual AliFemtoString Report();
+  virtual bool Pass(const AliFemtoEvent* event);
+
+  AliFemtoBasicEventCut* Clone();
+
+private:   // here are the quantities I want to cut on...
+
+  int fEventMult[2];      // range of multiplicity
+  float fVertZPos[2];     // range of z-position of vertex
+  bool fAcceptBadVertex;  // Set to true to accept events with bad vertex
+  long fNEventsPassed;    // Number of events checked by this cut that passed
+  long fNEventsFailed;    // Number of events checked by this cut that failed
+  bool fAcceptOnlyPhysics;// Accept only physics events
+  int  fSelectTrigger;    // If set, only given trigger will be selected
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoBasicEventCut, 1)
+#endif
+
+};
+
+inline void AliFemtoBasicEventCut::SetEventMult(const int& lo, const int& hi){fEventMult[0]=lo; fEventMult[1]=hi;}
+inline void AliFemtoBasicEventCut::SetVertZPos(const float& lo, const float& hi){fVertZPos[0]=lo; fVertZPos[1]=hi;}
+inline int  AliFemtoBasicEventCut::NEventsPassed() const {return fNEventsPassed;}
+inline int  AliFemtoBasicEventCut::NEventsFailed() const {return fNEventsFailed;}
+inline void AliFemtoBasicEventCut::SetTriggerSelection(int trig) { fSelectTrigger = trig; }
+inline AliFemtoBasicEventCut* AliFemtoBasicEventCut::Clone() { AliFemtoBasicEventCut* c = new AliFemtoBasicEventCut(*this); return c;}
+inline AliFemtoBasicEventCut::AliFemtoBasicEventCut(AliFemtoBasicEventCut& c) : AliFemtoEventCut(c), fAcceptBadVertex(false), fNEventsPassed(0), fNEventsFailed(0), fAcceptOnlyPhysics(false), fSelectTrigger(0) {
+  fEventMult[0] = c.fEventMult[0];
+  fEventMult[1] = c.fEventMult[1];
+  fVertZPos[0] = c.fVertZPos[0];
+  fVertZPos[1] = c.fVertZPos[1];
+}
+
+inline AliFemtoBasicEventCut& AliFemtoBasicEventCut::operator=(AliFemtoBasicEventCut& c) {   
+  if (this != &c) {
+    AliFemtoEventCut::operator=(c);
+    fEventMult[0] = c.fEventMult[0];
+    fEventMult[1] = c.fEventMult[1];
+    fVertZPos[0] = c.fVertZPos[0];
+    fVertZPos[1] = c.fVertZPos[1];
+  }
+
+  return *this;
+}
+
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoBasicTrackCut.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoBasicTrackCut.cxx
new file mode 100644 (file)
index 0000000..34d0f28
--- /dev/null
@@ -0,0 +1,178 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoBasicTrackCut - the basic cut for tracks.                          //
+// Cuts on particle identification, transverse momentum, rapidity, distance   //
+// of closest approach to primary vertex and charge                           //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+
+#include "AliFemtoBasicTrackCut.h"
+#include <cstdio>
+
+#ifdef __ROOT__ 
+ClassImp(AliFemtoBasicTrackCut)
+#endif
+
+AliFemtoBasicTrackCut::AliFemtoBasicTrackCut():
+  fCharge(0),
+  fNTracksPassed(0),
+  fNTracksFailed(0)
+{
+  // Default constructor
+  fNTracksPassed = fNTracksFailed = 0;
+  fCharge = 1;  // takes both charges 0
+  fNSigmaPion[0] = -100.0;   fNSigmaPion[1] = 100.0;
+  fNSigmaKaon[0] = -100.0;   fNSigmaKaon[1] = 100.0;
+  fNSigmaProton[0] = -100.0; fNSigmaProton[1] = 100.0;
+  fNHits[0] = 10;          fNHits[1] = 180;
+  fPt[0]=0.0;              fPt[1] = 100.0;//100
+  fRapidity[0]=-2;       fRapidity[1]=2;//-2 2
+  fDCA[0] = -1.0;           fDCA[1] = 20.0;
+
+}
+//------------------------------
+//AliFemtoBasicTrackCut::~AliFemtoBasicTrackCut(){
+//  /* noop */
+//}
+//------------------------------
+bool AliFemtoBasicTrackCut::Pass(const AliFemtoTrack* track){
+  // test the particle and return 
+  // true if it meets all the criteria
+  // false if it doesn't meet at least one of the criteria
+
+  //  return true ;  // THIS CUT IS A STHBTDUMMY!!
+
+  /*
+    cout << endl;
+    cout << "#track " << trackCount++;
+    cout << " * pion " << (track->NSigmaPion() > fNSigmaPion[0]) && (track->NSigmaPion() < fNSigmaPion[1]);
+    cout << " * kaon " << (track->NSigmaKaon() > fNSigmaKaon[0]) && (track->NSigmaKaon() < fNSigmaKaon[1]);
+    cout << " * proton " << (track->NSigmaProton() > fNSigmaProton[0]) && (track->NSigmaProton() < fNSigmaProton[1]);
+    cout << " * charge " << (track->Charge() == fCharge);
+  */
+  bool goodPID = 1;  
+  /* ----- NOT DOING PID CUTS !!!! ------
+  bool goodPID = ((track->NSigmaPion()   > fNSigmaPion[0]) &&
+                  (track->NSigmaPion()   < fNSigmaPion[1]) &&
+                  (track->NSigmaKaon()   > fNSigmaKaon[0]) &&
+                  (track->NSigmaKaon()   < fNSigmaKaon[1]) &&
+                  (track->NSigmaProton() > fNSigmaProton[0]) &&
+                  (track->NSigmaProton() < fNSigmaProton[1]));
+  ----- NOT DOING PID CUTS !!!! ------ */
+  if (fCharge !=0){               // if user requests "charge=0" then that means ignore charge
+    goodPID = (goodPID&&(track->Charge() == fCharge));
+  }
+  if (goodPID){
+    float tEnergy = ::sqrt(track->P().Mag2()+fMass*fMass);
+    float tRapidity = 0.5*::log((tEnergy+track->P().z())/
+                           (tEnergy-track->P().z()));
+
+    float tPt = ::sqrt((track->P().x())*(track->P().x())+
+                    (track->P().y())*(track->P().y()));
+
+    
+    /*
+      cout << " * DCAxy " << (track->DCAxy()  > fDCA[0]) && (track->DCAxy()  < fDCA[1]);
+      cout << " * fDCA[0] " << fDCA[0];
+      cout << " * fDCA[1] " << fDCA[1];
+      cout << " * track->DCAxy " << track->DCAxy();
+      cout << " * NHits " <<  (track->NHits() > fNHits[0]) && (track->NHits() < fNHits[1]); 
+      cout << " * tPt " << (tPt > fPt[0]) && (tPt < fPt[1]);
+      cout << " * y " << (tRapidity > fRapidity[0]) && (tRapidity < fRapidity[1]);
+      cout << endl;
+    */
+
+    bool goodTrack=
+      (//(track->DCAxy()  > fDCA[0]) &&
+     //  (track->DCAxy()  < fDCA[1]) &&
+  //     (track->NHits() > fNHits[0]) &&
+    //   (track->NHits() < fNHits[1]) &&
+       (tPt             > fPt[0]) &&
+       (tPt             < fPt[1]) &&
+       (tRapidity      > fRapidity[0]) &&
+       (tRapidity      < fRapidity[1]));
+    //  &&
+    //       (track->PidProbPion()>0.5)&&//moje
+    //       (track->PidProbMuon()<0.47)&&//moje
+    //       (track->Label()>0);//moje
+
+    //    cout << track->DCAxy() << " " << track->NHits() << " " << Pt << " " << tRapidity << " " << tEnergy << endl;
+
+    goodTrack ? fNTracksPassed++ : fNTracksFailed++;
+    return (goodTrack);
+  }
+  else{
+    fNTracksFailed++;
+    return (goodPID);
+  }
+}
+//------------------------------
+AliFemtoString AliFemtoBasicTrackCut::Report(){
+  // construct report
+  string tStemp;
+  char tCtemp[100];
+  snprintf(tCtemp , 100, "Particle mass:\t%E\n",this->Mass());
+  tStemp=tCtemp;
+  snprintf(tCtemp , 100, "Particle charge:\t%d\n",fCharge);
+  tStemp=tCtemp;
+  snprintf(tCtemp , 100, "Particle Nsigma from pion:\t%E - %E\n",fNSigmaPion[0],fNSigmaPion[1]);
+  tStemp+=tCtemp;
+  snprintf(tCtemp , 100, "Particle Nsigma from kaon:\t%E - %E\n",fNSigmaKaon[0],fNSigmaKaon[1]);
+  tStemp+=tCtemp;
+  snprintf(tCtemp , 100, "Particle Nsigma from proton:\t%E - %E\n",fNSigmaProton[0],fNSigmaProton[1]);
+  tStemp+=tCtemp;
+  snprintf(tCtemp , 100, "Particle #hits:\t%d - %d\n",fNHits[0],fNHits[1]);
+  tStemp+=tCtemp;
+  snprintf(tCtemp , 100, "Particle pT:\t%E - %E\n",fPt[0],fPt[1]);
+  tStemp+=tCtemp;
+  snprintf(tCtemp , 100, "Particle rapidity:\t%E - %E\n",fRapidity[0],fRapidity[1]);
+  tStemp+=tCtemp;
+  snprintf(tCtemp , 100, "Particle DCA:\t%E - %E\n",fDCA[0],fDCA[1]);
+  tStemp+=tCtemp;
+  snprintf(tCtemp , 100, "Number of tracks which passed:\t%ld  Number which failed:\t%ld\n",fNTracksPassed,fNTracksFailed);
+  tStemp += tCtemp;
+  AliFemtoString returnThis = tStemp;
+  return returnThis;
+}
+
+TList *AliFemtoBasicTrackCut::ListSettings()
+{
+  // return a list of settings in a writable form
+  TList *tListSetttings = new TList();
+  char buf[200];
+  snprintf(buf, 200, "AliFemtoBasicTrackCut.mass=%f", this->Mass());
+  tListSetttings->AddLast(new TObjString(buf));
+
+  snprintf(buf, 200, "AliFemtoBasicTrackCut.charge=%i", fCharge);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoBasicTrackCut.nsigmapion.minimum=%f", fNSigmaPion[0]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoBasicTrackCut.nsigmapion.maximum=%f", fNSigmaPion[1]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoBasicTrackCut.nsigmakaon.minimum=%f", fNSigmaKaon[0]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoBasicTrackCut.nsigmakaon.maximum=%f", fNSigmaKaon[1]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoBasicTrackCut.nsigmaproton.minimum=%f", fNSigmaProton[0]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoBasicTrackCut.nsigmaproton.maximum=%f", fNSigmaProton[1]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoBasicTrackCut.nhits.minimum=%i", fNHits[0]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoBasicTrackCut.nhits.maximum=%i", fNHits[1]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoBasicTrackCut.pt.minimum=%f", fPt[0]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoBasicTrackCut.pt.maximum=%f", fPt[1]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoBasicTrackCut.rapidity.minimum=%f", fRapidity[0]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoBasicTrackCut.rapidity.maximum=%f", fRapidity[1]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoBasicTrackCut.dca.minimum=%f", fDCA[0]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoBasicTrackCut.dca.maximum=%f", fDCA[1]);
+  tListSetttings->AddLast(new TObjString(buf));
+
+  return tListSetttings;
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoBasicTrackCut.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoBasicTrackCut.h
new file mode 100644 (file)
index 0000000..d7ba801
--- /dev/null
@@ -0,0 +1,71 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoBasicTrackCut - the basic cut for tracks.                          //
+// Cuts on particle identification, transverse momentum, rapidity, distance   //
+// of closest approach to primary vertex and charge                           //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+
+#ifndef ALIFEMTOBASICTRACKCUT_H
+#define ALIFEMTOBASICTRACKCUT_H
+
+//#ifndef StMaker_H
+//#include "StMaker.h"
+//#endif
+
+#include "AliFemtoTrackCut.h"
+
+class AliFemtoBasicTrackCut : public AliFemtoTrackCut {
+
+public:
+
+  AliFemtoBasicTrackCut();
+  //~mikesTrackCut();
+
+  virtual bool Pass(const AliFemtoTrack* tr);
+
+  virtual AliFemtoString Report();
+  virtual TList *ListSettings();
+
+  void SetNSigmaPion(const float& lo, const float& hi);
+  void SetNSigmaKaon(const float& lo, const float& hi);
+  void SetNSigmaProton(const float& lo, const float& hi);
+
+  void SetNHits(const int& lo, const int& hi);
+  void SetPt(const float& lo, const float& hi);
+  void SetRapidity(const float& lo, const float& hi);
+  void SetDCA(const float& lo, const float& hi);
+  void SetCharge(const int& ch);
+
+
+private:   // here are the quantities I want to cut on...
+
+  int               fCharge;             // charge of the track
+  float             fNSigmaPion[2];      // bounds for nsigma dEdx from pion band 
+  float             fNSigmaKaon[2];      // bounds for nsigma dEdx from kaon band
+  float             fNSigmaProton[2];    // bounds for nsigma dEdx from proton band
+  int               fNHits[2];           // bounds for number of hits
+  float             fPt[2];              // bounds for transverse momentum
+  float             fRapidity[2];        // bounds for rapidity
+  float             fDCA[2];             // bounds for DCA to primary vertex
+
+  long              fNTracksPassed;      // passed tracks counter
+  long              fNTracksFailed;      // falied tracks counter
+
+#ifdef __ROOT__ 
+  ClassDef(AliFemtoBasicTrackCut, 1)
+#endif
+};
+
+
+inline void AliFemtoBasicTrackCut::SetNSigmaPion(const float& lo, const float& hi){fNSigmaPion[0]=lo; fNSigmaPion[1]=hi;}
+inline void AliFemtoBasicTrackCut::SetNSigmaKaon(const float& lo, const float& hi){fNSigmaKaon[0]=lo; fNSigmaKaon[1]=hi;}
+inline void AliFemtoBasicTrackCut::SetNSigmaProton(const float& lo, const float& hi){fNSigmaProton[0]=lo; fNSigmaProton[1]=hi;}
+
+inline void AliFemtoBasicTrackCut::SetNHits(const int& lo, const int& hi){fNHits[0]=lo;fNHits[1]=hi;}
+inline void AliFemtoBasicTrackCut::SetPt(const float& lo, const float& hi){fPt[0]=lo; fPt[1]=hi;}
+inline void AliFemtoBasicTrackCut::SetRapidity(const float& lo,const float& hi){fRapidity[0]=lo; fRapidity[1]=hi;}
+inline void AliFemtoBasicTrackCut::SetDCA(const float& lo,const float& hi){fDCA[0]=lo; fDCA[1]=hi;}
+inline void AliFemtoBasicTrackCut::SetCharge(const int& ch){fCharge = ch;}
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCorrFctn.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCorrFctn.cxx
new file mode 100644 (file)
index 0000000..0e25566
--- /dev/null
@@ -0,0 +1,21 @@
+////////////////////////////////////////////////////////////////////////////////
+/// AliFemtoCorrFctn - the pure virtual base class for correlation function  ///
+/// All correlation function classes must inherit from this one              ///
+////////////////////////////////////////////////////////////////////////////////
+#include "AliFemtoCorrFctn.h"
+
+void AliFemtoCorrFctn::AddRealPair(AliFemtoPair*) { cout << "Not implemented" << endl; }
+void AliFemtoCorrFctn::AddMixedPair(AliFemtoPair*) { cout << "Not implemented" << endl; }
+
+AliFemtoCorrFctn::AliFemtoCorrFctn(const AliFemtoCorrFctn& /* c */):fyAnalysis(0),fPairCut(0x0) {}
+AliFemtoCorrFctn::AliFemtoCorrFctn(): fyAnalysis(0),fPairCut(0x0) {/* no-op */}
+void AliFemtoCorrFctn::SetAnalysis(AliFemtoAnalysis* analysis) { fyAnalysis = analysis; }
+AliFemtoCorrFctn& AliFemtoCorrFctn::operator=(const AliFemtoCorrFctn& aCorrFctn) { if (this == &aCorrFctn) return *this; fyAnalysis = aCorrFctn.fyAnalysis; fPairCut = aCorrFctn.fPairCut; return *this; }
+
+void AliFemtoCorrFctn::EventBegin(const AliFemtoEvent* /* aEvent */) { /* no-op */ }
+void AliFemtoCorrFctn::EventEnd(const AliFemtoEvent* /* aEvent */) { /* no-op */ }
+void AliFemtoCorrFctn::SetPairSelectionCut(AliFemtoPairCut* aCut) { fPairCut =  aCut; }
+
+#ifdef __ROOT__
+ClassImp(AliFemtoCorrFctn)
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCorrFctn.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCorrFctn.h
new file mode 100644 (file)
index 0000000..a8f6e08
--- /dev/null
@@ -0,0 +1,51 @@
+////////////////////////////////////////////////////////////////////////////////
+/// AliFemtoCorrFctn - the pure virtual base class for correlation function  ///
+/// All correlation function classes must inherit from this one              ///
+////////////////////////////////////////////////////////////////////////////////
+#ifndef AliFemtoCorrFctn_hh
+#define AliFemtoCorrFctn_hh
+
+#include "AliFemtoAnalysis.h"
+#include "AliFemtoEvent.h"
+#include "AliFemtoPair.h"
+#include "AliFemtoPairCut.h"
+
+class AliFemtoCorrFctn{
+
+  friend class AliFemtoAnalysis;
+
+public:
+  AliFemtoCorrFctn();
+  AliFemtoCorrFctn(const AliFemtoCorrFctn& aCorrFctn);
+  virtual ~AliFemtoCorrFctn(){/* no-op */};
+  AliFemtoCorrFctn& operator=(const AliFemtoCorrFctn& aCorrFctn);
+
+  virtual AliFemtoString Report() = 0;
+
+  virtual void AddRealPair(AliFemtoPair* aPair);
+  virtual void AddMixedPair(AliFemtoPair* aPir);
+
+  virtual void EventBegin(const AliFemtoEvent* aEvent);
+  virtual void EventEnd(const AliFemtoEvent* aEvent);
+  virtual void Finish() = 0;
+
+  virtual TList* GetOutputList() = 0;
+
+  virtual AliFemtoCorrFctn* Clone() { return 0;}
+
+  AliFemtoAnalysis* HbtAnalysis(){return fyAnalysis;};
+  void SetAnalysis(AliFemtoAnalysis* aAnalysis);
+  void SetPairSelectionCut(AliFemtoPairCut* aCut);
+
+protected:
+  AliFemtoAnalysis* fyAnalysis; //! link to the analysis
+  AliFemtoPairCut* fPairCut;    //! this is a PairSelection criteria for this Correlation Function
+
+  private:
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoCorrFctn, 1)
+#endif
+};
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCorrFctn3DLCMSSym.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCorrFctn3DLCMSSym.cxx
new file mode 100644 (file)
index 0000000..9d6926d
--- /dev/null
@@ -0,0 +1,153 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFemtoCorrFctn3DLCMSSym: a class to calculate 3D correlation        //
+// for pairs of identical particles.                                     //
+// In analysis the function should be first created in a macro, then     //
+// added to the analysis, and at the end of the macro the procedure to   //
+// write out histograms should be called.                                //
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+
+#include "AliFemtoCorrFctn3DLCMSSym.h"
+#include <cstdio>
+
+#ifdef __ROOT__ 
+ClassImp(AliFemtoCorrFctn3DLCMSSym)
+#endif
+
+//____________________________
+AliFemtoCorrFctn3DLCMSSym::AliFemtoCorrFctn3DLCMSSym(char* title, const int& nbins, const float& QHi)
+  :
+  AliFemtoCorrFctn(),
+  fNumerator(0),
+  fDenominator(0)
+{
+  // Basic constructor
+
+  // set up numerator
+  char tTitNum[101] = "Num";
+  strncat(tTitNum,title, 100);
+  fNumerator = new TH3F(tTitNum,title,nbins,-QHi,QHi,nbins,-QHi,QHi,nbins/2,0.0,QHi);
+  // set up denominator
+  char tTitDen[101] = "Den";
+  strncat(tTitDen,title, 100);
+  fDenominator = new TH3F(tTitDen,title,nbins,-QHi,QHi,nbins,-QHi,QHi,nbins/2,0.0,QHi);
+
+  // to enable error bar calculation...
+  fNumerator->Sumw2();
+  fDenominator->Sumw2();
+}
+
+AliFemtoCorrFctn3DLCMSSym::AliFemtoCorrFctn3DLCMSSym(const AliFemtoCorrFctn3DLCMSSym& aCorrFctn) :
+  AliFemtoCorrFctn(aCorrFctn),
+  fNumerator(0),
+  fDenominator(0)
+{
+  // Copy constructor
+  fNumerator = new TH3F(*aCorrFctn.fNumerator);
+  fDenominator = new TH3F(*aCorrFctn.fDenominator);
+}
+//____________________________
+AliFemtoCorrFctn3DLCMSSym::~AliFemtoCorrFctn3DLCMSSym(){
+  // Destructor
+  delete fNumerator;
+  delete fDenominator;
+}
+//_________________________
+AliFemtoCorrFctn3DLCMSSym& AliFemtoCorrFctn3DLCMSSym::operator=(const AliFemtoCorrFctn3DLCMSSym& aCorrFctn)
+{
+  // assignment operator
+  if (this == &aCorrFctn)
+    return *this;
+
+  if (fNumerator) delete fNumerator;
+  fNumerator = new TH3F(*aCorrFctn.fNumerator);
+  if (fDenominator) delete fDenominator;
+  fDenominator = new TH3F(*aCorrFctn.fDenominator);
+
+  return *this;
+}
+
+//_________________________
+void AliFemtoCorrFctn3DLCMSSym::WriteOutHistos(){
+  // Write out all histograms to file
+  fNumerator->Write();
+  fDenominator->Write();
+}
+//______________________________
+TList* AliFemtoCorrFctn3DLCMSSym::GetOutputList()
+{
+  // Prepare the list of objects to be written to the output
+  TList *tOutputList = new TList();
+
+  tOutputList->Add(fNumerator); 
+  tOutputList->Add(fDenominator);  
+
+  return tOutputList;
+}
+
+//_________________________
+void AliFemtoCorrFctn3DLCMSSym::Finish(){
+  // here is where we should normalize, fit, etc...
+
+}
+
+//____________________________
+AliFemtoString AliFemtoCorrFctn3DLCMSSym::Report(){
+  // Construct the report
+  string stemp = "LCMS Frame Bertsch-Pratt 3D Correlation Function Report:\n";
+  char ctemp[100];
+  snprintf(ctemp , 100, "Number of entries in numerator:\t%E\n",fNumerator->GetEntries());
+  stemp += ctemp;
+  snprintf(ctemp , 100, "Number of entries in denominator:\t%E\n",fDenominator->GetEntries());
+  stemp += ctemp;
+
+  if (fPairCut){
+    snprintf(ctemp , 100, "Here is the PairCut specific to this CorrFctn\n");
+    stemp += ctemp;
+    stemp += fPairCut->Report();
+  }
+  else{
+    snprintf(ctemp , 100, "No PairCut specific to this CorrFctn\n");
+    stemp += ctemp;
+  }
+
+  //  
+  AliFemtoString returnThis = stemp;
+  return returnThis;
+}
+//____________________________
+void AliFemtoCorrFctn3DLCMSSym::AddRealPair( AliFemtoPair* pair){
+  // perform operations on real pairs
+  if (fPairCut){
+    if (!(fPairCut->Pass(pair))) return;
+  }
+
+  double qOut = (pair->QOutCMS());
+  double qSide = (pair->QSideCMS());
+  double qLong = (pair->QLongCMS());
+
+  if (qLong > 0.0)
+    fNumerator->Fill(qOut,qSide,qLong);
+  else
+    fNumerator->Fill(-qOut,-qSide,-qLong);
+    
+}
+//____________________________
+void AliFemtoCorrFctn3DLCMSSym::AddMixedPair( AliFemtoPair* pair){
+  // perform operations on mixed pairs
+  if (fPairCut){
+    if (!(fPairCut->Pass(pair))) return;
+  }
+
+  double qOut = (pair->QOutCMS());
+  double qSide = (pair->QSideCMS());
+  double qLong = (pair->QLongCMS());
+
+  if (qLong > 0.0)
+    fDenominator->Fill(qOut,qSide,qLong,1.0);
+  else
+    fDenominator->Fill(-qOut,-qSide,-qLong,1.0);
+}
+
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCorrFctn3DLCMSSym.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCorrFctn3DLCMSSym.h
new file mode 100644 (file)
index 0000000..561d68c
--- /dev/null
@@ -0,0 +1,49 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFemtoCorrFctn3DLCMSSym: a class to calculate 3D correlation        //
+// for pairs of identical particles vs. Bertsh-Pratt coordinates.        //
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+
+#ifndef ALIFEMTOCORRFCTN3DLCMS_H
+#define ALIFEMTOCORRFCTN3DLCMS_H
+
+#include "AliFemtoCorrFctn.h"
+#include "AliFemtoPairCut.h"
+#include "TH3F.h"
+
+class AliFemtoCorrFctn3DLCMSSym : public AliFemtoCorrFctn {
+public:
+  AliFemtoCorrFctn3DLCMSSym(char* title, const int& nbins, const float& QHi);
+  AliFemtoCorrFctn3DLCMSSym(const AliFemtoCorrFctn3DLCMSSym& aCorrFctn);
+  virtual ~AliFemtoCorrFctn3DLCMSSym();
+
+  AliFemtoCorrFctn3DLCMSSym& operator=(const AliFemtoCorrFctn3DLCMSSym& aCorrFctn);
+
+  virtual AliFemtoString Report();
+  virtual void AddRealPair( AliFemtoPair* aPair);
+  virtual void AddMixedPair( AliFemtoPair* aPair);
+
+  virtual void Finish();
+
+  TH3F* Numerator();
+  TH3F* Denominator();
+
+  void WriteOutHistos();
+  virtual TList* GetOutputList();
+
+private:
+
+  TH3F* fNumerator;         // numerator
+  TH3F* fDenominator;       // denominator
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoCorrFctn3DLCMSSym, 1)
+#endif
+};
+
+inline  TH3F* AliFemtoCorrFctn3DLCMSSym::Numerator(){return fNumerator;}
+inline  TH3F* AliFemtoCorrFctn3DLCMSSym::Denominator(){return fDenominator;}
+
+#endif
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCorrFctn3DSpherical.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCorrFctn3DSpherical.cxx
new file mode 100644 (file)
index 0000000..e0cd28f
--- /dev/null
@@ -0,0 +1,159 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFemtoCorrFctn3DSpherical: a class to calculate 3D correlation      //
+// for pairs of identical particles, binned in spherical coordinates.    //
+// In analysis the function should be first created in a macro, then     //
+// added to the analysis, and at the end of the macro the procedure to   //
+// write out histograms should be called.                                //
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+
+#include "AliFemtoCorrFctn3DSpherical.h"
+#include <TMath.h>
+#include <cstdio>
+
+#ifdef __ROOT__ 
+ClassImp(AliFemtoCorrFctn3DSpherical)
+#endif
+
+//____________________________
+  AliFemtoCorrFctn3DSpherical::AliFemtoCorrFctn3DSpherical(char* title, const int& nqbins, const float& QLo, const float& QHi, const int& nphibins, const int& ncthetabins):
+  fNumerator(0),
+  fDenominator(0) //,
+                                                         //  fPairCut(0x0)
+{
+  // set up numerator
+  char tTitNum[101] = "Num";
+  strncat(tTitNum,title, 100);
+  fNumerator = new TH3D(tTitNum,title,nqbins,QLo,QHi,nphibins,-TMath::Pi(),TMath::Pi(),ncthetabins,-1.0,1.0);
+  // set up denominator
+  char tTitDen[101] = "Den";
+  strncat(tTitDen,title, 100);
+  fDenominator = new TH3D(tTitDen,title,nqbins,QLo,QHi,nphibins,-TMath::Pi(),TMath::Pi(),ncthetabins,-1.0,1.0);
+
+  // to enable error bar calculation...
+  fNumerator->Sumw2();
+  fDenominator->Sumw2();
+}
+
+AliFemtoCorrFctn3DSpherical::AliFemtoCorrFctn3DSpherical(const AliFemtoCorrFctn3DSpherical& aCorrFctn) :
+  AliFemtoCorrFctn(aCorrFctn),
+  fNumerator(0),
+  fDenominator(0) //,
+                                                       //  fPairCut(0x0)
+{
+  // Copy constructor
+  fNumerator = new TH3D(*aCorrFctn.fNumerator);
+  fDenominator = new TH3D(*aCorrFctn.fDenominator);
+  //  fPairCut = aCorrFctn.fPairCut;
+}
+//____________________________
+AliFemtoCorrFctn3DSpherical::~AliFemtoCorrFctn3DSpherical(){
+  // Destructor
+  delete fNumerator;
+  delete fDenominator;
+}
+//_________________________
+AliFemtoCorrFctn3DSpherical& AliFemtoCorrFctn3DSpherical::operator=(const AliFemtoCorrFctn3DSpherical& aCorrFctn)
+{
+  // assignment operator
+  if (this == &aCorrFctn)
+    return *this;
+
+  if (fNumerator) delete fNumerator;
+  fNumerator = new TH3D(*aCorrFctn.fNumerator);
+  if (fDenominator) delete fDenominator;
+  fDenominator = new TH3D(*aCorrFctn.fDenominator);
+  
+  //  fPairCut = aCorrFctn.fPairCut;
+  
+  return *this;
+}
+
+//_________________________
+void AliFemtoCorrFctn3DSpherical::WriteOutHistos(){
+  // Write out all histograms to file
+  fNumerator->Write();
+  fDenominator->Write();
+}
+//______________________________
+TList* AliFemtoCorrFctn3DSpherical::GetOutputList()
+{
+  // Prepare the list of objects to be written to the output
+  TList *tOutputList = new TList();
+
+  tOutputList->Add(fNumerator); 
+  tOutputList->Add(fDenominator);  
+
+  return tOutputList;
+}
+
+//_________________________
+void AliFemtoCorrFctn3DSpherical::Finish(){
+  // here is where we should normalize, fit, etc...
+}
+
+//____________________________
+AliFemtoString AliFemtoCorrFctn3DSpherical::Report(){
+  // Construct the report
+  string stemp = "PRF Frame Spherical 3D Correlation Function Report:\n";
+  char ctemp[100];
+  snprintf(ctemp , 100, "Number of entries in numerator:\t%E\n",fNumerator->GetEntries());
+  stemp += ctemp;
+  snprintf(ctemp , 100, "Number of entries in denominator:\t%E\n",fDenominator->GetEntries());
+  stemp += ctemp;
+
+  if (fPairCut){
+    snprintf(ctemp , 100, "Here is the PairCut specific to this CorrFctn\n");
+    stemp += ctemp;
+    stemp += fPairCut->Report();
+  }
+  else{
+    snprintf(ctemp , 100, "No PairCut specific to this CorrFctn\n");
+    stemp += ctemp;
+  }
+
+  //  
+  AliFemtoString returnThis = stemp;
+  return returnThis;
+}
+//____________________________
+void AliFemtoCorrFctn3DSpherical::AddRealPair( AliFemtoPair* pair){
+  // perform operations on real pairs
+  if (fPairCut){
+    if (!(fPairCut->Pass(pair))) return;
+  }
+
+  double tKO = pair->KOut();
+  double tKS = pair->KSide();
+  double tKL = pair->KLong();
+
+  double tKR = sqrt(tKO*tKO + tKS*tKS + tKL*tKL);
+  double tKC;
+  if ( fabs(tKR) < 1e-10 ) tKC = 0.0;
+  else tKC=tKL/tKR;
+  double tKP=atan2(tKS,tKO);
+
+  fNumerator->Fill(tKR,tKP,tKC);
+}
+//____________________________
+void AliFemtoCorrFctn3DSpherical::AddMixedPair( AliFemtoPair* pair){
+  // perform operations on mixed pairs
+  if (fPairCut){
+    if (!(fPairCut->Pass(pair))) return;
+  }
+
+  double tKO = pair->KOut();
+  double tKS = pair->KSide();
+  double tKL = pair->KLong();
+
+  double tKR = sqrt(tKO*tKO + tKS*tKS + tKL*tKL);
+  double tKC;
+  if ( fabs(tKR) < 1e-10 ) tKC = 0.0;
+  else tKC=tKL/tKR;
+  double tKP=atan2(tKS,tKO);
+
+  fDenominator->Fill(tKR,tKP,tKC);
+}
+
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCorrFctn3DSpherical.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCorrFctn3DSpherical.h
new file mode 100644 (file)
index 0000000..de5b207
--- /dev/null
@@ -0,0 +1,52 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFemtoCorrFctn3DSpherical: a class to calculate 3D correlation      //
+// for pairs of identical particles, binned in spherical coordinates     //
+// (q_inv, phi, cos(theta))
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+
+#ifndef ALIFEMTOCORRFCTN3DSPHERICAL_H
+#define ALIFEMTOCORRFCTN3DSPHERICAL_H
+
+#include "AliFemtoCorrFctn.h"
+#include "AliFemtoPairCut.h"
+#include "TH3D.h"
+
+class AliFemtoCorrFctn3DSpherical : public AliFemtoCorrFctn {
+public:
+  AliFemtoCorrFctn3DSpherical(char* title, 
+                             const int& nqbins, const float& QLo, const float& QHi,
+                             const int& nphibins, const int& ncthetabins);
+  AliFemtoCorrFctn3DSpherical(const AliFemtoCorrFctn3DSpherical& aCorrFctn);
+  virtual ~AliFemtoCorrFctn3DSpherical();
+
+  AliFemtoCorrFctn3DSpherical& operator=(const AliFemtoCorrFctn3DSpherical& aCorrFctn);
+
+  virtual AliFemtoString Report();
+  virtual void AddRealPair( AliFemtoPair* aPair);
+  virtual void AddMixedPair( AliFemtoPair* aPair);
+
+  virtual void Finish();
+
+  void WriteOutHistos();
+  virtual TList* GetOutputList();
+
+  //  void SetSpecificPairCut(AliFemtoPairCut* aCut);
+
+private:
+  // here are a whole bunch of histos that get filled if we do resolution correction
+  TH3D* fNumerator;         // numerator
+  TH3D* fDenominator;       // denominator
+
+  //  AliFemtoPairCut* fPairCut;    //! this is a PairCut specific to THIS CorrFctn, not the Analysis
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoCorrFctn3DSpherical, 1)
+#endif
+};
+
+//inline  void AliFemtoCorrFctn3DSpherical::SetSpecificPairCut(AliFemtoPairCut* pc){fPairCut=pc;}
+
+#endif
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCorrFctnCollection.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCorrFctnCollection.h
new file mode 100644 (file)
index 0000000..0f3ce92
--- /dev/null
@@ -0,0 +1,48 @@
+/***************************************************************************
+ *
+ * $Id$
+ *
+ * Author: Mike Lisa, Ohio State, lisa@mps.ohio-state.edu
+ ***************************************************************************
+ *
+ * Description: part of STAR HBT Framework: AliFemtoMaker package
+ *   The CorrFctnCollection contains pointers to all Correlation Functions
+ *   that are associated with a particular Analysis object.
+ *
+ ***************************************************************************
+ *
+ * $Log$
+ * Revision 1.1.1.1  2007/04/25 15:38:41  panos
+ * Importing the HBT code dir
+ *
+ * Revision 1.1.1.1  2007/03/07 10:14:49  mchojnacki
+ * First version on CVS
+ *
+ * Revision 1.2  2000/02/01 00:33:32  laue
+ * namespaces changed to run on the new Solaris Compiler CC5
+ * since we can use member templates in franks1Histo.h we are doing it
+ *
+ * Revision 1.1.1.1  1999/06/29 16:02:57  lisa
+ * Installation of AliFemtoMaker
+ *
+ **************************************************************************/
+
+#ifndef AliFemtoCorrFctnCollection_hh
+#define AliFemtoCorrFctnCollection_hh
+
+
+#include <list>
+#if !defined(ST_NO_NAMESPACES)
+using std::list;
+#endif
+class AliFemtoCorrFctn;
+
+#ifdef ST_NO_TEMPLATE_DEF_ARGS
+typedef list<AliFemtoCorrFctn*, allocator<AliFemtoCorrFctn*> >            AliFemtoCorrFctnCollection;
+typedef list<AliFemtoCorrFctn*, allocator<AliFemtoCorrFctn*> >::iterator  AliFemtoCorrFctnIterator;
+#else
+typedef list<AliFemtoCorrFctn*>            AliFemtoCorrFctnCollection;
+typedef list<AliFemtoCorrFctn*>::iterator  AliFemtoCorrFctnIterator;
+#endif
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCorrFctnNonIdDR.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCorrFctnNonIdDR.cxx
new file mode 100644 (file)
index 0000000..2e85c43
--- /dev/null
@@ -0,0 +1,272 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoCorrFctnNonIdDR - correlation function for non-identical particles //
+// uses k* as a function variable. Stores the correlation function separately //
+// for positive and negative signs of k* projections into out, side and long  //
+// directions, enabling the calculations of double ratios                     //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+
+#include "AliFemtoCorrFctnNonIdDR.h"
+//#include "AliFemtoHisto.h"
+#include <cstdio>
+
+#ifdef __ROOT__ 
+ClassImp(AliFemtoCorrFctnNonIdDR)
+#endif
+
+//____________________________
+AliFemtoCorrFctnNonIdDR::AliFemtoCorrFctnNonIdDR(char* title, const int& nbins, const float& QinvLo, const float& QinvHi):
+  fNumOutP(0), 
+  fNumOutN(0),  
+  fNumSideP(0), 
+  fNumSideN(0), 
+  fNumLongP(0), 
+  fNumLongN(0), 
+  fDenOutP(0),  
+  fDenOutN(0),  
+  fDenSideP(0), 
+  fDenSideN(0), 
+  fDenLongP(0), 
+  fDenLongN(0)
+{
+  // Default constructor
+  // set up numerators
+  char bufname[200];
+  snprintf(bufname, 200, "NumOutP%s", title);
+  fNumOutP = new TH1D(bufname,title,nbins,QinvLo,QinvHi);
+  snprintf(bufname, 200, "NumOutN%s", title);
+  fNumOutN = new TH1D(bufname,title,nbins,QinvLo,QinvHi);
+  snprintf(bufname, 200, "NumSideP%s", title);
+  fNumSideP = new TH1D(bufname,title,nbins,QinvLo,QinvHi);
+  snprintf(bufname, 200, "NumSideN%s", title);
+  fNumSideN = new TH1D(bufname,title,nbins,QinvLo,QinvHi);
+  snprintf(bufname, 200, "NumLongP%s", title);
+  fNumLongP = new TH1D(bufname,title,nbins,QinvLo,QinvHi);
+  snprintf(bufname, 200, "NumLongN%s", title);
+  fNumLongN = new TH1D(bufname,title,nbins,QinvLo,QinvHi);
+
+  // set up denominators
+  snprintf(bufname, 200, "DenOutP%s", title);
+  fDenOutP = new TH1D(bufname,title,nbins,QinvLo,QinvHi);
+  snprintf(bufname, 200, "DenOutN%s", title);
+  fDenOutN = new TH1D(bufname,title,nbins,QinvLo,QinvHi);
+  snprintf(bufname, 200, "DenSideP%s", title);
+  fDenSideP = new TH1D(bufname,title,nbins,QinvLo,QinvHi);
+  snprintf(bufname, 200, "DenSideN%s", title);
+  fDenSideN = new TH1D(bufname,title,nbins,QinvLo,QinvHi);
+  snprintf(bufname, 200, "DenLongP%s", title);
+  fDenLongP = new TH1D(bufname,title,nbins,QinvLo,QinvHi);
+  snprintf(bufname, 200, "DenLongN%s", title);
+  fDenLongN = new TH1D(bufname,title,nbins,QinvLo,QinvHi);
+
+  // to enable error bar calculation...
+  fNumOutP->Sumw2(); 
+  fNumOutN->Sumw2();  
+  fNumSideP->Sumw2(); 
+  fNumSideN->Sumw2(); 
+  fNumLongP->Sumw2(); 
+  fNumLongN->Sumw2(); 
+  fDenOutP->Sumw2();  
+  fDenOutN->Sumw2();  
+  fDenSideP->Sumw2(); 
+  fDenSideN->Sumw2(); 
+  fDenLongP->Sumw2(); 
+  fDenLongN->Sumw2();
+}
+
+//____________________________
+AliFemtoCorrFctnNonIdDR::AliFemtoCorrFctnNonIdDR(const AliFemtoCorrFctnNonIdDR& aCorrFctn) :
+  AliFemtoCorrFctn(),
+  fNumOutP(0), 
+  fNumOutN(0),  
+  fNumSideP(0), 
+  fNumSideN(0), 
+  fNumLongP(0), 
+  fNumLongN(0), 
+  fDenOutP(0),  
+  fDenOutN(0),  
+  fDenSideP(0), 
+  fDenSideN(0), 
+  fDenLongP(0), 
+  fDenLongN(0)
+{
+  // copy constructor
+  if (aCorrFctn.fNumOutP)
+    fNumOutP = new TH1D(*aCorrFctn.fNumOutP);
+  if (aCorrFctn.fNumOutN)
+    fNumOutN = new TH1D(*aCorrFctn.fNumOutN);
+  if (aCorrFctn.fNumSideP)
+    fNumSideP = new TH1D(*aCorrFctn.fNumSideP);
+  if (aCorrFctn.fNumSideN)
+    fNumSideN = new TH1D(*aCorrFctn.fNumSideN);
+  if (aCorrFctn.fNumLongP)
+    fNumLongP = new TH1D(*aCorrFctn.fNumLongP);
+  if (aCorrFctn.fNumLongN)
+    fNumLongN = new TH1D(*aCorrFctn.fNumLongN);
+
+  if (aCorrFctn.fDenOutP)
+    fDenOutP = new TH1D(*aCorrFctn.fDenOutP);
+  if (aCorrFctn.fDenOutN)
+    fDenOutN = new TH1D(*aCorrFctn.fDenOutN);
+  if (aCorrFctn.fDenSideP)
+    fDenSideP = new TH1D(*aCorrFctn.fDenSideP);
+  if (aCorrFctn.fDenSideN)
+    fDenSideN = new TH1D(*aCorrFctn.fDenSideN);
+  if (aCorrFctn.fDenLongP)
+    fDenLongP = new TH1D(*aCorrFctn.fDenLongP);
+  if (aCorrFctn.fDenLongN)
+    fDenLongN = new TH1D(*aCorrFctn.fDenLongN);
+}
+//____________________________
+AliFemtoCorrFctnNonIdDR::~AliFemtoCorrFctnNonIdDR(){
+  delete fNumOutP; 
+  delete fNumOutN;  
+  delete fNumSideP; 
+  delete fNumSideN; 
+  delete fNumLongP; 
+  delete fNumLongN; 
+  delete fDenOutP;  
+  delete fDenOutN;  
+  delete fDenSideP; 
+  delete fDenSideN; 
+  delete fDenLongP; 
+  delete fDenLongN;
+}
+//_________________________
+AliFemtoCorrFctnNonIdDR& AliFemtoCorrFctnNonIdDR::operator=(const AliFemtoCorrFctnNonIdDR& aCorrFctn)
+{
+  // assignment operator
+  if (this == &aCorrFctn)
+    return *this;
+
+  if (aCorrFctn.fNumOutP)
+    fNumOutP = new TH1D(*aCorrFctn.fNumOutP);
+  if (aCorrFctn.fNumOutN)
+    fNumOutN = new TH1D(*aCorrFctn.fNumOutN);
+  if (aCorrFctn.fNumSideP)
+    fNumSideP = new TH1D(*aCorrFctn.fNumSideP);
+  if (aCorrFctn.fNumSideN)
+    fNumSideN = new TH1D(*aCorrFctn.fNumSideN);
+  if (aCorrFctn.fNumLongP)
+    fNumLongP = new TH1D(*aCorrFctn.fNumLongP);
+  if (aCorrFctn.fNumLongN)
+    fNumLongN = new TH1D(*aCorrFctn.fNumLongN);
+
+  if (aCorrFctn.fDenOutP)
+    fDenOutP = new TH1D(*aCorrFctn.fDenOutP);
+  if (aCorrFctn.fDenOutN)
+    fDenOutN = new TH1D(*aCorrFctn.fDenOutN);
+  if (aCorrFctn.fDenSideP)
+    fDenSideP = new TH1D(*aCorrFctn.fDenSideP);
+  if (aCorrFctn.fDenSideN)
+    fDenSideN = new TH1D(*aCorrFctn.fDenSideN);
+  if (aCorrFctn.fDenLongP)
+    fDenLongP = new TH1D(*aCorrFctn.fDenLongP);
+  if (aCorrFctn.fDenLongN)
+    fDenLongN = new TH1D(*aCorrFctn.fDenLongN);
+
+  return *this;
+}
+
+//_________________________
+void AliFemtoCorrFctnNonIdDR::Finish(){
+  // here is where we should normalize, fit, etc...
+  // we should NOT Draw() the histos (as I had done it below),
+  // since we want to insulate ourselves from root at this level
+  // of the code.  Do it instead at root command line with browser.
+  //  fNumerator->Draw();
+  //fDenominator->Draw();
+  //fRatio->Draw();
+  //  fRatio->Divide(fNumerator,fDenominator,1.0,1.0);
+
+}
+
+//____________________________
+AliFemtoString AliFemtoCorrFctnNonIdDR::Report(){
+  // construct report
+  string stemp = "Non-identical particles Correlation Function Report:\n";
+  char ctemp[100];
+  snprintf(ctemp , 100, "Number of entries in numerators:\t%E\n",fNumOutP->GetEntries()+fNumOutN->GetEntries());
+  stemp += ctemp;
+  snprintf(ctemp , 100, "Number of entries in denominators:\t%E\n",fDenOutP->GetEntries()+fDenOutN->GetEntries());
+  stemp += ctemp;
+  //  stemp += mCoulombWeight->Report();
+  AliFemtoString returnThis = stemp;
+  return returnThis;
+}
+//____________________________
+void AliFemtoCorrFctnNonIdDR::AddRealPair(AliFemtoPair* pair){
+  // add true pair
+  double tKStar = pair->KStar();
+  if (pair->KOut()>0.0)
+    fNumOutP->Fill(tKStar);
+  else
+    fNumOutN->Fill(tKStar);
+
+  if (pair->KSide()>0.0)
+    fNumSideP->Fill(tKStar);
+  else
+    fNumSideN->Fill(tKStar);
+
+  if (pair->KLong()>0.0)
+    fNumLongP->Fill(tKStar);
+  else
+    fNumLongN->Fill(tKStar);
+
+}
+//____________________________
+void AliFemtoCorrFctnNonIdDR::AddMixedPair(AliFemtoPair* pair){
+  // add mixed (background) pair
+  double tKStar = pair->KStar();
+  if (pair->KOut()>0.0)
+    fDenOutP->Fill(tKStar);
+  else
+    fDenOutN->Fill(tKStar);
+
+  if (pair->KSide()>0.0)
+    fDenSideP->Fill(tKStar);
+  else
+    fDenSideN->Fill(tKStar);
+
+  if (pair->KLong()>0.0)
+    fDenLongP->Fill(tKStar);
+  else
+    fDenLongN->Fill(tKStar);
+}
+//____________________________
+void AliFemtoCorrFctnNonIdDR::Write(){
+  fNumOutP->Write(); 
+  fNumOutN->Write();  
+  fNumSideP->Write(); 
+  fNumSideN->Write(); 
+  fNumLongP->Write(); 
+  fNumLongN->Write(); 
+  fDenOutP->Write();  
+  fDenOutN->Write();  
+  fDenSideP->Write(); 
+  fDenSideN->Write(); 
+  fDenLongP->Write(); 
+  fDenLongN->Write();
+}
+
+TList* AliFemtoCorrFctnNonIdDR::GetOutputList()
+{
+  // Prepare the list of objects to be written to the output
+  TList *tOutputList = new TList();
+
+  tOutputList->Add(fNumOutP); 
+  tOutputList->Add(fNumOutN);  
+  tOutputList->Add(fNumSideP); 
+  tOutputList->Add(fNumSideN); 
+  tOutputList->Add(fNumLongP); 
+  tOutputList->Add(fNumLongN); 
+  tOutputList->Add(fDenOutP);  
+  tOutputList->Add(fDenOutN);  
+  tOutputList->Add(fDenSideP); 
+  tOutputList->Add(fDenSideN); 
+  tOutputList->Add(fDenLongP); 
+  tOutputList->Add(fDenLongN);
+
+  return tOutputList;
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCorrFctnNonIdDR.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCorrFctnNonIdDR.h
new file mode 100644 (file)
index 0000000..45edb66
--- /dev/null
@@ -0,0 +1,54 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoCorrFctnNonIdDR - correlation function for non-identical particles //
+// uses k* as a function variable. Stores the correlation function separately //
+// for positive and negative signs of k* projections into out, side and long  //
+// directions, enabling the calculations of double ratios                     //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+#ifndef ALIFEMTOCORRFCTNNONIDDR_H
+#define ALIFEMTOCORRFCTNNONIDDR_H
+
+#include "TH1D.h"
+#include "AliFemtoCorrFctn.h"
+
+class AliFemtoCorrFctnNonIdDR : public AliFemtoCorrFctn {
+public:
+  AliFemtoCorrFctnNonIdDR(char* title, const int& nbins, const float& QinvLo, const float& QinvHi);
+  AliFemtoCorrFctnNonIdDR(const AliFemtoCorrFctnNonIdDR& aCorrFctn);
+  virtual ~AliFemtoCorrFctnNonIdDR();
+
+  AliFemtoCorrFctnNonIdDR& operator=(const AliFemtoCorrFctnNonIdDR& aCorrFctn);
+
+  virtual AliFemtoString Report();
+  virtual void AddRealPair(AliFemtoPair* aPair);
+  virtual void AddMixedPair(AliFemtoPair* aPair);
+
+  virtual void Finish();
+
+  virtual TList* GetOutputList();
+  void Write();
+
+private:
+  TH1D *fNumOutP;     // Numerator for pair with positive k*out
+  TH1D *fNumOutN;     // Numerator for pair with negative k*out
+  TH1D *fNumSideP;    // Numerator for pair with positive k*side
+  TH1D *fNumSideN;    // Numerator for pair with negative k*side
+  TH1D *fNumLongP;    // Numerator for pair with positive k*long
+  TH1D *fNumLongN;    // Numerator for pair with negative k*long
+
+  TH1D *fDenOutP;     // Denominator for pair with positive k*out
+  TH1D *fDenOutN;     // Denominator for pair with negative k*out
+  TH1D *fDenSideP;    // Denominator for pair with positive k*side
+  TH1D *fDenSideN;    // Denominator for pair with negative k*side
+  TH1D *fDenLongP;    // Denominator for pair with positive k*long
+  TH1D *fDenLongN;    // Denominator for pair with negative k*long
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoCorrFctnNonIdDR, 1)
+#endif
+};
+
+
+#endif
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCoulomb.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCoulomb.cxx
new file mode 100644 (file)
index 0000000..7f905df
--- /dev/null
@@ -0,0 +1,472 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFemtoCoulomb: This is a Coulomb correction class which             //
+//  1. Reads in the dat from a file                                      //  
+//  2. Performs a linear interpolation in R and creates any array of     //
+//     interpolations                                                    //
+//  3. Interpolates in eta and returns the Coulomb correction to user    //
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+
+#include "AliFemtoCoulomb.h"
+//#include "Stiostream.h"
+#include <stdio.h>
+#include <cassert>
+//#include "PhysicalConstants.h"
+#define fine_structure_const 0.00729735
+
+#ifdef __ROOT__
+ClassImp(AliFemtoCoulomb)
+#endif
+
+AliFemtoCoulomb::AliFemtoCoulomb() :
+  fFile(""),
+  fRadius(-1.0),
+  fZ1Z2(1.0),
+  fNLines(0)
+{
+  // Default constructor
+  fFile = "/afs/rhic/star/hbt/coul/AliFemtoCorrectionFiles/correctionpp.dat";
+  if (!fFile) {
+    cout << " No file, dummy!" << endl;
+    assert(0);
+  }
+  cout << "You have 1 default Coulomb correction!" << endl;
+
+  for (int ie=0; ie<1000; ie++) {
+    fEta[ie] = 0.0;
+    fCoulomb[ie] = 0.0;
+  }
+}
+
+AliFemtoCoulomb::AliFemtoCoulomb(const AliFemtoCoulomb& aCoul) :
+  fFile(aCoul.fFile),
+  fRadius(aCoul.fRadius),
+  fZ1Z2(aCoul.fZ1Z2),
+  fNLines(0)
+{
+  // copy constructor
+  CreateLookupTable(fRadius);
+}
+
+AliFemtoCoulomb::AliFemtoCoulomb(const char* readFile, const double& radius, const double& charge) :
+  fFile(readFile),
+  fRadius(radius),
+  fZ1Z2(0),
+  fNLines(0)
+{
+  // constructor with explicit filename
+  fFile = readFile;
+  fRadius = radius;
+  CreateLookupTable(fRadius);
+  fZ1Z2 = charge;
+  cout << "You have 1 Coulomb correction!" << endl;
+}
+
+AliFemtoCoulomb::~AliFemtoCoulomb() {
+  // destructor
+}
+
+AliFemtoCoulomb& AliFemtoCoulomb::operator=(const AliFemtoCoulomb& aCoul)
+{
+  // assignment operator
+  if (this == &aCoul)
+    return *this;
+
+  fFile = aCoul.fFile;
+  fRadius = aCoul.fRadius;
+  fZ1Z2 = aCoul.fZ1Z2;
+
+  CreateLookupTable(fRadius);
+  
+  return *this;
+}
+
+
+void AliFemtoCoulomb::SetRadius(const double& radius) {
+  // set the coulomb radius
+  cout << " AliFemtoCoulomb::setRadius() " << endl;
+  fRadius = radius;
+  CreateLookupTable(fRadius);
+}
+
+double AliFemtoCoulomb::GetRadius() const {
+  // return coulomb radius
+  return (fRadius);
+}
+
+void AliFemtoCoulomb::SetFile(const char* readFile) {
+  // set the filename with coulomb calculations
+  cout << " AliFemtoCoulomb::SetFile() " << endl;
+  fFile = readFile;
+  // Create new lookup table since file has changed
+  if (fRadius>0.0) {
+    CreateLookupTable(fRadius);
+  }
+}
+
+void AliFemtoCoulomb::SetChargeProduct(const double& charge) {
+  // set pair charge
+  cout << " AliFemtoCoulomb::SetChargeProduct() " << endl;
+  if ( fZ1Z2!=charge ) { 
+    fZ1Z2 = charge;
+    if ( fZ1Z2>0 ) {
+      fFile = "/afs/rhic/star/hbt/coul/AliFemtoCorrectionFiles/correctionpp.dat";
+    }
+    else {
+      fFile = "/afs/rhic/star/hbt/coul/AliFemtoCorrectionFiles/correctionpm.dat";
+    }
+    CreateLookupTable(fRadius);
+  }
+}
+
+void AliFemtoCoulomb::CreateLookupTable(const double& radius) {
+  // Read radii from fFile
+  // Create array(pair) of linear interpolation between radii
+  cout << " AliFemtoCoulomb::CreateLookupTable() " << endl;
+
+  if (radius<0.0) {
+    cout << " AliFemtoCoulomb::CreateLookupTable -> NEGATIVE RADIUS " << endl;
+    cout << "  call AliFemtoCoulomb::SetRadius(r) with positive r " << endl;
+    cerr << " AliFemtoCoulomb::CreateLookupTable -> NEGATIVE RADIUS " << endl;
+    cerr << "  call AliFemtoCoulomb::SetRadius(r) with positive r " << endl;
+    assert(0);
+  }
+  ifstream mystream(fFile);
+  if (!mystream) {
+    cout << "Could not open file" << endl;
+    assert(0);
+  }
+  else {
+    cout << "Input correction file opened" << endl;
+  }
+
+  static char tempstring[2001];
+  static float radii[2000];
+  static int tNRadii = 0;
+  tNRadii = 0;
+  if (!mystream.getline(tempstring,2000)) {
+    cout << "Could not read radii from file" << endl;
+    assert(0);
+  }
+  for (unsigned int ii=0; ii<strlen(tempstring); ii++) {
+    while (tempstring[ii]==' ') ii++;
+    sscanf(&tempstring[ii++],"%f",&radii[++tNRadii]);
+    while ( tempstring[ii]!=' ' && (ii)<strlen(tempstring) )ii++;
+  }
+  cout << " Read " << tNRadii << " radii from file" << endl;
+
+  static double tLowRadius = -1.0;
+  static double tHighRadius = -1.0;
+  static int tLowIndex = 0;
+  tLowRadius = -1.0;
+  tHighRadius = -1.0;
+  tLowIndex = 0;
+  for(int iii=1; iii<=tNRadii-1; iii++) { // Loop to one less than #radii
+    if ( radius >= radii[iii] && radius <= radii[iii+1] ) {
+      tLowRadius = radii[iii];
+      tHighRadius = radii[iii+1];
+      tLowIndex = iii;
+    }
+  }
+  if ( (tLowRadius < 0.0) || (tHighRadius < 0.0) ) {
+    cout << "AliFemtoCoulomb::CreateLookupTable --> Problem interpolating radius" << endl;
+    cout << "  Check range of radii in lookup file...." << endl;
+    cerr << "AliFemtoCoulomb::CreateLookupTable --> Problem interpolating radius" << endl;
+    cerr << "  Check range of radii in lookup file...." << endl;
+    assert(0);
+  }
+
+  static double corr[100];           // array of corrections ... must be > tNRadii
+  fNLines = 0;
+  static double tempEta = 0;
+  tempEta = 0;
+  while (mystream >> tempEta) {
+    for (int i=1; i<=tNRadii; i++) {
+      mystream >> corr[i];
+    }
+    static double tLowCoulomb = 0;
+    static double tHighCoulomb = 0;
+    static double nCorr = 0;
+    tLowCoulomb = corr[tLowIndex];
+    tHighCoulomb = corr[tLowIndex+1];
+    nCorr = ( (radius-tLowRadius)*tHighCoulomb+(tHighRadius-radius)*tLowCoulomb )/(tHighRadius-tLowRadius);
+      fEta[fNLines] = tempEta;     // Eta
+      fCoulomb[fNLines] = nCorr;   // Interpolated Coulomb correction for radius
+      fNLines++;
+  }
+  mystream.close();
+  cout << "Lookup Table is created with " << fNLines << " points" << endl;
+}
+
+double AliFemtoCoulomb::CoulombCorrect(const double& eta) {
+  // Interpolates in eta
+  if (fRadius < 0.0) {
+    cout << "AliFemtoCoulomb::CoulombCorrect(eta) --> Trying to correct for negative radius!" << endl;
+    cerr << "AliFemtoCoulomb::CoulombCorrect(eta) --> Trying to correct for negative radius!" << endl;
+    assert(0);
+  }
+  static int middle=0;
+  middle=int( (fNLines-1)/2 );
+  if (eta*fEta[middle]<0.0) {
+    cout << "AliFemtoCoulomb::CoulombCorrect(eta) --> eta: " << eta << " has wrong sign for data file! " << endl;
+    cerr << "AliFemtoCoulomb::CoulombCorrect(eta) --> eta: " << eta << " has wrong sign for data file! " << endl;
+    assert(0);
+  }
+
+  static double tCorr = 0;
+  tCorr = -1.0;
+  
+  if ( (eta>fEta[0]) && (fEta[0]>0.0) ) {
+    tCorr = fCoulomb[0];
+    return (tCorr);
+  }
+  if ( (eta<fEta[fNLines-1]) && (fEta[fNLines-1]<0.0) ) {
+    tCorr = fCoulomb[fNLines-1];
+    return (tCorr);
+  }
+  // This is a binary search for the bracketing pair of data points
+  static int high = 0;
+  static int low = 0;
+  static int width = 0;
+  high = fNLines-1;
+  low = 0;
+  width = high-low;
+  middle = int(width/2.0); // Was instantiated above
+  while (middle > 0) {
+    if (fEta[low+middle] < eta) {
+      // eta is in the 1st half
+      high-=middle;
+      width = high-low;
+      middle = int(width/2.0);
+    }
+    else {
+      // eta is in the 2nd half
+      low+=middle;
+      width = high-low;
+      middle = int(width/2.0);
+    }
+  }
+  // Make sure we found the right one
+  if ( (fEta[low] >= eta) && (eta >= fEta[low+1]) ) {
+    static double tLowEta = 0;
+    static double tHighEta = 0;    
+    static double tLowCoulomb = 0;
+    static double tHighCoulomb = 0;
+    tLowEta = fEta[low];
+    tHighEta = fEta[low+1];    
+    tLowCoulomb = fCoulomb[low];
+    tHighCoulomb = fCoulomb[low+1];
+    //      cout << tLowEta << " *** Eta *** " << tHighEta << endl;
+    //      cout << tLowCoulomb << " *** Coulomb *** " << tHighCoulomb << endl;
+    tCorr = ( (eta-tLowEta)*tHighCoulomb+(tHighEta-eta)*tLowCoulomb )/(tHighEta-tLowEta);
+  }
+  if (tCorr<0.0) {
+    cout << "AliFemtoCoulomb::CoulombCorrect(eta) --> No correction" << endl;
+    cout << "  Check range of eta in file: Input eta  " << eta << endl;
+    cerr << "AliFemtoCoulomb::CoulombCorrect(eta) --> No correction" << endl;
+    cerr << "  Check range of eta in file: Input eta  " << eta << endl;
+    assert(0);
+  } 
+  return (tCorr);
+
+}
+
+double AliFemtoCoulomb::CoulombCorrect(const double& eta,
+                               const double& radius) {
+  // Checks radii ... input radius and fRadius
+  // Calls createLookupTable if neccessary
+  // Interpolate(linear) between etas in the created lookup table
+
+  if (radius < 0.0) {
+    if (fRadius < 0.0) {
+      // Both radii are negative
+      cout << "AliFemtoCoulomb::CoulombCorrect(eta,r) --> input and member radii are negative!" << endl;
+      cerr << "AliFemtoCoulomb::CoulombCorrect(eta,r) --> input and member radii are negative!" << endl;
+      assert(0);
+    }
+  }
+  else {
+    // radius > 0.0
+    if (radius == fRadius) {
+      // Both radii are positive and equal
+      //      cout << "Radii are the same!!!" << endl;
+    }
+    else {
+      // Both radii are positive but not equal
+      fRadius = radius;
+      CreateLookupTable(fRadius);
+    }
+  }
+
+  // Interpolate in eta
+  return ( CoulombCorrect(eta) );
+}
+
+double AliFemtoCoulomb::CoulombCorrect(const AliFemtoPair* pair) {
+  return ( CoulombCorrect( Eta(pair) ) );;
+}
+
+double AliFemtoCoulomb::CoulombCorrect(const AliFemtoPair* pair, const double& radius) {
+  return ( CoulombCorrect( Eta(pair),radius ) );
+}
+
+double AliFemtoCoulomb::Eta(const AliFemtoPair* pair) {
+  // calculate eta
+  static double px1,py1,pz1,px2,py2,pz2;
+  static double px1new,py1new,pz1new;
+  static double px2new,py2new,pz2new;
+  static double vx1cms,vy1cms,vz1cms;
+  static double vx2cms,vy2cms,vz2cms;
+  static double tVcmsX,tVcmsY,tVcmsZ;
+  static double dv = 0.0;
+  static double e1,e2,e1new,e2new;
+  static double psi,theta;
+  static double beta,gamma;
+  static double tVcmsXnew;
+
+  px1 = pair->Track1()->FourMomentum().px();
+  py1 = pair->Track1()->FourMomentum().py();
+  pz1 = pair->Track1()->FourMomentum().pz();
+  e1 = pair->Track1()->FourMomentum().e();
+  px2 = pair->Track2()->FourMomentum().px();
+  py2 = pair->Track2()->FourMomentum().py();
+  pz2 = pair->Track2()->FourMomentum().pz();
+  e2 = pair->Track2()->FourMomentum().e();
+  
+  tVcmsX = ( px1+px2 )/( e1+e2 );
+  tVcmsY = ( py1+py2 )/( e1+e2 );
+  tVcmsZ = ( pz1+pz2 )/( e1+e2 );
+  // Rotate tVcms to x-direction
+  psi = atan(tVcmsY/tVcmsX);
+  tVcmsXnew = tVcmsX*cos(psi)+tVcmsY*sin(psi);
+  tVcmsX = tVcmsXnew;
+  theta = atan(tVcmsZ/tVcmsX);
+  tVcmsXnew = tVcmsX*cos(theta)+tVcmsZ*sin(theta);
+  tVcmsX = tVcmsXnew;
+  // Gamma and Beta
+  beta = tVcmsX;
+  gamma = 1.0/::sqrt( 1.0-beta*beta );
+
+  // Rotate p1 and p2 to new frame
+  px1new = px1*cos(psi)+py1*sin(psi);
+  py1new = -px1*sin(psi)+py1*cos(psi);
+  px1 = px1new;
+  px1new = px1*cos(theta)+pz1*sin(theta);
+  pz1new = -px1*sin(theta)+pz1*cos(theta);
+  px1 = px1new;
+  py1 = py1new;
+  pz1 = pz1new;
+
+  px2new = px2*cos(psi)+py2*sin(psi);
+  py2new = -px2*sin(psi)+py2*cos(psi);
+  px2 = px2new;
+  px2new = px2*cos(theta)+pz2*sin(theta);
+  pz2new = -px2*sin(theta)+pz2*cos(theta);
+  px2 = px2new;
+  py2 = py2new;
+  pz2 = pz2new;
+
+  // Lorentz transform the x component and energy
+  e1new = gamma*e1 - gamma*beta*px1;
+  px1new = -gamma*beta*e1 + gamma*px1;
+  e2new = gamma*e2 - gamma*beta*px2;
+  px2new = -gamma*beta*e2 + gamma*px2;
+  px1 = px1new;
+  px2 = px2new;
+
+  // New velocities
+  vx1cms = px1/e1new;
+  vy1cms = py1/e1new;
+  vz1cms = pz1/e1new;
+  vx2cms = px2/e2new;
+  vy2cms = py2/e2new;
+  vz2cms = pz2/e2new;
+
+  // Velocity difference in CMS frame
+  dv = ::sqrt( (vx1cms-vx2cms)*(vx1cms-vx2cms) +
+            (vy1cms-vy2cms)*(vy1cms-vy2cms) +
+            (vz1cms-vz2cms)*(vz1cms-vz2cms) );
+
+  return ( fZ1Z2*fine_structure_const/(dv) );
+}
+
+TH1D* AliFemtoCoulomb::CorrectionHistogram(const double& mass1, const double& mass2, const int& nBins, 
+                                               const double& low, const double& high) {
+  // return correction histogram
+
+  if ( mass1!=mass2 ) {
+    cout << "Masses not equal ... try again.  No histogram created." << endl;
+    assert(0);
+  }
+  TH1D* correction = new TH1D("correction","Coulomb correction",nBins,low,high);
+  const double kReducedMass = mass1*mass2/(mass1+mass2);
+  double qInv = low;
+  //double dQinv = (high-low)/( (double)nBins );
+  double eta;
+  for (int ii=1; ii<=nBins; ii++) 
+    {
+      qInv = correction->GetBinCenter(ii);
+      eta = 2.0*fZ1Z2*kReducedMass*fine_structure_const/( qInv );
+      CoulombCorrect( eta );
+      correction->Fill( qInv, CoulombCorrect(eta,fRadius) );
+    }
+
+  return (correction);
+}
+
+#ifdef __ROOT__
+TH1D* AliFemtoCoulomb::CorrectionHistogram(const TH1D* histo, const double mass) {
+  // return correction histogram - 1D case
+  TH1D* correction = (TH1D*) ((TH1D*)histo)->Clone();
+  correction->Reset();
+  correction->SetDirectory(0);
+  int    nBins = correction->GetXaxis()->GetNbins();
+  const double kReducedMass = 0.5*mass;
+  double qInv;
+  double eta;
+  for (int ii=1; ii<=nBins; ii++) 
+    {
+      qInv = correction->GetBinCenter(ii);
+      eta = 2.0*fZ1Z2*kReducedMass*fine_structure_const/( qInv );
+      correction->Fill( qInv, CoulombCorrect(eta,fRadius) );
+    }
+
+  return (correction);
+}
+
+TH3D* AliFemtoCoulomb::CorrectionHistogram(const TH3D* histo, const double mass) {
+  // return correction histogram - 3D case
+  TH3D* correction = (TH3D*) ((TH3D*)histo)->Clone();
+  correction->Reset();
+  correction->SetDirectory(0);
+  int    nBinsX = correction->GetXaxis()->GetNbins();
+  int    nBinsY = correction->GetYaxis()->GetNbins();
+  int    nBinsZ = correction->GetZaxis()->GetNbins();
+  const double kReducedMass = 0.5*mass;
+  double eta;
+  double qInv;
+  int binNumber;
+  for (int ii=1; ii<=nBinsX; ii++) { 
+    for (int iii=1; iii<=nBinsY; iii++) {
+      for (int iv=1; iv<=nBinsZ; iv++) {
+       binNumber = histo->GetBin(ii,iii,iv);
+       qInv = histo->GetBinContent(binNumber);
+       eta = 2.0*fZ1Z2*kReducedMass*fine_structure_const/( qInv );
+       correction->SetBinContent(binNumber, CoulombCorrect(eta,fRadius) );
+      }
+    }
+  }
+  return (correction);
+}
+#endif
+
+double AliFemtoCoulomb::CoulombCorrect(const double& mass, const double& charge,
+                                   const double& radius, const double& qInv) {
+  // return correction factor
+  fRadius = radius;
+  fZ1Z2 = charge;
+  const double kReducedMass = 0.5*mass; // must be same mass particles
+  double eta = 2.0*fZ1Z2*kReducedMass*fine_structure_const/( qInv );
+  return ( CoulombCorrect(eta,fRadius) );
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCoulomb.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCoulomb.h
new file mode 100644 (file)
index 0000000..468ab2b
--- /dev/null
@@ -0,0 +1,65 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFemtoCoulomb: This is a Coulomb correction class which             //
+//  1. Reads in the dat from a file                                      //  
+//  2. Performs a linear interpolation in R and creates any array of     //
+//     interpolations                                                    //
+//  3. Interpolates in eta and returns the Coulomb correction to user    //
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+
+#ifndef ALIFEMTOCOULOMB_H
+#define ALIFEMTOCOULOMB_H
+
+#include <stdio.h>
+#include "AliFemtoTypes.h"
+#include "AliFemtoPair.h"
+#include "AliFemtoParticle.h"
+#include "TH1D.h"
+#include "TH3D.h"
+
+class AliFemtoCoulomb {
+
+public:
+  AliFemtoCoulomb();
+  AliFemtoCoulomb(const char *readFile, const double& radius, const double& charge);
+  AliFemtoCoulomb(const AliFemtoCoulomb& aCoul);
+  virtual ~AliFemtoCoulomb();
+
+  AliFemtoCoulomb& operator=(const AliFemtoCoulomb& aCoul);
+
+  void SetRadius(const double& radius);
+  double GetRadius() const;
+  void SetFile(const char *readFile);
+  void SetChargeProduct(const double& charge);
+
+  // These have different names so eta/Qinv don't confuse the compiler
+  double CoulombCorrect(const double& eta);
+  double CoulombCorrect(const double& eta, const double& radius);
+  double CoulombCorrect(const AliFemtoPair* pair);
+  double CoulombCorrect(const AliFemtoPair* pair, const double& radius);
+  double CoulombCorrect(const double& mass, const double& charge,
+                       const double& radius, const double& qInv);
+  TH1D* CorrectionHistogram(const double& mass1, const double& mass2, const int& nBins, 
+                                   const double& low, const double& high);
+#ifdef __ROOT__
+  TH1D* CorrectionHistogram(const TH1D*, const double);
+  TH3D* CorrectionHistogram(const TH3D*, const double);
+#endif
+private:
+  double Eta(const AliFemtoPair* pair);          // Calculates eta
+  void CreateLookupTable(const double& radius);  // Creates look-up table
+  const char* fFile;                             // File to interpolate corrections from    
+  double fRadius;                                // Radius from previous iteration
+  double fZ1Z2;                                  // Charge product of particles
+  double fEta[1000];                             // interpolated Coulomb correction table
+  double fCoulomb[1000];                         // interpolated Coulomb correction table
+  int fNLines;                                   // Number of Eta's in lookup-table
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoCoulomb, 0)
+#endif
+};
+
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCutMonitor.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCutMonitor.cxx
new file mode 100644 (file)
index 0000000..24abd40
--- /dev/null
@@ -0,0 +1,63 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoCutMonitor - the  base class for cut monitor                       //
+// A cut monitor saves the entities that passed and failed the given cut      //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+#include "AliFemtoCutMonitor.h"
+
+inline void AliFemtoCutMonitor::EventBegin(const AliFemtoEvent* /* aEvent */ ) 
+{ /* no-op */ }
+
+inline void AliFemtoCutMonitor::EventEnd(const AliFemtoEvent* /* aEvent */ ) 
+{ /* no-op */ }
+
+inline void AliFemtoCutMonitor::Fill(const AliFemtoEvent* /* aEvent */) { 
+  // cut event
+#ifdef STHBTDEBUG
+    cout << " *** no user defined Fill(const AliFemtoEvent*), take from base class" << endl;
+#endif
+  }
+
+inline void AliFemtoCutMonitor::Fill(const AliFemtoTrack* /* aTrack */) { 
+  // cut track
+#ifdef STHBTDEBUG
+  cout << " *** no user defined Fill(const AliFemtoTrack*), take from base class" << endl;
+#endif
+}
+
+inline void AliFemtoCutMonitor::Fill(const AliFemtoV0* /* aV0 */ ) { 
+  // cut V0
+#ifdef STHBTDEBUG
+  cout << " *** no user defined Fill(const AliFemtoV0Track*), take from base class" << endl;
+#endif
+}
+inline void AliFemtoCutMonitor::Fill(const AliFemtoKink* /* aKink */) { 
+  // cut Kink
+#ifdef STHBTDEBUG
+  cout << " *** no user defined Fill(const AliFemtoKink*), take from base class" << endl;
+#endif
+}
+//-----------------------------------Gael 12/04/02------------------------------------
+inline void AliFemtoCutMonitor::Fill(const AliFemtoPair* /* aPair */) { 
+  // cut pair
+#ifdef STHBTDEBUG
+  cout << " *** no user defined Fill(const AliFemtoPair*), take from base class" << endl;
+#endif
+}
+//-----------------------------------Gael 19/06/02------------------------------------
+inline void AliFemtoCutMonitor::Fill(const AliFemtoParticleCollection* /* aCollection */) {
+  // cut particle collection
+#ifdef STHBTDEBUG
+  cout << " *** no user defined Fill(const AliFemtoParticleCollection*), take from base class" << endl;
+#endif
+}
+//-----------------------------------Gael 19/06/02------------------------------------
+inline void AliFemtoCutMonitor::Fill(const AliFemtoEvent* /* aEvent */,const AliFemtoParticleCollection* /* aCollection */) {
+  // cut event and particle collection
+#ifdef STHBTDEBUG
+  cout << " *** no user defined Fill(const AliFemtoEvent*,const AliFemtoParticleCollection*), take from base class" << endl;
+#endif
+}
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCutMonitor.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCutMonitor.h
new file mode 100644 (file)
index 0000000..e6c0bd7
--- /dev/null
@@ -0,0 +1,49 @@
+////////////////////////////////////////////////////////////////////////////////
+/// AliFemtoCutMonitor - the  base class for cut monitor                     ///
+/// A cut monitor saves the entities that passed and failed the given cut    ///
+////////////////////////////////////////////////////////////////////////////////
+#ifndef ALIFEMTOCUTMONITOR_H
+#define ALIFEMTOCUTMONITOR_H
+
+class AliFemtoEvent;
+class AliFemtoTrack;
+class AliFemtoV0;
+class AliFemtoKink;
+class AliFemtoPair; // Gael 12/04/02
+#include "AliFemtoString.h"
+#include "AliFemtoParticleCollection.h" // Gael 19/06/02
+#include <TList.h>
+
+class AliFemtoCutMonitor{
+  
+public:
+  AliFemtoCutMonitor(){/* no-op */};
+  virtual ~AliFemtoCutMonitor(){/* no-op */};
+  virtual AliFemtoString Report(){ 
+    string Stemp = "*** no user defined Fill(const AliFemtoEvent*), take from base class"; 
+    AliFemtoString returnThis = Stemp;
+    return returnThis; 
+  }
+  virtual void EventBegin(const AliFemtoEvent* aEvent);
+  virtual void EventEnd(const AliFemtoEvent* aEvent);
+  virtual TList *GetOutputList() { TList *tOutputList = new TList(); return tOutputList; };
+  virtual void Fill(const AliFemtoEvent* aEvent);
+  virtual void Fill(const AliFemtoTrack* aTrack);
+  virtual void Fill(const AliFemtoV0* aV0);
+  virtual void Fill(const AliFemtoKink* aKink);
+  virtual void Fill(const AliFemtoPair* aPair);
+  virtual void Fill(const AliFemtoParticleCollection* aCollection);
+  virtual void Fill(const AliFemtoEvent* aEvent,const AliFemtoParticleCollection* aCollection);
+  virtual void Finish() { 
+#ifdef STHBTDEBUG
+    cout << " *** no user defined Finish(), take from base class" << endl;
+#endif
+  }
+  virtual void Init() { 
+#ifdef STHBTDEBUG
+    cout << " *** no user defined Init(), take from base class" << endl;
+#endif
+  }
+};
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCutMonitorCollection.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCutMonitorCollection.h
new file mode 100644 (file)
index 0000000..fd1d947
--- /dev/null
@@ -0,0 +1,20 @@
+#ifndef AliFemtoCutMonitorCollection_hh
+#define AliFemtoCutMonitorCollection_hh
+
+
+//#include <list>
+#include <vector>
+#if !defined(ST_NO_NAMESPACES)
+using std::vector;
+#endif
+class AliFemtoCutMonitor;
+
+#ifdef ST_NO_TEMPLATE_DEF_ARGS
+typedef vector<AliFemtoCutMonitor*, allocator<AliFemtoCutMonitor*> >            AliFemtoCutMonitorCollection;
+typedef vector<AliFemtoCutMonitor*, allocator<AliFemtoCutMonitor*> >::iterator  AliFemtoCutMonitorIterator;
+#else
+typedef vector<AliFemtoCutMonitor*>            AliFemtoCutMonitorCollection;
+typedef vector<AliFemtoCutMonitor*>::iterator  AliFemtoCutMonitorIterator;
+#endif
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCutMonitorEventMult.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCutMonitorEventMult.cxx
new file mode 100644 (file)
index 0000000..830010d
--- /dev/null
@@ -0,0 +1,336 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoCutMonitorEventMult - the cut monitor for particles to study    //
+// the difference between reconstructed and true momentum                     //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+#include "AliFemtoCutMonitorEventMult.h"
+#include "AliFemtoModelHiddenInfo.h"
+#include "AliFemtoEvent.h"
+#include <TH1D.h>
+#include <TH2D.h>
+#include <TList.h>
+
+AliFemtoCutMonitorEventMult::AliFemtoCutMonitorEventMult():
+  fEvMult(0),
+  fNormEvMult(0),
+  fSPDMult(0),
+  fMultSumPt(0),
+  freadMC(kFALSE),
+  faddhists(kFALSE),
+  fEstimateITSTPC(0),
+  fEstimateTracklets(0),
+  fEstimateITSPure(0),
+  fEst1Est2(0),
+  fEst1Est3(0),
+  fEst2Est3(0),
+  fEst1Norm(0),
+  fEst2Norm(0),
+  fEst3Norm(0)
+{
+  // Default constructor
+  fEvMult = new TH1D("EvMult", "Event Multiplicity", 5001, -0.5, 5000.5);
+  fMultSumPt = new TH2D("EvMultSumPt","Event Multiplicity vs Total pT",5001,-0.5,5000.5,1000,0.0,100.0);
+}
+
+AliFemtoCutMonitorEventMult::AliFemtoCutMonitorEventMult(const char *aName):
+  AliFemtoCutMonitor(),
+  fEvMult(0),
+  fNormEvMult(0),
+  fSPDMult(0),
+  fMultSumPt(0),
+  freadMC(kFALSE),
+  faddhists(kFALSE),
+  fEstimateITSTPC(0),
+  fEstimateTracklets(0),
+  fEstimateITSPure(0),
+  fEst1Est2(0),
+  fEst1Est3(0),
+  fEst2Est3(0),
+  fEst1Norm(0),
+  fEst2Norm(0),
+  fEst3Norm(0)
+{
+  // Normal constructor
+  char name[200];
+  snprintf(name, 200, "EvMult%s", aName);
+  fEvMult = new TH1D(name, "Event Multiplicity", 5001, -0.5, 5000.5);
+
+  snprintf(name, 200, "NormEvMult%s", aName);
+  fNormEvMult = new TH1D(name, "Normalized Event Multiplicity", 5001, -0.5, 5000.5);
+
+  if(!freadMC) {
+    snprintf(name, 200, "SPDEvMult%s", aName);
+    fSPDMult = new TH1D(name, "SPD Tracklet Multiplicity", 5001, -0.5, 5000.5);
+  }
+
+  snprintf(name, 200, "EvMultTotPt%s", aName);
+  fMultSumPt = new TH2D(name,"Event Multiplicity vs Total pT",501,-0.5,500.5,1000,0.0,100.0);
+
+  if(faddhists)
+    {
+      snprintf(name, 200, "EvMultEstITSTPC%s", aName);
+      fEstimateITSTPC = new TH1D(name, "ITS+TPC Multiplicity Estimate", 5001, -0.5, 5000.5);
+
+      snprintf(name, 200, "EvMultEstTracklets%s", aName);
+      fEstimateTracklets = new TH1D(name, "Tracklets Multiplicity Estimate", 5001, -0.5, 5000.5);
+
+      snprintf(name, 200, "EvMultEstITSPure%s", aName);
+      fEstimateITSPure = new TH1D(name, "ITS Pure Multiplicity Estimate", 8001, -0.5, 8000.5);
+
+      snprintf(name, 200, "EstITSTPCEstTracklet%s", aName);
+      fEst1Est2 = new TH2D(name,"ITS+TPC vs Tracklets",501,-0.5,5000.5,501,-0.5,500.5);
+
+      snprintf(name, 200, "EstITSTPCEstITSPure%s", aName);
+      fEst1Est3 = new TH2D(name,"ITS+TPC vs ITS Pure",501,-0.5,5000.5,801,-0.5,8000.5);
+
+      snprintf(name, 200, "EstTrackletEstITSPure%s", aName);
+      fEst2Est3 = new TH2D(name,"Tracklets vs ITS Pure",501,-0.5,5000.5,801,-0.5,8000.5);
+
+      snprintf(name, 200, "EstITSTPCNormMult%s", aName);
+      fEst1Norm = new TH2D(name,"ITS+TPC vs Normalized Mult",501,-0.5,5000.5,501,-0.5,5000.5);
+
+      snprintf(name, 200, "EstTrackletsNormMult%s", aName);
+      fEst2Norm = new TH2D(name,"Tracklets vs Normalized Mult",501,-0.5,5000.5,501,-0.5,5000.5);
+
+      snprintf(name, 200, "EstITSPureNormMult%s", aName);
+      fEst3Norm = new TH2D(name,"ITS Pure vs Normalized Mult",501,-0.5,5000.5,501,-0.5,5000.5);
+    }
+
+}
+
+AliFemtoCutMonitorEventMult::AliFemtoCutMonitorEventMult(const AliFemtoCutMonitorEventMult &aCut):
+  AliFemtoCutMonitor(),
+  fEvMult(0),
+  fNormEvMult(0),
+  fSPDMult(0),
+  fMultSumPt(0),
+  freadMC(kFALSE),
+  faddhists(kFALSE),
+  fEstimateITSTPC(0),
+  fEstimateTracklets(0),
+  fEstimateITSPure(0),
+  fEst1Est2(0),
+  fEst1Est3(0),
+  fEst2Est3(0),
+  fEst1Norm(0),
+  fEst2Norm(0),
+  fEst3Norm(0)
+{
+  // copy constructor
+  if (fEvMult) delete fEvMult;
+  fEvMult = new TH1D(*aCut.fEvMult);
+
+  if (fNormEvMult) delete fNormEvMult;
+  fNormEvMult = new TH1D(*aCut.fNormEvMult);
+
+  
+  if(!freadMC){
+    if (fSPDMult) delete fSPDMult;
+    fSPDMult = new TH1D(*aCut.fSPDMult);
+  }
+
+  if (fMultSumPt) delete fMultSumPt;
+  fMultSumPt = new TH2D(*aCut.fMultSumPt);
+
+
+  if(faddhists)
+    {
+      if (fEstimateITSTPC) delete fEstimateITSTPC;
+      fEstimateITSTPC = new TH1D(*aCut.fEstimateITSTPC);
+
+      if (fEstimateTracklets) delete fEstimateTracklets;
+      fEstimateTracklets = new TH1D(*aCut.fEstimateTracklets);
+
+      if (fEstimateITSPure) delete fEstimateITSPure;
+      fEstimateITSPure = new TH1D(*aCut.fEstimateITSPure);
+
+      if (fEst1Est2) delete fEst1Est2;
+      fEst1Est2 = new TH2D(*aCut.fEst1Est2);
+
+      if (fEst1Est3) delete fEst1Est3;
+      fEst1Est3 = new TH2D(*aCut.fEst1Est3);
+
+      if (fEst2Est3) delete fEst2Est3;
+      fEst2Est3 = new TH2D(*aCut.fEst2Est3);
+
+      if (fEst1Norm) delete fEst1Norm;
+      fEst1Norm = new TH2D(*aCut.fEst1Norm);
+
+      if (fEst2Norm) delete fEst2Norm;
+      fEst2Norm = new TH2D(*aCut.fEst2Norm);
+
+      if (fEst3Norm) delete fEst3Norm;
+      fEst3Norm = new TH2D(*aCut.fEst3Norm);
+    }
+}
+
+AliFemtoCutMonitorEventMult::~AliFemtoCutMonitorEventMult()
+{
+  // Destructor
+  delete fEvMult;
+  delete fNormEvMult;
+  if(!freadMC){
+    delete fSPDMult;
+  }
+  delete fMultSumPt;
+
+  if(faddhists)
+    {
+      delete fEstimateITSTPC;
+      delete fEstimateTracklets;
+      delete fEstimateITSPure;
+      delete fEst1Est2;
+      delete fEst1Est3;
+      delete fEst2Est3;
+      delete fEst1Norm;
+      delete fEst2Norm;
+      delete fEst3Norm;
+    }      
+}
+
+AliFemtoCutMonitorEventMult& AliFemtoCutMonitorEventMult::operator=(const AliFemtoCutMonitorEventMult& aCut)
+{
+  // assignment operator
+  if (this == &aCut) 
+    return *this;
+
+  if (fEvMult) delete fEvMult;
+  fEvMult = new TH1D(*aCut.fEvMult);
+  
+  if (fNormEvMult) delete fNormEvMult;
+  fNormEvMult = new TH1D(*aCut.fNormEvMult);
+  
+  if(!freadMC){
+    if (fSPDMult) delete fSPDMult;
+    fSPDMult = new TH1D(*aCut.fSPDMult);
+  }
+  
+  if (fMultSumPt) delete fMultSumPt;
+  fMultSumPt = new TH2D(*aCut.fMultSumPt);
+
+
+  if(faddhists)
+    {
+      if (fEstimateITSTPC) delete fEstimateITSTPC;
+      fEstimateITSTPC = new TH1D(*aCut.fEstimateITSTPC);
+
+      if (fEstimateTracklets) delete fEstimateTracklets;
+      fEstimateTracklets = new TH1D(*aCut.fEstimateTracklets);
+
+      if (fEstimateITSPure) delete fEstimateITSPure;
+      fEstimateITSPure = new TH1D(*aCut.fEstimateITSPure);
+
+      if (fEst1Est2) delete fEst1Est2;
+      fEst1Est2 = new TH2D(*aCut.fEst1Est2);
+
+      if (fEst1Est3) delete fEst1Est3;
+      fEst1Est3 = new TH2D(*aCut.fEst1Est3);
+
+      if (fEst2Est3) delete fEst2Est3;
+      fEst2Est3 = new TH2D(*aCut.fEst2Est3);
+
+      if (fEst1Norm) delete fEst1Norm;
+      fEst1Norm = new TH2D(*aCut.fEst1Norm);
+
+      if (fEst2Norm) delete fEst2Norm;
+      fEst2Norm = new TH2D(*aCut.fEst2Norm);
+
+      if (fEst3Norm) delete fEst3Norm;
+      fEst3Norm = new TH2D(*aCut.fEst3Norm);
+    }
+
+  return *this;
+}
+
+AliFemtoString AliFemtoCutMonitorEventMult::Report(){ 
+  // Prepare report from the execution
+  string stemp = "*** AliFemtoCutMonitorEventMult report"; 
+  AliFemtoString returnThis = stemp;
+  return returnThis; 
+}
+
+void AliFemtoCutMonitorEventMult::Fill(const AliFemtoEvent* aEvent)
+{
+  // Fill in the monitor histograms with the values from the current track
+  fEvMult->Fill(aEvent->NumberOfTracks());
+  fNormEvMult->Fill(aEvent->UncorrectedNumberOfPrimaries());
+  if(!freadMC){
+    fSPDMult->Fill(aEvent->SPDMultiplicity());
+  }
+  fMultSumPt->Fill(aEvent->UncorrectedNumberOfPrimaries(), aEvent->ZDCEMEnergy());
+
+  if(faddhists)
+    {
+      fEstimateITSTPC->Fill(aEvent->MultiplicityEstimateITSTPC());
+      fEstimateTracklets->Fill(aEvent->MultiplicityEstimateTracklets());
+      fEstimateITSPure->Fill(aEvent->MultiplicityEstimateITSPure());
+      fEst1Est2->Fill(aEvent->MultiplicityEstimateITSTPC(),aEvent->MultiplicityEstimateTracklets());
+      fEst1Est3->Fill(aEvent->MultiplicityEstimateITSTPC(),aEvent->MultiplicityEstimateITSPure());
+      fEst2Est3->Fill(aEvent->MultiplicityEstimateTracklets(),aEvent->MultiplicityEstimateITSPure());
+      fEst1Norm->Fill(aEvent->MultiplicityEstimateITSTPC(),aEvent->UncorrectedNumberOfPrimaries());
+      fEst2Norm->Fill(aEvent->MultiplicityEstimateTracklets(),aEvent->UncorrectedNumberOfPrimaries());
+      fEst3Norm->Fill(aEvent->MultiplicityEstimateITSPure(),aEvent->UncorrectedNumberOfPrimaries());
+    }
+
+}
+
+void AliFemtoCutMonitorEventMult::Write()
+{
+  // Write out the relevant histograms
+  fEvMult->Write();
+  fNormEvMult->Write();
+  if(!freadMC){
+    fSPDMult->Write();
+  }
+  fMultSumPt->Write();
+
+  if(faddhists)
+    {
+      fEstimateITSTPC->Write();
+      fEstimateTracklets->Write();
+      fEstimateITSPure->Write();
+      fEst1Est2->Write();
+      fEst1Est3->Write();
+      fEst2Est3->Write();
+      fEst1Norm->Write();
+      fEst2Norm->Write();
+      fEst3Norm->Write();
+    }
+
+}
+
+TList *AliFemtoCutMonitorEventMult::GetOutputList()
+{
+  TList *tOutputList = new TList();
+  tOutputList->Add(fEvMult);
+  tOutputList->Add(fNormEvMult);
+  tOutputList->Add(fSPDMult);
+  tOutputList->Add(fMultSumPt);
+
+  if(faddhists)
+    {
+      tOutputList->Add(fEstimateITSTPC);
+      tOutputList->Add(fEstimateTracklets);
+      tOutputList->Add(fEstimateITSPure);
+      tOutputList->Add(fEst1Est2);
+      tOutputList->Add(fEst1Est3);
+      tOutputList->Add(fEst2Est3);
+      tOutputList->Add(fEst1Norm);
+      tOutputList->Add(fEst2Norm);
+      tOutputList->Add(fEst3Norm);
+    }
+  
+  return tOutputList;
+}
+
+void AliFemtoCutMonitorEventMult::SetReadMC(Bool_t mc)
+{
+  freadMC=mc;
+}
+
+void AliFemtoCutMonitorEventMult::AdditionalMultHistsOn(Bool_t addhists)
+{
+  faddhists=addhists;
+}
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCutMonitorEventMult.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCutMonitorEventMult.h
new file mode 100644 (file)
index 0000000..143109d
--- /dev/null
@@ -0,0 +1,70 @@
+////////////////////////////////////////////////////////////////////////////////
+///                                                                          ///
+/// AliFemtoCutMonitorEventMult - the cut monitor for events to study        ///
+/// the multiplicity distribution of events                                  ///
+///                                                                          ///
+////////////////////////////////////////////////////////////////////////////////
+#ifndef AliFemtoCutMonitorEventMult_hh
+#define AliFemtoCutMonitorEventMult_hh
+
+class AliFemtoEvent;
+class AliFemtoTrack;
+class AliFemtoV0;
+class AliFemtoKink;
+class AliFemtoPair; 
+class TH1D;
+class TH2D;
+class TList;
+#include "AliFemtoString.h"
+#include "AliFemtoParticleCollection.h"
+#include "AliFemtoCutMonitor.h"
+
+class AliFemtoCutMonitorEventMult : public AliFemtoCutMonitor{
+  
+ public:
+  AliFemtoCutMonitorEventMult();
+  AliFemtoCutMonitorEventMult(const char *aName);
+  AliFemtoCutMonitorEventMult(const AliFemtoCutMonitorEventMult &aCut);
+  virtual ~AliFemtoCutMonitorEventMult();
+
+  AliFemtoCutMonitorEventMult& operator=(const AliFemtoCutMonitorEventMult& aCut);
+
+  virtual AliFemtoString Report();
+  virtual void Fill(const AliFemtoEvent* aEvent);
+  virtual void Fill(const AliFemtoTrack* aTrack) {AliFemtoCutMonitor::Fill(aTrack);}
+  virtual void Fill(const AliFemtoV0* aV0) {AliFemtoCutMonitor::Fill(aV0);}
+  virtual void Fill(const AliFemtoKink* aKink) {AliFemtoCutMonitor::Fill(aKink);}
+  virtual void Fill(const AliFemtoPair* aPair) {AliFemtoCutMonitor::Fill(aPair);}
+  virtual void Fill(const AliFemtoParticleCollection* aCollection) {AliFemtoCutMonitor::Fill(aCollection);}
+  virtual void Fill(const AliFemtoEvent* aEvent,const AliFemtoParticleCollection* aCollection)
+  {AliFemtoCutMonitor::Fill(aEvent, aCollection);}
+
+  void SetReadMC(Bool_t mc);
+  void AdditionalMultHistsOn(Bool_t addhists);
+  void Write();
+
+  virtual TList *GetOutputList();
+
+ private:
+  TH1D *fEvMult;     // Multiplicity distribution
+  TH1D *fNormEvMult; // Normalized event multiplicity distribution
+  TH1D *fSPDMult;    // SPD tracklet multiplicity
+  TH2D *fMultSumPt;  // Event total pT vs. multiplicity
+
+  Bool_t freadMC;     // If true - add only one histogram to the output
+  Bool_t faddhists;   // If true - add only additional multiplicity histograms
+  
+  TH1D *fEstimateITSTPC;     // Multiplicity estimate ITS+TPC
+  TH1D *fEstimateTracklets;  // Multiplicity estimate Tracklets
+  TH1D *fEstimateITSPure;    // Multiplicity estimate ITS Pure
+
+  TH2D *fEst1Est2;           // ITS+TPC vs Tracklets
+  TH2D *fEst1Est3;           // ITS+TPC vs ITS Pure
+  TH2D *fEst2Est3;           // Tracklets vs ITS Pure
+  TH2D *fEst1Norm;           // ITS+TPC vs Normalized
+  TH2D *fEst2Norm;           // Tracklets vs Normalized
+  TH2D *fEst3Norm;           // ITS Pure vs Normalized
+
+};
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCutMonitorEventVertex.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCutMonitorEventVertex.cxx
new file mode 100644 (file)
index 0000000..df5b93e
--- /dev/null
@@ -0,0 +1,141 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoCutMonitorEventVertex - the cut monitor for events to study        //
+// the distribution and error of the primary vertex                           //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+#include "AliFemtoCutMonitorEventVertex.h"
+#include "AliFemtoModelHiddenInfo.h"
+#include "AliFemtoEvent.h"
+#include <TH1D.h>
+#include <TH2D.h>
+#include <TList.h>
+#include <TMath.h>
+
+AliFemtoCutMonitorEventVertex::AliFemtoCutMonitorEventVertex():
+  AliFemtoCutMonitor(),
+  fEvVertRad(0),
+  fEvVertXY(0),
+  fEvVertSigXY(0),
+  fEvVertZ(0),
+  fEvVertSigZ(0)
+{
+  // Default constructor
+  fEvVertRad   = new TH1D("EvVertRad",   "Vertex position radial", 200, 0.0, 0.2);
+  fEvVertXY    = new TH2D("EvVertXY",    "Vertex position xy plane", 200, -0.2, 0.2, 200, -0.2, 0.2);
+  fEvVertSigXY = new TH1D("EvVertSigXY", "Vertex error in xy plane", 200, 0.0, 0.2);
+  fEvVertZ     = new TH1D("EvVertZ",     "Vertex position in z", 500, -50.0, 50.0);
+  fEvVertSigZ  = new TH1D("EvVertSigZ",  "Vertex error in z", 100, 0.0, 0.2);
+}
+
+AliFemtoCutMonitorEventVertex::AliFemtoCutMonitorEventVertex(const char *aName):
+  AliFemtoCutMonitor(),
+  fEvVertRad(0),
+  fEvVertXY(0),
+  fEvVertSigXY(0),
+  fEvVertZ(0),
+  fEvVertSigZ(0)
+{
+  // Normal constructor
+  char name[200];
+  snprintf(name, 200, "EvVertRad%s", aName);
+  fEvVertRad   = new TH1D(name,   "Vertex position radial", 200, 0.0, 0.2);
+  snprintf(name, 200, "EvVertXY%s", aName);
+  fEvVertXY    = new TH2D(name,    "Vertex position xy plane", 200, -0.2, 0.2, 200, -0.2, 0.2);
+  snprintf(name, 200, "EvVertSigXY%s", aName);
+  fEvVertSigXY = new TH1D(name, "Vertex error in xy plane", 200, 0.0, 0.2);
+  snprintf(name, 200, "EvVertZ%s", aName);
+  fEvVertZ     = new TH1D(name,     "Vertex position in z", 500, -50.0, 50.0);
+  snprintf(name, 200, "EvVertSigZ%s", aName);
+  fEvVertSigZ  = new TH1D(name,  "Vertex error in z", 100, 0.0, 0.2);
+}
+
+AliFemtoCutMonitorEventVertex::AliFemtoCutMonitorEventVertex(const AliFemtoCutMonitorEventVertex &aCut):
+  AliFemtoCutMonitor(),
+  fEvVertRad(0),
+  fEvVertXY(0),
+  fEvVertSigXY(0),
+  fEvVertZ(0),
+  fEvVertSigZ(0)
+{
+  // copy constructor
+  if (fEvVertRad) delete fEvVertRad;
+  fEvVertRad = new TH1D(*aCut.fEvVertRad);
+  if (fEvVertXY) delete fEvVertXY;
+  fEvVertXY = new TH2D(*aCut.fEvVertXY);
+  if (fEvVertSigXY) delete fEvVertSigXY;
+  fEvVertSigXY = new TH1D(*aCut.fEvVertSigXY);
+  if (fEvVertZ) delete fEvVertZ;
+  fEvVertZ = new TH1D(*aCut.fEvVertZ);
+  if (fEvVertSigZ) delete fEvVertSigZ;
+  fEvVertSigZ = new TH1D(*aCut.fEvVertSigZ);
+}
+
+AliFemtoCutMonitorEventVertex::~AliFemtoCutMonitorEventVertex()
+{
+  // Destructor
+  delete fEvVertRad;
+  delete fEvVertXY;
+  delete fEvVertSigXY;
+  delete fEvVertZ;
+  delete fEvVertSigZ;
+}
+
+AliFemtoCutMonitorEventVertex& AliFemtoCutMonitorEventVertex::operator=(const AliFemtoCutMonitorEventVertex& aCut)
+{
+  // assignment operator
+  if (this == &aCut) 
+    return *this;
+
+  if (fEvVertRad) delete fEvVertRad;
+  fEvVertRad = new TH1D(*aCut.fEvVertRad);
+  if (fEvVertXY) delete fEvVertXY;
+  fEvVertXY = new TH2D(*aCut.fEvVertXY);
+  if (fEvVertSigXY) delete fEvVertSigXY;
+  fEvVertSigXY = new TH1D(*aCut.fEvVertSigXY);
+  if (fEvVertZ) delete fEvVertZ;
+  fEvVertZ = new TH1D(*aCut.fEvVertZ);
+  if (fEvVertSigZ) delete fEvVertSigZ;
+  fEvVertSigZ = new TH1D(*aCut.fEvVertSigZ);
+  
+  return *this;
+}
+
+AliFemtoString AliFemtoCutMonitorEventVertex::Report(){ 
+  // Prepare report from the execution
+  string stemp = "*** AliFemtoCutMonitorEventVertex report"; 
+  AliFemtoString returnThis = stemp;
+  return returnThis; 
+}
+
+void AliFemtoCutMonitorEventVertex::Fill(const AliFemtoEvent* aEvent)
+{
+  // Fill in the monitor histograms with the values from the current track
+  fEvVertRad->Fill(TMath::Hypot(aEvent->PrimVertPos().x(), aEvent->PrimVertPos().y()));
+  fEvVertXY->Fill(aEvent->PrimVertPos().x(), aEvent->PrimVertPos().y());
+  fEvVertSigXY->Fill(TMath::Sqrt(aEvent->PrimVertCov()[0]+aEvent->PrimVertCov()[2]));
+  fEvVertZ->Fill(aEvent->PrimVertPos().z());
+  fEvVertSigZ->Fill(TMath::Sqrt(aEvent->PrimVertCov()[5]));
+}
+
+void AliFemtoCutMonitorEventVertex::Write()
+{
+  // Write out the relevant histograms
+  fEvVertRad->Write();
+  fEvVertXY->Write();
+  fEvVertSigXY->Write();
+  fEvVertZ->Write();
+  fEvVertSigZ->Write();
+}
+
+TList *AliFemtoCutMonitorEventVertex::GetOutputList()
+{
+  TList *tOutputList = new TList();
+  tOutputList->Add(fEvVertRad);
+  tOutputList->Add(fEvVertXY);
+  tOutputList->Add(fEvVertSigXY);
+  tOutputList->Add(fEvVertZ);
+  tOutputList->Add(fEvVertSigZ);
+
+  return tOutputList;
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCutMonitorEventVertex.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCutMonitorEventVertex.h
new file mode 100644 (file)
index 0000000..7d0640a
--- /dev/null
@@ -0,0 +1,54 @@
+////////////////////////////////////////////////////////////////////////////////
+///                                                                          ///
+/// AliFemtoCutMonitorEventVertex - the cut monitor for events to study      ///
+/// the distribution and error of the primary vertex                         ///
+///                                                                          ///
+////////////////////////////////////////////////////////////////////////////////
+#ifndef AliFemtoCutMonitorEventVertex_hh
+#define AliFemtoCutMonitorEventVertex_hh
+
+class AliFemtoEvent;
+class AliFemtoTrack;
+class AliFemtoV0;
+class AliFemtoKink;
+class AliFemtoPair; 
+class TH1D;
+class TH2D;
+class TList;
+#include "AliFemtoString.h"
+#include "AliFemtoParticleCollection.h"
+#include "AliFemtoCutMonitor.h"
+
+class AliFemtoCutMonitorEventVertex : public AliFemtoCutMonitor{
+  
+public:
+  AliFemtoCutMonitorEventVertex();
+  AliFemtoCutMonitorEventVertex(const char *aName);
+  AliFemtoCutMonitorEventVertex(const AliFemtoCutMonitorEventVertex &aCut);
+  virtual ~AliFemtoCutMonitorEventVertex();
+
+  AliFemtoCutMonitorEventVertex& operator=(const AliFemtoCutMonitorEventVertex& aCut);
+
+  virtual AliFemtoString Report();
+  virtual void Fill(const AliFemtoEvent* aEvent);
+  virtual void Fill(const AliFemtoTrack* aTrack) {AliFemtoCutMonitor::Fill(aTrack);}
+  virtual void Fill(const AliFemtoV0* aV0) {AliFemtoCutMonitor::Fill(aV0);}
+  virtual void Fill(const AliFemtoKink* aKink) {AliFemtoCutMonitor::Fill(aKink);}
+  virtual void Fill(const AliFemtoPair* aPair) {AliFemtoCutMonitor::Fill(aPair);}
+  virtual void Fill(const AliFemtoParticleCollection* aCollection) {AliFemtoCutMonitor::Fill(aCollection);}
+  virtual void Fill(const AliFemtoEvent* aEvent,const AliFemtoParticleCollection* aCollection)
+  {AliFemtoCutMonitor::Fill(aEvent, aCollection);}
+
+  void Write();
+
+  virtual TList *GetOutputList();
+
+private:
+  TH1D *fEvVertRad;     // Vertex position in radial direction
+  TH2D *fEvVertXY;      // Vertex position in XY plane
+  TH1D *fEvVertSigXY;   // Sigma in XY plane
+  TH1D *fEvVertZ;       // Vertex position in Z direction
+  TH1D *fEvVertSigZ;    // Sigma in Z direction
+};
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCutMonitorHandler.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCutMonitorHandler.cxx
new file mode 100644 (file)
index 0000000..efdb4b7
--- /dev/null
@@ -0,0 +1,318 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFemtoCutMonitorHandler: a handler for cut monitors                 //
+// You add cut monitors to the collection which are stored in two        //
+// separate collections - one which stores characteristics of the        //
+// entities (tracks, particles, pairs, events) that pass the respective  //
+// cuts and the other for the ones that fail the cut.                    //
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+
+#include <TList.h>
+#include "AliFemtoCutMonitorHandler.h"
+#include "AliFemtoTypes.h"
+
+#ifdef __ROOT__
+ClassImp(AliFemtoCutMonitorHandler)
+#endif
+// ---------------------------------------------------------------------------
+AliFemtoCutMonitorHandler::AliFemtoCutMonitorHandler():
+  fCollectionsEmpty(0), fPassColl(0), fFailColl(0)
+{
+  // Default constructor
+  cout << " *** AliFemtoCutMonitorHandler::AliFemtoCutMonitorHandler() " << endl;
+  fCollectionsEmpty = 0;
+  fPassColl = new AliFemtoCutMonitorCollection();
+  fFailColl = new AliFemtoCutMonitorCollection();
+}
+// ---------------------------------------------------------------------------
+AliFemtoCutMonitorHandler::AliFemtoCutMonitorHandler(const AliFemtoCutMonitorHandler& aHan):
+  fCollectionsEmpty(0), fPassColl(0), fFailColl(0)
+{
+  // Copy constructor
+  fCollectionsEmpty = aHan.fCollectionsEmpty;
+  fPassColl = new AliFemtoCutMonitorCollection();
+  AliFemtoCutMonitorIterator iter;
+  for (iter=aHan.fPassColl->begin(); iter!=aHan.fPassColl->end(); iter++){
+    fPassColl->push_back(*iter);
+  }
+  fFailColl = new AliFemtoCutMonitorCollection();
+  for (iter=aHan.fFailColl->begin(); iter!=aHan.fFailColl->end(); iter++){
+    fFailColl->push_back(*iter);
+  }
+}
+
+// ---------------------------------------------------------------------------
+AliFemtoCutMonitorHandler::~AliFemtoCutMonitorHandler() { 
+  // Default destructor
+  delete fPassColl;
+  delete fFailColl;
+}   
+//__________________________
+AliFemtoCutMonitorHandler& AliFemtoCutMonitorHandler::operator=(const AliFemtoCutMonitorHandler& aHan)
+{
+  // assignment operator
+  if (this == &aHan)
+    return *this;
+
+  AliFemtoCutMonitorIterator iter;
+  if (fPassColl) {
+    fPassColl->clear();
+    delete fPassColl;
+  }
+  if (fFailColl) {
+    fFailColl->clear();
+    delete fFailColl;
+  }
+  fPassColl = new AliFemtoCutMonitorCollection();
+  for (iter=aHan.fPassColl->begin(); iter!=aHan.fPassColl->end(); iter++){
+    fPassColl->push_back(*iter);
+  }
+  fFailColl = new AliFemtoCutMonitorCollection();
+  for (iter=aHan.fFailColl->begin(); iter!=aHan.fFailColl->end(); iter++){
+    fFailColl->push_back(*iter);
+  }
+  return *this;
+}
+
+// ---------------------------------------------------------------------------
+void AliFemtoCutMonitorHandler::FillCutMonitor(const AliFemtoEvent* event, bool pass) { 
+  // fill event cut monitors
+  if (fCollectionsEmpty) return;
+  AliFemtoCutMonitorIterator iter;
+  AliFemtoCutMonitor* tCM;
+  if ( pass) {
+    for (iter=fPassColl->begin(); iter!=fPassColl->end(); iter++){
+      tCM = *iter;
+      tCM->Fill(event);
+    }
+  } else {
+    for (iter=fFailColl->begin(); iter!=fFailColl->end(); iter++){
+      tCM = *iter;
+      tCM->Fill(event);
+    }
+  }
+}
+// ---------------------------------------------------------------------------
+void AliFemtoCutMonitorHandler::FillCutMonitor(const AliFemtoTrack* track, bool pass) { 
+  // Fill track cut monitors
+  if (fCollectionsEmpty) return;
+  AliFemtoCutMonitorIterator iter;
+  AliFemtoCutMonitor* tCM;
+  if ( pass) {
+    for (iter=fPassColl->begin(); iter!=fPassColl->end(); iter++){
+      tCM = *iter;
+      tCM->Fill(track);
+    }
+  } else {
+    for (iter=fFailColl->begin(); iter!=fFailColl->end(); iter++){
+      tCM = *iter;
+      tCM->Fill(track);
+    }
+  }
+}
+// ---------------------------------------------------------------------------
+void AliFemtoCutMonitorHandler::FillCutMonitor(const AliFemtoV0* v0, bool pass) { 
+  // fill V0 cut monitors
+  if (fCollectionsEmpty) return;
+  AliFemtoCutMonitorIterator iter;
+  AliFemtoCutMonitor* tCM;
+  if ( pass) {
+    for (iter=fPassColl->begin(); iter!=fPassColl->end(); iter++){
+      tCM = *iter;
+      tCM->Fill(v0);
+    }
+  } else {
+    for (iter=fFailColl->begin(); iter!=fFailColl->end(); iter++){
+      tCM = *iter;
+      tCM->Fill(v0);
+    }
+  }
+}
+// ---------------------------------------------------------------------------
+void AliFemtoCutMonitorHandler::FillCutMonitor(const AliFemtoKink* kink, bool pass) { 
+  // fill kink cut monitors
+  if (fCollectionsEmpty) return;
+  AliFemtoCutMonitorIterator iter;
+  AliFemtoCutMonitor* tCM;
+  if ( pass) {
+    for (iter=fPassColl->begin(); iter!=fPassColl->end(); iter++){
+      tCM = *iter;
+      tCM->Fill(kink);
+    }
+  } else {
+    for (iter=fFailColl->begin(); iter!=fFailColl->end(); iter++){
+      tCM = *iter;
+      tCM->Fill(kink);
+    }
+  }
+}
+// ---------------------------------Gael/12/04/02-----------------------------
+void AliFemtoCutMonitorHandler::FillCutMonitor(const AliFemtoPair* pair, bool pass) { 
+  // fill pair cut monitors
+  if (fCollectionsEmpty) return;
+  AliFemtoCutMonitorIterator iter;
+  AliFemtoCutMonitor* tCM;
+  if ( pass) {
+    for (iter=fPassColl->begin(); iter!=fPassColl->end(); iter++){
+      tCM = *iter;
+      tCM->Fill(pair);
+    }
+  } else {
+    for (iter=fFailColl->begin(); iter!=fFailColl->end(); iter++){
+      tCM = *iter;
+      tCM->Fill(pair);
+    }
+  }
+}
+// ---------------------------------Gael/19/06/02-----------------------------
+void AliFemtoCutMonitorHandler::FillCutMonitor(const AliFemtoParticleCollection* partColl) {
+  // fill particle collection cut monitor 
+  if (fCollectionsEmpty) return;
+  AliFemtoCutMonitorIterator iter;
+  AliFemtoCutMonitor* tCM;
+  
+  for (iter=fPassColl->begin(); iter!=fPassColl->end(); iter++){
+    tCM = *iter;
+    tCM->Fill(partColl);
+  }
+}
+// ------------------------------------Gael/19/06/02-------------------------
+void AliFemtoCutMonitorHandler::FillCutMonitor(const AliFemtoEvent* event,const AliFemtoParticleCollection* partColl) {
+  // Fill event particle collection
+  cout<<"In AliFemtoCutMonitorHandler::FillCutMonitor(const AliFemtoEvent* event, AliFemtoPicoEvent* picoEvent)"<<endl;
+  if (fCollectionsEmpty) return;
+  AliFemtoCutMonitorIterator iter;
+  AliFemtoCutMonitor* tCM;
+  
+  for (iter=fPassColl->begin(); iter!=fPassColl->end(); iter++){
+    tCM = *iter;
+    tCM->Fill(event,partColl);
+  }
+}
+// ---------------------------------------------------------------------------
+void AliFemtoCutMonitorHandler::Finish() { 
+  // Perform finish operations on cut monitors
+  AliFemtoCutMonitorIterator iter;
+  for (iter=fPassColl->begin(); iter!=fPassColl->end(); iter++){
+    (*iter)->Finish();
+  }
+  for (iter=fFailColl->begin(); iter!=fFailColl->end(); iter++){
+    (*iter)->Finish();
+  }
+}
+// ---------------------------------------------------------------------------
+void AliFemtoCutMonitorHandler::AddCutMonitor(AliFemtoCutMonitor* cutMoni1, AliFemtoCutMonitor* cutMoni2) { 
+  // Add cut monitors to collections
+  fPassColl->push_back(cutMoni1);
+  fFailColl->push_back(cutMoni2);
+  fCollectionsEmpty=false;
+}
+// ---------------------------------------------------------------------------
+void AliFemtoCutMonitorHandler::AddCutMonitor(AliFemtoCutMonitor* cutMoni) { 
+  // make a copy of the cut monitor
+  cout << " make a copy of the cutmonitor and push both into the collections " << endl;
+  cout << " not yet implemented" << endl;
+  fPassColl->push_back(cutMoni);
+  cout << " only pass collection pushed" << endl;
+  fCollectionsEmpty=false;
+}
+// ---------------------------------------------------------------------------
+void AliFemtoCutMonitorHandler::AddCutMonitorPass(AliFemtoCutMonitor* cutMoni) { 
+  // add monitors to pass
+  fPassColl->push_back(cutMoni);
+  fCollectionsEmpty=false;
+}
+// ---------------------------------------------------------------------------
+void AliFemtoCutMonitorHandler::AddCutMonitorFail(AliFemtoCutMonitor* cutMoni) { 
+  // add monitors to fail
+  fFailColl->push_back(cutMoni);
+  fCollectionsEmpty=false;
+}
+// ---------------------------------------------------------------------------
+AliFemtoCutMonitor* AliFemtoCutMonitorHandler::PassMonitor(int n) { 
+  // return pass monitor number n
+  AliFemtoCutMonitorIterator iter = fPassColl->begin();
+  if ( (int)fPassColl->size() <= n ) return NULL;
+  for ( int i=0; i<n; i++)
+    iter++;
+  return *iter;
+}
+// ---------------------------------------------------------------------------
+AliFemtoCutMonitor* AliFemtoCutMonitorHandler::FailMonitor(int n) { 
+  // return fail monitor number n
+  AliFemtoCutMonitorIterator iter = fFailColl->begin();
+  if ( (int)fFailColl->size() <= n ) return NULL;
+  for ( int i=0; i<n; i++)
+    iter++;
+  return *iter;
+}
+//_____________________________________________________________________________
+TList *AliFemtoCutMonitorHandler::GetOutputList()
+{
+  TList *tOutputList = new TList();
+
+  for (unsigned int ipass=0; ipass<fPassColl->size(); ipass++) {
+    TList *tLp = PassMonitor(ipass)->GetOutputList();
+
+    TIter nextLp(tLp);
+    while (TObject *obj = nextLp()) {
+      tOutputList->Add(obj);
+    }
+    
+    delete tLp;
+  }
+
+  for (unsigned int ipass=0; ipass<fFailColl->size(); ipass++) {
+    TList *tLf = FailMonitor(ipass)->GetOutputList();
+
+    TIter nextLf(tLf);
+    while (TObject *obj = nextLf()) {
+      tOutputList->Add(obj);
+    }
+    
+    delete tLf;
+  }
+
+  return tOutputList;
+}
+//_____________________________________________________________________________
+void AliFemtoCutMonitorHandler::EventBegin(const AliFemtoEvent* aEvent) 
+{ 
+  if (fCollectionsEmpty) return;
+
+  AliFemtoCutMonitorIterator iter;
+  AliFemtoCutMonitor* tCM;
+
+  for (iter=fPassColl->begin(); iter!=fPassColl->end(); iter++){
+    tCM = *iter;
+    tCM->EventBegin(aEvent);
+  }
+  
+  for (iter=fFailColl->begin(); iter!=fFailColl->end(); iter++){
+    tCM = *iter;
+    tCM->EventBegin(aEvent);
+  }
+}
+//_____________________________________________________________________________
+void AliFemtoCutMonitorHandler::EventEnd(const AliFemtoEvent* aEvent) 
+{ 
+  if (fCollectionsEmpty) return;
+
+  AliFemtoCutMonitorIterator iter;
+  AliFemtoCutMonitor* tCM;
+
+  for (iter=fPassColl->begin(); iter!=fPassColl->end(); iter++){
+    tCM = *iter;
+    tCM->EventEnd(aEvent);
+  }
+  
+  for (iter=fFailColl->begin(); iter!=fFailColl->end(); iter++){
+    tCM = *iter;
+    tCM->EventEnd(aEvent);
+  }
+}
+
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCutMonitorHandler.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCutMonitorHandler.h
new file mode 100644 (file)
index 0000000..78d912b
--- /dev/null
@@ -0,0 +1,64 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFemtoCutMonitorHandler: a handler for cut monitors                 //
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+#ifndef AliFemtoCutMonitorHandler_hh
+#define AliFemtoCutMonitorHandler_hh
+
+
+#include "AliFemtoTypes.h"
+#include "AliFemtoEvent.h"
+#include "AliFemtoTrack.h"
+#include "AliFemtoV0.h"
+#include "AliFemtoKink.h"
+#include "AliFemtoPair.h" //Gael 12/04/02
+#include "AliFemtoParticleCollection.h" // Gael 19/06/02
+#include "AliFemtoCutMonitorCollection.h"
+#include "AliFemtoCutMonitor.h"
+
+class AliFemtoCutMonitorHandler{
+  
+ public:
+  
+  AliFemtoCutMonitorHandler();
+  AliFemtoCutMonitorHandler(const AliFemtoCutMonitorHandler& aHan);
+  virtual ~AliFemtoCutMonitorHandler();
+  AliFemtoCutMonitorHandler& operator=(const AliFemtoCutMonitorHandler& aHan);
+
+  AliFemtoCutMonitorCollection* PassMonitorColl(); 
+  AliFemtoCutMonitorCollection* FailMonitorColl(); 
+  AliFemtoCutMonitor* PassMonitor(int n); 
+  AliFemtoCutMonitor* FailMonitor(int n); 
+  void AddCutMonitor(AliFemtoCutMonitor* cutMoni1, AliFemtoCutMonitor* cutMoni2); 
+  void AddCutMonitor(AliFemtoCutMonitor* cutMoni); 
+  void AddCutMonitorPass(AliFemtoCutMonitor* cutMoni); 
+  void AddCutMonitorFail(AliFemtoCutMonitor* cutMoni); 
+  void FillCutMonitor(const AliFemtoEvent* event, bool pass); 
+  void FillCutMonitor(const AliFemtoTrack* track, bool pass); 
+  void FillCutMonitor(const AliFemtoV0* v0, bool pass); 
+  void FillCutMonitor(const AliFemtoKink* kink, bool pass);
+  void FillCutMonitor(const AliFemtoPair* pair, bool pass);//Gael 11/04/02
+  void FillCutMonitor(const AliFemtoParticleCollection* partColl);// Gael 19/06/02
+  void FillCutMonitor(const AliFemtoEvent* event, const AliFemtoParticleCollection* partColl);// Gael 19/06/02
+  void Finish();
+
+  virtual TList *GetOutputList();
+
+  virtual void EventBegin(const AliFemtoEvent* aEvent);
+  virtual void EventEnd(const AliFemtoEvent* aEvent);
+  
+ private:
+  bool fCollectionsEmpty;                  // Are the collections empty?
+  AliFemtoCutMonitorCollection* fPassColl; // Collection of cut monitors for passed entities
+  AliFemtoCutMonitorCollection* fFailColl; // Collection of cut monitors for failed entities
+#ifdef __ROOT__  
+  ClassDef(AliFemtoCutMonitorHandler, 0)
+#endif  
+  
+};
+
+inline AliFemtoCutMonitorCollection* AliFemtoCutMonitorHandler::PassMonitorColl() { return fPassColl;}
+inline AliFemtoCutMonitorCollection* AliFemtoCutMonitorHandler::FailMonitorColl() { return fFailColl;}
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCutMonitorParticlePID.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCutMonitorParticlePID.cxx
new file mode 100644 (file)
index 0000000..f225bcd
--- /dev/null
@@ -0,0 +1,128 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoCutMonitorParticlePID - the cut monitor for particles to study     //
+// various aspects of the PID determination                                   //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+#include "AliFemtoCutMonitorParticlePID.h"
+#include "AliFemtoModelHiddenInfo.h"
+#include <TH1D.h>
+#include <TH2D.h>
+#include <TList.h>
+#include <TMath.h>
+
+AliFemtoCutMonitorParticlePID::AliFemtoCutMonitorParticlePID():
+  fTPCdEdx(0),
+  fTOFParticle(0),
+  fTOFTime(0x0),
+  ftofHist(0)
+{
+  // Default constructor
+  fTPCdEdx =  new TH2D("TPCdEdx", "TPC dEdx vs. momentum", 200, 0.1, 4.0, 250, 0.0, 500.0);
+  fTOFTime = new TH2D("TOFTime", "TOF Time vs. momentum", 190, 0.1, 2.0, 400, -4000.0, 4000.0);
+  ftofHist=new TH2D("TOFHist","TOF momentum vs v",100,0.,1.1,100,0.,3.0);
+}
+
+AliFemtoCutMonitorParticlePID::AliFemtoCutMonitorParticlePID(const char *aName, Int_t aTOFParticle):
+  AliFemtoCutMonitor(),
+  fTPCdEdx(0),
+  fTOFParticle(aTOFParticle),
+  fTOFTime(0x0),
+  ftofHist(0)
+{
+  // Normal constructor
+  char name[200];
+  snprintf(name, 200, "TPCdEdx%s", aName);
+  fTPCdEdx = new TH2D(name, "TPC dEdx vs. momentum", 200, 0.1, 4.0, 250, 0.0, 500.0);
+
+  snprintf(name, 200, "TOFTime%s", aName);
+  fTOFTime = new TH2D(name, "TOF Time vs. momentum", 190, 0.1, 2.0, 400, -4000.0, 4000.0);
+
+  snprintf(name, 200, "TOFHist%s", aName);
+  ftofHist=new TH2D(name,"TOF momentum vs v",100,0.,1.1,100,0.,3.0);
+}
+
+AliFemtoCutMonitorParticlePID::AliFemtoCutMonitorParticlePID(const AliFemtoCutMonitorParticlePID &aCut):
+  AliFemtoCutMonitor(),
+  fTPCdEdx(0),
+  fTOFParticle(0),
+  fTOFTime(0x0),
+  ftofHist(0)
+{
+  // copy constructor
+  if (fTPCdEdx) delete fTPCdEdx;
+  fTPCdEdx = new TH2D(*aCut.fTPCdEdx);
+
+  if (fTOFTime) delete fTOFTime;
+  fTOFTime = new TH2D(*aCut.fTOFTime);
+
+  if (ftofHist) delete ftofHist; 
+  ftofHist= new TH2D(*aCut.ftofHist);
+}
+
+AliFemtoCutMonitorParticlePID::~AliFemtoCutMonitorParticlePID()
+{
+  // Destructor
+  delete fTPCdEdx;
+  delete fTOFTime;
+  delete ftofHist;
+}
+
+AliFemtoCutMonitorParticlePID& AliFemtoCutMonitorParticlePID::operator=(const AliFemtoCutMonitorParticlePID& aCut)
+{
+  // assignment operator
+  if (this == &aCut) 
+    return *this;
+
+  if (fTPCdEdx) delete fTPCdEdx;
+  fTPCdEdx = new TH2D(*aCut.fTPCdEdx);
+
+  if (fTOFTime) delete fTOFTime;
+  fTOFTime = new TH2D(*aCut.fTOFTime);
+  
+  if(ftofHist) delete ftofHist;
+  ftofHist = new TH2D(*aCut.ftofHist);
+  return *this;
+}
+
+AliFemtoString AliFemtoCutMonitorParticlePID::Report(){ 
+  // Prepare report from the execution
+  string stemp = "*** AliFemtoCutMonitorParticlePID report"; 
+  AliFemtoString returnThis = stemp;
+  return returnThis; 
+}
+
+void AliFemtoCutMonitorParticlePID::Fill(const AliFemtoTrack* aTrack)
+{
+  // Fill in the monitor histograms with the values from the current track
+  float tMom = aTrack->P().Mag();
+  float tdEdx = aTrack->TPCsignal();
+  float tTOF = 0.0;
+  //  short tchg = aTrack->Charge();
+  if (fTOFParticle == 0) tTOF = aTrack->TOFpionTime();
+  if (fTOFParticle == 1) tTOF = aTrack->TOFkaonTime();
+  if (fTOFParticle == 2) tTOF = aTrack->TOFprotonTime();
+
+  fTPCdEdx->Fill(tMom, tdEdx);
+  fTOFTime->Fill(tMom, tTOF);
+
+  float vp= aTrack->VTOF();
+  ftofHist->Fill(vp,tMom);
+}
+
+void AliFemtoCutMonitorParticlePID::Write()
+{
+  // Write out the relevant histograms
+  fTPCdEdx->Write();
+  fTOFTime->Write();
+  ftofHist->Write();
+}
+
+TList *AliFemtoCutMonitorParticlePID::GetOutputList()
+{
+  TList *tOutputList = new TList();
+  tOutputList->Add(fTPCdEdx);
+  tOutputList->Add(fTOFTime);
+  tOutputList->Add(ftofHist);
+  return tOutputList;
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCutMonitorParticlePID.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCutMonitorParticlePID.h
new file mode 100644 (file)
index 0000000..920de21
--- /dev/null
@@ -0,0 +1,56 @@
+////////////////////////////////////////////////////////////////////////////////
+///                                                                          ///
+/// AliFemtoCutMonitorParticlePID - the cut monitor for particles to study   ///
+/// various aspects of the PID determination                                 ///
+///                                                                          ///
+////////////////////////////////////////////////////////////////////////////////
+#ifndef AliFemtoCutMonitorParticlePID_hh
+#define AliFemtoCutMonitorParticlePID_hh
+
+class AliFemtoEvent;
+class AliFemtoTrack;
+class AliFemtoV0;
+class AliFemtoKink;
+class AliFemtoPair; // Gael 12/04/02
+class TH1D;
+class TH2D;
+class TList;
+#include "AliFemtoString.h"
+#include "AliFemtoParticleCollection.h"
+#include "AliFemtoCutMonitor.h"
+
+class AliFemtoCutMonitorParticlePID : public AliFemtoCutMonitor{
+  
+public:
+  AliFemtoCutMonitorParticlePID();
+  AliFemtoCutMonitorParticlePID(const char *aName, Int_t aTOFParticle);
+  AliFemtoCutMonitorParticlePID(const AliFemtoCutMonitorParticlePID &aCut);
+  virtual ~AliFemtoCutMonitorParticlePID();
+
+  AliFemtoCutMonitorParticlePID& operator=(const AliFemtoCutMonitorParticlePID& aCut);
+
+  virtual AliFemtoString Report();
+  virtual void Fill(const AliFemtoEvent* aEvent) {AliFemtoCutMonitor::Fill(aEvent);}
+  virtual void Fill(const AliFemtoTrack* aTrack);
+  virtual void Fill(const AliFemtoV0* aV0) {AliFemtoCutMonitor::Fill(aV0);}
+  virtual void Fill(const AliFemtoKink* aKink) {AliFemtoCutMonitor::Fill(aKink);}
+  virtual void Fill(const AliFemtoPair* aPair) {AliFemtoCutMonitor::Fill(aPair);}
+  virtual void Fill(const AliFemtoParticleCollection* aCollection) {AliFemtoCutMonitor::Fill(aCollection);}
+  virtual void Fill(const AliFemtoEvent* aEvent,const AliFemtoParticleCollection* aCollection)
+  {AliFemtoCutMonitor::Fill(aEvent, aCollection);}
+
+  void SetTOFParticle(Int_t ipart);
+
+  void Write();
+
+  virtual TList *GetOutputList();
+
+private:
+  TH2D *fTPCdEdx;     // TPC dEdx information
+  Int_t fTOFParticle; // Select TOF time hypothesis, 0-pion, 1-kaon, 2-proton
+  TH2D *fTOFTime;     // TOF time
+  TH2D* ftofHist;     // TOF hist with vp
+
+};
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCutMonitorParticleVertPos.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCutMonitorParticleVertPos.cxx
new file mode 100644 (file)
index 0000000..f752c15
--- /dev/null
@@ -0,0 +1,178 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoCutMonitorParticleVertPos - the cut monitor for particles to study    //
+// the difference between reconstructed and true momentum                     //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+#include "AliFemtoCutMonitorParticleVertPos.h"
+#include "AliFemtoModelHiddenInfo.h"
+#include "AliFemtoModelGlobalHiddenInfo.h"
+#include <TH1D.h>
+#include <TH2D.h>
+#include <TList.h>
+#include <TMath.h>
+
+AliFemtoCutMonitorParticleVertPos::AliFemtoCutMonitorParticleVertPos():
+  fVertPos(0),
+  fEtaZ(0),
+  fRadPos(0),
+  fEmPointX(0),
+  fEmPointY(0),
+  fEmPointZ(0),
+  fEmPointT(0)
+{
+  // Default constructor
+  fVertPos = new TH2D("VertPos", "Vertex position", 200, -20.0, 20.0, 200, -20.0, 20.0);
+  fEtaZ    = new TH2D("EtaZPos", "Z vs. Eta", 200, -100.0, 100.0, 100, -1.5, 1.5);
+  fRadPos  = new TH1D("RadPos",  "Radial position", 200, 0.0, 1.0);
+  fEmPointX = new TH1D("EmPointX","Emission point x", 400, -200.0, 200.0);
+  fEmPointY = new TH1D("EmPointY","Emission point y", 400, -200.0, 200.0);
+  fEmPointZ = new TH1D("EmPointZ","Emission point z", 400, -200.0, 200.0);
+  fEmPointT = new TH1D("EmPointT","Emission point t", 400, -200.0, 200.0);
+
+}
+
+AliFemtoCutMonitorParticleVertPos::AliFemtoCutMonitorParticleVertPos(const char *aName):
+  AliFemtoCutMonitor(),
+  fVertPos(0),
+  fEtaZ(0),
+  fRadPos(0),
+  fEmPointX(0),
+  fEmPointY(0),
+  fEmPointZ(0),
+  fEmPointT(0)
+{
+  // Normal constructor
+  char name[200];
+  snprintf(name, 200, "VertPos%s", aName);
+  fVertPos = new TH2D(name, "Rapdity vs Pt", 200, -20.0, 20.0, 200, -20.0, 20.0);
+  snprintf(name, 200, "EtaZPos%s", aName);
+  fEtaZ    = new TH2D(name, "Z vs. Eta", 200, -100.0, 100.0, 100, -1.5, 1.5);
+  snprintf(name, 200, "RadPos%s", aName);
+  fRadPos  = new TH1D(name,  "Radial position", 200, 0.0, 1.0);
+  snprintf(name, 200, "EmPosX%s", aName);
+  fEmPointX = new TH1D(name,"Emission point x", 400, -200.0, 200.0);
+  snprintf(name, 200, "EmPosY%s", aName);
+  fEmPointY = new TH1D(name,"Emission point y", 400, -200.0, 200.0);
+  snprintf(name, 200, "EmPosZ%s", aName);
+  fEmPointZ = new TH1D(name,"Emission point z", 400, -200.0, 200.0);
+  snprintf(name, 200, "EmPosT%s", aName);
+  fEmPointT = new TH1D(name,"Emission point t", 400, -200.0, 200.0);
+}
+
+AliFemtoCutMonitorParticleVertPos::AliFemtoCutMonitorParticleVertPos(const AliFemtoCutMonitorParticleVertPos &aCut):
+  AliFemtoCutMonitor(),
+  fVertPos(0),
+  fEtaZ(0),
+  fRadPos(0),
+  fEmPointX(0),
+  fEmPointY(0),
+  fEmPointZ(0),
+  fEmPointT(0)
+{
+  // copy constructor
+  if (fVertPos) delete fVertPos;
+  fVertPos = new TH2D(*aCut.fVertPos);
+  if (fEtaZ) delete fEtaZ;
+  fEtaZ = new TH2D(*aCut.fEtaZ);
+  if (fRadPos) delete fRadPos;
+  fRadPos = new TH1D(*aCut.fRadPos);
+  if (fEmPointX) delete fEmPointX;
+  fEmPointX = new TH1D(*aCut.fEmPointX);
+  if (fEmPointY) delete fEmPointY;
+  fEmPointY = new TH1D(*aCut.fEmPointY);
+  if (fEmPointZ) delete fEmPointZ;
+  fEmPointZ = new TH1D(*aCut.fEmPointZ);
+  if (fEmPointT) delete fEmPointT;
+  fEmPointT = new TH1D(*aCut.fEmPointT);
+}
+
+AliFemtoCutMonitorParticleVertPos::~AliFemtoCutMonitorParticleVertPos()
+{
+  // Destructor
+  delete fVertPos;
+  delete fEtaZ;
+  delete fRadPos;
+  delete fEmPointX;
+  delete fEmPointY;
+  delete fEmPointZ;
+  delete fEmPointT;
+}
+
+AliFemtoCutMonitorParticleVertPos& AliFemtoCutMonitorParticleVertPos::operator=(const AliFemtoCutMonitorParticleVertPos& aCut)
+{
+  // assignment operator
+  if (this == &aCut) 
+    return *this;
+
+  if (fVertPos) delete fVertPos;
+  fVertPos = new TH2D(*aCut.fVertPos);
+  if (fEtaZ) delete fEtaZ;
+  fEtaZ = new TH2D(*aCut.fEtaZ);
+  if (fRadPos) delete fRadPos;
+  fRadPos = new TH1D(*aCut.fRadPos);
+  if (fEmPointX) delete fEmPointX;
+  fEmPointX = new TH1D(*aCut.fEmPointX);
+  if (fEmPointY) delete fEmPointY;
+  fEmPointY = new TH1D(*aCut.fEmPointY);
+  if (fEmPointZ) delete fEmPointZ;
+  fEmPointZ = new TH1D(*aCut.fEmPointZ);
+  if (fEmPointT) delete fEmPointT;
+  fEmPointT = new TH1D(*aCut.fEmPointT);
+  
+  return *this;
+}
+
+AliFemtoString AliFemtoCutMonitorParticleVertPos::Report(){ 
+  // Prepare report from the execution
+  string stemp = "*** AliFemtoCutMonitorParticleVertPos report"; 
+  AliFemtoString returnThis = stemp;
+  return returnThis; 
+}
+
+void AliFemtoCutMonitorParticleVertPos::Fill(const AliFemtoTrack* aTrack)
+{
+  // Fill in the monitor histograms with the values from the current track
+  AliFemtoModelGlobalHiddenInfo *hinfo = dynamic_cast<AliFemtoModelGlobalHiddenInfo *>(aTrack->GetHiddenInfo());
+  if (hinfo) {
+    float tEta = -TMath::Log(TMath::Tan(hinfo->GetTrueMomentum()->Theta()/2.0));
+
+    fVertPos->Fill(hinfo->GetGlobalEmissionPoint()->x(), hinfo->GetGlobalEmissionPoint()->y());
+    fEtaZ->Fill(hinfo->GetGlobalEmissionPoint()->z(), tEta);
+    fRadPos->Fill(hinfo->GetGlobalEmissionPoint()->Perp());
+  }
+  
+  AliFemtoModelHiddenInfo *hminfo = dynamic_cast<AliFemtoModelHiddenInfo *>(aTrack->GetHiddenInfo());
+  if (hminfo) {
+    fEmPointX->Fill(hminfo->GetEmissionPoint()->x());
+    fEmPointY->Fill(hminfo->GetEmissionPoint()->y());
+    fEmPointZ->Fill(hminfo->GetEmissionPoint()->z());
+    fEmPointT->Fill(hminfo->GetEmissionPoint()->t());
+  }
+}
+
+void AliFemtoCutMonitorParticleVertPos::Write()
+{
+  // Write out the relevant histograms
+  fVertPos->Write();
+  fEtaZ->Write();
+  fRadPos->Write();
+  fEmPointX->Write();
+  fEmPointY->Write();
+  fEmPointZ->Write();
+  fEmPointT->Write();
+}
+
+TList *AliFemtoCutMonitorParticleVertPos::GetOutputList()
+{
+  TList *tOutputList = new TList();
+  tOutputList->Add(fVertPos);
+  tOutputList->Add(fEtaZ);
+  tOutputList->Add(fRadPos);
+  tOutputList->Add(fEmPointX);
+  tOutputList->Add(fEmPointY);
+  tOutputList->Add(fEmPointZ);
+  tOutputList->Add(fEmPointT);
+
+  return tOutputList;
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCutMonitorParticleVertPos.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCutMonitorParticleVertPos.h
new file mode 100644 (file)
index 0000000..806a427
--- /dev/null
@@ -0,0 +1,58 @@
+////////////////////////////////////////////////////////////////////////////////
+///                                                                          ///
+/// AliFemtoCutMonitorParticleVertPos - the cut monitor for particles to study  ///
+/// the difference between reconstructed and true momentum    ///
+///                                                                          ///
+////////////////////////////////////////////////////////////////////////////////
+#ifndef AliFemtoCutMonitorParticleVertPos_hh
+#define AliFemtoCutMonitorParticleVertPos_hh
+
+class AliFemtoEvent;
+class AliFemtoTrack;
+class AliFemtoV0;
+class AliFemtoKink;
+class AliFemtoPair; // Gael 12/04/02
+class TH1D;
+class TH2D;
+class TList;
+#include "AliFemtoString.h"
+#include "AliFemtoParticleCollection.h"
+#include "AliFemtoCutMonitor.h"
+
+class AliFemtoCutMonitorParticleVertPos : public AliFemtoCutMonitor{
+  
+public:
+  AliFemtoCutMonitorParticleVertPos();
+  AliFemtoCutMonitorParticleVertPos(const char *aName);
+  AliFemtoCutMonitorParticleVertPos(const AliFemtoCutMonitorParticleVertPos &aCut);
+  virtual ~AliFemtoCutMonitorParticleVertPos();
+
+  AliFemtoCutMonitorParticleVertPos& operator=(const AliFemtoCutMonitorParticleVertPos& aCut);
+
+  virtual AliFemtoString Report();
+  virtual void Fill(const AliFemtoEvent* aEvent) {AliFemtoCutMonitor::Fill(aEvent);}
+  virtual void Fill(const AliFemtoTrack* aTrack);
+  virtual void Fill(const AliFemtoV0* aV0) {AliFemtoCutMonitor::Fill(aV0);}
+  virtual void Fill(const AliFemtoKink* aKink) {AliFemtoCutMonitor::Fill(aKink);}
+  virtual void Fill(const AliFemtoPair* aPair) {AliFemtoCutMonitor::Fill(aPair);}
+  virtual void Fill(const AliFemtoParticleCollection* aCollection) {AliFemtoCutMonitor::Fill(aCollection);}
+  virtual void Fill(const AliFemtoEvent* aEvent,const AliFemtoParticleCollection* aCollection)
+  {AliFemtoCutMonitor::Fill(aEvent, aCollection);}
+
+
+  void Write();
+
+  virtual TList *GetOutputList();
+
+private:
+  TH2D *fVertPos;    // Vertex position x vs. y monitor
+  TH2D *fEtaZ;       // Vertex z position vs. eta monitor
+  TH1D *fRadPos;     // Radial position close to vertex
+  TH1D *fEmPointX;   // Emission point - x
+  TH1D *fEmPointY;   // Emission point - y
+  TH1D *fEmPointZ;   // Emission point - z
+  TH1D *fEmPointT;   // Emission point - t
+  
+};
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCutMonitorParticleYPt.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCutMonitorParticleYPt.cxx
new file mode 100644 (file)
index 0000000..a844d51
--- /dev/null
@@ -0,0 +1,206 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoCutMonitorParticleYPt - the cut monitor for particles to study    //
+// the difference between reconstructed and true momentum                     //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+#include "AliFemtoCutMonitorParticleYPt.h"
+#include "AliFemtoModelHiddenInfo.h"
+#include <TH1D.h>
+#include <TH2D.h>
+#include <TList.h>
+#include <TMath.h>
+
+AliFemtoCutMonitorParticleYPt::AliFemtoCutMonitorParticleYPt():
+  fYPt(0),
+  fYPhi(0),
+  fPtPhi(0),
+  fEtaPhi(0),
+  fEtaPt(0),
+  fEtaPhiW(0),
+  fEtaPtW(0),
+  fDCARPt(0),
+  fDCAZPt(0),
+  fMass(0.13957)
+{
+  // Default constructor
+  fYPt = new TH2D("YPt", "Rapidity vs Pt",              140, -1.4, 1.4, 100, 0.0, 2.0);
+  fYPhi = new TH2D("YPhi", "Rapidity vs Phi",           140, -1.4, 1.4, 100, -TMath::Pi(), TMath::Pi());
+  fPtPhi = new TH2D("PtPhi", "Pt vs Phi",               100,  0.0, 2.0, 100, -TMath::Pi(), TMath::Pi());
+  fEtaPhi = new TH2D("EtaPhi", "Pseudorapidity vs Phi", 140, -1.4, 1.4, 100, -TMath::Pi(), TMath::Pi());
+  fEtaPt = new TH2D("EtaPt", "Pseudorapidity vs Pt",    140, -1.4, 1.4, 100, 0.0, 2.0);
+  // fEtaPhiW = new TH2D("EtaPhiW", "Pseudorapidity vs Phi chi2/N weighted", 140, -1.4, 1.4, 100, -TMath::Pi(), TMath::Pi());
+  // fEtaPtW = new TH2D("EtaPtW", "Pseudorapidity vs Pt chi2/N weighted",    140, -1.4, 1.4, 100, 0.0, 2.0)
+    ;
+  fDCARPt = new TH2D("DCARPt", "DCA in XY vs. Pt", 400, -2.0, 2.0, 100,0.0,2.0);
+  fDCAZPt = new TH2D("DCAZPt", "DCA in Z vs. Pt", 400, -2.0, 2.0, 100,0.0,2.0);
+}
+
+AliFemtoCutMonitorParticleYPt::AliFemtoCutMonitorParticleYPt(const char *aName, float aMass):
+  AliFemtoCutMonitor(),
+  fYPt(0),
+  fYPhi(0),
+  fPtPhi(0),
+  fEtaPhi(0),
+  fEtaPt(0),
+  fEtaPhiW(0),
+  fEtaPtW(0),
+  fDCARPt(0),
+  fDCAZPt(0),
+  fMass(aMass)
+{
+  // Normal constructor
+  char name[200];
+  snprintf(name, 200, "YPt%s", aName);
+  fYPt = new TH2D(name, "Rapdity vs Pt", 140, -1.4, 1.4, 100, 0.0, 2.0);
+  snprintf(name, 200, "YPhi%s", aName);
+  fYPhi = new TH2D(name, "Rapidity vs Phi",           140, -1.4, 1.4, 100, -TMath::Pi(), TMath::Pi());
+  snprintf(name, 200, "PtPhi%s", aName);
+  fPtPhi = new TH2D(name, "Pt vs Phi",               100,  0.0, 2.0, 100, -TMath::Pi(), TMath::Pi());
+  snprintf(name, 200, "EtaPhi%s", aName);
+  fEtaPhi = new TH2D(name, "Pseudorapidity vs Phi", 140, -1.4, 1.4, 100, -TMath::Pi(), TMath::Pi());
+  snprintf(name, 200, "EtaPt%s", aName);
+  fEtaPt = new TH2D(name, "Pseudorapidity vs Pt",    140, -1.4, 1.4, 100, 0.0, 2.0);
+  // snprintf(name, 200, "EtaPhiW%s", aName);
+  // fEtaPhiW = new TH2D(name, "Pseudorapidity vs Phi chi2/N weighted", 140, -1.4, 1.4, 100, -TMath::Pi(), TMath::Pi());
+  // snprintf(name, 200, "EtaPtW%s", aName);
+  // fEtaPtW = new TH2D(name, "Pseudorapidity vs Pt chi2/N weighted",    140, -1.4, 1.4, 100, 0.0, 2.0);
+  snprintf(name, 200, "DCARPt%s", aName);
+  fDCARPt = new TH2D(name, "DCA in XY vs. Pt", 400, -2.0, 2.0, 100,0.0,2.0);
+  snprintf(name, 200, "DCAZPt%s", aName);
+  fDCAZPt = new TH2D(name, "DCA in Z vs. Pt", 400, -2.0, 2.0, 100,0.0,2.0);
+}
+
+AliFemtoCutMonitorParticleYPt::AliFemtoCutMonitorParticleYPt(const AliFemtoCutMonitorParticleYPt &aCut):
+  AliFemtoCutMonitor(),
+  fYPt(0),
+  fYPhi(0),
+  fPtPhi(0),
+  fEtaPhi(0),
+  fEtaPt(0),
+  fEtaPhiW(0),
+  fEtaPtW(0),
+  fDCARPt(0),
+  fDCAZPt(0),
+  fMass(0.13957)
+{
+  // copy constructor
+  fYPt = new TH2D(*aCut.fYPt);
+  fYPhi = new TH2D(*aCut.fYPhi);
+  fPtPhi = new TH2D(*aCut.fPtPhi);
+  fEtaPhi = new TH2D(*aCut.fEtaPhi);
+  fEtaPt = new TH2D(*aCut.fEtaPt);
+  // fEtaPhiW = new TH2D(*aCut.fEtaPhiW);
+  // fEtaPtW = new TH2D(*aCut.fEtaPtW);
+  fDCARPt = new TH2D(*aCut.fDCARPt);
+  fDCAZPt = new TH2D(*aCut.fDCAZPt);
+  fMass = aCut.fMass; 
+}
+
+AliFemtoCutMonitorParticleYPt::~AliFemtoCutMonitorParticleYPt()
+{
+  // Destructor
+  delete fYPt;
+  delete fYPhi;
+  delete fPtPhi;
+  delete fEtaPhi;
+  delete fEtaPt;
+  // delete fEtaPhiW;
+  // delete fEtaPtW;
+  delete fDCARPt;
+  delete fDCAZPt;
+}
+
+AliFemtoCutMonitorParticleYPt& AliFemtoCutMonitorParticleYPt::operator=(const AliFemtoCutMonitorParticleYPt& aCut)
+{
+  // assignment operator
+  if (this == &aCut) 
+    return *this;
+
+  if (fYPt) delete fYPt;
+  fYPt = new TH2D(*aCut.fYPt);
+  if (fYPhi) delete fYPhi;
+  fYPhi = new TH2D(*aCut.fYPhi);
+  if (fPtPhi) delete fPtPhi;
+  fPtPhi = new TH2D(*aCut.fPtPhi);
+  if (fEtaPhi) delete fEtaPhi;
+  fEtaPhi = new TH2D(*aCut.fEtaPhi);
+  if (fEtaPt) delete fEtaPt;
+  fEtaPt = new TH2D(*aCut.fEtaPt);
+  // if (fEtaPhiW) delete fEtaPhiW;
+  // fEtaPhiW = new TH2D(*aCut.fEtaPhiW);
+  // if (fEtaPtW) delete fEtaPtW;
+  // fEtaPtW = new TH2D(*aCut.fEtaPtW);
+  if (fDCARPt) delete fDCARPt;
+  fDCARPt = new TH2D(*aCut.fDCARPt);
+  if (fDCAZPt) delete fDCAZPt;
+  fDCAZPt = new TH2D(*aCut.fDCAZPt);
+  
+  return *this;
+}
+
+AliFemtoString AliFemtoCutMonitorParticleYPt::Report(){ 
+  // Prepare report from the execution
+  string stemp = "*** AliFemtoCutMonitorParticleYPt report"; 
+  AliFemtoString returnThis = stemp;
+  return returnThis; 
+}
+
+void AliFemtoCutMonitorParticleYPt::Fill(const AliFemtoTrack* aTrack)
+{
+  // Fill in the monitor histograms with the values from the current track
+  float tEnergy = ::sqrt(aTrack->P().Mag2()+fMass*fMass);
+  float tRapidity = 0.5*::log((tEnergy+aTrack->P().z())/(tEnergy-aTrack->P().z()));
+  float tPt = ::sqrt((aTrack->P().x())*(aTrack->P().x())+(aTrack->P().y())*(aTrack->P().y()));
+  float tEta = -TMath::Log(TMath::Tan(aTrack->P().Theta()/2.0));
+  float tPhi = aTrack->P().Phi();
+  // float chi2w;
+  float dcar = aTrack->ImpactD();
+  float dcaz = aTrack->ImpactZ();
+  // if (aTrack->TPCncls() > 0)
+  //   chi2w = aTrack->TPCchi2()/aTrack->TPCncls();
+  // else
+  //   chi2w = 6.0;
+
+  //  cout << " CMYPt: " << fYPt << " " << fYPt->GetEntries() << " " << tRapidity << " " << tPt << endl;
+
+  fYPt->Fill(tRapidity, tPt);
+  fYPhi->Fill(tRapidity, tPhi);
+  fPtPhi->Fill(tPt, tPhi);
+  fEtaPhi->Fill(tEta, tPhi);
+  fEtaPt->Fill(tEta, tPt);
+  // fEtaPhiW->Fill(tEta, tPhi, chi2w);
+  // fEtaPtW->Fill(tEta, tPt, chi2w);
+  fDCARPt->Fill(dcar, tPt);
+  fDCAZPt->Fill(dcaz, tPt);
+}
+
+void AliFemtoCutMonitorParticleYPt::Write()
+{
+  // Write out the relevant histograms
+  fYPt->Write();
+  fYPhi->Write();
+  fPtPhi->Write();
+  fEtaPhi->Write();
+  fEtaPt->Write();
+  // fEtaPhiW->Write();
+  // fEtaPtW->Write();
+  fDCARPt->Write();
+  fDCAZPt->Write();
+}
+
+TList *AliFemtoCutMonitorParticleYPt::GetOutputList()
+{
+  TList *tOutputList = new TList();
+  tOutputList->Add(fYPt);
+  tOutputList->Add(fYPhi);
+  tOutputList->Add(fPtPhi);
+  tOutputList->Add(fEtaPhi);
+  tOutputList->Add(fEtaPt);
+  // tOutputList->Add(fEtaPhiW);
+  // tOutputList->Add(fEtaPtW);
+  tOutputList->Add(fDCARPt);
+  tOutputList->Add(fDCAZPt);
+
+  return tOutputList;
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCutMonitorParticleYPt.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoCutMonitorParticleYPt.h
new file mode 100644 (file)
index 0000000..c7501d5
--- /dev/null
@@ -0,0 +1,60 @@
+////////////////////////////////////////////////////////////////////////////////
+///                                                                          ///
+/// AliFemtoCutMonitorParticleYPt - the cut monitor for particles to study  ///
+/// the difference between reconstructed and true momentum    ///
+///                                                                          ///
+////////////////////////////////////////////////////////////////////////////////
+#ifndef AliFemtoCutMonitorParticleYPt_hh
+#define AliFemtoCutMonitorParticleYPt_hh
+
+class AliFemtoEvent;
+class AliFemtoTrack;
+class AliFemtoV0;
+class AliFemtoKink;
+class AliFemtoPair; // Gael 12/04/02
+class TH1D;
+class TH2D;
+class TList;
+#include "AliFemtoString.h"
+#include "AliFemtoParticleCollection.h"
+#include "AliFemtoCutMonitor.h"
+
+class AliFemtoCutMonitorParticleYPt : public AliFemtoCutMonitor{
+  
+public:
+  AliFemtoCutMonitorParticleYPt();
+  AliFemtoCutMonitorParticleYPt(const char *aName, float aMass);
+  AliFemtoCutMonitorParticleYPt(const AliFemtoCutMonitorParticleYPt &aCut);
+  virtual ~AliFemtoCutMonitorParticleYPt();
+
+  AliFemtoCutMonitorParticleYPt& operator=(const AliFemtoCutMonitorParticleYPt& aCut);
+
+  virtual AliFemtoString Report();
+  virtual void Fill(const AliFemtoEvent* aEvent) {AliFemtoCutMonitor::Fill(aEvent);}
+  virtual void Fill(const AliFemtoTrack* aTrack);
+  virtual void Fill(const AliFemtoV0* aV0) {AliFemtoCutMonitor::Fill(aV0);}
+  virtual void Fill(const AliFemtoKink* aKink) {AliFemtoCutMonitor::Fill(aKink);}
+  virtual void Fill(const AliFemtoPair* aPair) {AliFemtoCutMonitor::Fill(aPair);}
+  virtual void Fill(const AliFemtoParticleCollection* aCollection) {AliFemtoCutMonitor::Fill(aCollection);}
+  virtual void Fill(const AliFemtoEvent* aEvent,const AliFemtoParticleCollection* aCollection)
+  {AliFemtoCutMonitor::Fill(aEvent, aCollection);}
+
+
+  void Write();
+
+  virtual TList *GetOutputList();
+
+private:
+  TH2D *fYPt;    // Rapidity vs. Pt monitor
+  TH2D *fYPhi;   // Rapidity cs. Phi monitor
+  TH2D *fPtPhi;  // Pt vs. Phi monitor
+  TH2D *fEtaPhi; // Pseudorapidity vs. Phi monitor
+  TH2D *fEtaPt;  // Pseudorapidity vs. Pt monitor
+  TH2D *fEtaPhiW;// Pseudorapidity vs. Phi monitor chi2 weighted
+  TH2D *fEtaPtW; // Pseudorapidity vs. Pt monitor chi2 weighted
+  TH2D *fDCARPt; // Pt vs. DCA XY
+  TH2D *fDCAZPt; // Pt vs. DCA Z 
+  float fMass;   // Mass hypothesis
+};
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoDummyPairCut.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoDummyPairCut.cxx
new file mode 100644 (file)
index 0000000..1d60033
--- /dev/null
@@ -0,0 +1,100 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFemtoDummyPairCut: a summy pair cut. Accepts all pairs             //
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+/***************************************************************************
+ *
+ * $Id$
+ *
+ * Author: Mike Lisa, Ohio State, lisa@mps.ohio-state.edu
+ ***************************************************************************
+ *
+ * Description: part of STAR HBT Framework: AliFemtoMaker package
+ *   a do-nothing pair cut that simply says "true" to every pair           
+ *
+ ***************************************************************************
+ *
+ * $Log$
+ * Revision 1.2.2.1  2007/10/12 14:28:37  akisiel
+ * New wave of cleanup and rule conformance
+ *
+ * Revision 1.2  2007/05/22 09:01:42  akisiel
+ * Add the possibiloity to save cut settings in the ROOT file
+ *
+ * Revision 1.1  2007/05/16 10:22:11  akisiel
+ * Making the directory structure of AliFemto flat. All files go into one common directory
+ *
+ * Revision 1.2  2007/05/03 09:41:06  akisiel
+ * Fixing Effective C++ warnings
+ *
+ * Revision 1.1.1.1  2007/04/25 15:38:41  panos
+ * Importing the HBT code dir
+ *
+ * Revision 1.1.1.1  2007-03-07 10:14:49  mchojnacki
+ * First version on CVS
+ *
+ * Revision 1.3  2000/01/25 17:35:02  laue
+ * I. In order to run the stand alone version of the AliFemtoMaker the following
+ * changes have been done:
+ * a) all ClassDefs and ClassImps have been put into #ifdef __ROOT__ statements
+ * b) unnecessary includes of StMaker.h have been removed
+ * c) the subdirectory AliFemtoMaker/doc/Make has been created including everything
+ * needed for the stand alone version
+ *
+ * II. To reduce the amount of compiler warning
+ * a) some variables have been type casted
+ * b) some destructors have been declared as virtual
+ *
+ * Revision 1.2  1999/07/06 22:33:21  lisa
+ * Adjusted all to work in pro and new - dev itself is broken
+ *
+ * Revision 1.1.1.1  1999/06/29 16:02:56  lisa
+ * Installation of AliFemtoMaker
+ *
+ **************************************************************************/
+
+#include "AliFemtoDummyPairCut.h"
+#include <string>
+#include <cstdio>
+
+#ifdef __ROOT__
+ClassImp(AliFemtoDummyPairCut)
+#endif
+
+//__________________
+AliFemtoDummyPairCut::AliFemtoDummyPairCut() :
+  fNPairsPassed(0),
+  fNPairsFailed(0)
+{
+  /* no-op */
+}
+//__________________
+AliFemtoDummyPairCut::~AliFemtoDummyPairCut(){
+  /* no-op */
+}
+//__________________
+bool AliFemtoDummyPairCut::Pass(const AliFemtoPair* /* pair */){
+  // Pass all pairs
+  bool temp = true;
+  temp ? fNPairsPassed++ : fNPairsFailed++;
+  return true;
+}
+//__________________
+AliFemtoString AliFemtoDummyPairCut::Report(){
+  // prepare a report from the execution
+  string stemp = "AliFemtoDummy Pair Cut - total dummy-- always returns true\n";
+  char ctemp[100];
+  snprintf(ctemp , 100, "Number of pairs which passed:\t%ld  Number which failed:\t%ld\n",fNPairsPassed,fNPairsFailed);
+  stemp += ctemp;
+  AliFemtoString returnThis = stemp;
+  return returnThis;
+}
+//__________________
+TList *AliFemtoDummyPairCut::ListSettings()
+{
+  // return a list of settings in a writable form
+  TList *tListSetttings = new TList();
+
+  return tListSetttings;
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoDummyPairCut.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoDummyPairCut.h
new file mode 100644 (file)
index 0000000..49a14ef
--- /dev/null
@@ -0,0 +1,113 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFemtoDummyPairCut: a summy pair cut. Accepts all pairs             //
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+/***************************************************************************
+ *
+ * $Id$
+ *
+ * Author: Mike Lisa, Ohio State, lisa@mps.ohio-state.edu
+ ***************************************************************************
+ *
+ * Description: part of STAR HBT Framework: AliFemtoMaker package
+ *   a do-nothing pair cut that simply says "true" to every pair           
+ *
+ ***************************************************************************
+ *
+ * $Log$
+ * Revision 1.2.2.1  2007/10/12 14:28:37  akisiel
+ * New wave of cleanup and rule conformance
+ *
+ * Revision 1.2  2007/05/22 09:01:42  akisiel
+ * Add the possibiloity to save cut settings in the ROOT file
+ *
+ * Revision 1.1  2007/05/16 10:22:11  akisiel
+ * Making the directory structure of AliFemto flat. All files go into one common directory
+ *
+ * Revision 1.2  2007/05/03 09:41:06  akisiel
+ * Fixing Effective C++ warnings
+ *
+ * Revision 1.1.1.1  2007/04/25 15:38:41  panos
+ * Importing the HBT code dir
+ *
+ * Revision 1.1.1.1  2007/03/07 10:14:49  mchojnacki
+ * First version on CVS
+ *
+ * Revision 1.5  2000/03/23 22:57:28  laue
+ * Clone() function implemented
+ *
+ * Revision 1.4  2000/01/25 17:35:03  laue
+ * I. In order to run the stand alone version of the AliFemtoMaker the following
+ * changes have been done:
+ * a) all ClassDefs and ClassImps have been put into #ifdef __ROOT__ statements
+ * b) unnecessary includes of StMaker.h have been removed
+ * c) the subdirectory AliFemtoMaker/doc/Make has been created including everything
+ * needed for the stand alone version
+ *
+ * II. To reduce the amount of compiler warning
+ * a) some variables have been type casted
+ * b) some destructors have been declared as virtual
+ *
+ * Revision 1.3  1999/10/15 01:57:05  lisa
+ * Important enhancement of AliFemtoMaker - implement Franks CutMonitors
+ * ----------------------------------------------------------
+ * This means 3 new files in Infrastructure area (CutMonitor),
+ * several specific CutMonitor classes in the Cut area
+ * and a new base class in the Base area (AliFemtoCutMonitor).
+ * This means also changing all Cut Base class header files from .h to .h
+ * so we have access to CutMonitor methods from Cint command line.
+ * This last means
+ * 1) files which include these header files are slightly modified
+ * 2) a side benefit: the TrackCuts and V0Cuts no longer need
+ * a SetMass() implementation in each Cut class, which was stupid.
+ * Also:
+ * -----
+ * Include Franks AliFemtoAssociationReader
+ * ** None of these changes should affect any user **
+ *
+ * Revision 1.2  1999/07/06 22:33:21  lisa
+ * Adjusted all to work in pro and new - dev itself is broken
+ *
+ * Revision 1.1.1.1  1999/06/29 16:02:56  lisa
+ * Installation of AliFemtoMaker
+ *
+ **************************************************************************/
+
+
+#ifndef ALIFEMTODUMMYPAIRCUT_H
+#define ALIFEMTODUMMYPAIRCUT_H
+
+// do I need these lines ?
+//#ifndef StMaker_H
+//#include "StMaker.h"
+//#endif
+
+#include "AliFemtoPairCut.h"
+
+class AliFemtoDummyPairCut : public AliFemtoPairCut{
+public:
+  AliFemtoDummyPairCut();
+  AliFemtoDummyPairCut(const AliFemtoDummyPairCut&);
+  virtual ~AliFemtoDummyPairCut();
+  AliFemtoDummyPairCut& operator=(const AliFemtoDummyPairCut&);
+
+  virtual bool Pass(const AliFemtoPair*);
+  virtual AliFemtoString Report();
+  virtual TList *ListSettings();
+  AliFemtoDummyPairCut* Clone();
+
+private:
+  long fNPairsPassed;  // number of pairs analyzed by this cut that passed
+  long fNPairsFailed;  // number of pairs analyzed by this cut that failed
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoDummyPairCut, 1)
+#endif
+};
+
+inline AliFemtoDummyPairCut::AliFemtoDummyPairCut(const AliFemtoDummyPairCut& c) : AliFemtoPairCut(c), fNPairsPassed(0), fNPairsFailed(0) { /* no-op */ }
+inline AliFemtoDummyPairCut& AliFemtoDummyPairCut::operator=(const AliFemtoDummyPairCut& c) {   if (this != &c) { AliFemtoPairCut::operator=(c); }  return *this; }
+inline AliFemtoDummyPairCut* AliFemtoDummyPairCut::Clone() { AliFemtoDummyPairCut* c = new AliFemtoDummyPairCut(*this); return c;}
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEnumeration.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEnumeration.h
new file mode 100644 (file)
index 0000000..5c88e50
--- /dev/null
@@ -0,0 +1,45 @@
+/***************************************************************************
+ *
+ * $Id$
+ *
+ * Author: Frank Laue, BNL, laue@bnl.gov
+ ***************************************************************************
+ *
+ ***************************************************************************
+ *
+ * $Log$
+ * Revision 1.1.1.1  2007/04/25 15:38:41  panos
+ * Importing the HBT code dir
+ *
+ * Revision 1.1.1.1  2007/03/07 10:14:49  mchojnacki
+ * First version on CVS
+ *
+ * Revision 1.3  2003/01/08 19:43:12  perev
+ * CleanUp
+ *
+ * Revision 1.2  2001/09/05 20:41:42  laue
+ * Updates of the hbtMuDstTree microDSTs
+ *
+ * Revision 1.1  2001/06/21 19:15:45  laue
+ * Modified fiels:
+ *   CTH.h : new constructor added
+ *   AliFemtoEvent, AliFemtoKink, AliFemtoTrack : constructors from the persistent
+ *                                   (TTree) classes added
+ *   AliFemtoLikeSignAnalysis : minor changes, for debugging
+ *   AliFemtoTypes: split into different files
+ * Added files: for the new TTree muDst's
+ *   StExceptions.cxx StExceptions.h AliFemtoEnumeration.h
+ *   AliFemtoHelix.h AliFemtoHisto.h AliFemtoString.h AliFemtoTFile.h
+ *   AliFemtoTTreeEvent.cxx AliFemtoTTreeEvent.h AliFemtoTTreeKink.cxx
+ *   AliFemtoTTreeKink.h AliFemtoTTreeTrack.cxx AliFemtoTTreeTrack.h
+ *   AliFemtoTTreeV0.cxx AliFemtoTTreeV0.h AliFemtoVector.h
+ *
+ *
+ ***************************************************************************/
+#ifndef AliFemtoEnumeration_hh
+#define AliFemtoEnumeration_hh
+
+enum AliFemtoParticleType {hbtUndefined, hbtTrack, hbtV0, hbtKink, hbtXi};
+enum AliFemtoIOMode {hbtRead, hbtWrite};
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEvent.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEvent.cxx
new file mode 100644 (file)
index 0000000..f09b0a8
--- /dev/null
@@ -0,0 +1,551 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+//  AliFemtoEvent: hold the information specific to the event and a      //
+//  track list                                                           //
+//  AliFemtoEvent is the "transient microDST"  Objects of this class are //
+//   generated from the input data by a Reader, and then presented to   //
+//   the Cuts of the various active Analyses.                           //
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+#include "AliFemtoEvent.h"
+#include "AliFemtoTrack.h"
+#include "AliFemtoV0.h"
+#include "AliFemtoXi.h"
+#include "AliFemtoKink.h"
+#include "AliFemtoTrackCut.h"
+#include "AliFemtoV0Cut.h"
+#include "AliFemtoXiCut.h"
+#include "AliFemtoKinkCut.h"
+#include "PhysicalConstants.h"
+#include "SystemOfUnits.h"
+#include "AliEventplane.h"
+
+// Mike removed all of the AliFemtoTTree stuff here 21apr2006 - it was not used for a long time.
+
+//___________________
+AliFemtoEvent::AliFemtoEvent():
+  fEventNumber(0),
+  fRunNumber(0),
+  fNumberOfTracks(0),
+  fNormalizedMult(-2),
+  fSPDMult(0),
+  fEstimateITSTPC(0),
+  fEstimateTracklets(0),
+  fEstimateITSPure(0),
+  fCentralityV0(0),
+  fCentralityFMD(0),
+  fCentralitySPD1(0),
+  fCentralityTrk(0),
+  fMagneticField(0),
+  fIsCollisionCandidate(kTRUE),
+  fPrimVertPos(0,0,0),
+  fPrimVertCov(),
+  fTrackCollection(0),
+  fV0Collection(0),
+  fXiCollection(0),
+  fKinkCollection(0),
+  fZDCN1Energy(0),   
+  fZDCP1Energy(0),   
+  fZDCN2Energy(0),   
+  fZDCP2Energy(0),   
+  fZDCEMEnergy(0),   
+  fZDCParticipants(0),
+  fTriggerMask(0),  
+  fTriggerCluster(0),
+  fReactionPlaneAngle(0),
+  fEP(0)
+{
+  // Default constructor
+  fPrimVertPos[0]=-999.0;
+  fPrimVertPos[1]=-999.0;
+  fPrimVertPos[2]=-999.0;
+  fPrimVertCov[0]=0.000000000001;
+  fPrimVertCov[1]=0.000000000001;
+  fPrimVertCov[2]=0.000000000001;
+  fPrimVertCov[3]=0.000000000001;
+  fPrimVertCov[4]=0.000000000001;
+  fPrimVertCov[5]=0.000000000001;
+  fTrackCollection = new AliFemtoTrackCollection;
+  fV0Collection = new AliFemtoV0Collection;
+  fXiCollection = new AliFemtoXiCollection;
+  fKinkCollection = new AliFemtoKinkCollection;
+  fMagneticField=0.0;
+}
+//___________________
+AliFemtoEvent::AliFemtoEvent(const AliFemtoEvent& ev, AliFemtoTrackCut* tCut, AliFemtoV0Cut* vCut, AliFemtoXiCut* xCut, AliFemtoKinkCut* kCut):
+  fEventNumber(0),
+  fRunNumber(0),
+  fNumberOfTracks(0),
+  fNormalizedMult(-2),
+  fSPDMult(0),
+  fEstimateITSTPC(0),
+  fEstimateTracklets(0),
+  fEstimateITSPure(0),
+  fCentralityV0(0),
+  fCentralityFMD(0),
+  fCentralitySPD1(0),
+  fCentralityTrk(0),
+  fMagneticField(0),
+  fIsCollisionCandidate(kTRUE),
+  fPrimVertPos(0,0,0),
+  fPrimVertCov(),
+  fTrackCollection(0),
+  fV0Collection(0),
+  fXiCollection(0),
+  fKinkCollection(0),
+  fZDCN1Energy(0),   
+  fZDCP1Energy(0),   
+  fZDCN2Energy(0),   
+  fZDCP2Energy(0),   
+  fZDCEMEnergy(0),   
+  fZDCParticipants(0),
+  fTriggerMask(0),  
+  fTriggerCluster(0),
+  fReactionPlaneAngle(0),
+  fEP(0)
+{ // copy constructor with track and v0 cuts
+  //cout << "AliFemtoEvent::AliFemtoEvent(const AliFemtoEvent& ev, AliFemtoTrackCut* tCut, AliFemtoV0Cut* vCut, AliFemtoV0Cut* kCut)" << endl;
+  fEventNumber = ev.fEventNumber;
+  fRunNumber = ev.fRunNumber;
+  
+  SetPrimVertCov(ev.PrimVertCov());
+
+  fZDCN1Energy=ev.fZDCN1Energy;     
+  fZDCP1Energy=ev.fZDCP1Energy;      
+  fZDCN2Energy=ev.fZDCN2Energy;      
+  fZDCP2Energy=ev.fZDCP2Energy;      
+  fZDCEMEnergy=ev.fZDCEMEnergy;
+  fZDCParticipants=ev.fZDCParticipants;
+  fNumberOfTracks = ev.fNumberOfTracks;
+  fNormalizedMult = ev.fNormalizedMult;
+  fEstimateITSTPC = ev.fEstimateITSTPC;
+  fEstimateTracklets = ev.fEstimateTracklets;
+  fEstimateITSPure = ev.fEstimateITSPure;
+  fCentralityV0 = ev.fCentralityV0; 
+  fCentralityFMD = ev.fCentralityFMD;
+  fCentralitySPD1 = ev.fCentralitySPD1;
+  fCentralityTrk = ev.fCentralityTrk;
+  fMagneticField= ev.fMagneticField;
+  fIsCollisionCandidate = ev.fIsCollisionCandidate;
+
+  fTriggerMask=ev.fTriggerMask;     // Trigger Type (mask)
+  fTriggerCluster=ev.fTriggerCluster;
+  fReactionPlaneAngle=ev.fReactionPlaneAngle;
+  fEP=ev.fEP;
+
+  // create collections
+  fTrackCollection = new AliFemtoTrackCollection;
+  fV0Collection = new AliFemtoV0Collection;
+  fXiCollection = new AliFemtoXiCollection;
+  fKinkCollection = new AliFemtoKinkCollection;
+  // copy track collection  
+  for ( AliFemtoTrackIterator tIter=ev.fTrackCollection->begin(); tIter!=ev.fTrackCollection->end(); tIter++) {
+    if ( !tCut || tCut->Pass(*tIter) ) {
+      AliFemtoTrack* trackCopy = new AliFemtoTrack(**tIter);
+      fTrackCollection->push_back(trackCopy);
+    }
+  }
+  // copy v0 collection
+  for ( AliFemtoV0Iterator vIter=ev.fV0Collection->begin(); vIter!=ev.fV0Collection->end(); vIter++) {
+    if ( !vCut || vCut->Pass(*vIter) ) {
+      AliFemtoV0* v0Copy = new AliFemtoV0(**vIter);
+      fV0Collection->push_back(v0Copy);
+    }
+  }
+  // copy xi collection
+  for ( AliFemtoXiIterator xIter=ev.fXiCollection->begin(); xIter!=ev.fXiCollection->end(); xIter++) {
+    if ( !xCut || xCut->Pass(*xIter) ) {
+      AliFemtoXi* xiCopy = new AliFemtoXi(**xIter);
+      fXiCollection->push_back(xiCopy);
+    }
+  }
+  // copy kink collection  
+  for ( AliFemtoKinkIterator kIter=ev.fKinkCollection->begin(); kIter!=ev.fKinkCollection->end(); kIter++) {
+    if ( !kCut || kCut->Pass(*kIter) ) {
+      //cout << " kinkCut passed " << endl;
+      AliFemtoKink* kinkCopy = new AliFemtoKink(**kIter);
+      fKinkCollection->push_back(kinkCopy);
+    }
+  }
+}
+//___________________
+AliFemtoEvent::AliFemtoEvent(const AliFemtoEvent& ev):
+  fEventNumber(0),
+  fRunNumber(0),
+  fNumberOfTracks(0),
+  fNormalizedMult(-2),
+  fSPDMult(0),
+  fEstimateITSTPC(0),
+  fEstimateTracklets(0),
+  fEstimateITSPure(0),
+  fCentralityV0(0),
+  fCentralityFMD(0),
+  fCentralitySPD1(0),
+  fCentralityTrk(0),
+  fMagneticField(0),
+  fIsCollisionCandidate(kTRUE),
+  fPrimVertPos(0,0,0),
+  fPrimVertCov(),
+  fTrackCollection(0),
+  fV0Collection(0),
+  fXiCollection(0),
+  fKinkCollection(0),
+  fZDCN1Energy(0),   
+  fZDCP1Energy(0),   
+  fZDCN2Energy(0),   
+  fZDCP2Energy(0),   
+  fZDCEMEnergy(0),   
+  fZDCParticipants(0),
+  fTriggerMask(0),  
+  fTriggerCluster(0),
+  fReactionPlaneAngle(0),
+  fEP(0)
+{ 
+  // copy constructor 
+  fEventNumber = ev.fEventNumber;
+  fRunNumber = ev.fRunNumber;
+  
+  SetPrimVertCov(ev.PrimVertCov());
+
+  fZDCN1Energy=ev.fZDCN1Energy;     
+  fZDCP1Energy=ev.fZDCP1Energy;      
+  fZDCN2Energy=ev.fZDCN2Energy;      
+  fZDCP2Energy=ev.fZDCP2Energy;      
+  fZDCEMEnergy=ev.fZDCEMEnergy;
+  fZDCParticipants=ev.fZDCParticipants;
+  fNumberOfTracks = ev.fNumberOfTracks;
+  fEstimateITSTPC = ev.fEstimateITSTPC;
+  fEstimateTracklets = ev.fEstimateTracklets;
+  fEstimateITSPure = ev.fEstimateITSPure;
+  fCentralityV0 = ev.fCentralityV0; 
+  fCentralityFMD = ev.fCentralityFMD;
+  fCentralitySPD1 = ev.fCentralitySPD1;
+  fCentralityTrk = ev.fCentralityTrk;
+  fMagneticField= ev.fMagneticField;
+  fIsCollisionCandidate = ev.fIsCollisionCandidate;
+  fTriggerMask=ev.fTriggerMask;     // Trigger Type (mask)
+  fTriggerCluster=ev.fTriggerCluster;
+  fReactionPlaneAngle=ev.fReactionPlaneAngle;
+  fEP=ev.fEP;
+  // create collections
+  fTrackCollection = new AliFemtoTrackCollection;
+  fV0Collection = new AliFemtoV0Collection;
+  fXiCollection = new AliFemtoXiCollection;
+  fKinkCollection = new AliFemtoKinkCollection;
+  // copy track collection  
+  for ( AliFemtoTrackIterator tIter=ev.fTrackCollection->begin(); tIter!=ev.fTrackCollection->end(); tIter++) {
+    AliFemtoTrack* trackCopy = new AliFemtoTrack(**tIter);
+    fTrackCollection->push_back(trackCopy);
+  }
+  // copy v0 collection
+  for ( AliFemtoV0Iterator vIter=ev.fV0Collection->begin(); vIter!=ev.fV0Collection->end(); vIter++) {
+    AliFemtoV0* v0Copy = new AliFemtoV0(**vIter);
+    fV0Collection->push_back(v0Copy);
+  }
+  // copy xi collection
+  for ( AliFemtoXiIterator xIter=ev.fXiCollection->begin(); xIter!=ev.fXiCollection->end(); xIter++) {
+    AliFemtoXi* xiCopy = new AliFemtoXi(**xIter);
+    fXiCollection->push_back(xiCopy);
+  }
+  // copy kink collection  
+  for ( AliFemtoKinkIterator kIter=ev.fKinkCollection->begin(); kIter!=ev.fKinkCollection->end(); kIter++) {
+    //cout << " kinkCut passed " << endl;
+    AliFemtoKink* kinkCopy = new AliFemtoKink(**kIter);
+    fKinkCollection->push_back(kinkCopy);
+  }
+}
+//______________________________
+AliFemtoEvent& AliFemtoEvent::operator=(const AliFemtoEvent& aEvent)
+{
+  // assignment operator
+  if (this == &aEvent)
+    return *this;
+
+  fEventNumber = aEvent.fEventNumber;
+  fRunNumber = aEvent.fRunNumber;
+  
+  fZDCN1Energy=aEvent.fZDCN1Energy;     
+  fZDCP1Energy=aEvent.fZDCP1Energy;      
+  fZDCN2Energy=aEvent.fZDCN2Energy;      
+  fZDCP2Energy=aEvent.fZDCP2Energy;      
+  fZDCEMEnergy=aEvent.fZDCEMEnergy;
+  fZDCParticipants=aEvent.fZDCParticipants;
+  fNumberOfTracks = aEvent.fNumberOfTracks;
+  fEstimateITSTPC = aEvent.fEstimateITSTPC;
+  fEstimateTracklets = aEvent.fEstimateTracklets;
+  fEstimateITSPure = aEvent.fEstimateITSPure;
+  fCentralityV0 = aEvent.fCentralityV0; 
+  fCentralityFMD = aEvent.fCentralityFMD;
+  fCentralitySPD1 = aEvent.fCentralitySPD1;
+  fCentralityTrk = aEvent.fCentralityTrk;
+  fNormalizedMult = aEvent.fNormalizedMult;
+  fEstimateITSTPC = aEvent.fEstimateITSTPC;
+  fEstimateTracklets = aEvent.fEstimateTracklets;
+  fEstimateITSPure = aEvent.fEstimateITSPure;
+  fMagneticField= aEvent.fMagneticField;
+  fIsCollisionCandidate = aEvent.fIsCollisionCandidate;
+
+  fTriggerMask=aEvent.fTriggerMask;     // Trigger Type (mask)
+  fTriggerCluster=aEvent.fTriggerCluster;
+  fReactionPlaneAngle=aEvent.fReactionPlaneAngle;
+  fEP=aEvent.fEP;
+  if (fTrackCollection) {
+    for (AliFemtoTrackIterator iter=fTrackCollection->begin();iter!=fTrackCollection->end();iter++){
+      delete *iter;
+    }
+    fTrackCollection->clear();
+    delete fTrackCollection;
+  }
+  fTrackCollection = new AliFemtoTrackCollection;
+
+  if (fV0Collection) {
+    for (AliFemtoV0Iterator tV0iter=fV0Collection->begin();tV0iter!=fV0Collection->end();tV0iter++){
+      delete *tV0iter;
+    }//added by M Chojnacki To avodid memory leak 
+    fV0Collection->clear();
+    delete fV0Collection;
+  }
+
+  fV0Collection = new AliFemtoV0Collection;
+
+  if (fXiCollection) {
+    for (AliFemtoXiIterator tXiIter=fXiCollection->begin();tXiIter!=fXiCollection->end();tXiIter++){
+      delete *tXiIter;
+    }
+    fXiCollection->clear();
+    delete fXiCollection;
+  }
+  fXiCollection = new AliFemtoXiCollection;
+  
+  if (fKinkCollection) {
+    for (AliFemtoKinkIterator kinkIter=fKinkCollection->begin();kinkIter!=fKinkCollection->end();kinkIter++){
+      delete *kinkIter;
+    }
+    fKinkCollection->clear();
+    delete fKinkCollection;
+  }
+  fKinkCollection = new AliFemtoKinkCollection;
+
+  // copy track collection  
+  for ( AliFemtoTrackIterator tIter=aEvent.fTrackCollection->begin(); tIter!=aEvent.fTrackCollection->end(); tIter++) {
+    AliFemtoTrack* trackCopy = new AliFemtoTrack(**tIter);
+    fTrackCollection->push_back(trackCopy);
+  }
+  // copy v0 collection
+  for ( AliFemtoV0Iterator vIter=aEvent.fV0Collection->begin(); vIter!=aEvent.fV0Collection->end(); vIter++) {
+    AliFemtoV0* v0Copy = new AliFemtoV0(**vIter);
+    fV0Collection->push_back(v0Copy);
+  }
+  // copy xi collection
+  for ( AliFemtoXiIterator xIter=aEvent.fXiCollection->begin(); xIter!=aEvent.fXiCollection->end(); xIter++) {
+    AliFemtoXi* xiCopy = new AliFemtoXi(**xIter);
+    fXiCollection->push_back(xiCopy);
+  }
+  // copy kink collection  
+  for ( AliFemtoKinkIterator kIter=aEvent.fKinkCollection->begin(); kIter!=aEvent.fKinkCollection->end(); kIter++) {
+    AliFemtoKink* kinkCopy = new AliFemtoKink(**kIter);
+    fKinkCollection->push_back(kinkCopy);
+  }
+
+  return *this;
+}
+
+//___________________
+AliFemtoEvent::~AliFemtoEvent(){
+  // destructor
+#ifdef STHBTDEBUG
+  cout << " AliFemtoEvent::~AliFemtoEvent() " << endl;
+#endif
+  for (AliFemtoTrackIterator iter=fTrackCollection->begin();iter!=fTrackCollection->end();iter++){
+    delete *iter;
+  }
+  fTrackCollection->clear();
+  delete fTrackCollection;
+  //must do the same for the V0 collection
+  for (AliFemtoV0Iterator tV0iter=fV0Collection->begin();tV0iter!=fV0Collection->end();tV0iter++){
+    delete *tV0iter;
+  }//added by M Chojnacki To avodid memory leak 
+  fV0Collection->clear();
+  delete fV0Collection;
+  //must do the same for the Xi collection
+  for (AliFemtoXiIterator tXiIter=fXiCollection->begin();tXiIter!=fXiCollection->end();tXiIter++){
+    delete *tXiIter;
+  }
+  fXiCollection->clear();
+  delete fXiCollection;
+  //must do the same for the Kink collection
+  for (AliFemtoKinkIterator kinkIter=fKinkCollection->begin();kinkIter!=fKinkCollection->end();kinkIter++){
+    delete *kinkIter;
+  }
+  fKinkCollection->clear();
+  delete fKinkCollection;
+}
+//___________________
+
+
+
+void AliFemtoEvent::SetEventNumber(const unsigned short& event){fEventNumber = event;}
+void AliFemtoEvent::SetRunNumber(const int& runNum){fRunNumber = runNum;}
+
+
+void AliFemtoEvent::SetZDCN1Energy(const float& aZDCN1Energy){fZDCN1Energy=aZDCN1Energy;}
+void AliFemtoEvent::SetZDCP1Energy(const float& aZDCP1Energy){fZDCP1Energy=aZDCP1Energy;}      
+void AliFemtoEvent::SetZDCN2Energy(const float& aZDCN2Energy){fZDCN2Energy=aZDCN2Energy;}      
+void AliFemtoEvent::SetZDCP2Energy(const float& aZDCP2Energy){fZDCP2Energy=aZDCP2Energy;}      
+void AliFemtoEvent::SetZDCEMEnergy(const float& aZDCEMEnergy){fZDCEMEnergy=aZDCEMEnergy;}    
+void AliFemtoEvent::SetZDCParticipants(const unsigned int& aZDCParticipants){fZDCParticipants=aZDCParticipants;}
+
+void AliFemtoEvent::SetNumberOfTracks(const unsigned short& tracks){fNumberOfTracks = tracks;}
+void AliFemtoEvent::SetNormalizedMult(const int& i){fNormalizedMult = i;}
+void AliFemtoEvent::SetSPDMult(const int& i){fSPDMult = i;}
+
+void AliFemtoEvent::SetPrimVertPos(const AliFemtoThreeVector& vp){fPrimVertPos = vp;}
+void AliFemtoEvent::SetPrimVertCov(const double* v){
+  fPrimVertCov[0] = v[0];
+  fPrimVertCov[1] = v[1];
+  fPrimVertCov[2] = v[2];
+  fPrimVertCov[3] = v[3];
+  fPrimVertCov[4] = v[4];
+  fPrimVertCov[5] = v[5];
+}
+void AliFemtoEvent::SetMagneticField(const double& magF){fMagneticField = magF;}
+void AliFemtoEvent::SetIsCollisionCandidate(const bool& is){fIsCollisionCandidate = is;}
+
+void AliFemtoEvent::SetTriggerMask(const unsigned long int& aTriggerMask) {fTriggerMask=aTriggerMask;}
+void AliFemtoEvent::SetTriggerCluster(const unsigned char& aTriggerCluster) {fTriggerCluster=aTriggerCluster;}
+
+
+unsigned short AliFemtoEvent::EventNumber() const {return fEventNumber;}
+int            AliFemtoEvent::RunNumber() const {return fRunNumber;}
+
+
+
+unsigned short AliFemtoEvent::NumberOfTracks() const {return fNumberOfTracks;}
+
+AliFemtoV0Collection* AliFemtoEvent::V0Collection() const {return fV0Collection;}
+AliFemtoXiCollection* AliFemtoEvent::XiCollection() const {return fXiCollection;}
+AliFemtoKinkCollection* AliFemtoEvent::KinkCollection() const {return fKinkCollection;}
+AliFemtoTrackCollection* AliFemtoEvent::TrackCollection() const {return fTrackCollection;}
+AliFemtoThreeVector AliFemtoEvent::PrimVertPos() const {return fPrimVertPos;}
+const double* AliFemtoEvent::PrimVertCov() const {return fPrimVertCov;}
+double AliFemtoEvent::MagneticField() const {return fMagneticField;}
+unsigned long int AliFemtoEvent::TriggerMask() const {return fTriggerMask;}
+unsigned char AliFemtoEvent::TriggerCluster() const {return fTriggerCluster;}
+bool AliFemtoEvent::IsCollisionCandidate() const {return fIsCollisionCandidate;}
+
+
+float AliFemtoEvent::ZDCN1Energy() const {return fZDCN1Energy;}       
+float AliFemtoEvent::ZDCP1Energy() const {return fZDCP1Energy;}       
+float AliFemtoEvent::ZDCN2Energy() const {return fZDCN2Energy;}       
+float AliFemtoEvent::ZDCP2Energy() const {return fZDCP2Energy;}       
+float AliFemtoEvent::ZDCEMEnergy() const {return fZDCEMEnergy;}   
+unsigned int  AliFemtoEvent::ZDCParticipants() const {return fZDCParticipants;}
+
+void AliFemtoEvent::SetReactionPlaneAngle(const float& a) { fReactionPlaneAngle = a;}
+float AliFemtoEvent::ReactionPlaneAngle() const { return fReactionPlaneAngle; }
+void AliFemtoEvent::SetEP(AliEventplane* ep) { fEP = ep;}
+AliEventplane* AliFemtoEvent::EP() const {return fEP; }
+
+//----------------------------- below here is only for star
+
+int AliFemtoEvent::UncorrectedNumberOfNegativePrimaries() const
+{
+  return NumberOfTracks()/2;
+}
+
+int AliFemtoEvent::SPDMultiplicity() const
+{
+  return fSPDMult;
+}
+
+int AliFemtoEvent::UncorrectedNumberOfPrimaries() const
+{
+  if (fNormalizedMult < -1) {
+    // Count number of normalized charged tracks 
+    Int_t tNormTrackCount = 0;
+    for (AliFemtoTrackIterator iter=fTrackCollection->begin();iter!=fTrackCollection->end();iter++){
+      if (!((*iter)->Flags()&(AliFemtoTrack::kTPCrefit))) continue;
+      if ((*iter)->TPCncls() < 50) continue;
+      if ((*iter)->TPCchi2()/(*iter)->TPCncls() > 60.0) continue;
+      if ((*iter)->ImpactD() > 6.0) continue;
+      if ((*iter)->ImpactZ() > 6.0) continue;
+      if (fabs((*iter)->P().PseudoRapidity()) > 0.9) continue;
+      
+      tNormTrackCount++;
+    }
+    return tNormTrackCount;
+  }
+
+  return fNormalizedMult;
+  //  return NumberOfTracks();
+}
+
+unsigned short AliFemtoEvent::MultiplicityEstimateITSTPC() const
+{
+  return fEstimateITSTPC;
+}
+
+unsigned short AliFemtoEvent::MultiplicityEstimateTracklets() const
+{
+  return fEstimateTracklets;
+}
+
+unsigned short AliFemtoEvent::MultiplicityEstimateITSPure() const
+{
+  return fEstimateITSPure;
+}
+
+void AliFemtoEvent::SetMultiplicityEstimateITSTPC(const unsigned short &s)
+{
+  fEstimateITSTPC = s;
+}
+
+void AliFemtoEvent::SetMultiplicityEstimateTracklets(const unsigned short &s)
+{
+  fEstimateTracklets = s;
+}
+
+void AliFemtoEvent::SetMultiplicityEstimateITSPure(const unsigned short &s)
+{
+  fEstimateITSPure = s;
+}
+
+void AliFemtoEvent::SetCentralityV0(const float &c)
+{
+  fCentralityV0 = c;
+}
+
+void AliFemtoEvent::SetCentralityFMD(const float &c)
+{
+  fCentralityFMD = c;
+}
+
+void AliFemtoEvent::SetCentralitySPD1(const float &c)
+{
+  fCentralitySPD1 = c;
+}
+
+void AliFemtoEvent::SetCentralityTrk(const float &c)
+{
+  fCentralityTrk = c;
+}
+
+float AliFemtoEvent::CentralityV0() const
+{
+  return fCentralityV0;
+}
+
+float AliFemtoEvent::CentralityFMD() const
+{
+  return fCentralityFMD;
+}
+
+float AliFemtoEvent::CentralitySPD1() const
+{
+  return fCentralitySPD1;
+}
+
+float AliFemtoEvent::CentralityTrk() const
+{
+  return fCentralityTrk;
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEvent.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEvent.h
new file mode 100644 (file)
index 0000000..1b56114
--- /dev/null
@@ -0,0 +1,157 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+//  AliFemtoEvent: hold the information specific to the event and a      //
+//  track list                                                           //
+//  AliFemtoEvent is the "transient microDST"  Objects of this class are //
+//   generated from the input data by a Reader, and then presented to   //
+//   the Cuts of the various active Analyses.                           //
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+
+#ifndef ALIFEMTOEVENT_H
+#define ALIFEMTOEVENT_H
+
+#include "AliFemtoTypes.h"
+#include "AliFemtoTrackCollection.h"
+#include "AliFemtoV0Collection.h"
+#include "AliFemtoXiCollection.h"
+#include "AliFemtoKinkCollection.h"
+
+class AliFemtoTrackCut;
+class AliFemtoV0Cut;
+class AliFemtoXiCut;
+class AliFemtoKinkCut;
+class AliEventplane;
+
+#ifdef __ROOT__
+// the following encapsulation by malisa 21apr2006
+#ifndef __NO_STAR_DEPENDENCE_ALLOWED__
+class StMuDst;
+#endif
+#endif
+
+class AliFemtoEvent{
+public:
+  AliFemtoEvent();
+#ifdef __ROOT__
+#ifndef __NO_STAR_DEPENDENCE_ALLOWED__
+//
+#endif
+#endif
+  
+  AliFemtoEvent(const AliFemtoEvent& ev, AliFemtoTrackCut* tCut=0, AliFemtoV0Cut* vCut=0,  AliFemtoXiCut* xCut=0, AliFemtoKinkCut* kCut=0); // copy constructor with track and v0 cuts
+  AliFemtoEvent(const AliFemtoEvent& ev); // copy constructor
+  ~AliFemtoEvent();
+  AliFemtoEvent& operator=(const AliFemtoEvent& aEvent);
+
+  unsigned short EventNumber() const;
+  int RunNumber() const;
+  unsigned short NumberOfTracks() const;
+  AliFemtoThreeVector PrimVertPos() const;
+  const double* PrimVertCov() const;
+  AliFemtoV0Collection* V0Collection() const;
+  AliFemtoXiCollection* XiCollection() const;
+  AliFemtoKinkCollection* KinkCollection() const;
+  AliFemtoTrackCollection* TrackCollection() const;
+  double MagneticField() const;
+  bool IsCollisionCandidate() const;
+
+  //functions for alice variables
+  float ZDCN1Energy() const;      
+  float ZDCP1Energy() const;      
+  float ZDCN2Energy() const;      
+  float ZDCP2Energy() const;      
+  float ZDCEMEnergy() const;    
+  unsigned int ZDCParticipants() const; 
+
+  unsigned long int     TriggerMask() const;     
+  unsigned char      TriggerCluster() const;  
+
+  float ReactionPlaneAngle() const;
+  AliEventplane* EP() const;
+  
+  void SetEventNumber(const unsigned short& s);
+  void SetRunNumber(const int& i);
+  void SetNumberOfTracks(const unsigned short& s);
+  void SetNormalizedMult(const int& i);
+  void SetMultiplicityEstimateITSTPC(const unsigned short &s);
+  void SetMultiplicityEstimateTracklets(const unsigned short &s);
+  void SetMultiplicityEstimateITSPure(const unsigned short &s);
+  void SetCentralityV0(const float &c);
+  void SetCentralityFMD(const float &c);
+  void SetCentralitySPD1(const float &c);
+  void SetCentralityTrk(const float &c);
+  void SetSPDMult(const int& i);
+  void SetPrimVertPos(const AliFemtoThreeVector& v);
+  void SetPrimVertCov(const double* v);
+  void SetMagneticField(const double& x);
+  void SetIsCollisionCandidate(const bool& is);
+
+   //functions for alice variables
+  void SetZDCN1Energy(const float& x);      
+  void SetZDCP1Energy(const float& x);      
+  void SetZDCN2Energy(const float& x);      
+  void SetZDCP2Energy(const float& x);      
+  void SetZDCEMEnergy(const float& x);    
+  void SetZDCParticipants(const unsigned int& i);
+  
+  void SetTriggerMask(const unsigned long int& i);     
+  void SetTriggerCluster(const unsigned char& c); 
+
+  void SetReactionPlaneAngle(const float& a);
+  void SetEP(AliEventplane* ep);
+  
+  int UncorrectedNumberOfNegativePrimaries() const;
+  int UncorrectedNumberOfPrimaries() const;
+  int SPDMultiplicity() const;
+
+  unsigned short MultiplicityEstimateITSTPC() const;
+  unsigned short MultiplicityEstimateTracklets() const;
+  unsigned short MultiplicityEstimateITSPure() const;
+
+  float CentralityV0() const;
+  float CentralityFMD() const;
+  float CentralitySPD1() const;
+  float CentralityTrk() const;
+
+private:
+  unsigned short fEventNumber;           // Event number in file
+  unsigned short fRunNumber;             // run number the event belong to
+  unsigned short fNumberOfTracks;        // total number of TPC tracks
+  int   fNormalizedMult;                 // normalized multiplicity
+  int   fSPDMult;                        // Multiplicity of SPD tracklets
+  unsigned short fEstimateITSTPC;        // Official multiplicity estimate ITS+TPC
+  unsigned short fEstimateTracklets;     // Official multiplicity estimate Tracklets
+  unsigned short fEstimateITSPure;       // Official multiplicity estimate ITS SA
+  float fCentralityV0;                   // Official centrality from V0
+  float fCentralityFMD;                  // Official centrality from FMD
+  float fCentralitySPD1;                 // Official centrality from SPD layer 1
+  float fCentralityTrk;                  // Official centrality from tracks
+  double fMagneticField;                 // magnetic field in Z direction
+  bool fIsCollisionCandidate;            // is collision candidate
+  
+  AliFemtoThreeVector fPrimVertPos;      // primary vertex position
+  double fPrimVertCov[6];                // primary vertex covariances
+  AliFemtoTrackCollection* fTrackCollection; // collection of tracks
+  AliFemtoV0Collection* fV0Collection;   // collection of V0s
+  AliFemtoXiCollection* fXiCollection;   // collection of Xis
+  AliFemtoKinkCollection* fKinkCollection; // collection of kinks
+
+  //for alice changed by Marek Chojnacki
+  float      fZDCN1Energy;      // reconstructed energy in the neutron ZDC
+  float      fZDCP1Energy;      // reconstructed energy in the proton ZDC
+  float      fZDCN2Energy;      // reconstructed energy in the neutron ZDC
+  float      fZDCP2Energy;      // reconstructed energy in the proton ZDC
+  float      fZDCEMEnergy;     // reconstructed energy in the electromagnetic ZDC
+  unsigned int        fZDCParticipants; // number of participants estimated by the ZDC
+  
+  unsigned long int     fTriggerMask;     // Trigger Type (mask)
+  unsigned char      fTriggerCluster;  // Trigger cluster (mask)
+
+  float      fReactionPlaneAngle; // reconstructed reaction plane angle
+  AliEventplane*  fEP; // pointer to full event plane information
+};
+
+
+
+#endif 
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventCut.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventCut.h
new file mode 100644 (file)
index 0000000..b7916a1
--- /dev/null
@@ -0,0 +1,46 @@
+////////////////////////////////////////////////////////////////////////////////
+/// AliFemtoEventCut - the pure virtual base class for the event cut         ///
+/// All event cuts must inherit from this one                                ///
+////////////////////////////////////////////////////////////////////////////////
+#ifndef AliFemtoEventCut_hh
+#define AliFemtoEventCut_hh
+
+class AliFemtoEvent;
+class AliFemtoAnalysis;
+
+#include "AliFemtoCutMonitorHandler.h"
+#include "AliFemtoString.h"
+
+class AliFemtoEventCut : public AliFemtoCutMonitorHandler {
+
+  friend class AliFemtoAnalysis;
+
+public:
+
+  AliFemtoEventCut();                // default constructor. - Users should write their own
+  AliFemtoEventCut(const AliFemtoEventCut& c); // copy constructor
+  virtual ~AliFemtoEventCut(){/* no-op */};       // destructor
+  AliFemtoEventCut& operator=(const AliFemtoEventCut& aCut);
+
+  virtual bool Pass(const AliFemtoEvent* event) =0;  // true if passes, false if not
+
+  virtual AliFemtoString Report() =0;    // user-written method to return string describing cuts
+  virtual AliFemtoEventCut* Clone() { return 0;}
+
+
+  AliFemtoAnalysis* HbtAnalysis(){return fyAnalysis;};
+  void SetAnalysis(AliFemtoAnalysis* aAnalysis);
+
+protected:
+  AliFemtoAnalysis* fyAnalysis;
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoEventCut, 0)
+#endif
+};
+
+inline AliFemtoEventCut::AliFemtoEventCut(const AliFemtoEventCut& /* c */) : AliFemtoCutMonitorHandler(), fyAnalysis(0) { }
+inline void AliFemtoEventCut::SetAnalysis(AliFemtoAnalysis* analysis) { fyAnalysis = analysis; }
+inline AliFemtoEventCut::AliFemtoEventCut(): AliFemtoCutMonitorHandler(), fyAnalysis(0){}                // default constructor. - Users should write their own
+inline AliFemtoEventCut& AliFemtoEventCut::operator=(const AliFemtoEventCut& aCut) { if (this == &aCut) return *this; fyAnalysis = aCut.fyAnalysis; return *this; }
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventCutEstimators.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventCutEstimators.cxx
new file mode 100644 (file)
index 0000000..f9d8b99
--- /dev/null
@@ -0,0 +1,119 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoEventCutEstimators - the basic cut for events.                          //
+// Only cuts on event multiplicity and z-vertex position                      //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+
+#include "AliFemtoEventCutEstimators.h"
+//#include <cstdio>
+
+#ifdef __ROOT__
+ClassImp(AliFemtoEventCutEstimators)
+#endif
+
+AliFemtoEventCutEstimators::AliFemtoEventCutEstimators() :
+  AliFemtoEventCut(),
+  fEventMultEst1(),
+  fEventMultEst2(),
+  fEventMultEst3(),
+  fUseMultEst1(0), 
+  fUseMultEst2(0), 
+  fUseMultEst3(0), 
+  fEventCentEst1(),
+  fEventCentEst2(),
+  fEventCentEst3(),
+  fEventCentEst4(),
+  fUseCentEst1(0), 
+  fUseCentEst2(0), 
+  fUseCentEst3(0), 
+  fUseCentEst4(0),
+  fNEventsPassed(0), 
+  fNEventsFailed(0) 
+{
+  // Default constructor
+  fEventMultEst1[0] = 0;  fEventMultEst1[1] = 10000;
+  fEventMultEst2[0] = 0;  fEventMultEst2[1] = 10000;
+  fEventMultEst3[0] = 0;  fEventMultEst3[1] = 10000;
+  fEventCentEst1[0] = 0;  fEventCentEst1[1] = 1000.0;
+  fEventCentEst2[0] = 0;  fEventCentEst2[1] = 1000.0;
+  fEventCentEst3[0] = 0;  fEventCentEst3[1] = 1000.0;
+  fEventCentEst4[0] = 0;  fEventCentEst4[1] = 1000.0;
+  fVertZPos[0] = -100.0;
+  fVertZPos[1] = 100.0;
+} 
+//------------------------------
+AliFemtoEventCutEstimators::~AliFemtoEventCutEstimators(){
+  // Default destructor
+}
+//------------------------------
+AliFemtoEventCutEstimators& AliFemtoEventCutEstimators::operator=(AliFemtoEventCutEstimators& c)
+{
+  if (this != &c) {
+    fEventMultEst1[0] = c.fEventMultEst1[0];  fEventMultEst1[1] = c.fEventMultEst1[1];
+    fEventMultEst2[0] = c.fEventMultEst2[0];  fEventMultEst2[1] = c.fEventMultEst2[1];
+    fEventMultEst3[0] = c.fEventMultEst3[0];  fEventMultEst3[1] = c.fEventMultEst3[1];
+    fEventCentEst1[0] = c.fEventCentEst1[0];  fEventCentEst1[1] = c.fEventCentEst1[1];
+    fEventCentEst2[0] = c.fEventCentEst2[0];  fEventCentEst2[1] = c.fEventCentEst2[1];
+    fEventCentEst3[0] = c.fEventCentEst3[0];  fEventCentEst3[1] = c.fEventCentEst3[1];
+    fEventCentEst4[0] = c.fEventCentEst4[0];  fEventCentEst4[1] = c.fEventCentEst4[1];
+    fVertZPos[0] = c.fVertZPos[0];
+    fVertZPos[1] = c.fVertZPos[1];
+  }
+
+  return *this;
+}
+
+//------------------------------
+bool AliFemtoEventCutEstimators::Pass(const AliFemtoEvent* event){
+  // Pass events if they fall within the multiplicity and z-vertex
+  // position range. Fail otherwise
+  //  int mult =  event->NumberOfTracks();
+  
+  bool goodEvent = true;
+
+  printf("Cutting event with %i %i %i - %i %i %i %i\n", fUseMultEst1, fUseMultEst2, fUseMultEst3, fUseCentEst1, fUseCentEst2, fUseCentEst3, fUseCentEst4);
+  printf("  On %i %i %i - %f %f %f %f\n", event->MultiplicityEstimateTracklets(), event->MultiplicityEstimateITSTPC(), event->MultiplicityEstimateITSPure(),
+        event->CentralityV0(), event->CentralityFMD(), event->CentralitySPD1(), event->CentralityTrk());
+
+  if (fUseMultEst1) { goodEvent &= ((event->MultiplicityEstimateTracklets() >= fEventMultEst1[0]) &&
+                                   (event->MultiplicityEstimateTracklets() <= fEventMultEst1[1])); }
+  if (fUseMultEst2) { goodEvent &= ((event->MultiplicityEstimateITSTPC() >= fEventMultEst2[0]) &&
+                                   (event->MultiplicityEstimateITSTPC() <= fEventMultEst2[1])); }
+  if (fUseMultEst3) { goodEvent &= ((event->MultiplicityEstimateITSPure() >= fEventMultEst3[0]) &&
+                                   (event->MultiplicityEstimateITSPure() <= fEventMultEst3[1])); }
+
+  if (fUseCentEst1) { goodEvent &= ((event->CentralityV0() > fEventCentEst1[0]) &&
+                                   (event->CentralityV0() < fEventCentEst1[1])); }
+  if (fUseCentEst2) { goodEvent &= ((event->CentralityFMD() > fEventCentEst2[0]) &&
+                                   (event->CentralityFMD() < fEventCentEst2[1])); }
+  if (fUseCentEst3) { goodEvent &= ((event->CentralitySPD1() > fEventCentEst3[0]) &&
+                                   (event->CentralitySPD1() < fEventCentEst3[1])); }
+  if (fUseCentEst4) { goodEvent &= ((event->CentralityTrk() > fEventCentEst4[0]) &&
+                                   (event->CentralityTrk() < fEventCentEst4[1])); }
+  double vertexZPos = event->PrimVertPos().z();
+  //   cout << "AliFemtoEventCutEstimators:: mult:       " << fEventMult[0] << " < " << mult << " < " << fEventMult[1] << endl;
+  //   cout << "AliFemtoEventCutEstimators:: VertexZPos: " << fVertZPos[0] << " < " << vertexZPos << " < " << fVertZPos[1] << endl;
+  //   cout << "AliFemtoEventCutEstimators:: VertexZErr: " << event->PrimVertCov()[4] << endl;
+  goodEvent &=
+    ((vertexZPos > fVertZPos[0]) &&
+     (vertexZPos < fVertZPos[1]));
+  goodEvent ? fNEventsPassed++ : fNEventsFailed++ ;
+  //   cout << "AliFemtoEventCutEstimators:: return : " << goodEvent << endl;
+  //     (fAcceptBadVertex || (event->PrimVertCov()[4] > -1000.0)) &&
+  return (goodEvent);
+}
+  //------------------------------
+AliFemtoString AliFemtoEventCutEstimators::Report(){
+  // Prepare report
+  string stemp;
+  char ctemp[100];
+  snprintf(ctemp , 100, "\nMultiplicity:\t %d-%d",fEventMultEst2[0],fEventMultEst2[1]);
+  stemp = ctemp;
+  snprintf(ctemp , 100, "\nVertex Z-position:\t %E-%E",fVertZPos[0],fVertZPos[1]);
+  stemp += ctemp;
+  snprintf(ctemp , 100, "\nNumber of events which passed:\t%ld  Number which failed:\t%ld",fNEventsPassed,fNEventsFailed);
+  stemp += ctemp;
+  AliFemtoString returnThis = stemp;
+  return returnThis;
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventCutEstimators.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventCutEstimators.h
new file mode 100644 (file)
index 0000000..a868436
--- /dev/null
@@ -0,0 +1,102 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoEventCutEstimators - the basic cut for events.                          //
+// Only cuts on event multiplicity and z-vertex position                      //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+
+#ifndef ALIFEMTOEVENTCUTESTIMATORS_H
+#define ALIFEMTOEVENTCUTESTIMATORS_H
+
+// do I need these lines ?
+//#ifndef StMaker_H
+//#include "StMaker.h"
+//#endif
+
+#include "AliFemtoEventCut.h"
+#include "AliFemtoEventReaderESDChain.h"
+
+class AliFemtoEventCutEstimators : public AliFemtoEventCut {
+
+public:
+
+  AliFemtoEventCutEstimators();
+  AliFemtoEventCutEstimators(AliFemtoEventCutEstimators& c);
+  virtual ~AliFemtoEventCutEstimators();
+  AliFemtoEventCutEstimators& operator=(AliFemtoEventCutEstimators& c);
+
+  void SetMultEst1Range(const unsigned short &lo, const unsigned short &hi);
+  void SetMultEst2Range(const unsigned short &lo, const unsigned short &hi);
+  void SetMultEst3Range(const unsigned short &lo, const unsigned short &hi);
+  
+  void SetCentEst1Range(const float &lo, const float &hi);
+  void SetCentEst2Range(const float &lo, const float &hi);
+  void SetCentEst3Range(const float &lo, const float &hi);
+  void SetCentEst4Range(const float &lo, const float &hi);
+
+  void SetVertZPos(const float& lo, const float& hi);
+  int NEventsPassed() const;
+  int NEventsFailed() const;
+
+  virtual AliFemtoString Report();
+  virtual bool Pass(const AliFemtoEvent* event);
+
+  AliFemtoEventCutEstimators* Clone();
+
+private:   // here are the quantities I want to cut on...
+
+  unsigned short fEventMultEst1[2];      // range of multiplicity
+  unsigned short fEventMultEst2[2];      // range of multiplicity
+  unsigned short fEventMultEst3[2];      // range of multiplicity
+  unsigned char fUseMultEst1;  // if 1 cut on Mult Est 1
+  unsigned char fUseMultEst2;  // if 1 cut on Mult Est 2
+  unsigned char fUseMultEst3;  // if 1 cut on Mult Est 3
+  
+  float fEventCentEst1[2];      // range of multiplicity
+  float fEventCentEst2[2];      // range of multiplicity
+  float fEventCentEst3[2];      // range of multiplicity
+  float fEventCentEst4[2];      // range of multiplicity
+  unsigned char fUseCentEst1;  // if 1 cut on Mult Est 1
+  unsigned char fUseCentEst2;  // if 1 cut on Mult Est 2
+  unsigned char fUseCentEst3;  // if 1 cut on Mult Est 3
+  unsigned char fUseCentEst4;  // if 1 cut on Mult Est 4
+
+  float fVertZPos[2];     // range of z-position of vertex
+  long fNEventsPassed;    // Number of events checked by this cut that passed
+  long fNEventsFailed;    // Number of events checked by this cut that failed
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoEventCutEstimators, 1)
+#endif
+
+};
+
+inline void AliFemtoEventCutEstimators::SetMultEst1Range(const unsigned short& lo, const unsigned short& hi){fEventMultEst1[0]=lo; fEventMultEst1[1]=hi; fUseMultEst1=1;}
+inline void AliFemtoEventCutEstimators::SetMultEst2Range(const unsigned short& lo, const unsigned short& hi){fEventMultEst2[0]=lo; fEventMultEst2[1]=hi; fUseMultEst2=1;}
+inline void AliFemtoEventCutEstimators::SetMultEst3Range(const unsigned short& lo, const unsigned short& hi){fEventMultEst3[0]=lo; fEventMultEst3[1]=hi; fUseMultEst3=1;}
+inline void AliFemtoEventCutEstimators::SetCentEst1Range(const float& lo, const float& hi){fEventCentEst1[0]=lo; fEventCentEst1[1]=hi; fUseCentEst1=1;}
+inline void AliFemtoEventCutEstimators::SetCentEst2Range(const float& lo, const float& hi){fEventCentEst2[0]=lo; fEventCentEst2[1]=hi; fUseCentEst2=1;}
+inline void AliFemtoEventCutEstimators::SetCentEst3Range(const float& lo, const float& hi){fEventCentEst3[0]=lo; fEventCentEst3[1]=hi; fUseCentEst3=1;}
+inline void AliFemtoEventCutEstimators::SetCentEst4Range(const float& lo, const float& hi){fEventCentEst4[0]=lo; fEventCentEst4[1]=hi; fUseCentEst4=1;}
+inline void AliFemtoEventCutEstimators::SetVertZPos(const float& lo, const float& hi){fVertZPos[0]=lo; fVertZPos[1]=hi;}
+inline int  AliFemtoEventCutEstimators::NEventsPassed() const {return fNEventsPassed;}
+inline int  AliFemtoEventCutEstimators::NEventsFailed() const {return fNEventsFailed;}
+inline AliFemtoEventCutEstimators* AliFemtoEventCutEstimators::Clone() { AliFemtoEventCutEstimators* c = new AliFemtoEventCutEstimators(*this); return c;}
+inline AliFemtoEventCutEstimators::AliFemtoEventCutEstimators(AliFemtoEventCutEstimators& c) : 
+  AliFemtoEventCut(c), 
+  fUseMultEst1(0), fUseMultEst2(0), fUseMultEst3(0), 
+  fUseCentEst1(0), fUseCentEst2(0), fUseCentEst3(0), fUseCentEst4(0),
+  fNEventsPassed(0), fNEventsFailed(0) {
+  fEventMultEst1[0] = c.fEventMultEst1[0];  fEventMultEst1[1] = c.fEventMultEst1[1];
+  fEventMultEst2[0] = c.fEventMultEst2[0];  fEventMultEst2[1] = c.fEventMultEst2[1];
+  fEventMultEst3[0] = c.fEventMultEst3[0];  fEventMultEst3[1] = c.fEventMultEst3[1];
+  fEventCentEst1[0] = c.fEventCentEst1[0];  fEventCentEst1[1] = c.fEventCentEst1[1];
+  fEventCentEst2[0] = c.fEventCentEst2[0];  fEventCentEst2[1] = c.fEventCentEst2[1];
+  fEventCentEst3[0] = c.fEventCentEst3[0];  fEventCentEst3[1] = c.fEventCentEst3[1];
+  fEventCentEst4[0] = c.fEventCentEst4[0];  fEventCentEst4[1] = c.fEventCentEst4[1];
+  fVertZPos[0] = c.fVertZPos[0];
+  fVertZPos[1] = c.fVertZPos[1];
+}
+
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReader.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReader.cxx
new file mode 100644 (file)
index 0000000..8caa5ab
--- /dev/null
@@ -0,0 +1,124 @@
+////////////////////////////////////////////////////////////////////////////////
+///                                                                          ///
+/// AliFemtoEventReader - the pure virtual base class for the event reader   ///
+/// All event readers must inherit from this one                             ///
+///                                                                          ///
+////////////////////////////////////////////////////////////////////////////////
+#include "AliFemtoEvent.h"
+#include "AliFemtoEventCut.h"
+#include "AliFemtoTrackCut.h"
+#include "AliFemtoV0Cut.h"
+#include "AliFemtoXiCut.h"
+#include "AliFemtoKinkCut.h"
+#include "AliFemtoEventReader.h"
+
+#ifdef __ROOT__
+ClassImp(AliFemtoEventReader)
+#endif
+
+AliFemtoEventReader::AliFemtoEventReader(const AliFemtoEventReader& aReader):
+  fEventCut(0),  
+  fTrackCut(0),    
+  fV0Cut(0),       
+  fXiCut(0),       
+  fKinkCut(0),    
+  fReaderStatus(0),  
+  fDebug(0)
+{
+  // Copy constructor
+  fEventCut = aReader.fEventCut;
+  fTrackCut = aReader.fTrackCut;
+  fV0Cut    = aReader.fV0Cut;
+  fXiCut    = aReader.fXiCut;
+  fKinkCut  = aReader.fKinkCut;
+  fReaderStatus = aReader.fReaderStatus;
+  fDebug = aReader.fDebug;
+}
+
+AliFemtoEventReader& AliFemtoEventReader::operator=(const AliFemtoEventReader& aReader)
+{
+  // Assignment operator
+  if (this == &aReader) 
+    return *this;
+
+  fEventCut = aReader.fEventCut;
+  fTrackCut = aReader.fTrackCut;
+  fV0Cut    = aReader.fV0Cut;
+  fXiCut    = aReader.fXiCut;
+  fKinkCut  = aReader.fKinkCut;
+  fReaderStatus = aReader.fReaderStatus;
+  fDebug = aReader.fDebug;
+
+  return *this;
+}
+
+
+AliFemtoString AliFemtoEventReader::Report(){
+  // Create a simple report from the workings of the reader
+  AliFemtoString temp = "\n This is the base class AliFemtoEventReader reporting";
+  temp += "\n---> EventCuts in Reader: ";
+  if (fEventCut) {
+    temp += fEventCut->Report();
+  }
+  else {
+    temp += "NONE";
+  }
+  temp += "\n---> TrackCuts in Reader: ";
+  if (fTrackCut) {
+    temp += fTrackCut->Report();
+  }
+  else {
+    temp += "NONE";
+  }
+  temp += "\n---> V0Cuts in Reader: ";
+  if (fV0Cut) {
+    temp += fV0Cut->Report();
+  }
+  else {
+    temp += "NONE";
+  }
+  temp += "\n---> XiCuts in Reader: ";
+  if (fXiCut) {
+    temp += fXiCut->Report();
+  }
+  else {
+    temp += "NONE";
+  }
+  temp += "\n---> KinkCuts in Reader: ";
+  if (fKinkCut) {
+    temp += fKinkCut->Report();
+  }
+  else {
+    temp += "NONE";
+  }
+  temp += "\n";
+  return temp;
+}
+//______________________________________
+void AliFemtoEventReader::SetEventCut(AliFemtoEventCut* ecut){fEventCut=ecut;}
+//______________________________________
+void AliFemtoEventReader::SetTrackCut(AliFemtoTrackCut* pcut){cout << pcut << endl; fTrackCut=pcut;}
+//______________________________________
+void AliFemtoEventReader::SetV0Cut(AliFemtoV0Cut* pcut){fV0Cut=pcut;}
+//______________________________________
+void AliFemtoEventReader::SetXiCut(AliFemtoXiCut* pcut){fXiCut=pcut;}
+//______________________________________
+void AliFemtoEventReader::SetKinkCut(AliFemtoKinkCut* pcut){fKinkCut=pcut;}
+//______________________________________
+AliFemtoEventCut* AliFemtoEventReader::EventCut(){return fEventCut;}
+//______________________________________
+AliFemtoTrackCut* AliFemtoEventReader::TrackCut(){return fTrackCut;}
+//______________________________________
+AliFemtoV0Cut*    AliFemtoEventReader::V0Cut(){return fV0Cut;} 
+//______________________________________
+AliFemtoXiCut*    AliFemtoEventReader::XiCut(){return fXiCut;} 
+//______________________________________
+AliFemtoKinkCut*    AliFemtoEventReader::KinkCut(){return fKinkCut;}
+//______________________________________
+int AliFemtoEventReader::Init(const char* /* ReadWrite */, AliFemtoString& /* Message */)
+{
+  cout << "do-nothing AliFemtoEventReader::Init()\n"; 
+  return(0);
+}
+
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReader.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReader.h
new file mode 100644 (file)
index 0000000..d90b90a
--- /dev/null
@@ -0,0 +1,82 @@
+////////////////////////////////////////////////////////////////////////////////
+/// AliFemtoEventReader - the pure virtual base class for the event reader   ///
+/// All event readers must inherit from this one                             ///
+////////////////////////////////////////////////////////////////////////////////
+#ifndef ALIFEMTOEVENTREADER_H
+#define ALIFEMTOEVENTREADER_H
+
+class AliFemtoEvent;
+class AliFemtoEventCut;
+class AliFemtoTrackCut;
+class AliFemtoV0Cut;
+class AliFemtoXiCut;
+class AliFemtoKinkCut;
+
+#include "AliFemtoString.h"
+#include <iostream>
+#include <fstream>
+#include <stdio.h>
+
+using namespace std;
+
+class AliFemtoEventReader {
+  
+ public:
+  // even tho it's only a base class and never constructed, if you don't have an implementation,
+  // you get "AliFemtoEventReader type_info node" upon dynamical loading
+  AliFemtoEventReader() : fEventCut(0), fTrackCut(0), fV0Cut(0), fXiCut(0), fKinkCut(0), fReaderStatus(0), fDebug(1) { /* no-op */ };
+  AliFemtoEventReader(const AliFemtoEventReader& aReader);
+  virtual ~AliFemtoEventReader(){/* no-op */}
+  
+  AliFemtoEventReader& operator=(const AliFemtoEventReader& aReader);
+  
+  virtual AliFemtoEvent* ReturnHbtEvent() =0;
+
+  virtual AliFemtoString Report();    // user-written method to return string describing reader
+                                      // Including whatever "early" cuts are being done
+
+  // this next method does NOT need to be implemented, in which case the 
+  // "default" method below is executed
+  virtual int WriteHbtEvent(AliFemtoEvent*){cout << "No WriteHbtEvent implemented\n"; return (0);}
+
+  // these next two are optional but would make sense for, e.g., opening and closing a file
+  virtual int Init(const char* ReadWrite, AliFemtoString& Message);
+  virtual void Finish(){/*no-op*/};
+  
+  int Status() const {return fReaderStatus;} // AliFemtoManager looks at this for guidance if it gets null pointer from ReturnHbtEvent
+
+  virtual void SetEventCut(AliFemtoEventCut* ecut);
+  virtual void SetTrackCut(AliFemtoTrackCut* pcut);
+  virtual void SetV0Cut(AliFemtoV0Cut* pcut);
+  virtual void SetXiCut(AliFemtoXiCut* pcut);
+  virtual void SetKinkCut(AliFemtoKinkCut* pcut);
+  virtual AliFemtoEventCut* EventCut();
+  virtual AliFemtoTrackCut* TrackCut();
+  virtual AliFemtoV0Cut*    V0Cut();
+  virtual AliFemtoXiCut*    XiCut();
+  virtual AliFemtoKinkCut*    KinkCut();
+
+  /* control of debug informations print out, my rule is: */
+  /* 0: no output at all                                  */
+  /* 1: once (e.g. in constructor, finsh                  */
+  /* 2: once per event                                    */
+  /* 3: once per track                                    */
+  /* 4: once per pair                                     */
+  int Debug() const {return fDebug;} 
+  void SetDebug(int d){fDebug=d;}
+
+protected:
+  AliFemtoEventCut* fEventCut;     //! link to the front-loaded event cut
+  AliFemtoTrackCut* fTrackCut;     //! link to the front-loaded track cut
+  AliFemtoV0Cut* fV0Cut;           //! link to the front-loaded V0 cut
+  AliFemtoXiCut* fXiCut;           //! link to the front-loaded Xi cut
+  AliFemtoKinkCut* fKinkCut;       //! link to the front-loaded Kink cut
+  int fReaderStatus;               // 0="good"
+  int fDebug;                      // Debug information level
+#ifdef __ROOT__
+  ClassDef(AliFemtoEventReader,0)
+#endif
+};
+
+#endif
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReaderAOD.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReaderAOD.cxx
new file mode 100644 (file)
index 0000000..0b0e4f5
--- /dev/null
@@ -0,0 +1,866 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoEventReaderAOD - the reader class for the Alice AOD                //
+// Reads in AOD information and converts it into internal AliFemtoEvent       //
+// Authors: Marek Chojnacki mchojnacki@knf.pw.edu.pl                          //
+//          Adam Kisiel kisiel@mps.ohio-state.edu                             //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+
+#include "AliFemtoEventReaderAOD.h"
+
+#include "TFile.h"
+#include "TTree.h"
+#include "AliAODEvent.h"
+#include "AliAODTrack.h"
+#include "AliAODVertex.h"
+#include "AliAODMCHeader.h"
+#include "AliESDtrack.h"
+
+#include "AliFmPhysicalHelixD.h"
+#include "AliFmThreeVectorF.h"
+
+#include "SystemOfUnits.h"
+
+#include "AliFemtoEvent.h"
+#include "AliFemtoModelHiddenInfo.h"
+#include "AliFemtoModelGlobalHiddenInfo.h"
+#include "AliPID.h"
+
+#include "AliAODpidUtil.h"
+
+ClassImp(AliFemtoEventReaderAOD)
+
+#if !(ST_NO_NAMESPACES)
+  using namespace units;
+#endif
+
+using namespace std;
+//____________________________
+//constructor with 0 parameters , look at default settings 
+AliFemtoEventReaderAOD::AliFemtoEventReaderAOD():
+  fNumberofEvent(0),
+  fCurEvent(0),
+  fEvent(0x0),
+  fAllTrue(160),
+  fAllFalse(160),
+  fFilterBit(0),
+  //  fPWG2AODTracks(0x0),
+  fReadMC(0),
+  fUsePreCent(0),
+  fAODpidUtil(0),
+  fInputFile(" "),
+  fFileName(" "),
+  fTree(0x0),
+  fAodFile(0x0)
+{
+  // default constructor
+  fAllTrue.ResetAllBits(kTRUE);
+  fAllFalse.ResetAllBits(kFALSE);
+  fCentRange[0] = 0;
+  fCentRange[1] = 1000;
+}
+
+AliFemtoEventReaderAOD::AliFemtoEventReaderAOD(const AliFemtoEventReaderAOD &aReader) :
+  AliFemtoEventReader(),
+  fNumberofEvent(0),
+  fCurEvent(0),
+  fEvent(0x0),
+  fAllTrue(160),
+  fAllFalse(160),
+  fFilterBit(0),
+  //  fPWG2AODTracks(0x0),
+  fReadMC(0),
+  fUsePreCent(0),
+  fAODpidUtil(0),
+  fInputFile(" "),
+  fFileName(" "),
+  fTree(0x0),
+  fAodFile(0x0)
+{
+  // copy constructor
+  fInputFile = aReader.fInputFile;
+  fFileName  = aReader.fFileName;
+  fNumberofEvent = aReader.fNumberofEvent;
+  fCurEvent = aReader.fCurEvent;
+  fEvent = new AliAODEvent();
+  fAodFile = new TFile(aReader.fAodFile->GetName());
+  fAllTrue.ResetAllBits(kTRUE);
+  fAllFalse.ResetAllBits(kFALSE);
+  fFilterBit = aReader.fFilterBit;
+  //  fPWG2AODTracks = aReader.fPWG2AODTracks;
+  fAODpidUtil = aReader.fAODpidUtil;
+  fCentRange[0] = aReader.fCentRange[0];
+  fCentRange[1] = aReader.fCentRange[1];
+}
+//__________________
+//Destructor
+AliFemtoEventReaderAOD::~AliFemtoEventReaderAOD()
+{
+  // destructor
+  delete fTree;
+  delete fEvent;
+  delete fAodFile;
+//   if (fPWG2AODTracks) {
+//     fPWG2AODTracks->Delete();
+//     delete fPWG2AODTracks;
+//   }
+}
+
+//__________________
+AliFemtoEventReaderAOD& AliFemtoEventReaderAOD::operator=(const AliFemtoEventReaderAOD& aReader)
+{
+  // assignment operator
+  if (this == &aReader)
+    return *this;
+
+  fInputFile = aReader.fInputFile;
+  fFileName  = aReader.fFileName;
+  fNumberofEvent = aReader.fNumberofEvent;
+  fCurEvent = aReader.fCurEvent;
+  if (fTree) delete fTree;
+  if (fEvent) delete fEvent;
+  fEvent = new AliAODEvent();
+  if (fAodFile) delete fAodFile;
+  fAodFile = new TFile(aReader.fAodFile->GetName());
+  fAllTrue.ResetAllBits(kTRUE);
+  fAllFalse.ResetAllBits(kFALSE);
+  fFilterBit = aReader.fFilterBit;
+  //  fPWG2AODTracks = aReader.fPWG2AODTracks;
+  fAODpidUtil = aReader.fAODpidUtil;
+  fCentRange[0] = aReader.fCentRange[0];
+  fCentRange[1] = aReader.fCentRange[1];
+
+  return *this;
+}
+//__________________
+AliFemtoString AliFemtoEventReaderAOD::Report()
+{
+  // create reader report
+  AliFemtoString temp = "\n This is the AliFemtoEventReaderAOD\n";
+  return temp;
+}
+
+//__________________
+void AliFemtoEventReaderAOD::SetInputFile(const char* inputFile)
+{
+  //setting the name of file where names of AOD file are written 
+  //it takes only this files which have good trees
+  char buffer[256];
+  fInputFile=string(inputFile);
+  ifstream infile(inputFile);
+
+  fTree = new TChain("aodTree");
+
+  if(infile.good()==true)
+    { 
+      //checking if all give files have good tree inside
+      while (infile.eof()==false)
+       {
+         infile.getline(buffer,256);
+         TFile *aodFile=TFile::Open(buffer,"READ");
+         if (aodFile!=0x0)
+           {   
+             TTree* tree = (TTree*) aodFile->Get("aodTree");
+             if (tree!=0x0)
+               {
+                 //              cout<<"putting file  "<<string(buffer)<<" into analysis"<<endl;
+                 fTree->AddFile(buffer);
+                 delete tree;
+               }
+             aodFile->Close(); 
+           }
+         delete aodFile;
+       }
+    }
+}
+
+AliFemtoEvent* AliFemtoEventReaderAOD::ReturnHbtEvent()
+{
+  // read in a next hbt event from the chain
+  // convert it to AliFemtoEvent and return
+  // for further analysis
+  AliFemtoEvent *hbtEvent = 0;
+  cout<<"reader"<<endl;
+  if (fCurEvent==fNumberofEvent)//open next file  
+    {
+      if(fNumberofEvent==0)    
+       {
+         fEvent=new AliAODEvent();
+         fEvent->ReadFromTree(fTree);
+
+         // Check for the existence of the additional information
+//       fPWG2AODTracks = (TClonesArray *) fEvent->GetList()->FindObject("pwg2aodtracks");
+
+//       if (fPWG2AODTracks) {
+//         cout << "Found additional PWG2 specific information in the AOD!" << endl;
+//         cout << "Reading only tracks with the additional information" << endl;
+//       }
+
+         fNumberofEvent=fTree->GetEntries();
+         //      cout<<"Number of Entries in file "<<fNumberofEvent<<endl;
+         fCurEvent=0;
+       }
+      else //no more data to read
+       {
+         cout<<"no more files "<<hbtEvent<<endl;
+         fReaderStatus=1;
+         return hbtEvent; 
+       }
+    }          
+
+  cout<<"starting to read event "<<fCurEvent<<endl;
+  fTree->GetEvent(fCurEvent);//getting next event
+  //  cout << "Read event " << fEvent << " from file " << fTree << endl;
+       
+  hbtEvent = new AliFemtoEvent;
+
+  CopyAODtoFemtoEvent(hbtEvent);
+  fCurEvent++;
+
+
+  return hbtEvent; 
+}
+
+void AliFemtoEventReaderAOD::CopyAODtoFemtoEvent(AliFemtoEvent *tEvent)
+{
+
+  // A function that reads in the AOD event
+  // and transfers the neccessary information into
+  // the internal AliFemtoEvent
+
+  // setting global event characteristics
+  tEvent->SetRunNumber(fEvent->GetRunNumber());
+  tEvent->SetMagneticField(fEvent->GetMagneticField()*kilogauss);//to check if here is ok
+  tEvent->SetZDCN1Energy(fEvent->GetZDCN1Energy());
+  tEvent->SetZDCP1Energy(fEvent->GetZDCP1Energy());
+  tEvent->SetZDCN2Energy(fEvent->GetZDCN2Energy());
+  tEvent->SetZDCP2Energy(fEvent->GetZDCP2Energy());
+  tEvent->SetZDCEMEnergy(fEvent->GetZDCEMEnergy(0));
+  tEvent->SetZDCParticipants(0);
+  tEvent->SetTriggerMask(fEvent->GetTriggerMask());
+  tEvent->SetTriggerCluster(fEvent->GetTriggerCluster());
+  
+  // Attempt to access MC header
+  AliAODMCHeader *mcH;
+  TClonesArray *mcP=0;
+  if (fReadMC) {
+    mcH = (AliAODMCHeader *) fEvent->FindListObject(AliAODMCHeader::StdBranchName());
+    if (!mcH) {
+      cout << "AOD MC information requested, but no header found!" << endl;
+    }
+
+    mcP = (TClonesArray *) fEvent->FindListObject(AliAODMCParticle::StdBranchName());
+    if (!mcP) {
+      cout << "AOD MC information requested, but no particle array found!" << endl;
+    }
+  }
+
+  tEvent->SetReactionPlaneAngle(fEvent->GetHeader()->GetQTheta(0)/2.0);
+
+  Int_t *motherids=0;
+  if (mcP) {
+    motherids = new Int_t[((AliAODMCParticle *) mcP->At(mcP->GetEntries()-1))->GetLabel()];
+    for (int ip=0; ip<mcP->GetEntries(); ip++) motherids[ip] = 0;
+
+    // Read in mother ids
+    AliAODMCParticle *motherpart;
+    for (int ip=0; ip<mcP->GetEntries(); ip++) {
+      motherpart = (AliAODMCParticle *) mcP->At(ip);
+      if (motherpart->GetDaughter(0) > 0)
+       motherids[motherpart->GetDaughter(0)] = ip;
+      if (motherpart->GetDaughter(1) > 0)
+       motherids[motherpart->GetDaughter(1)] = ip;
+    }
+  }
+
+  // Primary Vertex position
+  double fV1[3];
+  fEvent->GetPrimaryVertex()->GetPosition(fV1);
+
+  AliFmThreeVectorF vertex(fV1[0],fV1[1],fV1[2]);
+  tEvent->SetPrimVertPos(vertex);
+       
+  //starting to reading tracks
+  int nofTracks=0;  //number of reconstructed tracks in event
+
+  // Check to see whether the additional info exists
+//   if (fPWG2AODTracks)
+//     nofTracks=fPWG2AODTracks->GetEntries();
+//   else
+    nofTracks=fEvent->GetNumberOfTracks();
+  cout<<"nofTracks: "<<nofTracks<<endl;
+
+  AliCentrality *cent = fEvent->GetCentrality();
+  if (cent && fUsePreCent) {
+    if ((cent->GetCentralityPercentile("V0M")*10 < fCentRange[0]) ||
+       (cent->GetCentralityPercentile("V0M")*10 > fCentRange[1]))
+      {
+       cout << "Centrality " << cent->GetCentralityPercentile("V0M") << " outside of preselection range " << fCentRange[0] << " - " << fCentRange[1] << endl;
+       
+       return;
+      }
+  }
+
+  int realnofTracks=0;   // number of track which we use in a analysis
+  int tracksPrim=0;     
+
+  int labels[20000];   
+  for (int il=0; il<20000; il++) labels[il] = -1;
+
+  // looking for global tracks and saving their numbers to copy from them PID information to TPC-only tracks in the main loop over tracks
+  for (int i=0;i<nofTracks;i++) {
+    const AliAODTrack *aodtrack=fEvent->GetTrack(i);
+    if (!aodtrack->TestFilterBit(fFilterBit)) {
+      labels[aodtrack->GetID()] = i;
+    }
+  }
+
+  //  int tNormMult = 0;
+  for (int i=0;i<nofTracks;i++)
+    {
+      AliFemtoTrack* trackCopy = new AliFemtoTrack();  
+
+//       if (fPWG2AODTracks) {
+//     // Read tracks from the additional pwg2 specific AOD part
+//     // if they exist
+//     // Note that in that case all the AOD tracks without the 
+//     // additional information will be ignored !
+//     AliPWG2AODTrack *pwg2aodtrack = (AliPWG2AODTrack *) fPWG2AODTracks->At(i);
+
+//     // Getting the AOD track through the ref of the additional info
+//     AliAODTrack *aodtrack = pwg2aodtrack->GetRefAODTrack(); 
+//     if (!aodtrack->TestFilterBit(fFilterBit)) {
+//       delete trackCopy;
+//       continue;
+//     }
+
+//     if (aodtrack->IsOn(AliESDtrack::kTPCrefit))
+//       if (aodtrack->Chi2perNDF() < 6.0) 
+//         if (aodtrack->Eta() < 0.9)
+//           tNormMult++;
+
+
+//     CopyAODtoFemtoTrack(aodtrack, trackCopy, pwg2aodtrack);
+       
+//     if (mcP) {
+//       // Fill the hidden information with the simulated data
+//       //      Int_t pLabel = aodtrack->GetLabel();
+//       AliAODMCParticle *tPart = GetParticleWithLabel(mcP, (TMath::Abs(aodtrack->GetLabel())));
+
+//       // Check the mother information
+         
+//       // Using the new way of storing the freeze-out information
+//       // Final state particle is stored twice on the stack
+//       // one copy (mother) is stored with original freeze-out information
+//       //   and is not tracked
+//       // the other one (daughter) is stored with primary vertex position
+//       //   and is tracked
+         
+//       // Freeze-out coordinates
+//       double fpx=0.0, fpy=0.0, fpz=0.0, fpt=0.0;
+//       fpx = tPart->Xv() - fV1[0];
+//       fpy = tPart->Yv() - fV1[1];
+//       fpz = tPart->Zv() - fV1[2];
+//       fpt = tPart->T();
+
+//       AliFemtoModelGlobalHiddenInfo *tInfo = new AliFemtoModelGlobalHiddenInfo();
+//       tInfo->SetGlobalEmissionPoint(fpx, fpy, fpz);
+
+//       fpx *= 1e13;
+//       fpy *= 1e13;
+//       fpz *= 1e13;
+//       fpt *= 1e13;
+         
+//       //      cout << "Looking for mother ids " << endl;
+//       if (motherids[TMath::Abs(aodtrack->GetLabel())]>0) {
+//         //  cout << "Got mother id" << endl;
+//         AliAODMCParticle *mother = GetParticleWithLabel(mcP, motherids[TMath::Abs(aodtrack->GetLabel())]);
+//         // Check if this is the same particle stored twice on the stack
+//         if ((mother->GetPdgCode() == tPart->GetPdgCode() || (mother->Px() == tPart->Px()))) {
+//           // It is the same particle
+//           // Read in the original freeze-out information
+//           // and convert it from to [fm]
+             
+//           // EPOS style 
+//           //          fpx = mother->Xv()*1e13*0.197327;
+//           //          fpy = mother->Yv()*1e13*0.197327;
+//           //          fpz = mother->Zv()*1e13*0.197327;
+//           //          fpt = mother->T() *1e13*0.197327*0.5;
+             
+             
+//           // Therminator style 
+//           fpx = mother->Xv()*1e13;
+//           fpy = mother->Yv()*1e13;
+//           fpz = mother->Zv()*1e13;
+//           fpt = mother->T() *1e13*3e10;
+             
+//         }
+//       }
+         
+//       //       if (fRotateToEventPlane) {
+//       //    double tPhi = TMath::ATan2(fpy, fpx);
+//       //    double tRad = TMath::Hypot(fpx, fpy);
+       
+//       //    fpx = tRad*TMath::Cos(tPhi - tReactionPlane);
+//       //    fpy = tRad*TMath::Sin(tPhi - tReactionPlane);
+//       //       }
+
+//       tInfo->SetPDGPid(tPart->GetPdgCode());
+
+//       //      if (fRotateToEventPlane) {
+//       //        double tPhi = TMath::ATan2(tPart->Py(), tPart->Px());
+//       //        double tRad = TMath::Hypot(tPart->Px(), tPart->Py());
+           
+//       //        tInfo->SetTrueMomentum(tRad*TMath::Cos(tPhi - tReactionPlane),
+//       //                               tRad*TMath::Sin(tPhi - tReactionPlane),
+//       //                               tPart->Pz());
+//       //      }
+//       //       else
+//       tInfo->SetTrueMomentum(tPart->Px(), tPart->Py(), tPart->Pz());
+//       Double_t mass2 = (tPart->E() *tPart->E() -
+//                         tPart->Px()*tPart->Px() -
+//                         tPart->Py()*tPart->Py() -
+//                         tPart->Pz()*tPart->Pz());
+//       if (mass2>0.0)
+//         tInfo->SetMass(TMath::Sqrt(mass2));
+//       else 
+//         tInfo->SetMass(0.0);
+         
+//       tInfo->SetEmissionPoint(fpx, fpy, fpz, fpt);
+//       trackCopy->SetHiddenInfo(tInfo);
+
+//     }
+
+//     double pxyz[3];
+//     aodtrack->PxPyPz(pxyz);//reading noconstarined momentum
+//     const AliFmThreeVectorD ktP(pxyz[0],pxyz[1],pxyz[2]);
+//     // Check the sanity of the tracks - reject zero momentum tracks
+//     if (ktP.Mag() == 0) {
+//       delete trackCopy;
+//       continue;
+//     }
+//       }
+//       else {
+       // No additional information exists
+       // Read in the normal AliAODTracks 
+
+       //      const AliAODTrack *aodtrack=fEvent->GetTrack(i); // getting the AODtrack directly
+       AliAODTrack *aodtrack=fEvent->GetTrack(i); // getting the AODtrack directly
+
+       if (aodtrack->IsPrimaryCandidate()) tracksPrim++;
+       
+       if (!aodtrack->TestFilterBit(fFilterBit)) {
+         delete trackCopy;
+         continue;
+       }
+
+       CopyAODtoFemtoTrack(aodtrack, trackCopy);
+
+       // copying PID information from the correspondent track
+       //      const AliAODTrack *aodtrackpid = fEvent->GetTrack(labels[-1-fEvent->GetTrack(i)->GetID()]);
+       AliAODTrack *aodtrackpid = fEvent->GetTrack(labels[-1-fEvent->GetTrack(i)->GetID()]);
+       CopyPIDtoFemtoTrack(aodtrackpid, trackCopy);
+               
+       if (mcP) {
+         // Fill the hidden information with the simulated data
+         //      Int_t pLabel = aodtrack->GetLabel();
+         AliAODMCParticle *tPart = GetParticleWithLabel(mcP, (TMath::Abs(aodtrack->GetLabel())));
+         
+         AliFemtoModelGlobalHiddenInfo *tInfo = new AliFemtoModelGlobalHiddenInfo();
+         double fpx=0.0, fpy=0.0, fpz=0.0, fpt=0.0;
+         if (!tPart) {
+           fpx = fV1[0];
+           fpy = fV1[1];
+           fpz = fV1[2];
+           tInfo->SetGlobalEmissionPoint(fpx, fpy, fpz);
+           tInfo->SetPDGPid(0);
+           tInfo->SetTrueMomentum(0.0, 0.0, 0.0);
+           tInfo->SetEmissionPoint(0.0, 0.0, 0.0, 0.0);
+           tInfo->SetMass(0);
+         }
+         else {
+           // Check the mother information
+         
+           // Using the new way of storing the freeze-out information
+           // Final state particle is stored twice on the stack
+           // one copy (mother) is stored with original freeze-out information
+           //   and is not tracked
+           // the other one (daughter) is stored with primary vertex position
+           //   and is tracked
+           
+           // Freeze-out coordinates
+           fpx = tPart->Xv() - fV1[0];
+           fpy = tPart->Yv() - fV1[1];
+           fpz = tPart->Zv() - fV1[2];
+           //    fpt = tPart->T();
+           
+           tInfo->SetGlobalEmissionPoint(fpx, fpy, fpz);
+           
+           fpx *= 1e13;
+           fpy *= 1e13;
+           fpz *= 1e13;
+           //    fpt *= 1e13;
+           
+           //      cout << "Looking for mother ids " << endl;
+           if (motherids[TMath::Abs(aodtrack->GetLabel())]>0) {
+             //        cout << "Got mother id" << endl;
+             AliAODMCParticle *mother = GetParticleWithLabel(mcP, motherids[TMath::Abs(aodtrack->GetLabel())]);
+             // Check if this is the same particle stored twice on the stack
+             if (mother) {
+               if ((mother->GetPdgCode() == tPart->GetPdgCode() || (mother->Px() == tPart->Px()))) {
+                 // It is the same particle
+                 // Read in the original freeze-out information
+                 // and convert it from to [fm]
+                 
+                 // EPOS style 
+                 //      fpx = mother->Xv()*1e13*0.197327;
+                 //      fpy = mother->Yv()*1e13*0.197327;
+                 //      fpz = mother->Zv()*1e13*0.197327;
+                 //      fpt = mother->T() *1e13*0.197327*0.5;
+                 
+                 
+                 // Therminator style 
+                 fpx = mother->Xv()*1e13;
+                 fpy = mother->Yv()*1e13;
+                 fpz = mother->Zv()*1e13;
+                 //          fpt = mother->T() *1e13*3e10;
+                 
+               }
+             }
+           }
+           
+           //       if (fRotateToEventPlane) {
+           //  double tPhi = TMath::ATan2(fpy, fpx);
+           //  double tRad = TMath::Hypot(fpx, fpy);
+           
+           //  fpx = tRad*TMath::Cos(tPhi - tReactionPlane);
+           //  fpy = tRad*TMath::Sin(tPhi - tReactionPlane);
+           //       }
+           
+           tInfo->SetPDGPid(tPart->GetPdgCode());
+           
+           //    if (fRotateToEventPlane) {
+           //      double tPhi = TMath::ATan2(tPart->Py(), tPart->Px());
+           //      double tRad = TMath::Hypot(tPart->Px(), tPart->Py());
+           
+           //      tInfo->SetTrueMomentum(tRad*TMath::Cos(tPhi - tReactionPlane),
+           //                             tRad*TMath::Sin(tPhi - tReactionPlane),
+           //                             tPart->Pz());
+           //    }
+           //       else
+           tInfo->SetTrueMomentum(tPart->Px(), tPart->Py(), tPart->Pz());
+           Double_t mass2 = (tPart->E() *tPart->E() -
+                             tPart->Px()*tPart->Px() -
+                             tPart->Py()*tPart->Py() -
+                             tPart->Pz()*tPart->Pz());
+           if (mass2>0.0)
+             tInfo->SetMass(TMath::Sqrt(mass2));
+           else 
+             tInfo->SetMass(0.0);
+           
+           tInfo->SetEmissionPoint(fpx, fpy, fpz, fpt);
+         }
+         trackCopy->SetHiddenInfo(tInfo);
+       }
+
+       double pxyz[3];
+       aodtrack->PxPyPz(pxyz);//reading noconstarined momentum
+       const AliFmThreeVectorD ktP(pxyz[0],pxyz[1],pxyz[2]);
+       // Check the sanity of the tracks - reject zero momentum tracks
+       if (ktP.Mag() == 0) {
+         delete trackCopy;
+         continue;
+       }
+       //    }
+  
+  
+       tEvent->TrackCollection()->push_back(trackCopy);//adding track to analysis
+       realnofTracks++;//real number of tracks         
+    }
+  
+  tEvent->SetNumberOfTracks(realnofTracks);//setting number of track which we read in event    
+  tEvent->SetNormalizedMult(tracksPrim);
+
+  //  AliCentrality *cent = fEvent->GetCentrality();
+  if (cent) tEvent->SetNormalizedMult(lrint(10*cent->GetCentralityPercentile("V0M")));
+  //  if (cent) tEvent->SetNormalizedMult((int) cent->GetCentralityPercentile("V0M"));
+
+  if (cent) {
+    tEvent->SetCentralityV0(cent->GetCentralityPercentile("V0M"));
+    //    tEvent->SetCentralityFMD(cent->GetCentralityPercentile("FMD"));
+    tEvent->SetCentralitySPD1(cent->GetCentralityPercentile("CL1"));
+    //    tEvent->SetCentralityTrk(cent->GetCentralityPercentile("TRK"));
+  }
+  
+
+  if (mcP) delete [] motherids;
+
+  cout<<"end of reading nt "<<nofTracks<<" real number "<<realnofTracks<<endl;
+}
+
+void AliFemtoEventReaderAOD::CopyAODtoFemtoTrack(AliAODTrack *tAodTrack, 
+                                                AliFemtoTrack *tFemtoTrack 
+                                                //                                              AliPWG2AODTrack *tPWG2AODTrack
+                                                )
+{
+  // Copy the track information from the AOD into the internal AliFemtoTrack
+  // If it exists, use the additional information from the PWG2 AOD
+
+  // Primary Vertex position
+  double fV1[3];
+  fEvent->GetPrimaryVertex()->GetPosition(fV1);
+  //  fEvent->GetPrimaryVertex()->GetXYZ(fV1);
+
+  tFemtoTrack->SetCharge(tAodTrack->Charge());
+  
+  double pxyz[3];
+  tAodTrack->PxPyPz(pxyz);//reading noconstrained momentum
+  AliFemtoThreeVector v(pxyz[0],pxyz[1],pxyz[2]);
+  tFemtoTrack->SetP(v);//setting momentum
+  tFemtoTrack->SetPt(sqrt(pxyz[0]*pxyz[0]+pxyz[1]*pxyz[1]));
+  const AliFmThreeVectorD kOrigin(fV1[0],fV1[1],fV1[2]);
+  //setting track helix 
+  const AliFmThreeVectorD ktP(pxyz[0],pxyz[1],pxyz[2]);
+  AliFmPhysicalHelixD helix(ktP,kOrigin,(double)(fEvent->GetMagneticField())*kilogauss,(double)(tFemtoTrack->Charge())); 
+  tFemtoTrack->SetHelix(helix);
+               
+  // Flags
+  tFemtoTrack->SetTrackId(tAodTrack->GetID());
+  tFemtoTrack->SetFlags(tAodTrack->GetFlags());
+  tFemtoTrack->SetLabel(tAodTrack->GetLabel());
+               
+  // Track quality information 
+  float covmat[6];
+  tAodTrack->GetCovMatrix(covmat);  
+
+  double impact[2];
+  double covimpact[3];
+  
+  if (!tAodTrack->PropagateToDCA(fEvent->GetPrimaryVertex(),fEvent->GetMagneticField(),10000,impact,covimpact)) {
+    //cout << "sth went wrong with dca propagation" << endl;
+    tFemtoTrack->SetImpactD(-1000.0);
+    tFemtoTrack->SetImpactZ(-1000.0);
+
+  } 
+  else {
+    tFemtoTrack->SetImpactD(impact[0]);
+    tFemtoTrack->SetImpactZ(impact[1]);
+  }
+
+  //   if (TMath::Abs(tAodTrack->Xv()) > 0.00000000001)
+  //     tFemtoTrack->SetImpactD(TMath::Hypot(tAodTrack->Xv(), tAodTrack->Yv())*(tAodTrack->Xv()/TMath::Abs(tAodTrack->Xv())));
+  //   else
+  //     tFemtoTrack->SetImpactD(0.0);
+  //   tFemtoTrack->SetImpactD(tAodTrack->DCA());
+    
+  //   tFemtoTrack->SetImpactZ(tAodTrack->ZAtDCA());
+
+
+  //   tFemtoTrack->SetImpactD(TMath::Hypot(tAodTrack->Xv() - fV1[0], tAodTrack->Yv() - fV1[1]));
+  //   tFemtoTrack->SetImpactZ(tAodTrack->Zv() - fV1[2]);
+
+
+  //   cout 
+    //    << "dca" << TMath::Hypot(tAodTrack->Xv() - fV1[0], tAodTrack->Yv() - fV1[1]) 
+    //    << "xv - fv10 = "<< tAodTrack->Xv() - fV1[0] 
+    //    << tAodTrack->Yv() - fV1[1] 
+//     << "xv = " << tAodTrack->Xv() << endl 
+//     << "fv1[0] = " << fV1[0]  << endl 
+//     << "yv = " << tAodTrack->Yv()  << endl 
+//     << "fv1[1] = " << fV1[1]  << endl 
+//     << "zv = " << tAodTrack->Zv()  << endl 
+//     << "fv1[2] = " << fV1[2]  << endl 
+//     << "impact[0] = " << impact[0]  << endl 
+//     << "impact[1] = " << impact[1]  << endl 
+//     << endl << endl ;
+
+  tFemtoTrack->SetCdd(covmat[0]);
+  tFemtoTrack->SetCdz(covmat[1]);
+  tFemtoTrack->SetCzz(covmat[2]);
+  tFemtoTrack->SetITSchi2(tAodTrack->Chi2perNDF());    
+  tFemtoTrack->SetITSncls(tAodTrack->GetITSNcls());     
+  tFemtoTrack->SetTPCchi2(tAodTrack->Chi2perNDF());       
+  tFemtoTrack->SetTPCncls(tAodTrack->GetTPCNcls());       
+  tFemtoTrack->SetTPCnclsF(tAodTrack->GetTPCNcls());      
+  tFemtoTrack->SetTPCsignalN(1); 
+  tFemtoTrack->SetTPCsignalS(1); 
+  tFemtoTrack->SetTPCsignal(tAodTrack->GetTPCsignal());
+
+//   if (tPWG2AODTrack) {
+//     // Copy the PWG2 specific information if it exists
+//     tFemtoTrack->SetTPCClusterMap(tPWG2AODTrack->GetTPCClusterMap());
+//     tFemtoTrack->SetTPCSharedMap(tPWG2AODTrack->GetTPCSharedMap());
+    
+//     double xtpc[3] = {0,0,0};
+//     tPWG2AODTrack->GetTPCNominalEntrancePoint(xtpc);
+//     tFemtoTrack->SetNominalTPCEntrancePoint(xtpc);
+//     tPWG2AODTrack->GetTPCNominalExitPoint(xtpc);
+//     tFemtoTrack->SetNominalTPCExitPoint(xtpc);
+//   }
+//   else {
+    // If not use dummy values
+  tFemtoTrack->SetTPCClusterMap(tAodTrack->GetTPCClusterMap());
+  tFemtoTrack->SetTPCSharedMap(tAodTrack->GetTPCSharedMap());
+  
+  double xtpc[3] = {0,0,0};
+  tFemtoTrack->SetNominalTPCEntrancePoint(xtpc);
+  tFemtoTrack->SetNominalTPCExitPoint(xtpc);
+  //   }
+  
+  //   //  cout << "Track has " << TMath::Hypot(tAodTrack->Xv(), tAodTrack->Yv()) << "  " << tAodTrack->Zv() << "  " << tAodTrack->GetTPCNcls() << endl;
+  
+  
+  int indexes[3];
+  for (int ik=0; ik<3; ik++) {
+    indexes[ik] = 0;
+  }
+  tFemtoTrack->SetKinkIndexes(indexes);
+}
+
+void AliFemtoEventReaderAOD::SetFilterBit(UInt_t ibit)
+{
+  fFilterBit = (1 << (ibit));
+}
+
+void AliFemtoEventReaderAOD::SetReadMC(unsigned char a)
+{
+  fReadMC = a;
+}
+
+AliAODMCParticle* AliFemtoEventReaderAOD::GetParticleWithLabel(TClonesArray *mcP, Int_t aLabel)
+{
+  if (aLabel < 0) return 0;
+  AliAODMCParticle *aodP;
+  Int_t posstack = 0;
+  if (aLabel > mcP->GetEntries())
+    posstack = mcP->GetEntries();
+  else
+    posstack = aLabel;
+
+  aodP = (AliAODMCParticle *) mcP->At(posstack);
+  if (aodP->GetLabel() > posstack) {
+    do {
+      aodP = (AliAODMCParticle *) mcP->At(posstack);
+      if (aodP->GetLabel() == aLabel) return aodP;
+      posstack--;
+    }
+    while (posstack > 0);
+  }
+  else {
+    do {
+      aodP = (AliAODMCParticle *) mcP->At(posstack);
+      if (aodP->GetLabel() == aLabel) return aodP;
+      posstack++;
+    }
+    while (posstack < mcP->GetEntries());
+  }
+  
+  return 0;
+}
+
+void AliFemtoEventReaderAOD::CopyPIDtoFemtoTrack(AliAODTrack *tAodTrack, 
+                                                AliFemtoTrack *tFemtoTrack)
+{
+  double aodpid[10];
+  tAodTrack->GetPID(aodpid);
+  tFemtoTrack->SetPidProbElectron(aodpid[0]);
+  tFemtoTrack->SetPidProbMuon(aodpid[1]);
+  tFemtoTrack->SetPidProbPion(aodpid[2]);
+  tFemtoTrack->SetPidProbKaon(aodpid[3]);
+  tFemtoTrack->SetPidProbProton(aodpid[4]);
+
+  aodpid[0] = -100000.0;
+  aodpid[1] = -100000.0;
+  aodpid[2] = -100000.0;
+  aodpid[3] = -100000.0;
+  aodpid[4] = -100000.0;
+               
+  double tTOF = 0.0;
+
+  if (tAodTrack->GetStatus() & AliESDtrack::kTOFpid) {  //AliESDtrack::kTOFpid=0x8000
+    tTOF = tAodTrack->GetTOFsignal();
+    tAodTrack->GetIntegratedTimes(aodpid);
+  }
+
+  tFemtoTrack->SetTofExpectedTimes(tTOF-aodpid[2], tTOF-aodpid[3], tTOF-aodpid[4]);
+  //////  TPC ////////////////////////////////////////////
+
+  float nsigmaTPCK=-1000.;                                                  
+  float nsigmaTPCPi=-1000.;                                                 
+  float nsigmaTPCP=-1000.;                                                  
+          
+  //   cout<<"in reader fESDpid"<<fESDpid<<endl;
+
+  if (tAodTrack->IsOn(AliESDtrack::kTPCpid)){ //AliESDtrack::kTPCpid=0x0080
+    nsigmaTPCK = fAODpidUtil->NumberOfSigmasTPC(tAodTrack,AliPID::kKaon);
+    nsigmaTPCPi = fAODpidUtil->NumberOfSigmasTPC(tAodTrack,AliPID::kPion);
+    nsigmaTPCP = fAODpidUtil->NumberOfSigmasTPC(tAodTrack,AliPID::kProton);
+  }
+
+  tFemtoTrack->SetNSigmaTPCPi(nsigmaTPCPi);
+  tFemtoTrack->SetNSigmaTPCK(nsigmaTPCK);
+  tFemtoTrack->SetNSigmaTPCP(nsigmaTPCP);
+
+  tFemtoTrack->SetTPCchi2(tAodTrack->Chi2perNDF());       
+  tFemtoTrack->SetTPCncls(tAodTrack->GetTPCNcls());       
+  tFemtoTrack->SetTPCnclsF(tAodTrack->GetTPCNcls());      
+  
+  tFemtoTrack->SetTPCsignalN(1); 
+  tFemtoTrack->SetTPCsignalS(1); 
+  tFemtoTrack->SetTPCsignal(tAodTrack->GetTPCsignal());
+  ///////TOF//////////////////////
+
+    float vp=-1000.;
+    float nsigmaTOFPi=-1000.;
+    float nsigmaTOFK=-1000.;
+    float nsigmaTOFP=-1000.;
+
+    if ((tAodTrack->GetStatus() & AliESDtrack::kTOFpid) && //AliESDtrack::kTOFpid=0x8000
+       (tAodTrack->GetStatus() & AliESDtrack::kTOFout) && //AliESDtrack::kTOFout=0x2000
+       (tAodTrack->GetStatus() & AliESDtrack::kTIME) && //AliESDtrack::kTIME=0x80000000
+       !(tAodTrack->GetStatus() & AliESDtrack::kTOFmismatch)) //AliESDtrack::kTOFmismatch=0x100000
+      {
+       if(tAodTrack->IsOn(AliESDtrack::kTOFpid)) //AliESDtrack::kTOFpid=0x8000
+         {
+
+           nsigmaTOFPi = fAODpidUtil->NumberOfSigmasTOF(tAodTrack,AliPID::kPion);
+           nsigmaTOFK = fAODpidUtil->NumberOfSigmasTOF(tAodTrack,AliPID::kKaon);
+           nsigmaTOFP = fAODpidUtil->NumberOfSigmasTOF(tAodTrack,AliPID::kProton);
+
+           Double_t len=200;// esdtrack->GetIntegratedLength(); !!!!!
+           Double_t tof=tAodTrack->GetTOFsignal();
+           if(tof > 0.) vp=len/tof/0.03;
+         }
+      }
+    tFemtoTrack->SetVTOF(vp);
+    tFemtoTrack->SetNSigmaTOFPi(nsigmaTOFPi);
+    tFemtoTrack->SetNSigmaTOFK(nsigmaTOFK);
+    tFemtoTrack->SetNSigmaTOFP(nsigmaTOFP);
+
+    
+    //////////////////////////////////////
+
+}
+
+void AliFemtoEventReaderAOD::SetCentralityPreSelection(double min, double max)
+{
+  fCentRange[0] = min; fCentRange[1] = max;
+  fUsePreCent = 1; 
+}
+
+
+void AliFemtoEventReaderAOD::SetAODpidUtil(AliAODpidUtil *aAODpidUtil)
+{
+  fAODpidUtil = aAODpidUtil;
+  //  printf("fAODpidUtil: %x\n",fAODpidUtil);
+}
+
+
+
+
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReaderAOD.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReaderAOD.h
new file mode 100644 (file)
index 0000000..0ab8727
--- /dev/null
@@ -0,0 +1,85 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoEventReaderAOD - the reader class for the Alice AOD                //
+// Reads in AOD information and converts it into internal AliFemtoEvent       //
+// Authors: Adam Kisiel kisiel@mps.ohio-state.edu                             //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+
+#ifndef ALIFEMTOEVENTREADERAOD_H
+#define ALIFEMTOEVENTREADERAOD_H
+#include "AliFemtoEventReader.h"
+#include "AliFemtoEnumeration.h"
+
+#include <string>
+#include <vector>
+#include "TTree.h"
+#include "TChain.h"
+#include "TBits.h"
+#include "AliAODEvent.h"
+#include <list>
+//#include "AliPWG2AODTrack.h"
+#include "AliAODMCParticle.h"
+
+#include "AliAODpidUtil.h"
+
+class AliFemtoEvent;
+class AliFemtoTrack;
+
+class AliFemtoEventReaderAOD : public AliFemtoEventReader 
+{
+ public:
+  AliFemtoEventReaderAOD();
+  AliFemtoEventReaderAOD(const AliFemtoEventReaderAOD &aReader);
+  virtual ~AliFemtoEventReaderAOD();
+
+  AliFemtoEventReaderAOD& operator=(const AliFemtoEventReaderAOD& aReader);
+
+  virtual AliFemtoEvent* ReturnHbtEvent();
+  AliFemtoString Report();
+  void SetInputFile(const char* inputFile);
+  void SetFilterBit(UInt_t ibit);
+  void SetReadMC(unsigned char a);
+  void SetCentralityPreSelection(double min, double max);
+  void SetAODpidUtil(AliAODpidUtil *aAODpidUtil);
+
+ protected:
+  virtual void CopyAODtoFemtoEvent(AliFemtoEvent *tEvent);
+  virtual void CopyAODtoFemtoTrack( AliAODTrack *tAodTrack,  
+                                   AliFemtoTrack *tFemtoTrack
+                                   //                              AliPWG2AODTrack *tPWG2AODTrack
+                                   ); 
+  virtual void CopyPIDtoFemtoTrack( AliAODTrack *tAodTrack, 
+                                  AliFemtoTrack *tFemtoTrack);
+
+  int            fNumberofEvent;    // number of Events in AOD file
+  int            fCurEvent;         // number of current event
+  AliAODEvent*   fEvent;            // AOD event
+  TBits          fAllTrue;          // Bit set with all true bits
+  TBits          fAllFalse;         // Bit set with all false bits
+  UInt_t         fFilterBit;        // Bitmap bit for AOD filters
+  //  TClonesArray*  fPWG2AODTracks;    // Link to PWG2 specific AOD information (if it exists)
+  
+  unsigned char  fReadMC;           // Attempt to read the MC information from the AOD
+  unsigned char  fUsePreCent;       // Use centrality pre-selection to speed up analysis
+  double         fCentRange[2];     // Centrality pre-selection range
+  AliAODpidUtil* fAODpidUtil;
+
+ private:
+
+  AliAODMCParticle* GetParticleWithLabel(TClonesArray *mcP, Int_t aLabel); 
+
+  string         fInputFile;        // name of input file with AOD filenames
+  string         fFileName;         // name of current AOD file
+  TChain*        fTree;             // AOD tree
+  TFile*         fAodFile;          // AOD file 
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoEventReaderAOD, 11)
+#endif
+
+};
+  
+#endif
+
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReaderAODChain.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReaderAODChain.cxx
new file mode 100644 (file)
index 0000000..202d0a2
--- /dev/null
@@ -0,0 +1,108 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoEventReaderAODChain - the reader class for the Alice AOD from Chain//
+// Reads in AOD information and converts it into internal AliFemtoEvent       //
+// Authors: Adam Kisiel kisiel@mps.ohio-state.edu                             //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+
+#include "AliFemtoEventReaderAODChain.h"
+
+#include "TFile.h"
+#include "TTree.h"
+#include "AliAODEvent.h"
+#include "AliAODTrack.h"
+#include "AliAODVertex.h"
+
+#include "AliFmPhysicalHelixD.h"
+#include "AliFmThreeVectorF.h"
+
+#include "SystemOfUnits.h"
+
+#include "AliFemtoEvent.h"
+#include "AliFemtoModelHiddenInfo.h"
+
+ClassImp(AliFemtoEventReaderAODChain)
+
+#if !(ST_NO_NAMESPACES)
+  using namespace units;
+#endif
+
+using namespace std;
+//____________________________
+//constructor with 0 parameters , look at default settings 
+AliFemtoEventReaderAODChain::AliFemtoEventReaderAODChain():
+  AliFemtoEventReaderAOD()
+{
+  // default constructor
+}
+
+AliFemtoEventReaderAODChain::AliFemtoEventReaderAODChain(const AliFemtoEventReaderAODChain &aReader) :
+  AliFemtoEventReaderAOD(aReader)
+{
+  // copy constructor
+}
+//__________________
+//Destructor
+AliFemtoEventReaderAODChain::~AliFemtoEventReaderAODChain()
+{
+  // destructor
+}
+
+//__________________
+AliFemtoEventReaderAODChain& AliFemtoEventReaderAODChain::operator=(const AliFemtoEventReaderAODChain& aReader)
+{
+  // assignment operator
+  if (this == &aReader)
+    return *this;
+
+  *this = aReader;
+
+  return *this;
+}
+//__________________
+AliFemtoString AliFemtoEventReaderAODChain::Report()
+{
+  // create reader report
+  AliFemtoString temp = "\n This is the AliFemtoEventReaderAODChain\n";
+  return temp;
+}
+
+AliFemtoEvent* AliFemtoEventReaderAODChain::ReturnHbtEvent()
+{
+  // read in a next hbt event from the chain
+  // convert it to AliFemtoEvent and return
+  // for further analysis
+  if (!fEvent) return 0;
+
+  AliFemtoEvent *hbtEvent = 0;
+
+  // Get the PWG2 specific information if it exists
+//   fPWG2AODTracks = (TClonesArray *) fEvent->GetList()->FindObject("pwg2aodtracks");
+  
+//   if (fPWG2AODTracks) {
+//     cout << "Found additional PWG2 specific information in the AOD!" << endl;
+//     cout << "Reading only tracks with the additional information" << endl;
+//   }
+
+  cout<<"starting to read event "<<fCurEvent<<endl;
+       
+  hbtEvent = new AliFemtoEvent;
+
+  CopyAODtoFemtoEvent(hbtEvent);
+
+  fCurEvent++; 
+  return hbtEvent; 
+}
+
+//___________________
+void AliFemtoEventReaderAODChain::SetAODSource(AliAODEvent *aAOD)
+{
+  // The chain loads the AOD for us
+  // You must provide the address where it can be found
+  fEvent = aAOD;
+}
+
+
+
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReaderAODChain.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReaderAODChain.h
new file mode 100644 (file)
index 0000000..d42d5f5
--- /dev/null
@@ -0,0 +1,51 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoEventReaderAODChain - the reader class for the Alice AOD in Chain  //
+// Reads in AOD information and converts it into internal AliFemtoEvent       //
+// Authors: Adam Kisiel kisiel@mps.ohio-state.edu                             //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+#ifndef ALIFEMTOEVENTREADERAODCHAIN_H
+#define ALIFEMTOEVENTREADERAODCHAIN_H
+#include "AliFemtoEventReader.h"
+#include "AliFemtoEnumeration.h"
+
+#include <string>
+#include <vector>
+#include "TTree.h"
+#include "TChain.h"
+#include "TBits.h"
+#include "AliAODEvent.h"
+#include <list>
+/* #include "AliPWG2AODTrack.h" */
+#include "AliFemtoEventReaderAOD.h"
+
+class AliFemtoEvent;
+class AliFemtoTrack;
+
+class AliFemtoEventReaderAODChain : public AliFemtoEventReaderAOD 
+{
+ public:
+  AliFemtoEventReaderAODChain();
+  AliFemtoEventReaderAODChain(const AliFemtoEventReaderAODChain &aReader);
+  virtual ~AliFemtoEventReaderAODChain();
+
+  AliFemtoEventReaderAODChain& operator=(const AliFemtoEventReaderAODChain& aReader);
+
+  virtual AliFemtoEvent* ReturnHbtEvent();
+  AliFemtoString Report();
+  void SetAODSource(AliAODEvent *aAOD);
+
+ protected:
+
+ private:
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoEventReaderAODChain, 1)
+#endif
+
+    };
+  
+#endif
+
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReaderESD.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReaderESD.cxx
new file mode 100644 (file)
index 0000000..dc82e4b
--- /dev/null
@@ -0,0 +1,408 @@
+////////////////////////////////////////////////////////////////////////////////
+///                                                                          ///
+/// AliFemtoEventReaderESD - the reader class for the Alice ESD              ///
+/// Reads in ESD information and converts it into internal AliFemtoEvent     ///
+/// Reads in AliESDfriend to create shared hit/quality information           ///
+/// Authors: Marek Chojnacki mchojnacki@knf.pw.edu.pl                        ///
+///          Adam Kisiel kisiel@mps.ohio-state.edu                           ///
+///                                                                          ///
+////////////////////////////////////////////////////////////////////////////////
+
+/*
+ *$Id$
+ *$Log$
+ *Revision 1.2.2.2  2007/10/04 13:10:52  akisiel
+ *Add Kink index storageAliFemtoEventReaderESD.cxx AliFemtoTrack.cxx AliFemtoTrack.h
+ *
+ *Revision 1.2.2.1  2007/09/30 11:38:59  akisiel
+ *Adapt the readers to the new AliESDEvent structure
+ *
+ *Revision 1.2  2007/05/22 09:01:42  akisiel
+ *Add the possibiloity to save cut settings in the ROOT file
+ *
+ *Revision 1.1  2007/05/16 10:22:11  akisiel
+ *Making the directory structure of AliFemto flat. All files go into one common directory
+ *
+ *Revision 1.5  2007/05/03 09:45:20  akisiel
+ *Fixing Effective C++ warnings
+ *
+ *Revision 1.4  2007/04/27 07:28:34  akisiel
+ *Remove event number reading due to interface changes
+ *
+ *Revision 1.3  2007/04/27 07:25:16  akisiel
+ *Make revisions needed for compilation from the main AliRoot tree
+ *
+ *Revision 1.1.1.1  2007/04/25 15:38:41  panos
+ *Importing the HBT code dir
+ *
+ */
+
+#include "AliFemtoEventReaderESD.h"
+
+#include "TFile.h"
+#include "TTree.h"
+#include "AliESDEvent.h"
+#include "AliESDtrack.h"
+#include "AliESDVertex.h"
+
+//#include "TSystem.h"
+
+#include "AliFmPhysicalHelixD.h"
+#include "AliFmThreeVectorF.h"
+
+#include "SystemOfUnits.h"
+
+#include "AliFemtoEvent.h"
+#include "AliFemtoModelHiddenInfo.h"
+
+ClassImp(AliFemtoEventReaderESD)
+
+#if !(ST_NO_NAMESPACES)
+  using namespace units;
+#endif
+
+using namespace std;
+//____________________________
+//constructor with 0 parameters , look at default settings 
+AliFemtoEventReaderESD::AliFemtoEventReaderESD():
+  fInputFile(" "),
+  fFileName(" "),
+  fConstrained(true),
+  fReadInner(false),
+  fNumberofEvent(0),
+  fCurEvent(0),
+  fTree(0x0),
+  fEsdFile(0x0),
+  fEvent(0x0)
+{
+  // default constructor
+}
+
+AliFemtoEventReaderESD::AliFemtoEventReaderESD(const AliFemtoEventReaderESD &aReader) :
+  AliFemtoEventReader(aReader),
+  fInputFile(" "),
+  fFileName(" "),
+  fConstrained(true),
+  fReadInner(false),
+  fNumberofEvent(0),
+  fCurEvent(0),
+  fTree(0x0),
+  fEsdFile(0x0),
+  fEvent(0x0)
+{
+  // copy constructor
+  fInputFile = aReader.fInputFile;
+  fFileName  = aReader.fFileName;
+  fConstrained = aReader.fConstrained;
+  fReadInner = aReader.fReadInner;
+  fNumberofEvent = aReader.fNumberofEvent;
+  fCurEvent = aReader.fCurEvent;
+  //  fTree = aReader.fTree->CloneTree();
+  //  fEvent = new AliESD(*aReader.fEvent);
+  fEvent = new AliESDEvent();
+  fEsdFile = new TFile(aReader.fEsdFile->GetName());
+}
+//__________________
+//Destructor
+AliFemtoEventReaderESD::~AliFemtoEventReaderESD()
+{
+  // destructor
+  //delete fListOfFiles;
+  delete fTree;
+  delete fEvent;
+  delete fEsdFile;
+}
+
+//__________________
+AliFemtoEventReaderESD& AliFemtoEventReaderESD::operator=(const AliFemtoEventReaderESD& aReader)
+{
+  // assignment operator
+  if (this == &aReader)
+    return *this;
+
+  fInputFile = aReader.fInputFile;
+  fFileName  = aReader.fFileName;
+  fConstrained = aReader.fConstrained;
+  fReadInner = aReader.fReadInner;
+  fNumberofEvent = aReader.fNumberofEvent;
+  fCurEvent = aReader.fCurEvent;
+  if (fTree) delete fTree;
+  //  fTree = aReader.fTree->CloneTree();
+  if (fEvent) delete fEvent;
+  fEvent = new AliESDEvent();
+  if (fEsdFile) delete fEsdFile;
+  fEsdFile = new TFile(aReader.fEsdFile->GetName());
+
+  return *this;
+}
+//__________________
+AliFemtoString AliFemtoEventReaderESD::Report()
+{
+  // create reader report
+  AliFemtoString temp = "\n This is the AliFemtoEventReaderESD\n";
+  return temp;
+}
+
+//__________________
+void AliFemtoEventReaderESD::SetInputFile(const char* inputFile)
+{
+  //setting the name of file where names of ESD file are written 
+  //it takes only this files which have good trees
+  char buffer[256];
+  fInputFile=string(inputFile);
+  cout<<"Input File set on "<<fInputFile<<endl;
+  ifstream infile(inputFile);
+
+  fTree = new TChain("esdTree");
+
+  if(infile.good()==true)
+    { 
+      //checking if all give files have good tree inside
+      while (infile.eof()==false)
+       {
+         infile.getline(buffer,256);
+         //ifstream test_file(buffer);
+         TFile *esdFile=TFile::Open(buffer,"READ");
+         if (esdFile!=0x0)
+           {   
+             TTree* tree = (TTree*) esdFile->Get("esdTree");
+             if (tree!=0x0)
+               {
+                 cout<<"putting file  "<<string(buffer)<<" into analysis"<<endl;
+                 fTree->AddFile(buffer);
+                 delete tree;
+               }
+             esdFile->Close(); 
+           }
+         delete esdFile;
+       }
+    }
+}
+
+void AliFemtoEventReaderESD::SetConstrained(const bool constrained)
+{
+  fConstrained=constrained;
+}
+
+bool AliFemtoEventReaderESD::GetConstrained() const
+{
+  return fConstrained;
+}
+
+void AliFemtoEventReaderESD::SetReadTPCInner(const bool readinner)
+{
+  fReadInner=readinner;
+}
+
+bool AliFemtoEventReaderESD::GetReadTPCInner() const
+{
+  return fReadInner;
+}
+
+AliFemtoEvent* AliFemtoEventReaderESD::ReturnHbtEvent()
+{
+  // read in a next hbt event from the chain
+  // convert it to AliFemtoEvent and return
+  // for further analysis
+  AliFemtoEvent *hbtEvent = 0;
+
+  if (fCurEvent==fNumberofEvent)//open next file  
+    {
+      if(fNumberofEvent==0)    
+       {
+         //      delete fEvent;//added 1.04.2007
+         fEvent=new AliESDEvent();
+         //      delete fTree;
+         //fTree=0;
+         //      delete fEsdFile;
+               
+         //ESD data
+         //      fEsdFile=TFile::Open(fFileName.c_str(),"READ");
+         //      fTree = (TTree*) fEsdFile->Get("esdTree");                    
+         //      fTree->SetBranchAddress("ESD", &fEvent);                      
+         fTree->SetBranchStatus("MuonTracks*",0);
+         fTree->SetBranchStatus("PmdTracks*",0);
+         fTree->SetBranchStatus("TrdTracks*",0);
+         fTree->SetBranchStatus("V0s*",0);
+         fTree->SetBranchStatus("Cascades*",0);
+         fTree->SetBranchStatus("Kinks*",0);
+         fTree->SetBranchStatus("CaloClusters*",0);
+         fTree->SetBranchStatus("AliRawDataErrorLogs*",0);
+         fTree->SetBranchStatus("ESDfriend*",0);
+         fEvent->ReadFromTree(fTree);
+
+         fNumberofEvent=fTree->GetEntries();
+         cout<<"Number of Entries in file "<<fNumberofEvent<<endl;
+         fCurEvent=0;
+         //sim data
+       }
+      else //no more data to read
+       {
+         cout<<"no more files "<<hbtEvent<<endl;
+         fReaderStatus=1;
+         return hbtEvent; 
+       }
+    }          
+  cout<<"starting to read event "<<fCurEvent<<endl;
+  fTree->GetEvent(fCurEvent);//getting next event
+  cout << "Read event " << fEvent << " from file " << fTree << endl;
+  //  vector<int> tLabelTable;//to check labels
+       
+  hbtEvent = new AliFemtoEvent;
+  //setting basic things
+  //  hbtEvent->SetEventNumber(fEvent->GetEventNumber());
+  hbtEvent->SetRunNumber(fEvent->GetRunNumber());
+  //hbtEvent->SetNumberOfTracks(fEvent->GetNumberOfTracks());
+  hbtEvent->SetMagneticField(fEvent->GetMagneticField()*kilogauss);//to check if here is ok
+  hbtEvent->SetZDCN1Energy(fEvent->GetZDCN1Energy());
+  hbtEvent->SetZDCP1Energy(fEvent->GetZDCP1Energy());
+  hbtEvent->SetZDCN2Energy(fEvent->GetZDCN2Energy());
+  hbtEvent->SetZDCP2Energy(fEvent->GetZDCP2Energy());
+  hbtEvent->SetZDCEMEnergy(fEvent->GetZDCEMEnergy());
+  hbtEvent->SetZDCParticipants(fEvent->GetZDCParticipants());
+  hbtEvent->SetTriggerMask(fEvent->GetTriggerMask());
+  hbtEvent->SetTriggerCluster(fEvent->GetTriggerCluster());
+       
+  //Vertex
+  double fV1[3];
+  fEvent->GetVertex()->GetXYZ(fV1);
+
+  AliFmThreeVectorF vertex(fV1[0],fV1[1],fV1[2]);
+  hbtEvent->SetPrimVertPos(vertex);
+       
+  //starting to reading tracks
+  int nofTracks=0;  //number of reconstructed tracks in event
+  nofTracks=fEvent->GetNumberOfTracks();
+  int realnofTracks=0;//number of track which we use ina analysis
+  cout << "Event has " << nofTracks << " tracks " << endl;
+
+  for (int i=0;i<nofTracks;i++)
+    {
+      bool  tGoodMomentum=true; //flaga to chcek if we can read momentum of this track
+               
+      AliFemtoTrack* trackCopy = new AliFemtoTrack();  
+      const AliESDtrack *esdtrack=fEvent->GetTrack(i);//getting next track
+      //      const AliESDfriendTrack *tESDfriendTrack = esdtrack->GetFriendTrack();
+
+      trackCopy->SetCharge((short)esdtrack->GetSign());
+
+      //in aliroot we have AliPID 
+      //0-electron 1-muon 2-pion 3-kaon 4-proton 5-photon 6-pi0 7-neutron 8-kaon0 9-eleCon   
+      //we use only 5 first
+      double esdpid[5];
+      esdtrack->GetESDpid(esdpid);
+      trackCopy->SetPidProbElectron(esdpid[0]);
+      trackCopy->SetPidProbMuon(esdpid[1]);
+      trackCopy->SetPidProbPion(esdpid[2]);
+      trackCopy->SetPidProbKaon(esdpid[3]);
+      trackCopy->SetPidProbProton(esdpid[4]);
+                                               
+      double pxyz[3];
+      if (fReadInner == true) {
+       
+       if (esdtrack->GetTPCInnerParam()) {
+         AliExternalTrackParam *param = new AliExternalTrackParam(*esdtrack->GetTPCInnerParam());
+         param->PropagateToDCA(fEvent->GetPrimaryVertex(), (fEvent->GetMagneticField()), 10000);
+         param->GetPxPyPz(pxyz);//reading noconstarined momentum
+         delete param;
+
+         AliFemtoModelHiddenInfo *tInfo = new AliFemtoModelHiddenInfo();
+         tInfo->SetPDGPid(211);
+         tInfo->SetTrueMomentum(pxyz[0], pxyz[1], pxyz[2]);
+         tInfo->SetMass(0.13957);
+         trackCopy->SetHiddenInfo(tInfo);
+       }
+      }
+      if (fConstrained==true)              
+       tGoodMomentum=esdtrack->GetConstrainedPxPyPz(pxyz); //reading constrained momentum
+      else
+       tGoodMomentum=esdtrack->GetPxPyPz(pxyz);//reading noconstarined momentum
+      AliFemtoThreeVector v(pxyz[0],pxyz[1],pxyz[2]);
+      trackCopy->SetP(v);//setting momentum
+      trackCopy->SetPt(sqrt(pxyz[0]*pxyz[0]+pxyz[1]*pxyz[1]));
+      const AliFmThreeVectorD ktP(pxyz[0],pxyz[1],pxyz[2]);
+      if (ktP.Mag() == 0) {
+       delete trackCopy;
+       continue;
+      }
+      const AliFmThreeVectorD origin(fV1[0],fV1[1],fV1[2]);
+      //setting helix I do not if it is ok
+      AliFmPhysicalHelixD helix(ktP,origin,(double)(fEvent->GetMagneticField())*kilogauss,(double)(trackCopy->Charge())); 
+      trackCopy->SetHelix(helix);
+               
+      trackCopy->SetTrackId(esdtrack->GetID());
+      trackCopy->SetFlags(esdtrack->GetStatus());
+      trackCopy->SetLabel(esdtrack->GetLabel());
+               
+      //some stuff which could be useful 
+      float impact[2];
+      float covimpact[3];
+      esdtrack->GetImpactParameters(impact,covimpact);
+      trackCopy->SetImpactD(impact[0]);
+      trackCopy->SetImpactZ(impact[1]);
+      trackCopy->SetCdd(covimpact[0]);
+      trackCopy->SetCdz(covimpact[1]);
+      trackCopy->SetCzz(covimpact[2]);
+      trackCopy->SetITSchi2(esdtrack->GetITSchi2());    
+      trackCopy->SetITSncls(esdtrack->GetNcls(0));     
+      trackCopy->SetTPCchi2(esdtrack->GetTPCchi2());       
+      trackCopy->SetTPCncls(esdtrack->GetTPCNcls());       
+      trackCopy->SetTPCnclsF(esdtrack->GetTPCNclsF());      
+      trackCopy->SetTPCsignalN((short)esdtrack->GetTPCsignalN()); //due to bug in aliesdtrack class   
+      trackCopy->SetTPCsignalS(esdtrack->GetTPCsignalSigma()); 
+
+      trackCopy->SetTPCClusterMap(esdtrack->GetTPCClusterMap());
+      trackCopy->SetTPCSharedMap(esdtrack->GetTPCSharedMap());
+
+      double pvrt[3];
+      fEvent->GetPrimaryVertex()->GetXYZ(pvrt);
+
+      double xtpc[3];
+      esdtrack->GetInnerXYZ(xtpc);
+      xtpc[2] -= pvrt[2];
+      trackCopy->SetNominalTPCEntrancePoint(xtpc);
+
+      esdtrack->GetOuterXYZ(xtpc);
+      xtpc[2] -= pvrt[2];
+      trackCopy->SetNominalTPCExitPoint(xtpc);
+
+      int indexes[3];
+      for (int ik=0; ik<3; ik++) {
+       indexes[ik] = esdtrack->GetKinkIndex(ik);
+      }
+      trackCopy->SetKinkIndexes(indexes);
+      //decision if we want this track
+      //if we using diffrent labels we want that this label was use for first time 
+      //if we use hidden info we want to have match between sim data and ESD
+      if (tGoodMomentum==true)
+       {
+         hbtEvent->TrackCollection()->push_back(trackCopy);//adding track to analysis
+         realnofTracks++;//real number of tracks
+       }
+      else
+       {
+         delete  trackCopy;
+       }
+               
+    }
+
+  hbtEvent->SetNumberOfTracks(realnofTracks);//setting number of track which we read in event  
+  fCurEvent++; 
+  cout<<"end of reading nt "<<nofTracks<<" real number "<<realnofTracks<<endl;
+//   if (fCurEvent== fNumberofEvent)//if end of current file close all
+//     {   
+//       fTree->Reset(); 
+//       delete fTree;
+//       fEsdFile->Close();
+//     }
+  return hbtEvent; 
+}
+
+
+
+
+
+
+
+
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReaderESD.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReaderESD.h
new file mode 100644 (file)
index 0000000..36567aa
--- /dev/null
@@ -0,0 +1,86 @@
+////////////////////////////////////////////////////////////////////////////////
+///                                                                          ///
+/// AliFemtoEventReaderESD - the reader class for the Alice ESD              ///
+/// Reads in ESD information and converts it into internal AliFemtoEvent     ///
+/// Reads in AliESDfriend to create shared hit/quality information           ///
+/// Authors: Marek Chojnacki mchojnacki@knf.pw.edu.pl                        ///
+///          Adam Kisiel kisiel@mps.ohio-state.edu                           ///
+///                                                                          ///
+////////////////////////////////////////////////////////////////////////////////
+
+/*
+ *$Id$
+ *$Log$
+ *Revision 1.1.2.1  2007/09/30 11:38:59  akisiel
+ *Adapt the readers to the new AliESDEvent structure
+ *
+ *Revision 1.1  2007/05/16 10:22:11  akisiel
+ *Making the directory structure of AliFemto flat. All files go into one common directory
+ *
+ *Revision 1.4  2007/05/03 09:45:20  akisiel
+ *Fixing Effective C++ warnings
+ *
+ *Revision 1.3  2007/04/27 07:25:16  akisiel
+ *Make revisions needed for compilation from the main AliRoot tree
+ *
+ *Revision 1.1.1.1  2007/04/25 15:38:41  panos
+ *Importing the HBT code dir
+ *
+ */
+  
+
+#ifndef ALIFEMTOEVENTREADERESD_H
+#define ALIFEMTOEVENTREADERESD_H
+#include "AliFemtoEventReader.h"
+#include "AliFemtoEnumeration.h"
+
+#include <string>
+#include <vector>
+#include "TTree.h"
+#include "TChain.h"
+#include "AliESDEvent.h"
+#include <list>
+
+class AliFemtoEvent;
+
+class AliFemtoEventReaderESD : public AliFemtoEventReader 
+{
+ public:
+  AliFemtoEventReaderESD();
+  AliFemtoEventReaderESD(const AliFemtoEventReaderESD &aReader);
+  virtual ~AliFemtoEventReaderESD();
+
+  AliFemtoEventReaderESD& operator=(const AliFemtoEventReaderESD& aReader);
+
+  virtual AliFemtoEvent* ReturnHbtEvent();
+  AliFemtoString Report();
+  //void SetFileName(const char* fileName);
+  void SetInputFile(const char* inputFile);
+  void SetConstrained(const bool constrained);
+  bool GetConstrained() const;
+  void SetReadTPCInner(const bool readinner);
+  bool GetReadTPCInner() const;
+
+ protected:
+
+ private:
+  string         fInputFile;        // name of input file with ESD filenames
+  string         fFileName;         // name of current ESD file
+  bool           fConstrained;      // flag to set which momentum from ESD file will be use
+  bool           fReadInner;        // flag to set if one wants to read TPC-only momentum
+                                    // instead of the global one
+  int            fNumberofEvent;    // number of Events in ESD file
+  int            fCurEvent;         // number of current event
+  TChain*        fTree;             // ESD tree
+  TFile*         fEsdFile;          // ESD file 
+  AliESDEvent*   fEvent;            // ESD event
+               
+#ifdef __ROOT__
+  ClassDef(AliFemtoEventReaderESD, 11)
+#endif
+
+    };
+  
+#endif
+
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReaderESDChain.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReaderESDChain.cxx
new file mode 100644 (file)
index 0000000..606d407
--- /dev/null
@@ -0,0 +1,828 @@
+////////////////////////////////////////////////////////////////////////////////
+///                                                                          ///
+/// AliFemtoEventReaderESDChain - the reader class for the Alice ESD         ///
+/// tailored for the Task framework                                 ///
+/// Reads in AliESDfriend to create shared hit/quality information           ///
+/// Authors: Adam Kisiel kisiel@mps.ohio-state.edu                           ///
+///                                                                          ///
+////////////////////////////////////////////////////////////////////////////////
+#include "AliFemtoEventReaderESDChain.h"
+
+#include "TFile.h"
+#include "TTree.h"
+#include "AliESDEvent.h"
+#include "AliESDtrack.h"
+#include "AliESDVertex.h"
+#include "AliMultiplicity.h"
+#include "AliCentrality.h"
+#include "AliEventplane.h"
+#include "AliESDVZERO.h"
+#include "AliFmPhysicalHelixD.h"
+#include "AliFmThreeVectorF.h"
+#include "SystemOfUnits.h"
+#include "AliFemtoEvent.h"
+#include "AliFemtoModelHiddenInfo.h"
+#include "AliPID.h"
+
+ClassImp(AliFemtoEventReaderESDChain)
+
+#if !(ST_NO_NAMESPACES)
+  using namespace units;
+#endif
+
+using namespace std;
+//____________________________
+AliFemtoEventReaderESDChain::AliFemtoEventReaderESDChain():
+  fFileName(" "),
+  fConstrained(true),
+  fReadInner(false),
+  fUseTPCOnly(false),
+  fNumberofEvent(0),
+  fCurEvent(0),
+  fCurFile(0),
+  fEvent(0x0),
+  fUsePhysicsSel(kFALSE),
+  fSelect(0x0),
+  fTrackType(kGlobal),
+  fEstEventMult(kITSTPC), 
+  fEventTrig(AliVEvent::kMB), //trigger
+  fESDpid(0),
+  fIsPidOwner(0)
+{
+  //constructor with 0 parameters , look at default settings 
+  //   fClusterPerPadrow = (list<Int_t> **) malloc(sizeof(list<Int_t> *) * AliESDfriendTrack::kMaxTPCcluster);
+  //   for (int tPad=0; tPad<AliESDfriendTrack::kMaxTPCcluster; tPad++) {
+  //     fClusterPerPadrow[tPad] = new list<Int_t>();
+  //   }
+  //   fSharedList = (list<Int_t> **) malloc(sizeof(list<Int_t> *) * AliESDfriendTrack::kMaxTPCcluster);
+  //   for (int tPad=0; tPad<AliESDfriendTrack::kMaxTPCcluster; tPad++) {
+  //     fSharedList[tPad] = new list<Int_t>();
+  //   }
+}
+
+//__________________
+AliFemtoEventReaderESDChain::AliFemtoEventReaderESDChain(const AliFemtoEventReaderESDChain& aReader):
+  AliFemtoEventReader(aReader),
+  fFileName(" "),
+  fConstrained(true),
+  fReadInner(false),
+  fUseTPCOnly(false),
+  fNumberofEvent(0),
+  fCurEvent(0),
+  fCurFile(0),
+  fEvent(0x0),
+  fUsePhysicsSel(kFALSE),
+  fSelect(0x0),
+  fTrackType(kGlobal),
+  fEstEventMult(kITSTPC),
+  fEventTrig(AliVEvent::kMB), //trigger
+  fESDpid(0),
+  fIsPidOwner(0)
+{
+  // Copy constructor
+  fConstrained = aReader.fConstrained;
+  fReadInner = aReader.fReadInner;
+  fUseTPCOnly = aReader.fUseTPCOnly;
+  fNumberofEvent = aReader.fNumberofEvent;
+  fCurEvent = aReader.fCurEvent;
+  fCurFile = aReader.fCurFile;
+  //  fEvent = new AliESD(*aReader.fEvent);
+  fEvent = new AliESDEvent();
+  fUsePhysicsSel = aReader.fUsePhysicsSel;
+  if (aReader.fUsePhysicsSel)
+    fSelect = new AliPhysicsSelection();
+  fTrackType = aReader.fTrackType;
+  fEstEventMult = aReader.fEstEventMult;
+  fEventTrig = aReader.fEventTrig; //trigger
+
+  //   fEventFriend = aReader.fEventFriend;
+  //   fClusterPerPadrow = (list<Int_t> **) malloc(sizeof(list<Int_t> *) * AliESDfriendTrack::kMaxTPCcluster);
+  //   for (int tPad=0; tPad<AliESDfriendTrack::kMaxTPCcluster; tPad++) {
+  //     fClusterPerPadrow[tPad] = new list<Int_t>();
+  //     list<Int_t>::iterator iter;
+  //     for (iter=aReader.fClusterPerPadrow[tPad]->begin(); iter!=aReader.fClusterPerPadrow[tPad]->end(); iter++) {
+  //       fClusterPerPadrow[tPad]->push_back(*iter);
+  //     }
+  //   }
+  //   fSharedList = (list<Int_t> **) malloc(sizeof(list<Int_t> *) * AliESDfriendTrack::kMaxTPCcluster);
+  //   for (int tPad=0; tPad<AliESDfriendTrack::kMaxTPCcluster; tPad++) {
+  //     fSharedList[tPad] = new list<Int_t>();
+  //     list<Int_t>::iterator iter;
+  //     for (iter=aReader.fSharedList[tPad]->begin(); iter!=aReader.fSharedList[tPad]->end(); iter++) {
+  //       fSharedList[tPad]->push_back(*iter);
+  //     }
+  //   }
+}
+//__________________
+AliFemtoEventReaderESDChain::~AliFemtoEventReaderESDChain()
+{
+  //Destructor
+  delete fEvent;
+
+  //   for (int tPad=0; tPad<AliESDfriendTrack::kMaxTPCcluster; tPad++) {
+  //     fClusterPerPadrow[tPad]->clear();
+  //     delete fClusterPerPadrow[tPad];
+  //   }
+  //   delete [] fClusterPerPadrow;
+  //   for (int tPad=0; tPad<AliESDfriendTrack::kMaxTPCcluster; tPad++) {
+  //     fSharedList[tPad]->clear();
+  //     delete fSharedList[tPad];
+  //   }
+  //   delete [] fSharedList;
+  if (fSelect) delete fSelect;
+}
+
+//__________________
+AliFemtoEventReaderESDChain& AliFemtoEventReaderESDChain::operator=(const AliFemtoEventReaderESDChain& aReader)
+{
+  // Assignment operator
+  if (this == &aReader)
+    return *this;
+
+  fConstrained = aReader.fConstrained;
+  fReadInner = aReader.fReadInner;
+  fUseTPCOnly = aReader.fUseTPCOnly;
+  fNumberofEvent = aReader.fNumberofEvent;
+  fCurEvent = aReader.fCurEvent;
+  fCurFile = aReader.fCurFile;
+  if (fEvent) delete fEvent;
+  fEvent = new AliESDEvent();
+  fTrackType = aReader.fTrackType;
+  fEstEventMult = aReader.fEstEventMult;
+
+  fUsePhysicsSel = aReader.fUsePhysicsSel;
+  if (aReader.fUsePhysicsSel)
+    fSelect = new AliPhysicsSelection();
+  //  fEventFriend = aReader.fEventFriend;
+  
+  //   if (fClusterPerPadrow) {
+  //     for (int tPad=0; tPad<AliESDfriendTrack::kMaxTPCcluster; tPad++) {
+  //       fClusterPerPadrow[tPad]->clear();
+  //       delete fClusterPerPadrow[tPad];
+  //     }
+  //     delete [] fClusterPerPadrow;
+  //   }
+  
+  //   if (fSharedList) {
+  //     for (int tPad=0; tPad<AliESDfriendTrack::kMaxTPCcluster; tPad++) {
+  //       fSharedList[tPad]->clear();
+  //       delete fSharedList[tPad];
+  //     }
+  //     delete [] fSharedList;
+  //   }
+
+  //   fClusterPerPadrow = (list<Int_t> **) malloc(sizeof(list<Int_t> *) * AliESDfriendTrack::kMaxTPCcluster);
+  //   for (int tPad=0; tPad<AliESDfriendTrack::kMaxTPCcluster; tPad++) {
+  //     fClusterPerPadrow[tPad] = new list<Int_t>();
+  //     list<Int_t>::iterator iter;
+  //     for (iter=aReader.fClusterPerPadrow[tPad]->begin(); iter!=aReader.fClusterPerPadrow[tPad]->end(); iter++) {
+  //       fClusterPerPadrow[tPad]->push_back(*iter);
+  //     }
+  //   }
+  //   fSharedList = (list<Int_t> **) malloc(sizeof(list<Int_t> *) * AliESDfriendTrack::kMaxTPCcluster);
+  //   for (int tPad=0; tPad<AliESDfriendTrack::kMaxTPCcluster; tPad++) {
+  //     fSharedList[tPad] = new list<Int_t>();
+  //     list<Int_t>::iterator iter;
+  //     for (iter=aReader.fSharedList[tPad]->begin(); iter!=aReader.fSharedList[tPad]->end(); iter++) {
+  //       fSharedList[tPad]->push_back(*iter);
+  //     }
+  //   }
+  
+  return *this;
+}
+//__________________
+// Simple report
+AliFemtoString AliFemtoEventReaderESDChain::Report()
+{
+  AliFemtoString temp = "\n This is the AliFemtoEventReaderESDChain\n";
+  return temp;
+}
+
+//__________________
+void AliFemtoEventReaderESDChain::SetConstrained(const bool constrained)
+{
+  // Select whether to read constrained or not constrained momentum
+  fConstrained=constrained;
+}
+//__________________
+bool AliFemtoEventReaderESDChain::GetConstrained() const
+{
+  // Check whether we read constrained or not constrained momentum
+  return fConstrained;
+}
+//__________________
+void AliFemtoEventReaderESDChain::SetReadTPCInner(const bool readinner)
+{
+  fReadInner=readinner;
+}
+
+bool AliFemtoEventReaderESDChain::GetReadTPCInner() const
+{
+  return fReadInner;
+}
+
+//__________________
+void AliFemtoEventReaderESDChain::SetUseTPCOnly(const bool usetpconly)
+{
+  fUseTPCOnly=usetpconly;
+}
+
+bool AliFemtoEventReaderESDChain::GetUseTPCOnly() const
+{
+  return fUseTPCOnly;
+}
+
+void AliFemtoEventReaderESDChain::SetUsePhysicsSelection(const bool usephysics)
+{
+  fUsePhysicsSel = usephysics;
+  if (!fSelect) fSelect = new AliPhysicsSelection();
+}
+
+void AliFemtoEventReaderESDChain::SetUseMultiplicity(EstEventMult aType)
+{
+  fEstEventMult = aType;
+}
+
+AliFemtoEvent* AliFemtoEventReaderESDChain::ReturnHbtEvent()
+{
+  // Get the event, read all the relevant information
+  // and fill the AliFemtoEvent class
+  // Returns a valid AliFemtoEvent
+  AliFemtoEvent *hbtEvent = 0;
+  string tFriendFileName;
+
+  // Get the friend information
+  if (Debug()>1) cout<<"starting to read event "<<fCurEvent<<endl;
+  //  fEvent->SetESDfriend(fEventFriend);
+  if(fEvent->GetAliESDOld())fEvent->CopyFromOldESD();
+  
+  hbtEvent = new AliFemtoEvent;
+
+  if (fUsePhysicsSel) {
+    hbtEvent->SetIsCollisionCandidate(fSelect->IsCollisionCandidate(fEvent));
+    if (!(fSelect->IsCollisionCandidate(fEvent)))
+      printf("Event not a collision candidate\n");
+  }
+  else
+    hbtEvent->SetIsCollisionCandidate(kTRUE);
+
+  //setting basic things
+  //  hbtEvent->SetEventNumber(fEvent->GetEventNumber());
+  hbtEvent->SetRunNumber(fEvent->GetRunNumber());
+  //hbtEvent->SetNumberOfTracks(fEvent->GetNumberOfTracks());
+  hbtEvent->SetMagneticField(fEvent->GetMagneticField()*kilogauss);//to check if here is ok
+  hbtEvent->SetZDCN1Energy(fEvent->GetZDCN1Energy());
+  hbtEvent->SetZDCP1Energy(fEvent->GetZDCP1Energy());
+  hbtEvent->SetZDCN2Energy(fEvent->GetZDCN2Energy());
+  hbtEvent->SetZDCP2Energy(fEvent->GetZDCP2Energy());
+  hbtEvent->SetZDCEMEnergy(fEvent->GetZDCEMEnergy());
+  hbtEvent->SetZDCParticipants(fEvent->GetZDCParticipants());
+  hbtEvent->SetTriggerMask(fEvent->GetTriggerMask());
+  //  hbtEvent->SetTriggerCluster(fEvent->GetTriggerCluster());
+
+  if ((fEvent->IsTriggerClassFired("CINT1WU-B-NOPF-ALL")) ||
+      (fEvent->IsTriggerClassFired("CINT1B-ABCE-NOPF-ALL")) ||
+      (fEvent->IsTriggerClassFired("CINT1-B-NOPF-ALLNOTRD")) ||
+      (fEvent->IsTriggerClassFired("CINT1-B-NOPF-FASTNOTRD")))
+    hbtEvent->SetTriggerCluster(1);
+  else if ((fEvent->IsTriggerClassFired("CSH1WU-B-NOPF-ALL")) ||
+          (fEvent->IsTriggerClassFired("CSH1-B-NOPF-ALLNOTRD")))
+    hbtEvent->SetTriggerCluster(2);
+  else 
+    hbtEvent->SetTriggerCluster(0);
+       
+  //Vertex
+  double fV1[3];
+  double fVCov[6];
+  if (fUseTPCOnly) {
+    fEvent->GetPrimaryVertexTPC()->GetXYZ(fV1);
+    fEvent->GetPrimaryVertexTPC()->GetCovMatrix(fVCov);
+    if (!fEvent->GetPrimaryVertexTPC()->GetStatus())
+      fVCov[4] = -1001.0;
+  }
+  else {
+    fEvent->GetPrimaryVertex()->GetXYZ(fV1);
+    fEvent->GetPrimaryVertex()->GetCovMatrix(fVCov);
+    if (!fEvent->GetPrimaryVertex()->GetStatus())
+      fVCov[4] = -1001.0;
+  }
+
+  AliFmThreeVectorF vertex(fV1[0],fV1[1],fV1[2]);
+  hbtEvent->SetPrimVertPos(vertex);
+  hbtEvent->SetPrimVertCov(fVCov);
+  
+  Int_t spdetaonecount = 0;
+  
+  for (int iter=0; iter<fEvent->GetMultiplicity()->GetNumberOfTracklets(); iter++) 
+    if (fabs(fEvent->GetMultiplicity()->GetEta(iter)) < 1.0)
+      spdetaonecount++;
+
+  //  hbtEvent->SetSPDMult(fEvent->GetMultiplicity()->GetNumberOfTracklets());
+  hbtEvent->SetSPDMult(spdetaonecount);
+
+  //starting to reading tracks
+  int nofTracks=0;  //number of reconstructed tracks in event
+  nofTracks=fEvent->GetNumberOfTracks();
+  int realnofTracks=0;//number of track which we use ina analysis
+
+  //   // Clear the shared cluster list
+  //   for (int tPad=0; tPad<AliESDfriendTrack::kMaxTPCcluster; tPad++) {
+  //     fClusterPerPadrow[tPad]->clear();
+  //   }
+  //   for (int tPad=0; tPad<AliESDfriendTrack::kMaxTPCcluster; tPad++) {
+  //     fSharedList[tPad]->clear();
+  //   }
+
+
+  //   for (int i=0;i<nofTracks;i++) {
+  //     const AliESDtrack *esdtrack=fEvent->GetTrack(i);//getting next track
+
+  //     list<Int_t>::iterator tClustIter;
+
+  //     Int_t tTrackIndices[AliESDfriendTrack::kMaxTPCcluster];
+  //     Int_t tNClusters = esdtrack->GetTPCclusters(tTrackIndices);
+  //     for (int tNcl=0; tNcl<AliESDfriendTrack::kMaxTPCcluster; tNcl++) {
+  //       if (tTrackIndices[tNcl] >= 0) {
+  //   tClustIter = find(fClusterPerPadrow[tNcl]->begin(), fClusterPerPadrow[tNcl]->end(), tTrackIndices[tNcl]);
+  //   if (tClustIter == fClusterPerPadrow[tNcl]->end()) {
+  //     fClusterPerPadrow[tNcl]->push_back(tTrackIndices[tNcl]);
+  //   }
+  //   else {
+  //     fSharedList[tNcl]->push_back(tTrackIndices[tNcl]);
+  //   }
+  //       }
+  //     }
+      
+  //   }
+
+  int tNormMult = 0;
+  int tNormMultPos = 0;
+  int tNormMultNeg = 0;
+
+  Float_t tTotalPt = 0.0;
+
+  Float_t b[2];
+  Float_t bCov[3];
+
+  Int_t tTracklet=0, tITSTPC=0, tITSPure=0;
+  
+  fEvent->EstimateMultiplicity(tTracklet, tITSTPC, tITSPure, 1.2);
+  
+  hbtEvent->SetMultiplicityEstimateITSTPC(tITSTPC);
+  hbtEvent->SetMultiplicityEstimateTracklets(tTracklet);
+  //  hbtEvent->SetMultiplicityEstimateITSPure(tITSPure);
+  hbtEvent->SetMultiplicityEstimateITSPure(fEvent->GetMultiplicity()->GetNumberOfITSClusters(1));
+  
+  for (int i=0;i<nofTracks;i++)
+    {
+      bool  tGoodMomentum=true; //flaga to chcek if we can read momentum of this track
+
+      const AliESDtrack *esdtrack=fEvent->GetTrack(i);//getting next track
+      //      const AliESDfriendTrack *tESDfriendTrack = esdtrack->GetFriendTrack();
+
+      if ((esdtrack->GetStatus() & AliESDtrack::kTPCrefit) &&
+         (esdtrack->GetStatus() & AliESDtrack::kITSrefit)) {
+       if (esdtrack->GetTPCNcls() > 70) 
+         if (esdtrack->GetTPCchi2()/esdtrack->GetTPCNcls() < 4.0) {
+           if (TMath::Abs(esdtrack->Eta()) < 1.2) {
+             esdtrack->GetImpactParameters(b,bCov);
+             if ((b[0]<0.2) && (b[1] < 0.25)) {
+               tNormMult++;
+               tTotalPt += esdtrack->Pt();
+             }
+           }
+         }
+      }
+      else if (esdtrack->GetStatus() & AliESDtrack::kTPCrefit) {
+       if (esdtrack->GetTPCNcls() > 100) 
+         if (esdtrack->GetTPCchi2()/esdtrack->GetTPCNcls() < 4.0) {
+           if (TMath::Abs(esdtrack->Eta()) < 1.2) {
+             esdtrack->GetImpactParameters(b,bCov);
+             if ((b[0]<2.4) && (b[1] < 3.2)) {
+               tNormMult++;
+               tTotalPt += esdtrack->Pt();
+             }
+           }
+         }
+      }
+      
+      hbtEvent->SetZDCEMEnergy(tTotalPt);
+      //       if (esdtrack->GetStatus() & AliESDtrack::kTPCrefit)
+      //       if (esdtrack->GetTPCNcls() > 80) 
+      //         if (esdtrack->GetTPCchi2()/esdtrack->GetTPCNcls() < 6.0) 
+      //           if (esdtrack->GetConstrainedParam())
+      //             if (fabs(esdtrack->GetConstrainedParam()->Eta()) < 0.5)
+      //               if (esdtrack->GetConstrainedParam()->Pt() < 1.0) {
+      //                 if (esdtrack->GetSign() > 0)
+      //                   tNormMultPos++;
+      //                 else if (esdtrack->GetSign() < 0)
+      //                   tNormMultNeg--;
+      //               }
+
+      // If reading ITS-only tracks, reject all with TPC
+      if (fTrackType == kITSOnly) {
+       if (esdtrack->GetStatus() & AliESDtrack::kTPCrefit) continue;
+       if (!(esdtrack->GetStatus() & AliESDtrack::kITSrefit)) continue;
+       if (esdtrack->GetStatus() & AliESDtrack::kTPCin) continue;
+       UChar_t iclm = esdtrack->GetITSClusterMap();
+       Int_t incls = 0;
+       for (int iter=0; iter<6; iter++) if (iclm&(1<<iter)) incls++;
+       if (incls<=3) {
+         if (Debug()>1) cout << "Rejecting track with " << incls << " clusters" << endl;
+         continue;
+       }
+      }
+
+      AliFemtoTrack* trackCopy = new AliFemtoTrack();  
+      trackCopy->SetCharge((short)esdtrack->GetSign());
+
+      //in aliroot we have AliPID 
+      //0-electron 1-muon 2-pion 3-kaon 4-proton 5-photon 6-pi0 7-neutron 8-kaon0 9-eleCon   
+      //we use only 5 first
+      double esdpid[5];
+      //       esdtrack->GetESDpid(esdpid);
+      esdtrack->GetTPCpid(esdpid);
+      trackCopy->SetPidProbElectron(esdpid[0]);
+      trackCopy->SetPidProbMuon(esdpid[1]);
+      trackCopy->SetPidProbPion(esdpid[2]);
+      trackCopy->SetPidProbKaon(esdpid[3]);
+      trackCopy->SetPidProbProton(esdpid[4]);
+      
+      esdpid[0] = -100000.0;
+      esdpid[1] = -100000.0;
+      esdpid[2] = -100000.0;
+      esdpid[3] = -100000.0;
+      esdpid[4] = -100000.0;
+      
+      double tTOF = 0.0;
+
+      if (esdtrack->GetStatus()&AliESDtrack::kTOFpid) {
+       tTOF = esdtrack->GetTOFsignal();
+       esdtrack->GetIntegratedTimes(esdpid);
+      }
+
+      trackCopy->SetTofExpectedTimes(tTOF-esdpid[2], tTOF-esdpid[3], tTOF-esdpid[4]);
+
+      //////  TPC ////////////////////////////////////////////
+
+      float nsigmaTPCK=-1000.;                                                        
+      float nsigmaTPCPi=-1000.;                                                        
+      float nsigmaTPCP=-1000.;                                                        
+          
+  
+      if ((fESDpid) && (esdtrack->IsOn(AliESDtrack::kTPCpid))){
+        nsigmaTPCK = fESDpid->NumberOfSigmasTPC(esdtrack,AliPID::kKaon);
+        nsigmaTPCPi = fESDpid->NumberOfSigmasTPC(esdtrack,AliPID::kPion);
+        nsigmaTPCP = fESDpid->NumberOfSigmasTPC(esdtrack,AliPID::kProton);
+
+      }
+      trackCopy->SetNSigmaTPCPi(nsigmaTPCPi);
+      trackCopy->SetNSigmaTPCK(nsigmaTPCK);
+      trackCopy->SetNSigmaTPCP(nsigmaTPCP);
+
+      ///// TOF ///////////////////////////////////////////////
+
+       float vp=-1000.;
+       float nsigmaTOFPi=-1000.;
+       float nsigmaTOFK=-1000.;
+       float nsigmaTOFP=-1000.;
+
+       if ((esdtrack->GetStatus()&AliESDtrack::kTOFpid) &&
+           (esdtrack->GetStatus()&AliESDtrack::kTOFout) &&
+           (esdtrack->GetStatus()&AliESDtrack::kTIME) &&
+           !(esdtrack->GetStatus()&AliESDtrack::kTOFmismatch))
+         {
+
+           //if ((esdtrack->GetStatus()&AliESDtrack::kTOFpid) &&
+           //(esdtrack->GetStatus()&AliESDtrack::kTOFout) &&
+           //(esdtrack->GetStatus()&AliESDtrack::kTIME)){
+           // collect info from ESDpid class
+         
+           if ((fESDpid) && (esdtrack->IsOn(AliESDtrack::kTOFpid))) {
+             
+             
+             double tZero = fESDpid->GetTOFResponse().GetStartTime(esdtrack->P());
+             
+             nsigmaTOFPi = fESDpid->NumberOfSigmasTOF(esdtrack,AliPID::kPion,tZero);
+             nsigmaTOFK = fESDpid->NumberOfSigmasTOF(esdtrack,AliPID::kKaon,tZero);
+             nsigmaTOFP = fESDpid->NumberOfSigmasTOF(esdtrack,AliPID::kProton,tZero);
+             
+             Double_t len=esdtrack->GetIntegratedLength();
+             Double_t tof=esdtrack->GetTOFsignal();
+             if(tof > 0.) vp=len/tof/0.03;
+           }
+         }
+       
+       trackCopy->SetVTOF(vp);
+       trackCopy->SetNSigmaTOFPi(nsigmaTOFPi);
+       trackCopy->SetNSigmaTOFK(nsigmaTOFK);
+       trackCopy->SetNSigmaTOFP(nsigmaTOFP);
+       
+       double pxyz[3];
+       double rxyz[3];
+       double impact[2];
+       double covimpact[3];
+      
+       if (fUseTPCOnly) {
+         if (!esdtrack->GetTPCInnerParam()) {
+           delete trackCopy;
+           continue;
+         }
+
+
+         AliExternalTrackParam *param = new AliExternalTrackParam(*esdtrack->GetTPCInnerParam());
+         param->GetXYZ(rxyz);
+         param->PropagateToDCA(fEvent->GetPrimaryVertexTPC(), (fEvent->GetMagneticField()), 10000, impact, covimpact);
+         param->GetPxPyPz(pxyz);//reading noconstarined momentum
+
+         if (fReadInner == true) {
+           AliFemtoModelHiddenInfo *tInfo = new AliFemtoModelHiddenInfo();
+           tInfo->SetPDGPid(211);
+           tInfo->SetTrueMomentum(pxyz[0], pxyz[1], pxyz[2]);
+           tInfo->SetMass(0.13957);
+           //    tInfo->SetEmissionPoint(rxyz[0], rxyz[1], rxyz[2], 0.0);
+           //    tInfo->SetEmissionPoint(fV1[0], fV1[1], fV1[2], 0.0);
+           tInfo->SetEmissionPoint(rxyz[0]-fV1[0], rxyz[1]-fV1[1], rxyz[2]-fV1[2], 0.0);
+           trackCopy->SetHiddenInfo(tInfo);
+         }
+       
+         AliFemtoThreeVector v(pxyz[0],pxyz[1],pxyz[2]);
+         if (v.Mag() < 0.0001) {
+           //  cout << "Found 0 momentum ???? " <<endl;
+           delete trackCopy;
+           continue;
+         }
+         trackCopy->SetP(v);//setting momentum
+         trackCopy->SetPt(sqrt(pxyz[0]*pxyz[0]+pxyz[1]*pxyz[1]));
+
+         const AliFmThreeVectorD kP(pxyz[0],pxyz[1],pxyz[2]);
+         const AliFmThreeVectorD kOrigin(fV1[0],fV1[1],fV1[2]);
+         //setting helix I do not if it is ok
+         AliFmPhysicalHelixD helix(kP,kOrigin,(double)(fEvent->GetMagneticField())*kilogauss,(double)(trackCopy->Charge())); 
+         trackCopy->SetHelix(helix);
+
+         //some stuff which could be useful 
+         trackCopy->SetImpactD(impact[0]);
+         trackCopy->SetImpactZ(impact[1]);
+         trackCopy->SetCdd(covimpact[0]);
+         trackCopy->SetCdz(covimpact[1]);
+         trackCopy->SetCzz(covimpact[2]);
+         trackCopy->SetSigmaToVertex(GetSigmaToVertex(impact, covimpact));     
+
+         delete param;
+       }
+       else {
+         if (fReadInner == true) {
+         
+           if (esdtrack->GetTPCInnerParam()) {
+             AliExternalTrackParam *param = new AliExternalTrackParam(*esdtrack->GetTPCInnerParam());
+             param->GetXYZ(rxyz);
+             //            param->PropagateToDCA(fEvent->GetPrimaryVertex(), (fEvent->GetMagneticField()), 10000);
+             param->GetPxPyPz(pxyz);//reading noconstarined momentum
+             delete param;
+           
+             AliFemtoModelHiddenInfo *tInfo = new AliFemtoModelHiddenInfo();
+             tInfo->SetPDGPid(211);
+             tInfo->SetTrueMomentum(pxyz[0], pxyz[1], pxyz[2]);
+             tInfo->SetMass(0.13957);
+             //            tInfo->SetEmissionPoint(rxyz[0], rxyz[1], rxyz[2], 0.0);
+             //tInfo->SetEmissionPoint(fV1[0], fV1[1], fV1[2], 0.0);
+             tInfo->SetEmissionPoint(rxyz[0]-fV1[0], rxyz[1]-fV1[1], rxyz[2]-fV1[2], 0.0);
+             trackCopy->SetHiddenInfo(tInfo);
+           }
+         }
+
+         if (fTrackType == kGlobal) {
+           if (fConstrained==true)                 
+             tGoodMomentum=esdtrack->GetConstrainedPxPyPz(pxyz); //reading constrained momentum
+           else
+             tGoodMomentum=esdtrack->GetPxPyPz(pxyz);//reading noconstarined momentum
+         }
+         else if (fTrackType == kTPCOnly) {
+           if (esdtrack->GetTPCInnerParam())
+             esdtrack->GetTPCInnerParam()->GetPxPyPz(pxyz);
+           else {
+             delete trackCopy;
+             continue;
+           }
+         }
+         else if (fTrackType == kITSOnly) {
+           if (fConstrained==true)                 
+             tGoodMomentum=esdtrack->GetConstrainedPxPyPz(pxyz); //reading constrained momentum
+           else
+             tGoodMomentum=esdtrack->GetPxPyPz(pxyz);//reading noconstarined momentum
+         }
+
+
+         AliFemtoThreeVector v(pxyz[0],pxyz[1],pxyz[2]);
+         if (v.Mag() < 0.0001) {
+           //  cout << "Found 0 momentum ???? " <<endl;
+           delete trackCopy;
+           continue;
+         }
+         trackCopy->SetP(v);//setting momentum
+         trackCopy->SetPt(sqrt(pxyz[0]*pxyz[0]+pxyz[1]*pxyz[1]));
+         const AliFmThreeVectorD kP(pxyz[0],pxyz[1],pxyz[2]);
+         const AliFmThreeVectorD kOrigin(fV1[0],fV1[1],fV1[2]);
+         //setting helix I do not if it is ok
+         AliFmPhysicalHelixD helix(kP,kOrigin,(double)(fEvent->GetMagneticField())*kilogauss,(double)(trackCopy->Charge())); 
+         trackCopy->SetHelix(helix);
+
+         //some stuff which could be useful 
+         float imp[2];
+         float cim[3];
+         // if (fTrackType == kTPCOnly) {
+         //   esdtrack->GetTPCInnerParam()->GetImpactParameters(imp,cim);
+         // }
+         // else {
+         esdtrack->GetImpactParameters(imp,cim);
+         // }
+
+         impact[0] = imp[0];
+         impact[1] = imp[1];
+         covimpact[0] = cim[0];
+         covimpact[1] = cim[1];
+         covimpact[2] = cim[2];
+
+         trackCopy->SetImpactD(impact[0]);
+         trackCopy->SetImpactZ(impact[1]);
+         trackCopy->SetCdd(covimpact[0]);
+         trackCopy->SetCdz(covimpact[1]);
+         trackCopy->SetCzz(covimpact[2]);
+         trackCopy->SetSigmaToVertex(GetSigmaToVertex(impact,covimpact));
+       }
+
+       trackCopy->SetTrackId(esdtrack->GetID());
+       trackCopy->SetFlags(esdtrack->GetStatus());
+       trackCopy->SetLabel(esdtrack->GetLabel());
+               
+       trackCopy->SetITSchi2(esdtrack->GetITSchi2());    
+       if (esdtrack->GetITSFakeFlag())
+         trackCopy->SetITSncls(-esdtrack->GetNcls(0));     
+       else
+         trackCopy->SetITSncls(esdtrack->GetNcls(0));     
+       trackCopy->SetTPCchi2(esdtrack->GetTPCchi2());       
+       trackCopy->SetTPCncls(esdtrack->GetTPCNcls());       
+       trackCopy->SetTPCnclsF(esdtrack->GetTPCNclsF());      
+       trackCopy->SetTPCsignal(esdtrack->GetTPCsignal());
+       trackCopy->SetTPCsignalN((short)esdtrack->GetTPCsignalN()); //due to bug in aliesdtrack class   
+       trackCopy->SetTPCsignalS(esdtrack->GetTPCsignalSigma()); 
+
+       trackCopy->SetTPCClusterMap(esdtrack->GetTPCClusterMap());
+       trackCopy->SetTPCSharedMap(esdtrack->GetTPCSharedMap());
+
+       double xtpc[3];
+       esdtrack->GetInnerXYZ(xtpc);
+       xtpc[2] -= fV1[2];
+       trackCopy->SetNominalTPCEntrancePoint(xtpc);
+
+       esdtrack->GetOuterXYZ(xtpc);
+       xtpc[2] -= fV1[2];
+       trackCopy->SetNominalTPCExitPoint(xtpc);
+
+       int indexes[3];
+       for (int ik=0; ik<3; ik++) {
+         indexes[ik] = esdtrack->GetKinkIndex(ik);
+       }
+       trackCopy->SetKinkIndexes(indexes);
+       //decision if we want this track
+       //if we using diffrent labels we want that this label was use for first time 
+       //if we use hidden info we want to have match between sim data and ESD
+       if (tGoodMomentum==true)
+         {
+           hbtEvent->TrackCollection()->push_back(trackCopy);//adding track to analysis
+           realnofTracks++;//real number of tracks
+           //    delete trackCopy;
+         }
+       else
+         {
+           delete  trackCopy;
+         }
+               
+    }
+
+  hbtEvent->SetNumberOfTracks(realnofTracks);//setting number of track which we read in event  
+
+  AliCentrality *cent = fEvent->GetCentrality();
+  if (cent) {
+    hbtEvent->SetCentralityV0(cent->GetCentralityPercentile("V0M"));
+    //    hbtEvent->SetCentralityFMD(cent->GetCentralityPercentile("FMD"));
+    hbtEvent->SetCentralitySPD1(cent->GetCentralityPercentile("CL1"));
+    //    hbtEvent->SetCentralityTrk(cent->GetCentralityPercentile("TRK"));
+
+    if (Debug()>1) printf("  FemtoReader Got Event with %f %f %f %f\n", cent->GetCentralityPercentile("V0M"), 0.0, cent->GetCentralityPercentile("CL1"), 0.0);
+  }
+
+  if (fEstEventMult == kGlobalCount) 
+    hbtEvent->SetNormalizedMult(tNormMult);
+  else if (fEstEventMult == kTracklet)
+    hbtEvent->SetNormalizedMult(tTracklet);
+  else if (fEstEventMult == kITSTPC)
+    hbtEvent->SetNormalizedMult(tITSTPC);
+  else if (fEstEventMult == kITSPure)
+    hbtEvent->SetNormalizedMult(tITSPure);
+  else if (fEstEventMult == kSPDLayer1)
+    hbtEvent->SetNormalizedMult(fEvent->GetMultiplicity()->GetNumberOfITSClusters(1));
+  else if (fEstEventMult == kV0Centrality) {
+    // centrality between 0 (central) and 1 (very peripheral)
+
+    if (cent) {
+      if (cent->GetCentralityPercentile("V0M") < 0.00001)
+       hbtEvent->SetNormalizedMult(-1);
+      else
+       hbtEvent->SetNormalizedMult(lrint(10.0*cent->GetCentralityPercentile("V0M")));
+      if (Debug()>1) printf ("Set Centrality %i %f %li\n", hbtEvent->UncorrectedNumberOfPrimaries(), 
+                            10.0*cent->GetCentralityPercentile("V0M"), lrint(10.0*cent->GetCentralityPercentile("V0M")));
+    }
+  }
+
+  if (tNormMultPos > tNormMultNeg)
+    hbtEvent->SetZDCParticipants(tNormMultPos);
+  else
+    hbtEvent->SetZDCParticipants(tNormMultNeg);
+  
+  AliEventplane* ep = fEvent->GetEventplane();
+  if (ep) {
+    hbtEvent->SetEP(ep);
+    hbtEvent->SetReactionPlaneAngle(ep->GetEventplane("Q"));
+  }
+
+  fCurEvent++; 
+  if (Debug()>1) cout<<"end of reading nt "<<nofTracks<<" real number "<<realnofTracks<<endl;
+
+  return hbtEvent; 
+}
+//___________________
+void AliFemtoEventReaderESDChain::SetESDSource(AliESDEvent *aESD)
+{
+  // The chain loads the ESD for us
+  // You must provide the address where it can be found
+  fEvent = aESD;
+}
+//___________________
+// void AliFemtoEventReaderESDChain::SetESDfriendSource(AliESDfriend *aFriend)
+// {
+//   // We need the ESD tree to obtain
+//   // information about the friend file location
+//   fEventFriend = aFriend;
+// }
+
+//____________________________________________________________________
+Float_t AliFemtoEventReaderESDChain::GetSigmaToVertex(double *impact, double *covar)
+{
+  // Calculates the number of sigma to the vertex.
+
+  Float_t b[2];
+  Float_t bRes[2];
+  Float_t bCov[3];
+
+  b[0] = impact[0];
+  b[1] = impact[1];
+  bCov[0] = covar[0];
+  bCov[1] = covar[1];
+  bCov[2] = covar[2];
+
+  bRes[0] = TMath::Sqrt(bCov[0]);
+  bRes[1] = TMath::Sqrt(bCov[2]);
+
+  // -----------------------------------
+  // How to get to a n-sigma cut?
+  //
+  // The accumulated statistics from 0 to d is
+  //
+  // ->  Erf(d/Sqrt(2)) for a 1-dim gauss (d = n_sigma)
+  // ->  1 - Exp(-d**2) for a 2-dim gauss (d*d = dx*dx + dy*dy != n_sigma)
+  //
+  // It means that for a 2-dim gauss: n_sigma(d) = Sqrt(2)*ErfInv(1 - Exp((-x**2)/2)
+  // Can this be expressed in a different way?
+
+  if (bRes[0] == 0 || bRes[1] ==0)
+    return -1;
+
+  Float_t d = TMath::Sqrt(TMath::Power(b[0]/bRes[0],2) + TMath::Power(b[1]/bRes[1],2));
+
+  // stupid rounding problem screws up everything:
+  // if d is too big, TMath::Exp(...) gets 0, and TMath::ErfInverse(1) that should be infinite, gets 0 :(
+  if (TMath::Exp(-d * d / 2) < 1e-10)
+    return 1000;
+
+  d = TMath::ErfInverse(1 - TMath::Exp(-d * d / 2)) * TMath::Sqrt(2);
+  return d;
+}
+
+void AliFemtoEventReaderESDChain::SetReadTrackType(ReadTrackType aType)
+{
+  fTrackType = aType;
+}
+
+//trigger
+void AliFemtoEventReaderESDChain::SetEventTrigger(UInt_t eventtrig)
+{
+  fEventTrig = eventtrig;
+}
+
+
+
+
+
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReaderESDChain.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReaderESDChain.h
new file mode 100644 (file)
index 0000000..fb3b3a1
--- /dev/null
@@ -0,0 +1,99 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoEventReaderESDChain - the reader class for the Alice ESD           //
+// tailored for the Task framework                                            //
+// Reads in AliESDfriend to create shared hit/quality information             //
+// Authors: Adam Kisiel kisiel@mps.ohio-state.edu                             //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+#ifndef ALIFEMTOEVENTREADERESDCHAIN_H
+#define ALIFEMTOEVENTREADERESDCHAIN_H
+
+#include "AliFemtoEventReader.h"
+#include "AliFemtoEnumeration.h"
+
+#include <string>
+#include <vector>
+#include "TTree.h"
+#include "TGraph.h"
+#include "AliESDEvent.h"
+#include "AliESDfriend.h"
+#include "AliPhysicsSelection.h"
+#include <list>
+
+#include "AliESDpid.h"
+
+class AliFemtoEvent;
+
+class AliFemtoEventReaderESDChain : public AliFemtoEventReader 
+{
+ public:
+  enum TrackType {kGlobal=0, kTPCOnly=1, kITSOnly=2, kSPDTracklet=3};
+  typedef enum TrackType ReadTrackType;
+
+  enum EventMult {kTracklet=0, kITSTPC=1, kITSPure=2, kGlobalCount=3, kSPDLayer1=4, kV0Centrality=5 };
+  typedef enum EventMult EstEventMult;
+
+  AliFemtoEventReaderESDChain();
+  AliFemtoEventReaderESDChain(const AliFemtoEventReaderESDChain& aReader);
+  ~AliFemtoEventReaderESDChain();
+
+  AliFemtoEventReaderESDChain& operator=(const AliFemtoEventReaderESDChain& aReader);
+
+  AliFemtoEvent* ReturnHbtEvent();
+  AliFemtoString Report();
+  void SetConstrained(const bool constrained);
+  void SetReadTPCInner(const bool readinner);
+  void SetUseTPCOnly(const bool usetpconly);
+
+  void SetUsePhysicsSelection(const bool usephysics);
+  void SetUseMultiplicity(EstEventMult aType);
+  void SetEventTrigger(UInt_t eventtrig); //trigger
+
+  bool GetConstrained() const;
+  bool GetReadTPCInner() const;
+  bool GetUseTPCOnly() const;
+  
+  void SetReadTrackType(ReadTrackType aType);
+
+  void SetESDSource(AliESDEvent *aESD);
+  //  void SetESDfriendSource(AliESDfriend *aFriend);
+  void SetESDPid(AliESDpid *esdPid) { fESDpid = esdPid; }
+ protected:
+
+ private:
+  string         fFileName;      //name of current ESD file
+  bool           fConstrained;   //flag to set which momentum from ESD file will be use
+  bool           fReadInner;     // flag to set if one wants to read TPC-only momentum
+                                 // and store it in the hidden info
+  bool           fUseTPCOnly;    // flag to set if one wants to replace the global parameters 
+                                 // by the TPC only ones
+  int            fNumberofEvent; //number of Events in ESD file
+  int            fCurEvent;      //number of current event
+  unsigned int   fCurFile;       //number of current file
+  AliESDEvent*   fEvent;         //ESD event
+  //  AliESDfriend*  fEventFriend;
+  bool           fUsePhysicsSel; //if true the physics selection class will be used
+  AliPhysicsSelection *fSelect;  //Class to select only physics events
+  ReadTrackType  fTrackType;     // Type of track read
+  EstEventMult   fEstEventMult;  // Type of the event multiplicity estimator
+  UInt_t         fEventTrig;     //event trigger
+
+/*   list<Int_t>  **fSharedList;       //! Table (one list per padrow) of clusters which are shared */
+/*   list<Int_t>  **fClusterPerPadrow; //! Table (one list per padrow) of clusters in each padrow */
+               
+  Float_t GetSigmaToVertex(double *impact, double *covar);
+
+
+  AliESDpid *fESDpid;
+  Bool_t fIsPidOwner;
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoEventReaderESDChain, 1)
+#endif
+
+    };
+  
+#endif
+
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReaderESDChainKine.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReaderESDChainKine.cxx
new file mode 100644 (file)
index 0000000..a49f97d
--- /dev/null
@@ -0,0 +1,890 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoEventReaderESDChainKine - the reader class for the Alice ESD and   //
+// the model Kinematics information tailored for the Task framework and the   //
+// Reads in AliESDfriend to create shared hit/quality information             //
+// Authors: Adam Kisiel kisiel@mps.ohio-state.edu                             //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+#include "AliFemtoEventReaderESDChainKine.h"
+
+#include "TFile.h"
+#include "TTree.h"
+#include "TList.h"
+#include "AliESDEvent.h"
+#include "AliESDtrack.h"
+#include "AliESDVertex.h"
+
+#include "AliMultiplicity.h"
+#include "AliCentrality.h"
+#include "AliEventplane.h"
+
+#include "AliFmPhysicalHelixD.h"
+#include "AliFmThreeVectorF.h"
+
+#include "SystemOfUnits.h"
+
+#include "AliFemtoEvent.h"
+
+#include "TParticle.h"
+#include "AliFemtoModelHiddenInfo.h"
+#include "AliFemtoModelGlobalHiddenInfo.h"
+#include "AliGenHijingEventHeader.h"
+#include "AliGenCocktailEventHeader.h"
+
+#include "AliVertexerTracks.h"
+
+#include "AliPID.h"
+
+ClassImp(AliFemtoEventReaderESDChainKine)
+
+#if !(ST_NO_NAMESPACES)
+  using namespace units;
+#endif
+
+using namespace std;
+//____________________________
+AliFemtoEventReaderESDChainKine::AliFemtoEventReaderESDChainKine():
+  fFileName(" "),
+  fConstrained(true),
+  fReadInner(false),
+  fUseTPCOnly(false),
+  fNumberofEvent(0),
+  fCurEvent(0),
+  fCurFile(0),
+  fEvent(0x0),
+  fStack(0x0),
+  fGenHeader(0x0),
+  fTrackType(kGlobal),
+  fEstEventMult(kV0Centrality),
+  fRotateToEventPlane(0),
+  fESDpid(0),
+  fIsPidOwner(0)
+
+{
+  //constructor with 0 parameters , look at default settings 
+}
+
+//__________________
+AliFemtoEventReaderESDChainKine::AliFemtoEventReaderESDChainKine(const AliFemtoEventReaderESDChainKine& aReader):
+  AliFemtoEventReader(aReader),
+  fFileName(" "),
+  fConstrained(true),
+  fReadInner(false),
+  fUseTPCOnly(false),
+  fNumberofEvent(0),
+  fCurEvent(0),
+  fCurFile(0),
+  fEvent(0x0),
+  fStack(0x0),
+  fGenHeader(0x0),
+  fTrackType(kGlobal),
+  fEstEventMult(kV0Centrality),
+  fRotateToEventPlane(0),
+  fESDpid(0),
+  fIsPidOwner(0)
+{
+  // Copy constructor
+  fConstrained = aReader.fConstrained;
+  fReadInner = aReader.fReadInner;
+  fUseTPCOnly = aReader.fUseTPCOnly;
+  fNumberofEvent = aReader.fNumberofEvent;
+  fCurEvent = aReader.fCurEvent;
+  fCurFile = aReader.fCurFile;
+  fEvent = new AliESDEvent();
+  fStack = aReader.fStack;
+  fTrackType = aReader.fTrackType;
+  fEstEventMult = aReader.fEstEventMult;
+  fRotateToEventPlane = aReader.fRotateToEventPlane;
+  fESDpid = aReader.fESDpid;
+  fIsPidOwner = aReader.fIsPidOwner;
+}
+//__________________
+AliFemtoEventReaderESDChainKine::~AliFemtoEventReaderESDChainKine()
+{
+  //Destructor
+  delete fEvent;
+}
+
+//__________________
+AliFemtoEventReaderESDChainKine& AliFemtoEventReaderESDChainKine::operator=(const AliFemtoEventReaderESDChainKine& aReader)
+{
+  // Assignment operator
+  if (this == &aReader)
+    return *this;
+
+  fConstrained = aReader.fConstrained;
+  fUseTPCOnly = aReader.fUseTPCOnly;
+  fNumberofEvent = aReader.fNumberofEvent;
+  fCurEvent = aReader.fCurEvent;
+  fCurFile = aReader.fCurFile;
+  if (fEvent) delete fEvent;
+  fEvent = new AliESDEvent();
+  fStack = aReader.fStack;
+  fGenHeader = aReader.fGenHeader;
+  fRotateToEventPlane = aReader.fRotateToEventPlane;
+  fESDpid = aReader.fESDpid;
+  fIsPidOwner = aReader.fIsPidOwner;
+
+  return *this;
+}
+//__________________
+// Simple report
+AliFemtoString AliFemtoEventReaderESDChainKine::Report()
+{
+  AliFemtoString temp = "\n This is the AliFemtoEventReaderESDChainKine\n";
+  return temp;
+}
+
+//__________________
+void AliFemtoEventReaderESDChainKine::SetConstrained(const bool constrained)
+{
+  // Select whether to read constrained or not constrained momentum
+  fConstrained=constrained;
+}
+//__________________
+bool AliFemtoEventReaderESDChainKine::GetConstrained() const
+{
+  // Check whether we read constrained or not constrained momentum
+  return fConstrained;
+}
+//__________________
+void AliFemtoEventReaderESDChainKine::SetReadTPCInner(const bool readinner)
+{
+  fReadInner=readinner;
+}
+
+bool AliFemtoEventReaderESDChainKine::GetReadTPCInner() const
+{
+  return fReadInner;
+}
+
+//__________________
+void AliFemtoEventReaderESDChainKine::SetUseTPCOnly(const bool usetpconly)
+{
+  fUseTPCOnly=usetpconly;
+}
+
+bool AliFemtoEventReaderESDChainKine::GetUseTPCOnly() const
+{
+  return fUseTPCOnly;
+}
+void AliFemtoEventReaderESDChainKine::SetUseMultiplicity(EstEventMult aType)
+{
+  fEstEventMult = aType;
+}
+//__________________
+AliFemtoEvent* AliFemtoEventReaderESDChainKine::ReturnHbtEvent()
+{
+  // Get the event, read all the relevant information
+  // and fill the AliFemtoEvent class
+  // Returns a valid AliFemtoEvent
+  AliFemtoEvent *hbtEvent = 0;
+  string tFriendFileName;
+
+  // Get the friend information
+  cout << "AliFemtoEventReaderESDChainKine::Starting to read event: "<<fCurEvent<<endl;
+  //  fEvent->SetESDfriend(fEventFriend);
+       
+  hbtEvent = new AliFemtoEvent;
+  //setting basic things
+  //  hbtEvent->SetEventNumber(fEvent->GetEventNumber());
+  hbtEvent->SetRunNumber(fEvent->GetRunNumber());
+  //hbtEvent->SetNumberOfTracks(fEvent->GetNumberOfTracks());
+  hbtEvent->SetMagneticField(fEvent->GetMagneticField()*kilogauss);//to check if here is ok
+  hbtEvent->SetZDCN1Energy(fEvent->GetZDCN1Energy());
+  hbtEvent->SetZDCP1Energy(fEvent->GetZDCP1Energy());
+  hbtEvent->SetZDCN2Energy(fEvent->GetZDCN2Energy());
+  hbtEvent->SetZDCP2Energy(fEvent->GetZDCP2Energy());
+  hbtEvent->SetZDCEMEnergy(fEvent->GetZDCEMEnergy());
+  hbtEvent->SetZDCParticipants(fEvent->GetZDCParticipants());
+  hbtEvent->SetTriggerMask(fEvent->GetTriggerMask());
+  //hbtEvent->SetTriggerCluster(fEvent->GetTriggerCluster());
+
+  if ((fEvent->IsTriggerClassFired("CINT1WU-B-NOPF-ALL")) ||
+      (fEvent->IsTriggerClassFired("CINT1B-ABCE-NOPF-ALL")) ||
+      (fEvent->IsTriggerClassFired("CINT1-B-NOPF-ALLNOTRD")) ||
+      (fEvent->IsTriggerClassFired("CINT1-B-NOPF-FASTNOTRD")))
+    hbtEvent->SetTriggerCluster(1);
+  else if ((fEvent->IsTriggerClassFired("CSH1WU-B-NOPF-ALL")) ||
+          (fEvent->IsTriggerClassFired("CSH1-B-NOPF-ALLNOTRD")))
+    hbtEvent->SetTriggerCluster(2);
+  else 
+    hbtEvent->SetTriggerCluster(0);
+
+  //Vertex
+  double fV1[3];
+  double fVCov[6];
+  if (fUseTPCOnly) {
+    fEvent->GetPrimaryVertexTPC()->GetXYZ(fV1);
+    fEvent->GetPrimaryVertexTPC()->GetCovMatrix(fVCov);
+    if (!fEvent->GetPrimaryVertexTPC()->GetStatus())
+      fVCov[4] = -1001.0;
+  }
+  else {
+    fEvent->GetPrimaryVertex()->GetXYZ(fV1);
+    fEvent->GetPrimaryVertex()->GetCovMatrix(fVCov);
+    if (!fEvent->GetPrimaryVertex()->GetStatus())
+      fVCov[4] = -1001.0;
+  }
+
+  AliFmThreeVectorF vertex(fV1[0],fV1[1],fV1[2]);
+  hbtEvent->SetPrimVertPos(vertex);
+  hbtEvent->SetPrimVertCov(fVCov);
+
+  Double_t tReactionPlane = 0;
+
+  AliGenHijingEventHeader *hdh = dynamic_cast<AliGenHijingEventHeader *> (fGenHeader); 
+  if (!hdh) {
+    AliGenCocktailEventHeader *cdh = dynamic_cast<AliGenCocktailEventHeader *> (fGenHeader);
+    if (cdh) {
+      TList *tGenHeaders = cdh->GetHeaders();
+      for (int ihead = 0; ihead<tGenHeaders->GetEntries(); ihead++) {
+       hdh = dynamic_cast<AliGenHijingEventHeader *> (fGenHeader);     
+       if (hdh) break;
+      }
+    }
+  }
+
+  if (hdh)
+    {
+      tReactionPlane = hdh->ReactionPlaneAngle();
+      cout << "Got reaction plane " << tReactionPlane << endl;
+    }
+
+  hbtEvent->SetReactionPlaneAngle(tReactionPlane);
+
+  Int_t spdetaonecount = 0;
+  
+  for (int iter=0; iter<fEvent->GetMultiplicity()->GetNumberOfTracklets(); iter++) 
+    if (fabs(fEvent->GetMultiplicity()->GetEta(iter)) < 1.0)
+      spdetaonecount++;
+
+  //  hbtEvent->SetSPDMult(fEvent->GetMultiplicity()->GetNumberOfTracklets());
+  hbtEvent->SetSPDMult(spdetaonecount);
+
+  //starting to reading tracks
+  int nofTracks=0;  //number of reconstructed tracks in event
+  nofTracks=fEvent->GetNumberOfTracks();
+  int realnofTracks=0;//number of track which we use ina analysis
+
+  int tNormMult = 0;
+  int tNormMultPos = 0;
+  int tNormMultNeg = 0;
+
+  Float_t tTotalPt = 0.0;
+
+  Float_t b[2];
+  Float_t bCov[3];
+
+  Int_t tTracklet=0, tITSTPC=0, tITSPure=0;
+  
+  fEvent->EstimateMultiplicity(tTracklet, tITSTPC, tITSPure, 1.2);
+  
+  hbtEvent->SetMultiplicityEstimateITSTPC(tITSTPC);
+  hbtEvent->SetMultiplicityEstimateTracklets(tTracklet);
+  //  hbtEvent->SetMultiplicityEstimateITSPure(tITSPure);
+  hbtEvent->SetMultiplicityEstimateITSPure(fEvent->GetMultiplicity()->GetNumberOfITSClusters(1));
+
+  Int_t *motherids;
+  if (fStack) {
+    motherids = new Int_t[fStack->GetNtrack()];
+    for (int ip=0; ip<fStack->GetNtrack(); ip++) motherids[ip] = 0;
+
+    // Read in mother ids
+    TParticle *motherpart;
+    for (int ip=0; ip<fStack->GetNtrack(); ip++) {
+      motherpart = fStack->Particle(ip);
+      if (motherpart->GetDaughter(0) > 0)
+       motherids[motherpart->GetDaughter(0)] = ip;
+      if (motherpart->GetDaughter(1) > 0)
+       motherids[motherpart->GetDaughter(1)] = ip;
+      
+//     if (motherpart->GetPdgCode() == 211) {
+//       cout << "Mother " << ip << " has daughters " 
+//        << motherpart->GetDaughter(0) << " " 
+//        << motherpart->GetDaughter(1) << " " 
+//        << motherpart->Vx() << " " 
+//        << motherpart->Vy() << " " 
+//        << motherpart->Vz() << " " 
+//        << endl;
+      
+//     }
+    }
+  }
+  else {
+    printf ("No Stack ???\n");
+    delete hbtEvent;
+    return 0;
+  }
+
+  for (int i=0;i<nofTracks;i++)
+    {
+      //      cout << "Reading track " << i << endl;
+      bool  tGoodMomentum=true; //flaga to chcek if we can read momentum of this track
+               
+       
+      const AliESDtrack *esdtrack=fEvent->GetTrack(i);//getting next track
+      //      const AliESDfriendTrack *tESDfriendTrack = esdtrack->GetFriendTrack();
+
+
+      if ((esdtrack->GetStatus() & AliESDtrack::kTPCrefit) &&
+         (esdtrack->GetStatus() & AliESDtrack::kITSrefit)) {
+       if (esdtrack->GetTPCNcls() > 70) 
+         if (esdtrack->GetTPCchi2()/esdtrack->GetTPCNcls() < 4.0) {
+           if (TMath::Abs(esdtrack->Eta()) < 1.2) {
+             esdtrack->GetImpactParameters(b,bCov);
+             if ((b[0]<0.2) && (b[1] < 0.25)) {
+               tNormMult++;
+               tTotalPt += esdtrack->Pt();
+             }
+           }
+         }
+      }
+      else if (esdtrack->GetStatus() & AliESDtrack::kTPCrefit) {
+       if (esdtrack->GetTPCNcls() > 100) 
+         if (esdtrack->GetTPCchi2()/esdtrack->GetTPCNcls() < 4.0) {
+           if (TMath::Abs(esdtrack->Eta()) < 1.2) {
+             esdtrack->GetImpactParameters(b,bCov);
+             if ((b[0]<2.4) && (b[1] < 3.2)) {
+               tNormMult++;
+               tTotalPt += esdtrack->Pt();
+             }
+           }
+         }
+      }
+      
+      hbtEvent->SetZDCEMEnergy(tTotalPt);
+      //       if (esdtrack->GetStatus() & AliESDtrack::kTPCrefit)
+      //       if (esdtrack->GetTPCNcls() > 80) 
+      //         if (esdtrack->GetTPCchi2()/esdtrack->GetTPCNcls() < 6.0) 
+      //           if (esdtrack->GetConstrainedParam())
+      //             if (fabs(esdtrack->GetConstrainedParam()->Eta()) < 0.5)
+      //               if (esdtrack->GetConstrainedParam()->Pt() < 1.0) {
+      //                 if (esdtrack->GetSign() > 0)
+      //                   tNormMultPos++;
+      //                 else if (esdtrack->GetSign() < 0)
+      //                   tNormMultNeg--;
+      //               }
+
+      // If reading ITS-only tracks, reject all with TPC
+      if (fTrackType == kITSOnly) {
+       if (esdtrack->GetStatus() & AliESDtrack::kTPCrefit) continue;
+       if (!(esdtrack->GetStatus() & AliESDtrack::kITSrefit)) continue;
+       if (esdtrack->GetStatus() & AliESDtrack::kTPCin) continue;
+       UChar_t iclm = esdtrack->GetITSClusterMap();
+       Int_t incls = 0;
+       for (int iter=0; iter<6; iter++) if (iclm&(1<<iter)) incls++;
+       if (incls<=3) {
+         if (Debug()>1) cout << "Rejecting track with " << incls << " clusters" << endl;
+         continue;
+       }
+      }
+
+
+
+      AliFemtoTrack* trackCopy = new AliFemtoTrack();
+      trackCopy->SetCharge((short)esdtrack->GetSign());
+
+      //in aliroot we have AliPID 
+      //0-electron 1-muon 2-pion 3-kaon 4-proton 5-photon 6-pi0 7-neutron 8-kaon0 9-eleCon   
+      //we use only 5 first
+      double esdpid[5];
+      esdtrack->GetESDpid(esdpid);
+      trackCopy->SetPidProbElectron(esdpid[0]);
+      trackCopy->SetPidProbMuon(esdpid[1]);
+      trackCopy->SetPidProbPion(esdpid[2]);
+      trackCopy->SetPidProbKaon(esdpid[3]);
+      trackCopy->SetPidProbProton(esdpid[4]);
+
+      esdpid[0] = -100000.0;
+      esdpid[1] = -100000.0;
+      esdpid[2] = -100000.0;
+      esdpid[3] = -100000.0;
+      esdpid[4] = -100000.0;
+
+      double tTOF = 0.0;
+
+      if (esdtrack->GetStatus()&AliESDtrack::kTOFpid) {
+       tTOF = esdtrack->GetTOFsignal();
+       esdtrack->GetIntegratedTimes(esdpid);
+      }
+
+      trackCopy->SetTofExpectedTimes(tTOF-esdpid[2], tTOF-esdpid[3], tTOF-esdpid[4]);
+
+
+      //////  TPC ////////////////////////////////////////////
+      float nsigmaTPCK=-1000.;                                                        
+      float nsigmaTPCPi=-1000.;                                                        
+      float nsigmaTPCP=-1000.;  
+
+     if ((fESDpid) && (esdtrack->IsOn(AliESDtrack::kTPCpid))){
+        nsigmaTPCK = fESDpid->NumberOfSigmasTPC(esdtrack,AliPID::kKaon);
+        nsigmaTPCPi = fESDpid->NumberOfSigmasTPC(esdtrack,AliPID::kPion);
+        nsigmaTPCP = fESDpid->NumberOfSigmasTPC(esdtrack,AliPID::kProton);
+
+      }
+      trackCopy->SetNSigmaTPCPi(nsigmaTPCPi);
+      trackCopy->SetNSigmaTPCK(nsigmaTPCK);
+      trackCopy->SetNSigmaTPCP(nsigmaTPCP);
+
+      ///// TOF ///////////////////////////////////////////////
+
+      float vp=-1000.;
+      float nsigmaTOFPi=-1000.;
+      float nsigmaTOFK=-1000.;
+      float nsigmaTOFP=-1000.;
+
+       if ((esdtrack->GetStatus()&AliESDtrack::kTOFpid) &&
+           (esdtrack->GetStatus()&AliESDtrack::kTOFout) &&
+           (esdtrack->GetStatus()&AliESDtrack::kTIME) &&
+           !(esdtrack->GetStatus()&AliESDtrack::kTOFmismatch))
+         {
+
+           //if ((esdtrack->GetStatus()&AliESDtrack::kTOFpid) &&
+           //(esdtrack->GetStatus()&AliESDtrack::kTOFout) &&
+           //(esdtrack->GetStatus()&AliESDtrack::kTIME)){
+           // collect info from ESDpid class
+         
+             if ((fESDpid) && (esdtrack->IsOn(AliESDtrack::kTOFpid))) {
+             
+             
+             double tZero = fESDpid->GetTOFResponse().GetStartTime(esdtrack->P());
+             
+             nsigmaTOFPi = fESDpid->NumberOfSigmasTOF(esdtrack,AliPID::kPion,tZero);
+             nsigmaTOFK = fESDpid->NumberOfSigmasTOF(esdtrack,AliPID::kKaon,tZero);
+             nsigmaTOFP = fESDpid->NumberOfSigmasTOF(esdtrack,AliPID::kProton,tZero);
+             
+             Double_t len=esdtrack->GetIntegratedLength();
+             Double_t tof=esdtrack->GetTOFsignal();
+             if(tof > 0.) vp=len/tof/0.03;
+           }
+         }
+
+      trackCopy->SetVTOF(vp);
+      trackCopy->SetNSigmaTOFPi(nsigmaTOFPi);
+      trackCopy->SetNSigmaTOFK(nsigmaTOFK);
+      trackCopy->SetNSigmaTOFP(nsigmaTOFP);
+
+                                               
+      double pxyz[3];
+      double rxyz[3];
+      double impact[2];
+      double covimpact[3];
+      
+      if (fUseTPCOnly) {
+       if (!esdtrack->GetTPCInnerParam()) {
+         cout << "No TPC inner param !" << endl;
+         delete trackCopy;
+         continue;
+       }
+
+       AliExternalTrackParam *param = new AliExternalTrackParam(*esdtrack->GetTPCInnerParam());
+       param->GetXYZ(rxyz);
+       param->PropagateToDCA(fEvent->GetPrimaryVertexTPC(), (fEvent->GetMagneticField()), 10000, impact, covimpact);
+       param->GetPxPyPz(pxyz);//reading noconstarined momentum
+
+         if (fReadInner == true) {
+           AliFemtoModelHiddenInfo *tInfo = new AliFemtoModelHiddenInfo();
+           tInfo->SetPDGPid(211);
+           tInfo->SetTrueMomentum(pxyz[0], pxyz[1], pxyz[2]);
+           tInfo->SetMass(0.13957);
+           //    tInfo->SetEmissionPoint(rxyz[0], rxyz[1], rxyz[2], 0.0);
+           //    tInfo->SetEmissionPoint(fV1[0], fV1[1], fV1[2], 0.0);
+           tInfo->SetEmissionPoint(rxyz[0]-fV1[0], rxyz[1]-fV1[1], rxyz[2]-fV1[2], 0.0);
+           trackCopy->SetHiddenInfo(tInfo);
+         }
+
+       if (fRotateToEventPlane) {
+         double tPhi = TMath::ATan2(pxyz[1], pxyz[0]);
+         double tRad = TMath::Hypot(pxyz[0], pxyz[1]);
+         
+         pxyz[0] = tRad*TMath::Cos(tPhi - tReactionPlane);
+         pxyz[1] = tRad*TMath::Sin(tPhi - tReactionPlane);
+       }
+
+       AliFemtoThreeVector v(pxyz[0],pxyz[1],pxyz[2]);
+       if (v.Mag() < 0.0001) {
+         //      cout << "Found 0 momentum ???? " << pxyz[0] << " " << pxyz[1] << " " << pxyz[2] << endl;
+         delete trackCopy;
+         continue;
+       }
+       trackCopy->SetP(v);//setting momentum
+       trackCopy->SetPt(sqrt(pxyz[0]*pxyz[0]+pxyz[1]*pxyz[1]));
+
+       const AliFmThreeVectorD kP(pxyz[0],pxyz[1],pxyz[2]);
+       const AliFmThreeVectorD kOrigin(fV1[0],fV1[1],fV1[2]);
+       //setting helix I do not if it is ok
+       AliFmPhysicalHelixD helix(kP,kOrigin,(double)(fEvent->GetMagneticField())*kilogauss,(double)(trackCopy->Charge())); 
+       trackCopy->SetHelix(helix);
+
+       //some stuff which could be useful 
+       trackCopy->SetImpactD(impact[0]);
+       trackCopy->SetImpactZ(impact[1]);
+       trackCopy->SetCdd(covimpact[0]);
+       trackCopy->SetCdz(covimpact[1]);
+       trackCopy->SetCzz(covimpact[2]);
+       trackCopy->SetSigmaToVertex(GetSigmaToVertex(impact, covimpact));       
+
+       delete param;
+      }
+      else {
+         if (fReadInner == true) {
+         
+           if (esdtrack->GetTPCInnerParam()) {
+             AliExternalTrackParam *param = new AliExternalTrackParam(*esdtrack->GetTPCInnerParam());
+             param->GetXYZ(rxyz);
+             //            param->PropagateToDCA(fEvent->GetPrimaryVertex(), (fEvent->GetMagneticField()), 10000);
+             param->GetPxPyPz(pxyz);//reading noconstarined momentum
+             delete param;
+           
+             AliFemtoModelHiddenInfo *tInfo = new AliFemtoModelHiddenInfo();
+             tInfo->SetPDGPid(211);
+             tInfo->SetTrueMomentum(pxyz[0], pxyz[1], pxyz[2]);
+             tInfo->SetMass(0.13957);
+             //            tInfo->SetEmissionPoint(rxyz[0], rxyz[1], rxyz[2], 0.0);
+             //tInfo->SetEmissionPoint(fV1[0], fV1[1], fV1[2], 0.0);
+             tInfo->SetEmissionPoint(rxyz[0]-fV1[0], rxyz[1]-fV1[1], rxyz[2]-fV1[2], 0.0);
+             trackCopy->SetHiddenInfo(tInfo);
+           }
+         }
+
+
+       if(fTrackType == kGlobal) {
+       if (fConstrained==true)             
+         tGoodMomentum=esdtrack->GetConstrainedPxPyPz(pxyz); //reading constrained momentum
+       else
+         tGoodMomentum=esdtrack->GetPxPyPz(pxyz);//reading noconstarined momentum
+       }
+         else if (fTrackType == kTPCOnly) {
+           if (esdtrack->GetTPCInnerParam())
+             esdtrack->GetTPCInnerParam()->GetPxPyPz(pxyz);
+           else {
+             delete trackCopy;
+             continue;
+           }
+         }
+         else if (fTrackType == kITSOnly) {
+           if (fConstrained==true)                 
+             tGoodMomentum=esdtrack->GetConstrainedPxPyPz(pxyz); //reading constrained momentum
+           else
+             tGoodMomentum=esdtrack->GetPxPyPz(pxyz);//reading noconstarined momentum
+         }
+
+       if (fRotateToEventPlane) {
+         double tPhi = TMath::ATan2(pxyz[1], pxyz[0]);
+         double tRad = TMath::Hypot(pxyz[0], pxyz[1]);
+         
+         pxyz[0] = tRad*TMath::Cos(tPhi - tReactionPlane);
+         pxyz[1] = tRad*TMath::Sin(tPhi - tReactionPlane);
+       }
+
+       AliFemtoThreeVector v(pxyz[0],pxyz[1],pxyz[2]);
+       if (v.Mag() < 0.0001) {
+         //      cout << "Found 0 momentum ???? "  << pxyz[0] << " " << pxyz[1] << " " << pxyz[2] << endl;
+         delete trackCopy;
+         continue;
+       }
+
+       trackCopy->SetP(v);//setting momentum
+       trackCopy->SetPt(sqrt(pxyz[0]*pxyz[0]+pxyz[1]*pxyz[1]));
+       const AliFmThreeVectorD kP(pxyz[0],pxyz[1],pxyz[2]);
+       const AliFmThreeVectorD kOrigin(fV1[0],fV1[1],fV1[2]);
+       //setting helix I do not if it is ok
+       AliFmPhysicalHelixD helix(kP,kOrigin,(double)(fEvent->GetMagneticField())*kilogauss,(double)(trackCopy->Charge())); 
+       trackCopy->SetHelix(helix);
+       
+       //some stuff which could be useful 
+       float imp[2];
+       float cim[3];
+       esdtrack->GetImpactParameters(imp,cim);
+
+       impact[0] = imp[0];
+       impact[1] = imp[1];
+       covimpact[0] = cim[0];
+       covimpact[1] = cim[1];
+       covimpact[2] = cim[2];
+
+       trackCopy->SetImpactD(impact[0]);
+       trackCopy->SetImpactZ(impact[1]);
+       trackCopy->SetCdd(covimpact[0]);
+       trackCopy->SetCdz(covimpact[1]);
+       trackCopy->SetCzz(covimpact[2]);
+       trackCopy->SetSigmaToVertex(GetSigmaToVertex(impact,covimpact));
+      }
+               
+      trackCopy->SetTrackId(esdtrack->GetID());
+      trackCopy->SetFlags(esdtrack->GetStatus());
+      trackCopy->SetLabel(esdtrack->GetLabel());
+               
+      trackCopy->SetITSchi2(esdtrack->GetITSchi2());    
+      trackCopy->SetITSncls(esdtrack->GetNcls(0));     
+      trackCopy->SetTPCchi2(esdtrack->GetTPCchi2());       
+      trackCopy->SetTPCncls(esdtrack->GetTPCNcls());       
+      trackCopy->SetTPCnclsF(esdtrack->GetTPCNclsF());      
+      trackCopy->SetTPCsignalN((short)esdtrack->GetTPCsignalN()); //due to bug in aliesdtrack class   
+      trackCopy->SetTPCsignalS(esdtrack->GetTPCsignalSigma()); 
+
+
+      trackCopy->SetTPCClusterMap(esdtrack->GetTPCClusterMap());
+      trackCopy->SetTPCSharedMap(esdtrack->GetTPCSharedMap());
+
+      double xtpc[3];
+      esdtrack->GetInnerXYZ(xtpc);
+      xtpc[2] -= fV1[2];
+      trackCopy->SetNominalTPCEntrancePoint(xtpc);
+
+      esdtrack->GetOuterXYZ(xtpc);
+      xtpc[2] -= fV1[2];
+      trackCopy->SetNominalTPCExitPoint(xtpc);
+
+      int indexes[3];
+      for (int ik=0; ik<3; ik++) {
+       indexes[ik] = esdtrack->GetKinkIndex(ik);
+      }
+      trackCopy->SetKinkIndexes(indexes);
+
+
+      // Fill the hidden information with the simulated data
+      if (TMath::Abs(esdtrack->GetLabel()) < fStack->GetNtrack()) {
+       TParticle *tPart = fStack->Particle(TMath::Abs(esdtrack->GetLabel()));
+
+       // Check the mother information
+       
+       // Using the new way of storing the freeze-out information
+       // Final state particle is stored twice on the stack
+       // one copy (mother) is stored with original freeze-out information
+       //   and is not tracked
+       // the other one (daughter) is stored with primary vertex position
+       //   and is tracked
+       
+       // Freeze-out coordinates
+       double fpx=0.0, fpy=0.0, fpz=0.0, fpt=0.0;
+       fpx = tPart->Vx() - fV1[0];
+       fpy = tPart->Vy() - fV1[1];
+       fpz = tPart->Vz() - fV1[2];
+       fpt = tPart->T();
+       
+       AliFemtoModelGlobalHiddenInfo *tInfo = new AliFemtoModelGlobalHiddenInfo();
+       tInfo->SetGlobalEmissionPoint(fpx, fpy, fpz);
+       
+       fpx *= 1e13;
+       fpy *= 1e13;
+       fpz *= 1e13;
+       fpt *= 1e13;
+       
+       //      cout << "Looking for mother ids " << endl;
+       if (motherids[TMath::Abs(esdtrack->GetLabel())]>0) {
+         //    cout << "Got mother id" << endl;
+         TParticle *mother = fStack->Particle(motherids[TMath::Abs(esdtrack->GetLabel())]);
+         // Check if this is the same particle stored twice on the stack
+         if ((mother->GetPdgCode() == tPart->GetPdgCode() || (mother->Px() == tPart->Px()))) {
+           // It is the same particle
+           // Read in the original freeze-out information
+           // and convert it from to [fm]
+           
+           // EPOS style 
+           fpx = mother->Vx()*1e13*0.197327;
+           fpy = mother->Vy()*1e13*0.197327;
+           fpz = mother->Vz()*1e13*0.197327;
+           fpt = mother->T() *1e13*0.197327;
+           
+           
+           // Therminator style 
+//         fpx = mother->Vx()*1e13;
+//         fpy = mother->Vy()*1e13;
+//         fpz = mother->Vz()*1e13;
+//         fpt = mother->T() *1e13*3e10;
+           
+         }
+       }
+       
+       if (fRotateToEventPlane) {
+         double tPhi = TMath::ATan2(fpy, fpx);
+         double tRad = TMath::Hypot(fpx, fpy);
+         
+         fpx = tRad*TMath::Cos(tPhi - tReactionPlane);
+         fpy = tRad*TMath::Sin(tPhi - tReactionPlane);
+       }
+       
+       tInfo->SetPDGPid(tPart->GetPdgCode());
+       
+       if (fRotateToEventPlane) {
+         double tPhi = TMath::ATan2(tPart->Py(), tPart->Px());
+         double tRad = TMath::Hypot(tPart->Px(), tPart->Py());
+         
+         tInfo->SetTrueMomentum(tRad*TMath::Cos(tPhi - tReactionPlane),
+                                tRad*TMath::Sin(tPhi - tReactionPlane),
+                                tPart->Pz());
+       }
+       else
+         tInfo->SetTrueMomentum(tPart->Px(), tPart->Py(), tPart->Pz());
+       Double_t mass2 = (tPart->Energy() *tPart->Energy() -
+                         tPart->Px()*tPart->Px() -
+                         tPart->Py()*tPart->Py() -
+                         tPart->Pz()*tPart->Pz());
+       if (mass2>0.0)
+         tInfo->SetMass(TMath::Sqrt(mass2));
+       else 
+         tInfo->SetMass(0.0);
+       
+       tInfo->SetEmissionPoint(fpx, fpy, fpz, fpt);
+       trackCopy->SetHiddenInfo(tInfo);
+      }
+      else {
+       AliFemtoModelGlobalHiddenInfo *tInfo = new AliFemtoModelGlobalHiddenInfo();
+       tInfo->SetMass(0.0);
+       double fpx=0.0, fpy=0.0, fpz=0.0, fpt=0.0;
+       fpx = fV1[0]*1e13;
+       fpy = fV1[1]*1e13;
+       fpz = fV1[2]*1e13;
+       fpt = 0.0;
+       tInfo->SetEmissionPoint(fpx, fpy, fpz, fpt);
+
+       tInfo->SetTrueMomentum(pxyz[0],pxyz[1],pxyz[2]);
+       
+       trackCopy->SetHiddenInfo(tInfo);
+      }
+      //      cout << "Got freeze-out " << fpx << " " << fpy << " " << fpz << " " << fpt << " " <<  mass2 << " " << tPart->GetPdgCode() << endl; 
+      
+      //decision if we want this track
+      //if we using diffrent labels we want that this label was use for first time 
+      //if we use hidden info we want to have match between sim data and ESD
+      if (tGoodMomentum==true)
+       {
+         hbtEvent->TrackCollection()->push_back(trackCopy);//adding track to analysis
+         realnofTracks++;//real number of tracks
+         //      delete trackCopy;
+       }
+      else
+       {
+         delete  trackCopy;
+       }
+               
+    }
+
+  delete [] motherids;
+  
+  hbtEvent->SetNumberOfTracks(realnofTracks);//setting number of track which we read in event  
+
+  AliCentrality *cent = fEvent->GetCentrality();
+  if (cent) {
+    hbtEvent->SetCentralityV0(cent->GetCentralityPercentile("V0M"));
+    //    hbtEvent->SetCentralityFMD(cent->GetCentralityPercentile("FMD"));
+    hbtEvent->SetCentralitySPD1(cent->GetCentralityPercentile("CL1"));
+    //    hbtEvent->SetCentralityTrk(cent->GetCentralityPercentile("TRK"));
+
+    if (Debug()>1) printf("  FemtoReader Got Event with %f %f %f %f\n", cent->GetCentralityPercentile("V0M"), 0.0, cent->GetCentralityPercentile("CL1"), 0.0);
+  }
+
+  if (fEstEventMult == kGlobalCount) 
+    hbtEvent->SetNormalizedMult(tNormMult);
+  else if (fEstEventMult == kTracklet)
+    hbtEvent->SetNormalizedMult(tTracklet);
+  else if (fEstEventMult == kITSTPC)
+    hbtEvent->SetNormalizedMult(tITSTPC);
+  else if (fEstEventMult == kITSPure)
+    hbtEvent->SetNormalizedMult(tITSPure);
+  else if (fEstEventMult == kSPDLayer1)
+    hbtEvent->SetNormalizedMult(fEvent->GetMultiplicity()->GetNumberOfITSClusters(1));
+  else if (fEstEventMult == kV0Centrality) {
+    // centrality between 0 (central) and 1 (very peripheral)
+
+    if (cent) {
+      if (cent->GetCentralityPercentile("V0M") < 0.00001)
+       hbtEvent->SetNormalizedMult(-1);
+      else
+       hbtEvent->SetNormalizedMult(lrint(10.0*cent->GetCentralityPercentile("V0M")));
+      if (Debug()>1) printf ("Set Centrality %i %f %li\n", hbtEvent->UncorrectedNumberOfPrimaries(), 
+                            10.0*cent->GetCentralityPercentile("V0M"), lrint(10.0*cent->GetCentralityPercentile("V0M")));
+    }
+  }
+
+  if (tNormMultPos > tNormMultNeg)
+    hbtEvent->SetZDCParticipants(tNormMultPos);
+  else
+    hbtEvent->SetZDCParticipants(tNormMultNeg);
+  
+  AliEventplane* ep = fEvent->GetEventplane();
+  if (ep) {
+    hbtEvent->SetEP(ep);
+    hbtEvent->SetReactionPlaneAngle(ep->GetEventplane("Q"));
+  }
+
+
+  fCurEvent++; 
+  //  cout<<"end of reading nt "<<nofTracks<<" real number "<<realnofTracks<<endl;
+  return hbtEvent; 
+}
+//___________________
+void AliFemtoEventReaderESDChainKine::SetESDSource(AliESDEvent *aESD)
+{
+  // The chain loads the ESD for us
+  // You must provide the address where it can be found
+  fEvent = aESD;
+}
+//___________________
+void AliFemtoEventReaderESDChainKine::SetStackSource(AliStack *aStack)
+{
+  // The chain loads the stack for us
+  // You must provide the address where it can be found
+  fStack = aStack;
+}
+//___________________
+void AliFemtoEventReaderESDChainKine::SetGenEventHeader(AliGenEventHeader *aGenHeader)
+{
+  // The chain loads the generator event header for us
+  // You must provide the address where it can be found
+  fGenHeader = aGenHeader;
+}
+void AliFemtoEventReaderESDChainKine::SetRotateToEventPlane(short dorotate)
+{
+  fRotateToEventPlane=dorotate;
+}
+Float_t AliFemtoEventReaderESDChainKine::GetSigmaToVertex(double *impact, double *covar)
+{
+  // Calculates the number of sigma to the vertex.
+
+  Float_t b[2];
+  Float_t bRes[2];
+  Float_t bCov[3];
+
+  b[0] = impact[0];
+  b[1] = impact[1];
+  bCov[0] = covar[0];
+  bCov[1] = covar[1];
+  bCov[2] = covar[2];
+
+  bRes[0] = TMath::Sqrt(bCov[0]);
+  bRes[1] = TMath::Sqrt(bCov[2]);
+
+  // -----------------------------------
+  // How to get to a n-sigma cut?
+  //
+  // The accumulated statistics from 0 to d is
+  //
+  // ->  Erf(d/Sqrt(2)) for a 1-dim gauss (d = n_sigma)
+  // ->  1 - Exp(-d**2) for a 2-dim gauss (d*d = dx*dx + dy*dy != n_sigma)
+  //
+  // It means that for a 2-dim gauss: n_sigma(d) = Sqrt(2)*ErfInv(1 - Exp((-x**2)/2)
+  // Can this be expressed in a different way?
+
+  if (bRes[0] == 0 || bRes[1] ==0)
+    return -1;
+
+  Float_t d = TMath::Sqrt(TMath::Power(b[0]/bRes[0],2) + TMath::Power(b[1]/bRes[1],2));
+
+  // stupid rounding problem screws up everything:
+  // if d is too big, TMath::Exp(...) gets 0, and TMath::ErfInverse(1) that should be infinite, gets 0 :(
+  if (TMath::Exp(-d * d / 2) < 1e-10)
+    return 1000;
+
+  d = TMath::ErfInverse(1 - TMath::Exp(-d * d / 2)) * TMath::Sqrt(2);
+  return d;
+}
+
+void AliFemtoEventReaderESDChainKine::SetReadTrackType(ReadTrackType aType)
+{
+  fTrackType = aType;
+}
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReaderESDChainKine.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReaderESDChainKine.h
new file mode 100644 (file)
index 0000000..09f07bc
--- /dev/null
@@ -0,0 +1,94 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoEventReaderESDChainKine - the reader class for the Alice ESD and   //
+// the model Kinematics information tailored for the Task framework and the   //
+// Reads in AliESDfriend to create shared hit/quality information             //
+// Authors: Adam Kisiel kisiel@mps.ohio-state.edu                             //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+#ifndef ALIFEMTOEVENTREADERESDCHAINKINE_H
+#define ALIFEMTOEVENTREADERESDCHAINKINE_H
+
+#include "AliFemtoEventReader.h"
+#include "AliFemtoEnumeration.h"
+
+#include <string>
+#include <vector>
+#include <TTree.h>
+#include <AliESDEvent.h>
+#include <AliESDfriend.h>
+#include <AliStack.h>
+#include <list>
+#include <AliGenEventHeader.h>
+
+#include "AliESDpid.h"
+
+class AliFemtoEvent;
+
+class AliFemtoEventReaderESDChainKine : public AliFemtoEventReader 
+{
+ public:
+  enum TrackType {kGlobal=0, kTPCOnly=1, kITSOnly=2, kSPDTracklet=3};
+  typedef enum TrackType ReadTrackType;
+
+  enum EventMult {kTracklet=0, kITSTPC=1, kITSPure=2, kGlobalCount=3, kSPDLayer1=4, kV0Centrality=5 };
+  typedef enum EventMult EstEventMult;
+
+  AliFemtoEventReaderESDChainKine();
+  AliFemtoEventReaderESDChainKine(const AliFemtoEventReaderESDChainKine& aReader);
+  ~AliFemtoEventReaderESDChainKine();
+
+  AliFemtoEventReaderESDChainKine& operator=(const AliFemtoEventReaderESDChainKine& aReader);
+
+  AliFemtoEvent* ReturnHbtEvent();
+  AliFemtoString Report();
+  void SetConstrained(const bool constrained);
+  bool GetConstrained() const;
+  void SetUseTPCOnly(const bool usetpconly);
+  bool GetUseTPCOnly() const;
+  void SetReadTPCInner(const bool readinner);
+  bool GetReadTPCInner() const;
+
+  void SetUseMultiplicity(EstEventMult aType);
+
+  void SetReadTrackType(ReadTrackType aType);
+
+  void SetESDSource(AliESDEvent *aESD);
+  void SetStackSource(AliStack *aStack);
+  void SetGenEventHeader(AliGenEventHeader *aGenHeader);
+  void SetRotateToEventPlane(short dorotate);
+
+  void SetESDPid(AliESDpid *esdPid) { fESDpid = esdPid; }
+
+ protected:
+
+ private:
+  string         fFileName;      // name of current ESD file
+  bool           fConstrained;   // flag to set which momentum from ESD file will be use
+  bool           fReadInner;     // flag to set if one wants to read TPC-only momentum
+  bool           fUseTPCOnly;    // flog to set to read TPC only momentum instead of the full
+  int            fNumberofEvent; // number of Events in ESD file
+  int            fCurEvent;      // number of current event
+  unsigned int   fCurFile;       // number of current file
+  AliESDEvent*   fEvent;         // ESD event
+  AliStack      *fStack;         // Kinematics stack pointer
+  AliGenEventHeader *fGenHeader; // Link to the generator event header
+  ReadTrackType  fTrackType;     // Type of track read
+  EstEventMult   fEstEventMult;  // Type of the event multiplicity estimator
+
+  short          fRotateToEventPlane; // Rotate the event so that event plane is at x=0
+
+  Float_t GetSigmaToVertex(double *impact, double *covar);
+
+  AliESDpid *fESDpid;
+  Bool_t fIsPidOwner;
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoEventReaderESDChainKine, 1)
+#endif
+
+    };
+  
+#endif
+
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReaderKinematicsChain.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReaderKinematicsChain.cxx
new file mode 100644 (file)
index 0000000..a53dea4
--- /dev/null
@@ -0,0 +1,347 @@
+/////////////////////////////////////////////////////////////////////////////////////
+//                                                                                 //
+// AliFemtoEventReaderKinematicsChain - the reader class for the Alice ESD and     //
+// the model Kinematics information tailored for the Task framework and the        //
+// Reads in AliESDfriend to create shared hit/quality information                  //
+// Authors: Malgorzata Janik, Warsaw University of Technology, majanik@cern.ch     //
+//          Lukasz Graczykowski, Warsaw University of Technology, lgraczyk@cern.ch //
+//                                                                                //
+/////////////////////////////////////////////////////////////////////////////////////
+
+#include "AliFemtoEventReaderKinematicsChain.h"
+
+#include "TFile.h"
+#include "TTree.h"
+#include "TList.h"
+
+#include "AliFmPhysicalHelixD.h"
+#include "AliFmThreeVectorF.h"
+
+#include "SystemOfUnits.h"
+
+#include "AliFemtoEvent.h"
+
+#include "TParticle.h"
+#include "AliStack.h"
+#include "TParticlePDG.h"
+#include "AliFemtoModelHiddenInfo.h"
+#include "AliFemtoModelGlobalHiddenInfo.h"
+#include "AliGenHijingEventHeader.h"
+#include "AliGenCocktailEventHeader.h"
+
+#include "AliVertexerTracks.h"
+
+ClassImp(AliFemtoEventReaderKinematicsChain)
+
+#if !(ST_NO_NAMESPACES)
+  using namespace units;
+#endif
+
+using namespace std;
+//____________________________
+AliFemtoEventReaderKinematicsChain::AliFemtoEventReaderKinematicsChain():
+  fFileName(" "),
+  fConstrained(true),
+  fNumberofEvent(0),
+  fCurEvent(0),
+  fCurFile(0),
+  fStack(0x0),
+  fGenHeader(0x0),
+  fRotateToEventPlane(0)
+{
+  //constructor with 0 parameters , look at default settings 
+}
+
+//__________________
+AliFemtoEventReaderKinematicsChain::AliFemtoEventReaderKinematicsChain(const AliFemtoEventReaderKinematicsChain& aReader):
+  AliFemtoEventReader(aReader),
+  fFileName(" "),
+  fConstrained(true),
+  fNumberofEvent(0),
+  fCurEvent(0),
+  fCurFile(0),
+  fStack(0x0),
+  fGenHeader(0x0),
+  fRotateToEventPlane(0)
+{
+  // Copy constructor
+  fConstrained = aReader.fConstrained;
+  fNumberofEvent = aReader.fNumberofEvent;
+  fCurEvent = aReader.fCurEvent;
+  fCurFile = aReader.fCurFile;
+  fStack = aReader.fStack;
+  fRotateToEventPlane = aReader.fRotateToEventPlane;
+}
+//__________________
+AliFemtoEventReaderKinematicsChain::~AliFemtoEventReaderKinematicsChain()
+{
+  //Destructor
+  //delete fEvent;
+}
+
+//__________________
+AliFemtoEventReaderKinematicsChain& AliFemtoEventReaderKinematicsChain::operator=(const AliFemtoEventReaderKinematicsChain& aReader)
+{
+  // Assignment operator
+  if (this == &aReader)
+    return *this;
+
+  fConstrained = aReader.fConstrained;
+  fNumberofEvent = aReader.fNumberofEvent;
+  fCurEvent = aReader.fCurEvent;
+  fCurFile = aReader.fCurFile;
+  fStack = aReader.fStack;
+  fGenHeader = aReader.fGenHeader;
+  fRotateToEventPlane = aReader.fRotateToEventPlane;
+  return *this;
+}
+//__________________
+// Simple report
+AliFemtoString AliFemtoEventReaderKinematicsChain::Report()
+{
+  AliFemtoString temp = "\n This is the AliFemtoEventReaderKinematicsChain\n";
+  return temp;
+}
+
+//__________________
+void AliFemtoEventReaderKinematicsChain::SetConstrained(const bool constrained)
+{
+  // Select whether to read constrained or not constrained momentum
+  fConstrained=constrained;
+}
+//__________________
+bool AliFemtoEventReaderKinematicsChain::GetConstrained() const
+{
+  // Check whether we read constrained or not constrained momentum
+  return fConstrained;
+}
+//__________________
+AliFemtoEvent* AliFemtoEventReaderKinematicsChain::ReturnHbtEvent()
+{
+  // Get the event, read all the relevant information from the stack
+  // and fill the AliFemtoEvent class
+  // Returns a valid AliFemtoEvent
+  AliFemtoEvent *hbtEvent = 0;
+  string tFriendFileName;
+
+  cout << "AliFemtoEventReaderKinematlaicsChain::Starting to read event: "<<fCurEvent<<endl;
+       
+  hbtEvent = new AliFemtoEvent;
+  //setting basic things
+  //  hbtEvent->SetEventNumber(fEvent->GetEventNumber());
+  hbtEvent->SetRunNumber(0); //No Run number in Kinematics!
+  hbtEvent->SetMagneticField(0*kilogauss);//to check if here is ok
+  hbtEvent->SetZDCN1Energy(0);
+  hbtEvent->SetZDCP1Energy(0);
+  hbtEvent->SetZDCN2Energy(0);
+  hbtEvent->SetZDCP2Energy(0);
+  hbtEvent->SetZDCEMEnergy(0);
+  hbtEvent->SetZDCParticipants(0);
+  hbtEvent->SetTriggerMask(0);
+  hbtEvent->SetTriggerCluster(0);
+       
+  //Vertex
+  double fV1[3] = {0.0,0.0,0.0};
+  double fVCov[6] = {0.0, 0.0, 0.0, 0.0, 0.0, 0.0};
+
+
+  AliFmThreeVectorF vertex(0,0,0);
+    
+  
+  hbtEvent->SetPrimVertPos(vertex);
+  hbtEvent->SetPrimVertCov(fVCov);
+
+  Double_t tReactionPlane = 0;
+
+  AliGenHijingEventHeader *hdh = dynamic_cast<AliGenHijingEventHeader *> (fGenHeader); 
+  if (!hdh) {
+    AliGenCocktailEventHeader *cdh = dynamic_cast<AliGenCocktailEventHeader *> (fGenHeader);
+    if (cdh) {
+      TList *tGenHeaders = cdh->GetHeaders();
+      for (int ihead = 0; ihead<tGenHeaders->GetEntries(); ihead++) {
+       hdh = dynamic_cast<AliGenHijingEventHeader *> (fGenHeader);     
+       if (hdh) break;
+      }
+    }
+  }
+
+  if (hdh)
+    {
+      tReactionPlane = hdh->ReactionPlaneAngle();
+      cout << "Got reaction plane " << tReactionPlane << endl;
+    }
+
+  hbtEvent->SetReactionPlaneAngle(tReactionPlane);
+
+  //starting to reading tracks
+  int nofTracks=0;  //number of all tracks in MC event
+  nofTracks=fStack->GetNtrack(); 
+  int realnofTracks=0;//number of track which we use in analysis
+
+
+  int tNormMult = 0;
+  for (int i=0;i<nofTracks;i++)
+    {
+
+      //take only primaries
+      if(!fStack->IsPhysicalPrimary(i)) {continue;}
+                 
+      AliFemtoTrack* trackCopy = new AliFemtoTrack();  
+       
+         //getting next track
+      TParticle *kinetrack= fStack->Particle(i);
+
+      //setting multiplicity
+        realnofTracks++;//real number of tracks (only primary particles)
+
+      //setting normalized multiplicity
+      if (kinetrack->Eta() < 0.9)
+       if(kinetrack->GetPDG()->Charge()/3!=0)
+         tNormMult++;
+         
+         
+         //charge
+      trackCopy->SetCharge((short)(fStack->Particle(i)->GetPDG()->Charge()/3));
+
+
+      //in aliroot we have AliPID 
+      //0-electron 1-muon 2-pion 3-kaon 4-proton 5-photon 6-pi0 7-neutron 8-kaon0 9-eleCon   
+      //we use only 5 first
+      double kinepid[5];
+      for(int pid_iter=0;pid_iter<5;pid_iter++)
+         kinepid[pid_iter]=0;
+
+      int pdgcode = kinetrack->GetPdgCode();
+      //proton
+      if(pdgcode==2212 || pdgcode==-2212)
+        kinepid[4]=1000;
+      //kaon
+      if(pdgcode==321 || pdgcode==-321 )
+        kinepid[3]=1000;
+      //pion
+      if( pdgcode==211 || pdgcode==-211)
+        kinepid[2]=1000;
+      //electron
+      if(pdgcode==11 || pdgcode==-11)
+        kinepid[0]=1000;
+      //muon
+      if(pdgcode==13 || pdgcode==-13)
+        kinepid[1]=1000;
+
+      trackCopy->SetPidProbElectron(kinepid[0]);
+      trackCopy->SetPidProbMuon(kinepid[1]);
+      trackCopy->SetPidProbPion(kinepid[2]);
+      trackCopy->SetPidProbKaon(kinepid[3]);
+      trackCopy->SetPidProbProton(kinepid[4]);
+                                       
+                                       
+       //Momentum
+      double pxyz[3];
+      double rxyz[3];
+     
+       pxyz[0]=kinetrack->Px();
+       pxyz[1]=kinetrack->Py();
+       pxyz[2]=kinetrack->Pz();
+
+       rxyz[0]=kinetrack->Vx();
+       rxyz[1]=kinetrack->Vy();
+       rxyz[2]=kinetrack->Vz();
+
+       if (fRotateToEventPlane) {
+         double tPhi = TMath::ATan2(pxyz[1], pxyz[0]);
+         double tRad = TMath::Hypot(pxyz[0], pxyz[1]);
+         
+         pxyz[0] = tRad*TMath::Cos(tPhi - tReactionPlane);
+         pxyz[1] = tRad*TMath::Sin(tPhi - tReactionPlane);
+       }
+
+       AliFemtoThreeVector v(pxyz[0],pxyz[1],pxyz[2]);
+       if (v.Mag() < 0.0001) {
+         //      cout << "Found 0 momentum ???? "  << pxyz[0] << " " << pxyz[1] << " " << pxyz[2] << endl;
+         delete trackCopy;
+         continue;
+       }
+
+       trackCopy->SetP(v);//setting momentum
+       trackCopy->SetPt(sqrt(pxyz[0]*pxyz[0]+pxyz[1]*pxyz[1]));
+       const AliFmThreeVectorD kP(pxyz[0],pxyz[1],pxyz[2]);
+       const AliFmThreeVectorD kOrigin(fV1[0],fV1[1],fV1[2]);
+
+       //label
+    trackCopy->SetLabel(i);
+
+
+       hbtEvent->TrackCollection()->push_back(trackCopy);//adding track to analysis
+       
+               
+    }
+  
+  hbtEvent->SetNumberOfTracks(realnofTracks);//setting number of track which we read in event
+  hbtEvent->SetNormalizedMult(tNormMult);
+  fCurEvent++; 
+
+  return hbtEvent; 
+}
+
+//___________________
+void AliFemtoEventReaderKinematicsChain::SetStackSource(AliStack *aStack)
+{
+  // The chain loads the stack for us
+  // You must provide the address where it can be found
+  fStack = aStack;
+}
+//___________________
+void AliFemtoEventReaderKinematicsChain::SetGenEventHeader(AliGenEventHeader *aGenHeader)
+{
+  // The chain loads the generator event header for us
+  // You must provide the address where it can be found
+  fGenHeader = aGenHeader;
+}
+
+//__________________
+void AliFemtoEventReaderKinematicsChain::SetRotateToEventPlane(short dorotate)
+{
+  fRotateToEventPlane=dorotate;
+}
+
+Float_t AliFemtoEventReaderKinematicsChain::GetSigmaToVertex(double *impact, double *covar)
+{
+  // Calculates the number of sigma to the vertex.
+
+  Float_t b[2];
+  Float_t bRes[2];
+  Float_t bCov[3];
+
+  b[0] = impact[0];
+  b[1] = impact[1];
+  bCov[0] = covar[0];
+  bCov[1] = covar[1];
+  bCov[2] = covar[2];
+
+  bRes[0] = TMath::Sqrt(bCov[0]);
+  bRes[1] = TMath::Sqrt(bCov[2]);
+
+  // -----------------------------------
+  // How to get to a n-sigma cut?
+  //
+  // The accumulated statistics from 0 to d is
+  //
+  // ->  Erf(d/Sqrt(2)) for a 1-dim gauss (d = n_sigma)
+  // ->  1 - Exp(-d**2) for a 2-dim gauss (d*d = dx*dx + dy*dy != n_sigma)
+  //
+  // It means that for a 2-dim gauss: n_sigma(d) = Sqrt(2)*ErfInv(1 - Exp((-x**2)/2)
+  // Can this be expressed in a different way?
+
+  if (bRes[0] == 0 || bRes[1] ==0)
+    return -1;
+
+  Float_t d = TMath::Sqrt(TMath::Power(b[0]/bRes[0],2) + TMath::Power(b[1]/bRes[1],2));
+
+  // stupid rounding problem screws up everything:
+  // if d is too big, TMath::Exp(...) gets 0, and TMath::ErfInverse(1) that should be infinite, gets 0 :(
+  if (TMath::Exp(-d * d / 2) < 1e-10)
+    return 1000;
+
+  d = TMath::ErfInverse(1 - TMath::Exp(-d * d / 2)) * TMath::Sqrt(2);
+  return d;
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReaderKinematicsChain.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReaderKinematicsChain.h
new file mode 100644 (file)
index 0000000..2b61045
--- /dev/null
@@ -0,0 +1,69 @@
+/////////////////////////////////////////////////////////////////////////////////////
+//                                                                                 //
+// AliFemtoEventReaderKinematicsChain - the reader class for the Alice ESD and     //
+// the model Kinematics information tailored for the Task framework and the        //
+// Reads in AliESDfriend to create shared hit/quality information                  //
+// Authors: Malgorzata Janik, Warsaw University of Technology, majanik@cern.ch     //
+//          Lukasz Graczykowski, Warsaw University of Technology, lgraczyk@cern.ch //
+//                                                                                //
+/////////////////////////////////////////////////////////////////////////////////////
+
+
+#ifndef ALIFEMTOEVENTREADERKINEMATICSCHAIN_H
+#define ALIFEMTOEVENTREADERKINEMATICSCHAIN_H
+
+#include "AliFemtoEventReader.h"
+#include "AliFemtoEnumeration.h"
+
+#include <string>
+#include <vector>
+#include <TTree.h>
+#include <AliStack.h>
+#include <list>
+#include <AliGenEventHeader.h>
+
+class AliFemtoEvent;
+
+class AliFemtoEventReaderKinematicsChain : public AliFemtoEventReader 
+{
+ public:
+  AliFemtoEventReaderKinematicsChain();
+  AliFemtoEventReaderKinematicsChain(const AliFemtoEventReaderKinematicsChain& aReader);
+  ~AliFemtoEventReaderKinematicsChain();
+
+  AliFemtoEventReaderKinematicsChain& operator=(const AliFemtoEventReaderKinematicsChain& aReader);
+
+  AliFemtoEvent* ReturnHbtEvent();
+  AliFemtoString Report();
+  void SetConstrained(const bool constrained);
+  bool GetConstrained() const;
+
+  //void SetESDSource(AliESDEvent *aESD);
+  void SetStackSource(AliStack *aStack);
+  void SetGenEventHeader(AliGenEventHeader *aGenHeader);
+  void SetRotateToEventPlane(short dorotate);
+
+ protected:
+
+ private:
+  string         fFileName;      // name of current ESD file
+  bool           fConstrained;   // flag to set which momentum from ESD file will be use
+  int            fNumberofEvent; // number of Events in ESD file
+  int            fCurEvent;      // number of current event
+  unsigned int   fCurFile;       // number of current file
+  AliStack       *fStack;         // Kinematics stack pointer
+  AliGenEventHeader *fGenHeader; // Link to the generator event header
+
+  short          fRotateToEventPlane; // Rotate the event so that event plane is at x=0
+
+  Float_t GetSigmaToVertex(double *impact, double *covar);
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoEventReaderKinematicsChain, 1)
+#endif
+
+    };
+  
+#endif
+
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReaderStandard.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReaderStandard.cxx
new file mode 100644 (file)
index 0000000..5c2aa67
--- /dev/null
@@ -0,0 +1,880 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoEventReaderStandard - the reader class for the Alice ESD, AOD      //
+// the model Kinematics information tailored for the Task framework           //
+// Authors: Adam Kisiel Adam.Kisiel@cern.ch                                   //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+#include "AliFemtoEventReaderStandard.h"
+
+#include "TFile.h"
+#include "TTree.h"
+#include "TList.h"
+#include "TBits.h"
+#include "AliESDEvent.h"
+#include "AliESDtrack.h"
+#include "AliESDVertex.h"
+
+#include "AliFmPhysicalHelixD.h"
+#include "AliFmThreeVectorF.h"
+
+#include "SystemOfUnits.h"
+
+#include "AliFemtoEvent.h"
+
+#include "TParticle.h"
+#include "AliFemtoModelHiddenInfo.h"
+#include "AliFemtoModelGlobalHiddenInfo.h"
+#include "AliGenHijingEventHeader.h"
+#include "AliGenCocktailEventHeader.h"
+
+#include "AliAODMCHeader.h"
+#include "AliAODMCParticle.h"
+
+#include "AliVertexerTracks.h"
+
+ClassImp(AliFemtoEventReaderStandard)
+
+#if !(ST_NO_NAMESPACES)
+  using namespace units;
+#endif
+
+using namespace std;
+//____________________________
+AliFemtoEventReaderStandard::AliFemtoEventReaderStandard():
+  AliFemtoEventReader(),
+  fFileName(" "),
+  fNumberofEvent(0),
+  fCurEvent(0),
+  fCurFile(0),
+  fESDEvent(0x0),
+  fAODEvent(0x0),
+  fStack(0x0),
+  fGenHeader(0x0),
+  fInputType(kUnknown),
+  fUsePhysicsSel(kFALSE),
+  fSelect(0),
+  fTrackCuts(0x0),
+  fUseTPCOnly(kFALSE)
+{
+  //constructor with 0 parameters , look at default settings 
+}
+
+//__________________
+AliFemtoEventReaderStandard::AliFemtoEventReaderStandard(const AliFemtoEventReaderStandard& aReader):
+  AliFemtoEventReader(aReader),
+  fFileName(" "),
+  fNumberofEvent(0),
+  fCurEvent(0),
+  fCurFile(0),
+  fESDEvent(0x0),
+  fAODEvent(0x0),
+  fStack(0x0),
+  fGenHeader(0x0),
+  fInputType(kUnknown),
+  fUsePhysicsSel(kFALSE),
+  fSelect(0),
+  fTrackCuts(0x0),
+  fUseTPCOnly(kFALSE)
+{
+  // Copy constructor
+  fCurEvent = aReader.fCurEvent;
+  fCurFile = aReader.fCurFile;
+  fESDEvent = new AliESDEvent();
+  fAODEvent = new AliAODEvent();
+  fStack = aReader.fStack;
+  fInputType = aReader.fInputType;
+  fUsePhysicsSel = aReader.fUsePhysicsSel;
+  if (fUsePhysicsSel) fSelect = new AliPhysicsSelection();
+  fTrackCuts = new AliESDtrackCuts(*(aReader.fTrackCuts));
+  fUseTPCOnly = aReader.fUseTPCOnly;
+}
+//__________________
+AliFemtoEventReaderStandard::~AliFemtoEventReaderStandard()
+{
+  //Destructor
+  delete fESDEvent;
+  delete fAODEvent;
+  if (fTrackCuts) delete fTrackCuts;
+}
+
+//__________________
+AliFemtoEventReaderStandard& AliFemtoEventReaderStandard::operator=(const AliFemtoEventReaderStandard& aReader)
+{
+  // Assignment operator
+  if (this == &aReader)
+    return *this;
+
+  fCurEvent = aReader.fCurEvent;
+  fCurFile = aReader.fCurFile;
+  if (fESDEvent) delete fESDEvent;
+  fESDEvent = new AliESDEvent();
+  if (fAODEvent) delete fAODEvent;
+  fAODEvent = new AliAODEvent();
+  fStack = aReader.fStack;
+  fGenHeader = aReader.fGenHeader;
+  fInputType = aReader.fInputType;
+  fUsePhysicsSel = aReader.fUsePhysicsSel;
+  if (fUsePhysicsSel) fSelect = new AliPhysicsSelection();
+  if (fTrackCuts) delete fTrackCuts;
+  fTrackCuts = new AliESDtrackCuts(*(aReader.fTrackCuts));
+  fUseTPCOnly = aReader.fUseTPCOnly;
+
+  return *this;
+}
+//__________________
+// Simple report
+AliFemtoString AliFemtoEventReaderStandard::Report()
+{
+  AliFemtoString temp = "\n This is the AliFemtoEventReaderStandard\n";
+  return temp;
+}
+//__________________
+AliFemtoEvent* AliFemtoEventReaderStandard::ReturnHbtEvent()
+{
+  // Get the event, read all the relevant information
+  // and fill the AliFemtoEvent class
+  // Returns a valid AliFemtoEvent
+  AliFemtoEvent *hbtEvent = 0;
+  string tFriendFileName;
+
+  hbtEvent = new AliFemtoEvent;
+
+  // Get the friend information
+  cout<<"starting to read event "<<fCurEvent<<endl;
+  if ((fInputType == kESD) || (fInputType == kESDKine)) {
+    if(fESDEvent->GetAliESDOld())fESDEvent->CopyFromOldESD();
+  
+    if (fUsePhysicsSel) {
+      hbtEvent->SetIsCollisionCandidate(fSelect->IsCollisionCandidate(fESDEvent));
+      if (!(fSelect->IsCollisionCandidate(fESDEvent)))
+       printf("Event not a collision candidate\n");
+    }
+    else
+      hbtEvent->SetIsCollisionCandidate(kTRUE);
+  }
+  else {
+    hbtEvent->SetIsCollisionCandidate(kTRUE);
+  }
+
+  double fV1[3];
+
+  //setting basic things
+  if ((fInputType == kESD) || (fInputType == kESDKine)) {
+    hbtEvent->SetRunNumber(fESDEvent->GetRunNumber());
+    hbtEvent->SetMagneticField(fESDEvent->GetMagneticField()*kilogauss);//to check if here is ok
+    hbtEvent->SetZDCN1Energy(fESDEvent->GetZDCN1Energy());
+    hbtEvent->SetZDCP1Energy(fESDEvent->GetZDCP1Energy());
+    hbtEvent->SetZDCN2Energy(fESDEvent->GetZDCN2Energy());
+    hbtEvent->SetZDCP2Energy(fESDEvent->GetZDCP2Energy());
+    hbtEvent->SetZDCEMEnergy(fESDEvent->GetZDCEMEnergy());
+    hbtEvent->SetZDCParticipants(fESDEvent->GetZDCParticipants());
+    hbtEvent->SetTriggerMask(fESDEvent->GetTriggerMask());
+    hbtEvent->SetTriggerCluster(fESDEvent->GetTriggerCluster());
+
+    printf("Got event type %i\n", fESDEvent->GetEventType());
+
+    //Vertex
+    double fVCov[6];
+    //   if (fUseTPCOnly) {
+    //     fESDEvent->GetPrimaryVertexTPC()->GetXYZ(fV1);
+    //     fESDEvent->GetPrimaryVertexTPC()->GetCovMatrix(fVCov);
+    //     if (!fESDEvent->GetPrimaryVertexTPC()->GetStatus())
+    //       fVCov[4] = -1001.0;
+    //   }
+    //   else {
+    if (fESDEvent->GetPrimaryVertex()) {
+      fESDEvent->GetPrimaryVertex()->GetXYZ(fV1);
+      fESDEvent->GetPrimaryVertex()->GetCovMatrix(fVCov);
+      
+      if (!fESDEvent->GetPrimaryVertex()->GetStatus()) {
+       // Get the vertex from SPD
+       fESDEvent->GetPrimaryVertexSPD()->GetXYZ(fV1);
+       fESDEvent->GetPrimaryVertexSPD()->GetCovMatrix(fVCov);
+       
+       
+       if (!fESDEvent->GetPrimaryVertexSPD()->GetStatus())
+         fVCov[4] = -1001.0;
+       else {
+         fESDEvent->GetPrimaryVertexSPD()->GetXYZ(fV1);
+         fESDEvent->GetPrimaryVertexSPD()->GetCovMatrix(fVCov);
+       }
+      }
+    }
+    else {
+      if (fESDEvent->GetPrimaryVertexSPD()) {
+       fESDEvent->GetPrimaryVertexSPD()->GetXYZ(fV1);
+       fESDEvent->GetPrimaryVertexSPD()->GetCovMatrix(fVCov);
+      }
+    }
+    if ((!fESDEvent->GetPrimaryVertex()) && (!fESDEvent->GetPrimaryVertexSPD()))
+      {
+       cout << "No vertex found !!!" << endl;
+       fV1[0] = 10000.0;
+       fV1[1] = 10000.0;
+       fV1[2] = 10000.0;
+       fVCov[4] = -1001.0;
+      }
+    
+    AliFmThreeVectorF vertex(fV1[0],fV1[1],fV1[2]);
+    
+    hbtEvent->SetPrimVertPos(vertex);
+    hbtEvent->SetPrimVertCov(fVCov);
+  }
+  
+  if ((fInputType == kAOD) || (fInputType == kAODKine)) {
+    hbtEvent->SetRunNumber(fAODEvent->GetRunNumber());
+    hbtEvent->SetMagneticField(fAODEvent->GetMagneticField()*kilogauss);//to check if here is ok
+    hbtEvent->SetZDCN1Energy(fAODEvent->GetZDCN1Energy());
+    hbtEvent->SetZDCP1Energy(fAODEvent->GetZDCP1Energy());
+    hbtEvent->SetZDCN2Energy(fAODEvent->GetZDCN2Energy());
+    hbtEvent->SetZDCP2Energy(fAODEvent->GetZDCP2Energy());
+    hbtEvent->SetZDCEMEnergy(fAODEvent->GetZDCEMEnergy(0));
+    hbtEvent->SetZDCParticipants(0);
+    hbtEvent->SetTriggerMask(fAODEvent->GetTriggerMask());
+    hbtEvent->SetTriggerCluster(fAODEvent->GetTriggerCluster());
+
+    // Primary Vertex position
+    fAODEvent->GetPrimaryVertex()->GetPosition(fV1);
+    
+    AliFmThreeVectorF vertex(fV1[0],fV1[1],fV1[2]);
+    hbtEvent->SetPrimVertPos(vertex);
+  }
+
+  if ((fInputType == kESDKine) || (fInputType == kAODKine)) {
+    Double_t tReactionPlane = 0;
+
+    AliGenHijingEventHeader *hdh = dynamic_cast<AliGenHijingEventHeader *> (fGenHeader);       
+    if (!hdh) {
+      AliGenCocktailEventHeader *cdh = dynamic_cast<AliGenCocktailEventHeader *> (fGenHeader);
+      if (cdh) {
+       TList *tGenHeaders = cdh->GetHeaders();
+       for (int ihead = 0; ihead<tGenHeaders->GetEntries(); ihead++) {
+         hdh = dynamic_cast<AliGenHijingEventHeader *> (fGenHeader);   
+         if (hdh) break;
+       }
+      }
+    }
+    if (hdh)
+      {
+       tReactionPlane = hdh->ReactionPlaneAngle();
+       cout << "Got reaction plane " << tReactionPlane << endl;
+      }
+    
+    hbtEvent->SetReactionPlaneAngle(tReactionPlane);
+  }
+
+  //starting to reading tracks
+  int nofTracks=0;  //number of reconstructed tracks in event
+  if ((fInputType == kESD) || (fInputType == kESDKine))
+    nofTracks = fESDEvent->GetNumberOfTracks();
+  else if ((fInputType == kAOD) || (fInputType == kAODKine))
+    nofTracks = fAODEvent->GetNumberOfTracks();
+
+  int realnofTracks=0;//number of track which we use ina analysis
+
+  TClonesArray *mcP = 0;
+  Int_t *motherids=0;
+
+  if (fInputType == kAODKine) {
+    // Attempt to access MC header
+    AliAODMCHeader *mcH;
+    mcH = (AliAODMCHeader *) fAODEvent->FindListObject(AliAODMCHeader::StdBranchName());
+    if (!mcH) {
+      cout << "AOD MC information requested, but no header found!" << endl;
+    }
+    
+    mcP = (TClonesArray *) fAODEvent->FindListObject(AliAODMCParticle::StdBranchName());
+    if (!mcP) {
+      cout << "AOD MC information requested, but no particle array found!" << endl;
+    }
+
+    hbtEvent->SetReactionPlaneAngle(fAODEvent->GetHeader()->GetQTheta(0)/2.0);
+    
+    if (mcP) {
+      motherids = new Int_t[((AliAODMCParticle *) mcP->At(mcP->GetEntries()-1))->GetLabel()];
+      for (int ip=0; ip<mcP->GetEntries(); ip++) motherids[ip] = 0;
+      
+      // Read in mother ids
+      AliAODMCParticle *motherpart;
+      for (int ip=0; ip<mcP->GetEntries(); ip++) {
+       motherpart = (AliAODMCParticle *) mcP->At(ip);
+       if (motherpart->GetDaughter(0) > 0)
+         motherids[motherpart->GetDaughter(0)] = ip;
+       if (motherpart->GetDaughter(1) > 0)
+         motherids[motherpart->GetDaughter(1)] = ip;
+      }
+    }
+  }
+  
+  if (fInputType == kESDKine) {
+    motherids = new Int_t[fStack->GetNtrack()];
+    for (int ip=0; ip<fStack->GetNtrack(); ip++) motherids[ip] = 0;
+
+    // Read in mother ids
+    TParticle *motherpart;
+    for (int ip=0; ip<fStack->GetNtrack(); ip++) {
+      motherpart = fStack->Particle(ip);
+      if (motherpart->GetDaughter(0) > 0)
+       motherids[motherpart->GetDaughter(0)] = ip;
+      if (motherpart->GetDaughter(1) > 0)
+       motherids[motherpart->GetDaughter(1)] = ip;
+    }
+  }
+
+  for (int i=0;i<nofTracks;i++)
+    {
+      //      cout << "Reading track " << i << endl;
+      bool  tGoodMomentum=true; //flaga to chcek if we can read momentum of this track
+               
+      AliFemtoTrack* trackCopy = new AliFemtoTrack();  
+
+      if ((fInputType == kESD) || (fInputType == kESDKine)) {
+       
+       AliESDtrack *esdtrack = 0x0;
+       if (fUseTPCOnly) {
+         AliESDtrack *mcp = fESDEvent->GetTrack(i);
+         esdtrack = AliESDtrackCuts::GetTPCOnlyTrack(fESDEvent, mcp->GetID());
+         //      printf("Got %p for track %i | ", esdtrack, mcp->GetID());
+       }
+       else {
+         esdtrack = fESDEvent->GetTrack(i);//getting next track
+       }
+
+       if (esdtrack && (fTrackCuts->AcceptTrack(esdtrack))) {
+
+         trackCopy->SetCharge((short)esdtrack->GetSign());
+
+         //in aliroot we have AliPID 
+         //0-electron 1-muon 2-pion 3-kaon 4-proton 5-photon 6-pi0 7-neutron 8-kaon0 9-eleCon   
+         //we use only 5 first
+         double esdpid[5];
+         esdtrack->GetESDpid(esdpid);
+         trackCopy->SetPidProbElectron(esdpid[0]);
+         trackCopy->SetPidProbMuon(esdpid[1]);
+         trackCopy->SetPidProbPion(esdpid[2]);
+         trackCopy->SetPidProbKaon(esdpid[3]);
+         trackCopy->SetPidProbProton(esdpid[4]);
+         
+         double pxyz[3];
+         double impact[2];
+         double covimpact[3];
+      
+         //      if (fUseTPCOnly) {
+         //        if (!esdtrack->GetTPCInnerParam()) {
+         //          cout << "No TPC inner param !" << endl;
+         //          delete trackCopy;
+         //          continue;
+         //        }
+
+         //        AliExternalTrackParam *param = new AliExternalTrackParam(*esdtrack->GetTPCInnerParam());
+         //        param->GetXYZ(rxyz);
+         //        param->PropagateToDCA(fESDEvent->GetPrimaryVertexTPC(), (fESDEvent->GetMagneticField()), 10000, impact, covimpact);
+         //        param->GetPxPyPz(pxyz);//reading noconstarined momentum
+           
+         //        if (fRotateToEventPlane) {
+         //          double tPhi = TMath::ATan2(pxyz[1], pxyz[0]);
+         //          double tRad = TMath::Hypot(pxyz[0], pxyz[1]);
+             
+         //          pxyz[0] = tRad*TMath::Cos(tPhi - tReactionPlane);
+         //          pxyz[1] = tRad*TMath::Sin(tPhi - tReactionPlane);
+         //        }
+           
+         //        AliFemtoThreeVector v(pxyz[0],pxyz[1],pxyz[2]);
+         //        if (v.mag() < 0.0001) {
+         //          //          cout << "Found 0 momentum ???? " << pxyz[0] << " " << pxyz[1] << " " << pxyz[2] << endl;
+         //          delete trackCopy;
+         //          continue;
+         //        }
+           
+         //        trackCopy->SetP(v);//setting momentum
+         //        trackCopy->SetPt(sqrt(pxyz[0]*pxyz[0]+pxyz[1]*pxyz[1]));
+           
+         //        const AliFmThreeVectorD kP(pxyz[0],pxyz[1],pxyz[2]);
+         //        const AliFmThreeVectorD kOrigin(fV1[0],fV1[1],fV1[2]);
+         //        //setting helix I do not if it is ok
+         //        AliFmPhysicalHelixD helix(kP,kOrigin,(double)(fESDEvent->GetMagneticField())*kilogauss,(double)(trackCopy->Charge())); 
+         //        trackCopy->SetHelix(helix);
+           
+         //        //some stuff which could be useful 
+         //        trackCopy->SetImpactD(impact[0]);
+         //        trackCopy->SetImpactZ(impact[1]);
+         //        trackCopy->SetCdd(covimpact[0]);
+         //        trackCopy->SetCdz(covimpact[1]);
+         //        trackCopy->SetCzz(covimpact[2]);
+         //        trackCopy->SetSigmaToVertex(GetSigmaToVertex(impact, covimpact));   
+           
+         //        delete param;
+         //      }
+         //      else {
+         if (fUseTPCOnly)
+           tGoodMomentum=esdtrack->GetPxPyPz(pxyz);
+         else
+           tGoodMomentum=esdtrack->GetConstrainedPxPyPz(pxyz); //reading constrained momentum
+         //      printf("Got good momentum %i\n", tGoodMomentum);
+
+         AliFemtoThreeVector v(pxyz[0],pxyz[1],pxyz[2]);
+         if (v.Mag() < 0.0001) {
+           
+           delete trackCopy;
+           continue;
+         }
+         
+         trackCopy->SetP(v);//setting momentum
+         trackCopy->SetPt(sqrt(pxyz[0]*pxyz[0]+pxyz[1]*pxyz[1]));
+         const AliFmThreeVectorD kP(pxyz[0],pxyz[1],pxyz[2]);
+         const AliFmThreeVectorD kOrigin(fV1[0],fV1[1],fV1[2]);
+         //setting helix I do not if it is ok
+         AliFmPhysicalHelixD helix(kP,kOrigin,(double)(fESDEvent->GetMagneticField())*kilogauss,(double)(trackCopy->Charge())); 
+         trackCopy->SetHelix(helix);
+       
+         //some stuff which could be useful 
+         float imp[2];
+         float cim[3];
+         esdtrack->GetImpactParameters(imp,cim);
+         
+         impact[0] = imp[0];
+         impact[1] = imp[1];
+         covimpact[0] = cim[0];
+         covimpact[1] = cim[1];
+         covimpact[2] = cim[2];
+
+         trackCopy->SetImpactD(impact[0]);
+         trackCopy->SetImpactZ(impact[1]);
+         trackCopy->SetCdd(covimpact[0]);
+         trackCopy->SetCdz(covimpact[1]);
+         trackCopy->SetCzz(covimpact[2]);
+         trackCopy->SetSigmaToVertex(AliESDtrackCuts::GetSigmaToVertex(esdtrack));
+               
+         trackCopy->SetTrackId(esdtrack->GetID());
+         trackCopy->SetFlags(esdtrack->GetStatus());
+         trackCopy->SetLabel(esdtrack->GetLabel());
+               
+         trackCopy->SetITSchi2(esdtrack->GetITSchi2());    
+         trackCopy->SetITSncls(esdtrack->GetNcls(0));     
+         trackCopy->SetTPCchi2(esdtrack->GetTPCchi2());       
+         trackCopy->SetTPCncls(esdtrack->GetTPCNcls());       
+         trackCopy->SetTPCnclsF(esdtrack->GetTPCNclsF());      
+         trackCopy->SetTPCsignalN((short)esdtrack->GetTPCsignalN()); //due to bug in aliesdtrack class   
+         trackCopy->SetTPCsignalS(esdtrack->GetTPCsignalSigma()); 
+
+         trackCopy->SetTPCClusterMap(esdtrack->GetTPCClusterMap());
+         trackCopy->SetTPCSharedMap(esdtrack->GetTPCSharedMap());
+
+         double xtpc[3];
+         esdtrack->GetInnerXYZ(xtpc);
+         xtpc[2] -= fV1[2];
+         trackCopy->SetNominalTPCEntrancePoint(xtpc);
+
+         esdtrack->GetOuterXYZ(xtpc);
+         xtpc[2] -= fV1[2];
+         trackCopy->SetNominalTPCExitPoint(xtpc);
+
+         int indexes[3];
+         for (int ik=0; ik<3; ik++) {
+           indexes[ik] = esdtrack->GetKinkIndex(ik);
+         }
+         trackCopy->SetKinkIndexes(indexes);
+
+         // Fill the hidden information with the simulated data
+         if (fInputType == kESDKine) {
+           if (TMath::Abs(esdtrack->GetLabel()) < fStack->GetNtrack()) {
+             TParticle *tPart = fStack->Particle(TMath::Abs(esdtrack->GetLabel()));
+
+             // Check the mother information
+             
+             // Using the new way of storing the freeze-out information
+             // Final state particle is stored twice on the stack
+             // one copy (mother) is stored with original freeze-out information
+             //   and is not tracked
+             // the other one (daughter) is stored with primary vertex position
+             //   and is tracked
+             
+             // Freeze-out coordinates
+             double fpx=0.0, fpy=0.0, fpz=0.0, fpt=0.0;
+             fpx = tPart->Vx() - fV1[0];
+             fpy = tPart->Vy() - fV1[1];
+             fpz = tPart->Vz() - fV1[2];
+             fpt = tPart->T();
+             
+             AliFemtoModelGlobalHiddenInfo *tInfo = new AliFemtoModelGlobalHiddenInfo();
+             tInfo->SetGlobalEmissionPoint(fpx, fpy, fpz);
+             
+             fpx *= 1e13;
+             fpy *= 1e13;
+             fpz *= 1e13;
+             fpt *= 1e13;
+             
+             if (motherids[TMath::Abs(esdtrack->GetLabel())]>0) {
+               TParticle *mother = fStack->Particle(motherids[TMath::Abs(esdtrack->GetLabel())]);
+               // Check if this is the same particle stored twice on the stack
+               if ((mother->GetPdgCode() == tPart->GetPdgCode() || (mother->Px() == tPart->Px()))) {
+                 // It is the same particle
+                 // Read in the original freeze-out information
+                 // and convert it from to [fm]
+                 
+                 // EPOS style 
+                 fpx = mother->Vx()*1e13*0.197327;
+                 fpy = mother->Vy()*1e13*0.197327;
+                 fpz = mother->Vz()*1e13*0.197327;
+                 fpt = mother->T() *1e13*0.197327;
+                 
+                 
+                 // Therminator style 
+                 //        fpx = mother->Vx()*1e13;
+                 //        fpy = mother->Vy()*1e13;
+                 //        fpz = mother->Vz()*1e13;
+                 //        fpt = mother->T() *1e13*3e10;
+                 
+               }
+             }
+       
+             tInfo->SetPDGPid(tPart->GetPdgCode());
+       
+             tInfo->SetTrueMomentum(tPart->Px(), tPart->Py(), tPart->Pz());
+             Double_t mass2 = (tPart->Energy() *tPart->Energy() -
+                               tPart->Px()*tPart->Px() -
+                               tPart->Py()*tPart->Py() -
+                               tPart->Pz()*tPart->Pz());
+             if (mass2>0.0)
+               tInfo->SetMass(TMath::Sqrt(mass2));
+             else 
+               tInfo->SetMass(0.0);
+             
+             tInfo->SetEmissionPoint(fpx, fpy, fpz, fpt);
+             trackCopy->SetHiddenInfo(tInfo);
+           }
+           else {
+             AliFemtoModelGlobalHiddenInfo *tInfo = new AliFemtoModelGlobalHiddenInfo();
+             tInfo->SetMass(0.0);
+             double fpx=0.0, fpy=0.0, fpz=0.0, fpt=0.0;
+             fpx = fV1[0]*1e13;
+             fpy = fV1[1]*1e13;
+             fpz = fV1[2]*1e13;
+             fpt = 0.0;
+             tInfo->SetEmissionPoint(fpx, fpy, fpz, fpt);
+             
+             tInfo->SetTrueMomentum(pxyz[0],pxyz[1],pxyz[2]);
+             
+             trackCopy->SetHiddenInfo(tInfo);
+           }
+         }
+         //      cout << "Got freeze-out " << fpx << " " << fpy << " " << fpz << " " << fpt << " " <<  mass2 << " " << tPart->GetPdgCode() << endl; 
+       }
+       else 
+         tGoodMomentum = false;
+       
+       if (fUseTPCOnly)
+         if (esdtrack) delete esdtrack;
+      }
+
+      if ((fInputType == kAOD) || (fInputType == kAODKine)) {
+       // Read in the normal AliAODTracks 
+       const AliAODTrack *aodtrack=fAODEvent->GetTrack(i); // getting the AODtrack directly
+       
+       //      if (!aodtrack->TestFilterBit(fFilterBit))
+       //        continue;
+       
+       CopyAODtoFemtoTrack(aodtrack, trackCopy);
+       
+       if (mcP) {
+         // Fill the hidden information with the simulated data
+         //      Int_t pLabel = aodtrack->GetLabel();
+         AliAODMCParticle *tPart = GetParticleWithLabel(mcP, (TMath::Abs(aodtrack->GetLabel())));
+         
+         AliFemtoModelGlobalHiddenInfo *tInfo = new AliFemtoModelGlobalHiddenInfo();
+         double fpx=0.0, fpy=0.0, fpz=0.0, fpt=0.0;
+         if (!tPart) {
+           fpx = fV1[0];
+           fpy = fV1[1];
+           fpz = fV1[2];
+           tInfo->SetGlobalEmissionPoint(fpx, fpy, fpz);
+           tInfo->SetPDGPid(0);
+           tInfo->SetTrueMomentum(0.0, 0.0, 0.0);
+           tInfo->SetEmissionPoint(0.0, 0.0, 0.0, 0.0);
+           tInfo->SetMass(0);
+         }
+         else {
+           // Check the mother information
+         
+           // Using the new way of storing the freeze-out information
+           // Final state particle is stored twice on the stack
+           // one copy (mother) is stored with original freeze-out information
+           //   and is not tracked
+           // the other one (daughter) is stored with primary vertex position
+           //   and is tracked
+           
+           // Freeze-out coordinates
+           fpx = tPart->Xv() - fV1[0];
+           fpy = tPart->Yv() - fV1[1];
+           fpz = tPart->Zv() - fV1[2];
+           //    fpt = tPart->T();
+           
+           tInfo->SetGlobalEmissionPoint(fpx, fpy, fpz);
+           
+           fpx *= 1e13;
+           fpy *= 1e13;
+           fpz *= 1e13;
+           //    fpt *= 1e13;
+           
+           //      cout << "Looking for mother ids " << endl;
+           if (motherids[TMath::Abs(aodtrack->GetLabel())]>0) {
+             //        cout << "Got mother id" << endl;
+             AliAODMCParticle *mother = GetParticleWithLabel(mcP, motherids[TMath::Abs(aodtrack->GetLabel())]);
+             // Check if this is the same particle stored twice on the stack
+             if (mother) {
+               if ((mother->GetPdgCode() == tPart->GetPdgCode() || (mother->Px() == tPart->Px()))) {
+                 // It is the same particle
+                 // Read in the original freeze-out information
+                 // and convert it from to [fm]
+                 
+                 // EPOS style 
+                 //      fpx = mother->Xv()*1e13*0.197327;
+                 //      fpy = mother->Yv()*1e13*0.197327;
+                 //      fpz = mother->Zv()*1e13*0.197327;
+                 //      fpt = mother->T() *1e13*0.197327*0.5;
+                 
+                 
+                 // Therminator style 
+                 fpx = mother->Xv()*1e13;
+                 fpy = mother->Yv()*1e13;
+                 fpz = mother->Zv()*1e13;
+                 //          fpt = mother->T() *1e13*3e10;
+                 
+               }
+             }
+           }
+           
+           //       if (fRotateToEventPlane) {
+           //  double tPhi = TMath::ATan2(fpy, fpx);
+           //  double tRad = TMath::Hypot(fpx, fpy);
+           
+           //  fpx = tRad*TMath::Cos(tPhi - tReactionPlane);
+           //  fpy = tRad*TMath::Sin(tPhi - tReactionPlane);
+           //       }
+           
+           tInfo->SetPDGPid(tPart->GetPdgCode());
+           
+           //    if (fRotateToEventPlane) {
+           //      double tPhi = TMath::ATan2(tPart->Py(), tPart->Px());
+           //      double tRad = TMath::Hypot(tPart->Px(), tPart->Py());
+           
+           //      tInfo->SetTrueMomentum(tRad*TMath::Cos(tPhi - tReactionPlane),
+           //                             tRad*TMath::Sin(tPhi - tReactionPlane),
+           //                             tPart->Pz());
+           //    }
+           //       else
+           tInfo->SetTrueMomentum(tPart->Px(), tPart->Py(), tPart->Pz());
+           Double_t mass2 = (tPart->E() *tPart->E() -
+                             tPart->Px()*tPart->Px() -
+                             tPart->Py()*tPart->Py() -
+                             tPart->Pz()*tPart->Pz());
+           if (mass2>0.0)
+             tInfo->SetMass(TMath::Sqrt(mass2));
+           else 
+             tInfo->SetMass(0.0);
+           
+           tInfo->SetEmissionPoint(fpx, fpy, fpz, fpt);
+         }
+         trackCopy->SetHiddenInfo(tInfo);
+       }
+
+       double pxyz[3];
+       aodtrack->PxPyPz(pxyz);//reading noconstarined momentum
+       const AliFmThreeVectorD ktP(pxyz[0],pxyz[1],pxyz[2]);
+       // Check the sanity of the tracks - reject zero momentum tracks
+       if (ktP.Mag() == 0) {
+         delete trackCopy;
+         continue;
+       }
+       
+
+      }
+      
+       
+      //decision if we want this track
+      //if we using diffrent labels we want that this label was use for first time 
+      //if we use hidden info we want to have match between sim data and ESD
+      if (tGoodMomentum==true)
+       {
+         hbtEvent->TrackCollection()->push_back(trackCopy);//adding track to analysis
+         realnofTracks++;//real number of tracks
+         //      delete trackCopy;
+       }
+      else
+       {
+         delete  trackCopy;
+       }
+      
+    }
+  
+  if (motherids)
+    delete [] motherids;
+  
+  hbtEvent->SetNumberOfTracks(realnofTracks);//setting number of track which we read in event  
+  fCurEvent++; 
+  //  cout<<"end of reading nt "<<nofTracks<<" real number "<<realnofTracks<<endl;
+  return hbtEvent; 
+}
+//___________________
+void AliFemtoEventReaderStandard::SetESDSource(AliESDEvent *aESD)
+{
+  // The chain loads the ESD for us
+  // You must provide the address where it can be found
+  fESDEvent = aESD;
+}
+//___________________
+void AliFemtoEventReaderStandard::SetAODSource(AliAODEvent *aAOD)
+{
+  // The chain loads the ESD for us
+  // You must provide the address where it can be found
+  fAODEvent = aAOD;
+}
+//___________________
+void AliFemtoEventReaderStandard::SetStackSource(AliStack *aStack)
+{
+  // The chain loads the stack for us
+  // You must provide the address where it can be found
+  fStack = aStack;
+}
+void AliFemtoEventReaderStandard::SetInputType(AliFemtoInputType aInput)
+{
+  // Set the proper input type
+  fInputType = aInput;
+}
+//___________________
+void AliFemtoEventReaderStandard::SetGenEventHeader(AliGenEventHeader *aGenHeader)
+{
+  // The chain loads the generator event header for us
+  // You must provide the address where it can be found
+  fGenHeader = aGenHeader;
+}
+
+void AliFemtoEventReaderStandard::SetUsePhysicsSelection(const bool usephysics)
+{
+  fUsePhysicsSel = usephysics;
+  if (!fSelect) fSelect = new AliPhysicsSelection();
+}
+
+void AliFemtoEventReaderStandard::SetESDTrackCuts(AliESDtrackCuts *esdcuts)
+{
+  // Set external ESD track cuts
+  fTrackCuts = esdcuts;
+}
+
+void AliFemtoEventReaderStandard::SetUseTPCOnly(const bool usetpconly)
+{
+  // Set flag to use TPC only tracks
+  fUseTPCOnly = usetpconly;
+}
+
+void AliFemtoEventReaderStandard::CopyAODtoFemtoTrack(const AliAODTrack *tAodTrack, 
+                                                     AliFemtoTrack *tFemtoTrack)
+{
+  // Copy the track information from the AOD into the internal AliFemtoTrack
+  // If it exists, use the additional information from the PWG2 AOD
+
+  // Primary Vertex position
+  double fV1[3];
+  fAODEvent->GetPrimaryVertex()->GetPosition(fV1);
+
+  tFemtoTrack->SetCharge(tAodTrack->Charge());
+  
+  //in aliroot we have AliPID 
+  //0-electron 1-muon 2-pion 3-kaon 4-proton 5-photon 6-pi0 7-neutron 8-kaon0 9-eleCon   
+  //we use only 5 first
+
+  // AOD pid has 10 components
+  double aodpid[10];
+  tAodTrack->GetPID(aodpid);
+  tFemtoTrack->SetPidProbElectron(aodpid[0]);
+  tFemtoTrack->SetPidProbMuon(aodpid[1]);
+  tFemtoTrack->SetPidProbPion(aodpid[2]);
+  tFemtoTrack->SetPidProbKaon(aodpid[3]);
+  tFemtoTrack->SetPidProbProton(aodpid[4]);
+                                               
+  double pxyz[3];
+  tAodTrack->PxPyPz(pxyz);//reading noconstrained momentum
+  AliFemtoThreeVector v(pxyz[0],pxyz[1],pxyz[2]);
+  tFemtoTrack->SetP(v);//setting momentum
+  tFemtoTrack->SetPt(sqrt(pxyz[0]*pxyz[0]+pxyz[1]*pxyz[1]));
+  const AliFmThreeVectorD kOrigin(fV1[0],fV1[1],fV1[2]);
+  //setting track helix 
+  const AliFmThreeVectorD ktP(pxyz[0],pxyz[1],pxyz[2]);
+  AliFmPhysicalHelixD helix(ktP,kOrigin,(double)(fAODEvent->GetMagneticField())*kilogauss,(double)(tFemtoTrack->Charge())); 
+  tFemtoTrack->SetHelix(helix);
+               
+  // Flags
+  tFemtoTrack->SetTrackId(tAodTrack->GetID());
+  tFemtoTrack->SetFlags(1);
+  tFemtoTrack->SetLabel(tAodTrack->GetLabel());
+               
+  // Track quality information 
+  float covmat[6];
+  tAodTrack->GetCovMatrix(covmat);
+  tFemtoTrack->SetImpactD(covmat[0]);
+  tFemtoTrack->SetImpactZ(covmat[2]);
+  tFemtoTrack->SetCdd(covmat[3]);
+  tFemtoTrack->SetCdz(covmat[4]);
+  tFemtoTrack->SetCzz(covmat[5]);
+  // This information is only available in the ESD
+  // We put in fake values or reasonable estimates
+  tFemtoTrack->SetITSchi2(tAodTrack->Chi2perNDF());    
+  tFemtoTrack->SetITSncls(1);     
+  tFemtoTrack->SetTPCchi2(tAodTrack->Chi2perNDF());       
+  tFemtoTrack->SetTPCncls(1);       
+  tFemtoTrack->SetTPCnclsF(1);      
+  tFemtoTrack->SetTPCsignalN(1); 
+  tFemtoTrack->SetTPCsignalS(1); 
+
+  TBits tAllTrue;
+  TBits tAllFalse;
+  tAllTrue.ResetAllBits(kTRUE);
+  tAllFalse.ResetAllBits(kFALSE);
+  
+
+  // If not use dummy values
+  tFemtoTrack->SetTPCClusterMap(tAllTrue);
+  tFemtoTrack->SetTPCSharedMap(tAllFalse);
+  
+  double xtpc[3] = {0,0,0};
+  tFemtoTrack->SetNominalTPCEntrancePoint(xtpc);
+  tFemtoTrack->SetNominalTPCExitPoint(xtpc);
+
+  int indexes[3];
+  for (int ik=0; ik<3; ik++) {
+    indexes[ik] = 0;
+  }
+  tFemtoTrack->SetKinkIndexes(indexes);
+}
+
+AliAODMCParticle* AliFemtoEventReaderStandard::GetParticleWithLabel(TClonesArray *mcP, Int_t aLabel)
+{
+  if (aLabel < 0) return 0;
+  AliAODMCParticle *aodP;
+  Int_t posstack = 0;
+  if (aLabel > mcP->GetEntries())
+    posstack = mcP->GetEntries();
+  else
+    posstack = aLabel;
+
+  aodP = (AliAODMCParticle *) mcP->At(posstack);
+  if (aodP->GetLabel() > posstack) {
+    do {
+      aodP = (AliAODMCParticle *) mcP->At(posstack);
+      if (aodP->GetLabel() == aLabel) return aodP;
+      posstack--;
+    }
+    while (posstack > 0);
+  }
+  else {
+    do {
+      aodP = (AliAODMCParticle *) mcP->At(posstack);
+      if (aodP->GetLabel() == aLabel) return aodP;
+      posstack++;
+    }
+    while (posstack < mcP->GetEntries());
+  }
+  
+  return 0;
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReaderStandard.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventReaderStandard.h
new file mode 100644 (file)
index 0000000..cd912b4
--- /dev/null
@@ -0,0 +1,85 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoEventReaderStandard - the reader class for the Alice ESD, AOD      //
+// the model Kinematics information tailored for the Task framework           //
+// Authors: Adam Kisiel Adam.Kisiel@cern.ch                                   //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+#ifndef ALIFEMTOEVENTREADERSTANDARD_H
+#define ALIFEMTOEVENTREADERSTANDARD_H
+
+#include "AliFemtoEventReader.h"
+#include "AliFemtoEnumeration.h"
+
+#include <string>
+#include <vector>
+#include <TTree.h>
+#include <AliESDEvent.h>
+#include <AliAODEvent.h>
+#include <AliESDfriend.h>
+#include <AliStack.h>
+#include <list>
+#include <AliGenEventHeader.h>
+#include <AliPhysicsSelection.h>
+#include <AliESDtrackCuts.h>
+#include <AliAODMCParticle.h>
+
+class AliFemtoEvent;
+class AliFemtoTrack;
+
+class AliFemtoEventReaderStandard : public AliFemtoEventReader 
+{
+ public:
+  enum InputType {kUnknown = -1, kESD=0, kAOD=1, kESDKine=2, kAODKine=3};
+  typedef enum InputType AliFemtoInputType;
+
+  AliFemtoEventReaderStandard();
+  AliFemtoEventReaderStandard(const AliFemtoEventReaderStandard& aReader);
+  ~AliFemtoEventReaderStandard();
+
+  AliFemtoEventReaderStandard& operator=(const AliFemtoEventReaderStandard& aReader);
+
+  AliFemtoEvent* ReturnHbtEvent();
+  AliFemtoString Report();
+
+  void SetESDSource(AliESDEvent *aESD);
+  void SetAODSource(AliAODEvent *aAOD);
+  void SetStackSource(AliStack *aStack);
+  void SetInputType(AliFemtoInputType aInput);
+  void SetGenEventHeader(AliGenEventHeader *aGenHeader);
+  void SetUsePhysicsSelection(const bool usephysics);
+
+  void SetESDTrackCuts(AliESDtrackCuts *esdcuts);
+  void SetUseTPCOnly(const bool usetpconly);
+
+ protected:
+
+  void CopyAODtoFemtoTrack(const AliAODTrack *tAodTrack, AliFemtoTrack *tFemtoTrack);
+  AliAODMCParticle* GetParticleWithLabel(TClonesArray *mcP, Int_t aLabel);
+
+ private:
+  string             fFileName;      //  name of current ESD file
+  int                fNumberofEvent; //  number of Events in ESD file
+  int                fCurEvent;      //  number of current event
+  unsigned int       fCurFile;       //  number of current file
+  AliESDEvent       *fESDEvent;      //! ESD event
+  AliAODEvent       *fAODEvent;      //! AOD event
+  AliStack          *fStack;         //! Kinematics stack pointer
+  AliGenEventHeader *fGenHeader;     //! Link to the generator event header
+  AliFemtoInputType  fInputType;     //  Select data input type
+
+  bool                 fUsePhysicsSel; // if true the physics selection class will be used
+  AliPhysicsSelection *fSelect;        // Class to select only physics events
+
+  AliESDtrackCuts     *fTrackCuts;     // Link to external ESD track cut
+  bool                 fUseTPCOnly;    // if true the TPC only parameters will be used
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoEventReaderStandard, 1)
+#endif
+
+};
+  
+#endif
+
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventWriter.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventWriter.h
new file mode 100644 (file)
index 0000000..ddd796e
--- /dev/null
@@ -0,0 +1,12 @@
+////////////////////////////////////////////////////////////////////////////////
+/// AliFemtoEventWrite - a wrapper for the base class                        ///
+////////////////////////////////////////////////////////////////////////////////
+#ifndef AliFemtoEventWriter_hh
+#define AliFemtoEventWriter_hh
+
+#include "AliFemtoEventReader.h"
+
+typedef AliFemtoEventReader AliFemtoEventWriter;//!  // yes, because our writer are reader-writers
+
+#endif
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventWriterCollection.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoEventWriterCollection.h
new file mode 100644 (file)
index 0000000..a486d1a
--- /dev/null
@@ -0,0 +1,34 @@
+/***************************************************************************
+ *
+ * $Id$
+ *
+ * Author: Frank Laue, Ohio State, laue@mps.ohio-state.edu
+ ***************************************************************************
+ *
+ * Description: part of STAR HBT Framework: AliFemtoMaker package
+ *  The EventWriterCollection is pointed to by the Manager, and holds pointers
+ *  to all EventWriter objects currently active
+ *
+ ***************************************************************************
+ *
+ **************************************************************************/
+
+#ifndef AliFemtoEventWriterCollection_hh
+#define AliFemtoEventWriterCollection_hh
+
+#include "AliFemtoEventWriter.h"
+
+#include <list>
+#if !defined(ST_NO_NAMESPACES)
+using std::list;
+#endif
+
+#ifdef ST_NO_TEMPLATE_DEF_ARGS
+typedef list<AliFemtoEventWriter*, allocator<AliFemtoEventWriter*> >            AliFemtoEventWriterCollection;
+typedef list<AliFemtoEventWriter*, allocator<AliFemtoEventWriter*> >::iterator  AliFemtoEventWriterIterator;
+#else
+typedef list<AliFemtoEventWriter*>            AliFemtoEventWriterCollection;
+typedef list<AliFemtoEventWriter*>::iterator  AliFemtoEventWriterIterator;
+#endif
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoFsiTools.F b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoFsiTools.F
new file mode 100644 (file)
index 0000000..09ad1ec
--- /dev/null
@@ -0,0 +1,363 @@
+*
+* $Id$
+*
+* $Log$
+* Revision 1.1.1.1  2007/03/07 10:14:49  mchojnacki
+* First version on CVS
+*
+* Revision 1.1.1.1  1996/04/01 15:01:55  mclareni
+* Mathlib gen
+*
+*
+      FUNCTION CGAMMA(Z)
+
+      DIMENSION C(0:15)
+      COMPLEX*8 Z,CGAMMA
+      COMPLEX*8 U,V,F,H,S
+      CHARACTER NAME*(*)
+      CHARACTER*80 ERRTXT
+      PARAMETER (NAME = 'CGAMMA')
+
+      PARAMETER (Z1 = 1, HF = Z1/2)
+
+      DATA PI /3.14159 26535 89793 24D0/
+      DATA C1 /2.50662 82746 31000 50D0/
+
+      DATA C( 0) / 41.62443 69164 39068D0/
+      DATA C( 1) /-51.22424 10223 74774D0/
+      DATA C( 2) / 11.33875 58134 88977D0/
+      DATA C( 3) / -0.74773 26877 72388D0/
+      DATA C( 4) /  0.00878 28774 93061D0/
+      DATA C( 5) / -0.00000 18990 30264D0/
+      DATA C( 6) /  0.00000 00019 46335D0/
+      DATA C( 7) / -0.00000 00001 99345D0/
+      DATA C( 8) /  0.00000 00000 08433D0/
+      DATA C( 9) /  0.00000 00000 01486D0/
+      DATA C(10) / -0.00000 00000 00806D0/
+      DATA C(11) /  0.00000 00000 00293D0/
+      DATA C(12) / -0.00000 00000 00102D0/
+      DATA C(13) /  0.00000 00000 00037D0/
+      DATA C(14) / -0.00000 00000 00014D0/
+      DATA C(15) /  0.00000 00000 00006D0/
+
+
+      U=Z
+      X=U
+      IF(AIMAG(U) .EQ. 0 .AND. -ABS(X) .EQ. INT(X)) THEN
+       F=0
+       H=0
+       WRITE(ERRTXT,101) X
+c       CALL MTLPRT(NAME,'C305.1',ERRTXT)
+      ELSE
+       IF(X .GE. 1) THEN
+        F=1
+        V=U
+       ELSEIF(X .GE. 0) THEN
+        F=1/U
+        V=1+U
+       ELSE
+        F=1
+        V=1-U
+       END IF
+       H=1
+       S=C(0)
+       DO 1 K = 1,15
+       H=((V-K)/(V+(K-1)))*H
+    1  S=S+C(K)*H
+       H=V+(4+HF)
+       H=C1*EXP((V-HF)*LOG(H)-H)*S
+       IF(X .LT. 0) H=PI/(SIN(PI*U)*H)
+      ENDIF
+      CGAMMA=F*H
+      RETURN
+  101 FORMAT('ARGUMENT EQUALS NON-POSITIVE INTEGER = ',1P,E15.1)
+      END
+
+*
+* $Id$
+*
+* $Log$
+* Revision 1.1.1.1  2007/03/07 10:14:49  mchojnacki
+* First version on CVS
+*
+* Revision 1.1.1.1  1996/04/01 15:02:02  mclareni
+* Mathlib gen
+*
+*
+      FUNCTION DFRSIN(X)
+
+      IMPLICIT REAL*8 (A-H,O-Z)
+      DIMENSION A(0:16),B(0:15),C1(0:25),C2(0:28)
+
+      PARAMETER (Z1 = 1, R8 = Z1/8, R32 = Z1/32)
+
+      DATA C0 /1.25331 41373 15500 3D0/
+
+      DATA NA,NB,NC1,NC2 /16,15,25,28/
+
+      DATA A( 0) / 0.76435 13866 41860 002D0/
+      DATA A( 1) /-0.43135 54754 76601 793D0/
+      DATA A( 2) / 0.43288 19997 97266 531D0/
+      DATA A( 3) /-0.26973 31033 83871 110D0/
+      DATA A( 4) / 0.08416 04532 08769 354D0/
+      DATA A( 5) /-0.01546 52448 44613 820D0/
+      DATA A( 6) / 0.00187 85542 34398 220D0/
+      DATA A( 7) /-0.00016 26497 76188 875D0/
+      DATA A( 8) / 0.00001 05739 76563 833D0/
+      DATA A( 9) /-0.00000 05360 93398 892D0/
+      DATA A(10) / 0.00000 00218 16584 549D0/
+      DATA A(11) /-0.00000 00007 29016 212D0/
+      DATA A(12) / 0.00000 00000 20373 325D0/
+      DATA A(13) /-0.00000 00000 00483 440D0/
+      DATA A(14) / 0.00000 00000 00009 865D0/
+      DATA A(15) /-0.00000 00000 00000 175D0/
+      DATA A(16) / 0.00000 00000 00000 003D0/
+
+      DATA B( 0) / 0.63041 40431 45705 392D0/
+      DATA B( 1) /-0.42344 51140 57053 335D0/
+      DATA B( 2) / 0.37617 17264 33436 566D0/
+      DATA B( 3) /-0.16249 48915 45095 674D0/
+      DATA B( 4) / 0.03822 25577 86330 087D0/
+      DATA B( 5) /-0.00564 56347 71321 909D0/
+      DATA B( 6) / 0.00057 45495 19768 974D0/
+      DATA B( 7) /-0.00004 28707 15321 020D0/
+      DATA B( 8) / 0.00000 24512 07499 233D0/
+      DATA B( 9) /-0.00000 01109 88418 409D0/
+      DATA B(10) / 0.00000 00040 82497 317D0/
+      DATA B(11) /-0.00000 00001 24498 302D0/
+      DATA B(12) / 0.00000 00000 03200 484D0/
+      DATA B(13) /-0.00000 00000 00070 324D0/
+      DATA B(14) / 0.00000 00000 00001 336D0/
+      DATA B(15) /-0.00000 00000 00000 022D0/
+
+      DATA C1( 0) / 0.99056 04793 73497 549D0/
+      DATA C1( 1) /-0.01218 35098 31478 997D0/
+      DATA C1( 2) /-0.00248 27428 23113 060D0/
+      DATA C1( 3) / 0.00026 60949 52647 247D0/
+      DATA C1( 4) /-0.00000 10790 68987 406D0/
+      DATA C1( 5) /-0.00000 48836 81753 933D0/
+      DATA C1( 6) / 0.00000 09990 55266 368D0/
+      DATA C1( 7) /-0.00000 00750 92717 372D0/
+      DATA C1( 8) /-0.00000 00190 79487 573D0/
+      DATA C1( 9) / 0.00000 00090 90797 293D0/
+      DATA C1(10) /-0.00000 00019 66236 033D0/
+      DATA C1(11) / 0.00000 00001 64772 911D0/
+      DATA C1(12) / 0.00000 00000 63079 714D0/
+      DATA C1(13) /-0.00000 00000 36432 219D0/
+      DATA C1(14) / 0.00000 00000 10536 930D0/
+      DATA C1(15) /-0.00000 00000 01716 438D0/
+      DATA C1(16) /-0.00000 00000 00107 124D0/
+      DATA C1(17) / 0.00000 00000 00204 099D0/
+      DATA C1(18) /-0.00000 00000 00090 064D0/
+      DATA C1(19) / 0.00000 00000 00025 506D0/
+      DATA C1(20) /-0.00000 00000 00004 036D0/
+      DATA C1(21) /-0.00000 00000 00000 570D0/
+      DATA C1(22) / 0.00000 00000 00000 762D0/
+      DATA C1(23) /-0.00000 00000 00000 363D0/
+      DATA C1(24) / 0.00000 00000 00000 118D0/
+      DATA C1(25) /-0.00000 00000 00000 025D0/
+
+      DATA C2( 0) / 0.04655 77987 37516 4561D0/
+      DATA C2( 1) / 0.04499 21302 01239 4140D0/
+      DATA C2( 2) /-0.00175 42871 39651 4532D0/
+      DATA C2( 3) /-0.00014 65340 02581 0678D0/
+      DATA C2( 4) / 0.00003 91330 40863 0159D0/
+      DATA C2( 5) /-0.00000 34932 28659 7731D0/
+      DATA C2( 6) /-0.00000 03153 53003 2345D0/
+      DATA C2( 7) / 0.00000 01876 58200 8529D0/
+      DATA C2( 8) /-0.00000 00377 55280 4930D0/
+      DATA C2( 9) / 0.00000 00026 65516 5010D0/
+      DATA C2(10) / 0.00000 00010 88144 8122D0/
+      DATA C2(11) /-0.00000 00005 35500 7671D0/
+      DATA C2(12) / 0.00000 00001 31576 5447D0/
+      DATA C2(13) /-0.00000 00000 15286 0881D0/
+      DATA C2(14) /-0.00000 00000 03394 7646D0/
+      DATA C2(15) / 0.00000 00000 02702 0267D0/
+      DATA C2(16) /-0.00000 00000 00946 3142D0/
+      DATA C2(17) / 0.00000 00000 00207 1565D0/
+      DATA C2(18) /-0.00000 00000 00012 6931D0/
+      DATA C2(19) /-0.00000 00000 00013 9756D0/
+      DATA C2(20) / 0.00000 00000 00008 5929D0/
+      DATA C2(21) /-0.00000 00000 00003 1070D0/
+      DATA C2(22) / 0.00000 00000 00000 7515D0/
+      DATA C2(23) /-0.00000 00000 00000 0648D0/
+      DATA C2(24) /-0.00000 00000 00000 0522D0/
+      DATA C2(25) / 0.00000 00000 00000 0386D0/
+      DATA C2(26) /-0.00000 00000 00000 0165D0/
+      DATA C2(27) / 0.00000 00000 00000 0050D0/
+      DATA C2(28) /-0.00000 00000 00000 0009D0/
+
+      V=ABS(X)
+      IF(V .LT. 8) THEN
+       Y=R8*V
+       H=2*Y**2-1
+       ALFA=H+H
+       B1=0
+       B2=0
+       DO 4 I = NB,0,-1
+       B0=B(I)+ALFA*B1-B2
+       B2=B1
+    4  B1=B0
+       H=SQRT(V)*Y*(B0-B2)
+      ELSE
+       R=1/V
+       H=10*R-1
+       ALFA=H+H
+       B1=0
+       B2=0
+       DO 5 I = NC1,0,-1
+       B0=C1(I)+ALFA*B1-B2
+       B2=B1
+    5  B1=B0
+       S=B0-H*B2
+       B1=0
+       B2=0
+       DO 6 I = NC2,0,-1
+       B0=C2(I)+ALFA*B1-B2
+       B2=B1
+    6  B1=B0
+       H=C0-SQRT(R)*(S*COS(V)+(B0-H*B2)*SIN(V))
+      END IF
+      IF(X .LT. 0) H=-H
+      DFRSIN=H
+      return
+      end
+
+
+      function DFRCOS(X)
+
+      IMPLICIT REAL*8 (A-H,O-Z)
+      DIMENSION A(0:16),B(0:15),C1(0:25),C2(0:28)
+
+      PARAMETER (Z1 = 1, R8 = Z1/8, R32 = Z1/32)
+
+      DATA C0 /1.25331 41373 15500 3D0/
+
+      DATA NA,NB,NC1,NC2 /16,15,25,28/
+
+      DATA A( 0) / 0.76435 13866 41860 002D0/
+      DATA A( 1) /-0.43135 54754 76601 793D0/
+      DATA A( 2) / 0.43288 19997 97266 531D0/
+      DATA A( 3) /-0.26973 31033 83871 110D0/
+      DATA A( 4) / 0.08416 04532 08769 354D0/
+      DATA A( 5) /-0.01546 52448 44613 820D0/
+      DATA A( 6) / 0.00187 85542 34398 220D0/
+      DATA A( 7) /-0.00016 26497 76188 875D0/
+      DATA A( 8) / 0.00001 05739 76563 833D0/
+      DATA A( 9) /-0.00000 05360 93398 892D0/
+      DATA A(10) / 0.00000 00218 16584 549D0/
+      DATA A(11) /-0.00000 00007 29016 212D0/
+      DATA A(12) / 0.00000 00000 20373 325D0/
+      DATA A(13) /-0.00000 00000 00483 440D0/
+      DATA A(14) / 0.00000 00000 00009 865D0/
+      DATA A(15) /-0.00000 00000 00000 175D0/
+      DATA A(16) / 0.00000 00000 00000 003D0/
+
+      DATA B( 0) / 0.63041 40431 45705 392D0/
+      DATA B( 1) /-0.42344 51140 57053 335D0/
+      DATA B( 2) / 0.37617 17264 33436 566D0/
+      DATA B( 3) /-0.16249 48915 45095 674D0/
+      DATA B( 4) / 0.03822 25577 86330 087D0/
+      DATA B( 5) /-0.00564 56347 71321 909D0/
+      DATA B( 6) / 0.00057 45495 19768 974D0/
+      DATA B( 7) /-0.00004 28707 15321 020D0/
+      DATA B( 8) / 0.00000 24512 07499 233D0/
+      DATA B( 9) /-0.00000 01109 88418 409D0/
+      DATA B(10) / 0.00000 00040 82497 317D0/
+      DATA B(11) /-0.00000 00001 24498 302D0/
+      DATA B(12) / 0.00000 00000 03200 484D0/
+      DATA B(13) /-0.00000 00000 00070 324D0/
+      DATA B(14) / 0.00000 00000 00001 336D0/
+      DATA B(15) /-0.00000 00000 00000 022D0/
+
+      DATA C1( 0) / 0.99056 04793 73497 549D0/
+      DATA C1( 1) /-0.01218 35098 31478 997D0/
+      DATA C1( 2) /-0.00248 27428 23113 060D0/
+      DATA C1( 3) / 0.00026 60949 52647 247D0/
+      DATA C1( 4) /-0.00000 10790 68987 406D0/
+      DATA C1( 5) /-0.00000 48836 81753 933D0/
+      DATA C1( 6) / 0.00000 09990 55266 368D0/
+      DATA C1( 7) /-0.00000 00750 92717 372D0/
+      DATA C1( 8) /-0.00000 00190 79487 573D0/
+      DATA C1( 9) / 0.00000 00090 90797 293D0/
+      DATA C1(10) /-0.00000 00019 66236 033D0/
+      DATA C1(11) / 0.00000 00001 64772 911D0/
+      DATA C1(12) / 0.00000 00000 63079 714D0/
+      DATA C1(13) /-0.00000 00000 36432 219D0/
+      DATA C1(14) / 0.00000 00000 10536 930D0/
+      DATA C1(15) /-0.00000 00000 01716 438D0/
+      DATA C1(16) /-0.00000 00000 00107 124D0/
+      DATA C1(17) / 0.00000 00000 00204 099D0/
+      DATA C1(18) /-0.00000 00000 00090 064D0/
+      DATA C1(19) / 0.00000 00000 00025 506D0/
+      DATA C1(20) /-0.00000 00000 00004 036D0/
+      DATA C1(21) /-0.00000 00000 00000 570D0/
+      DATA C1(22) / 0.00000 00000 00000 762D0/
+      DATA C1(23) /-0.00000 00000 00000 363D0/
+      DATA C1(24) / 0.00000 00000 00000 118D0/
+      DATA C1(25) /-0.00000 00000 00000 025D0/
+
+      DATA C2( 0) / 0.04655 77987 37516 4561D0/
+      DATA C2( 1) / 0.04499 21302 01239 4140D0/
+      DATA C2( 2) /-0.00175 42871 39651 4532D0/
+      DATA C2( 3) /-0.00014 65340 02581 0678D0/
+      DATA C2( 4) / 0.00003 91330 40863 0159D0/
+      DATA C2( 5) /-0.00000 34932 28659 7731D0/
+      DATA C2( 6) /-0.00000 03153 53003 2345D0/
+      DATA C2( 7) / 0.00000 01876 58200 8529D0/
+      DATA C2( 8) /-0.00000 00377 55280 4930D0/
+      DATA C2( 9) / 0.00000 00026 65516 5010D0/
+      DATA C2(10) / 0.00000 00010 88144 8122D0/
+      DATA C2(11) /-0.00000 00005 35500 7671D0/
+      DATA C2(12) / 0.00000 00001 31576 5447D0/
+      DATA C2(13) /-0.00000 00000 15286 0881D0/
+      DATA C2(14) /-0.00000 00000 03394 7646D0/
+      DATA C2(15) / 0.00000 00000 02702 0267D0/
+      DATA C2(16) /-0.00000 00000 00946 3142D0/
+      DATA C2(17) / 0.00000 00000 00207 1565D0/
+      DATA C2(18) /-0.00000 00000 00012 6931D0/
+      DATA C2(19) /-0.00000 00000 00013 9756D0/
+      DATA C2(20) / 0.00000 00000 00008 5929D0/
+      DATA C2(21) /-0.00000 00000 00003 1070D0/
+      DATA C2(22) / 0.00000 00000 00000 7515D0/
+      DATA C2(23) /-0.00000 00000 00000 0648D0/
+      DATA C2(24) /-0.00000 00000 00000 0522D0/
+      DATA C2(25) / 0.00000 00000 00000 0386D0/
+      DATA C2(26) /-0.00000 00000 00000 0165D0/
+      DATA C2(27) / 0.00000 00000 00000 0050D0/
+      DATA C2(28) /-0.00000 00000 00000 0009D0/
+
+      V=ABS(X)
+      IF(V .LT. 8) THEN
+       H=R32*V**2-1
+       ALFA=H+H
+       B1=0
+       B2=0
+       DO 1 I = NA,0,-1
+       B0=A(I)+ALFA*B1-B2
+       B2=B1
+    1  B1=B0
+       H=SQRT(V)*(B0-H*B2)
+      ELSE
+       R=1/V
+       H=10*R-1
+       ALFA=H+H
+       B1=0
+       B2=0
+       DO 2 I = NC1,0,-1
+       B0=C1(I)+ALFA*B1-B2
+       B2=B1
+    2  B1=B0
+       S=B0-H*B2
+       B1=0
+       B2=0
+       DO 3 I = NC2,0,-1
+       B0=C2(I)+ALFA*B1-B2
+       B2=B1
+    3  B1=B0
+       H=C0-SQRT(R)*((B0-H*B2)*COS(V)-S*SIN(V))
+      END IF
+      IF(X .LT. 0) H=-H
+      DFRCOS=H
+      RETURN
+      END
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoFsiWeightLednicky.F b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoFsiWeightLednicky.F
new file mode 100644 (file)
index 0000000..0b51e60
--- /dev/null
@@ -0,0 +1,1577 @@
+c         1         2         3         4         5         6         7         8
+c---------|---------|---------|---------|---------|---------|---------|---------|
+*-- Author :    R.Lednicky      20/01/95
+      SUBROUTINE FSIW(J,WEIF,WEI,WEIN)
+
+C=======================================================================
+C    Calculates final state interaction (FSI) weights
+C    WEIF = weight due to particle - (effective) nucleus FSI (p-N)
+C    WEI  = weight due to p-p-N FSI
+C    WEIN = weight due to p-p FSI; note that WEIN=WEI if I3C=0;
+C                                  note that if I3C=1 the calculation of
+C                                  WEIN can be skipped by putting J=0
+C.......................................................................
+C    Correlation Functions:
+C    CF(p-p-N)   = sum(WEI)/sum(WEIF)
+C    CF(p-p)     = sum(WEIN)/sum(1); here the nucleus is completely
+C                                    inactive
+C    CF(p-p-"N") = sum(WEIN*WEIF')/sum(WEIF'), where WEIN and WEIF'
+C                  are not correlated (calculated at different emission
+C                  points, e.g., for different events);
+C                  thus here the nucleus affects one-particle
+C                  spectra but not the correlation
+C.......................................................................
+C    User must supply data file <fn> on unit NUNIT (e.g. =11) specifying
+C    LL   : particle pair
+C    NS   : approximation used to calculate Bethe-Salpeter amplitude
+C    ITEST: test switch
+C           If ITEST=1 then also following parameters are required
+C    ICH  : 1(0) Coulomb interaction between the two particles ON (OFF)
+C    IQS  : 1(0) quantum statistics for the two particles ON (OFF)
+C    ISI  : 1(0) strong interaction between the two particles ON (OFF)
+C    I3C  : 1(0) Coulomb interaction with residual nucleus ON (OFF)
+C    This data file can contain other information useful for the user.
+C    It is read by subroutines READINT4 and READREA8(4) (or READ_FILE).
+C----------------------------------------------------------------------
+C-   LL       1  2  3  4  5   6   7   8  9 10  11  12  13  14 15 16 17
+C-   part. 1: n  p  n  a  pi+ pi0 pi+ n  p pi+ pi+ pi+ pi- K+ K+ K+ K-
+C-   part. 2: n  p  p  a  pi- pi0 pi+ d  d  K-  K+  p   p  K- K+ p  p
+C   NS=1 y/n: +  +  +  +  +   -   -   -  -  -   -   -   -  -  -  -  -
+C----------------------------------------------------------------------
+C-   LL       18 19 20 21 22 23  24 25 26 27 28 29 30
+C-   part. 1: d  d  t  t  K0 K0  d  p  p  p  n  lam p
+C-   part. 2: d  a  t  a  K0 K0b t  t  a  lam lam lam pb
+C   NS=1 y/n: -  -  -  -  -  -   -  -  -  +  +  +  -
+C----------------------------------------------------------------------
+C   NS=1  Square well potential,
+C   NS=3  not used
+C   NS=4  scattered wave approximated by the spherical wave,
+C   NS=2  same as NS=4 but the approx. of equal emission times in PRF
+C         not required (t=0 approx. used in all other cases).
+C   Note: if NS=2,4, the B-S amplitude diverges at zero distance r* in
+C         the two-particle c.m.s.; user can specify a cutoff AA in
+C         SUBROUTINE FSIINI, for example:
+C         IF(NS.EQ.2.OR.NS.EQ.4)AA=5.D0 !! in 1/GeV --> AA=1. fm
+C---------------------------------------------------------------------
+C    ITEST=1 any values of parameters ICH, IQS, ISI, I3C are allowed
+C            and should be given in data file <fn>
+C    ITEST=0 physical values of these parameters are put automatically
+C            in FSIINI (their values are not required in data file)
+C=====================================================================
+C    At the beginning of calculation user should call FSIINI,
+C    which reads LL, NS, ITEST (and eventually ICH, IQS, ISI, I3C)
+C    and initializes various parameters.
+C    In particular the constants in
+C      COMMON/FSI_CONS/PI,PI2,SPI,DR,W
+C    may be useful for the user:
+C     W=1/.1973D0    ! from fm to 1/GeV
+C     PI=4*DATAN(1.D0)
+C     PI2=2*PI
+C     SPI=DSQRT(PI)
+C     DR=180.D0/PI   ! from radian to degree
+C      _______________________________________________________
+C  !! |Important note: all real quantities are assumed REAL*8 | !!
+C      -------------------------------------------------------
+C    For each event user should fill in the following information
+C    in COMMONs (all COMMONs in FSI calculation start with FSI_):
+C    ...................................................................
+C     COMMON/FSI_POC/AMN,AM1,AM2,CN,C1,C2,AC1,AC2
+C    Only
+C         AMN  = mass of the effective nucleus   [GeV/c**2]
+C         CN   = charge of the effective nucleus [elem. charge units]
+C    are required
+C    ...................................................................
+C     COMMON/FSI_MOM/P1X,P1Y,P1Z,E1,P1, !part. momenta in the rest frame 
+C    1               P2X,P2Y,P2Z,E2,P2  !of effective nucleus (NRF)
+C    Only the components
+C                        PiX,PiY,PiZ  [GeV/c]
+C    in NRF are required.
+C    To make the corresponding Lorentz transformation user can use the
+C    subroutines LTRAN and LTRANB
+C    ...................................................................
+C    COMMON/FSI_COOR/X1,Y1,Z1,T1,R1,     ! 4-coord. of emission
+C    1               X2,Y2,Z2,T2,R2      ! points in NRF
+C    The componets
+C                       Xi,Yi,Zi  [fm]
+C    and emission times
+C                          Ti   [fm/c]
+C    should be given in NRF with the origin assumed at the center
+C    of the effective nucleus. If the effect of residual nucleus is
+C    not calculated within FSIW, the NRF can be any fixed frame.
+C-----------------------------------------------------------------------
+C    Before calling FSIW the user must call
+C     CALL LTRAN12
+C    Besides Lorentz transformation to pair rest frame:
+C    (p1-p2)/2 --> k* it also transforms 4-coordinates of
+C    emission points from fm to 1/GeV and calculates Ei,Pi and Ri.
+C    Note that |k*|=AK in COMMON/FSI_PRF/
+C-----------------------------------------------------------------------
+C    After making some additional filtering using k* (say k* < k*max)
+C    or direction of vector k*,
+C    user can finally call FSIW to calculate the FSI weights
+C    to be used to construct the correlation function
+C=======================================================================
+      IMPLICIT REAL*8 (A-H,O-Z)
+      COMMON/FSI_JR/JRAT
+      COMMON/FSI_POC/AMN,AM1,AM2,CN,C1,C2,AC1,AC2
+      COMMON/FSI_MOM/P1X,P1Y,P1Z,E1,P1,  ! particle momenta in NRF
+     1               P2X,P2Y,P2Z,E2,P2
+      COMMON/FSI_PRF/PPX,PPY,PPZ,AK,AKS, ! k*=(p1-p2)/2 and x1-x2 
+     1               X,Y,Z,T,RP,RPS      ! in pair rest frame (PRF)
+      COMMON/FSI_COOR/X1,Y1,Z1,T1,R1, !4-coord. of emis. points in NRF
+     1                X2,Y2,Z2,T2,R2
+      COMMON/FSI_NS/LL,NS,ICH,ISI,IQS,I3C,I3S
+      COMMON/FSI_FFPN/FF12,FF21
+      COMPLEX*16 FF12,FF21
+C------------------------------------------------------------------
+C==> AC1,2 = "relativistic" Bohr radii for particle-nucleus systems
+      C1N=C1*CN
+      IF(C1N.NE.0.D0)AC1=137.036D0/(C1N*E1) !m1-->E1
+      C2N=C2*CN
+      IF(C2N.NE.0.D0)AC2=137.036D0/(C2N*E2) !m2-->E2
+C-----------------------------------------------------------
+      CALL FSIPN(WEIF) !weight due to particle-nucleus FSI
+      JRAT=0
+      call BoostToPrf()
+      CALL FSIWF(WEI)  !weight due to particle-particle-nucleus FSI
+      WEIN=WEI
+         IF(I3C*J.NE.0) THEN
+      FF12=DCMPLX(1.D0,0.D0)
+      FF21=DCMPLX(1.D0,0.D0)
+      JRAT=1
+      CALL VZ(WEIN) ! weight due to particle-particle FSI
+         ENDIF
+      RETURN
+      END
+C=======================================================================
+      SUBROUTINE LTRAN(P0,P,PS)
+C==>calculating particle 4-momentum PS={PSX,PSY,PSZ,ES}
+C   in rest frame of a system 0 with 4-momentum P0={P0X,P0Y,P0Z,E0}
+C   from its 4-momentum P={PX,PY,PZ,E}
+      IMPLICIT REAL*8 (A-H,O-Z)
+      DIMENSION P0(4),P(4),PS(4)
+C-----------------------------------------------------------------------
+      P0S=P0(1)**2+P0(2)**2+P0(3)**2
+      AM0=DSQRT(P0(4)**2-P0S)
+      EPM=P0(4)+AM0
+      PP0=P(1)*P0(1)+P(2)*P0(2)+P(3)*P0(3)
+      H=(PP0/EPM-P(4))/AM0
+      PS(1)=P(1)+P0(1)*H
+      PS(2)=P(2)+P0(2)*H
+      PS(3)=P(3)+P0(3)*H
+      PS(4)=(P0(4)*P(4)-PP0)/AM0
+      RETURN
+      END
+      SUBROUTINE LTRANB(P0,PS,P)
+C==>calculating particle 4-momentum P={PX,PY,PZ,E}
+C   from its 4-momentum PS={PSX,PSY,PSZ,ES}
+C   in rest frame of a system 0 with 4-momentum P0={P0X,P0Y,P0Z,E0}
+      IMPLICIT REAL*8 (A-H,O-Z)
+      DIMENSION P0(4),P(4),PS(4)
+C-----------------------------------------------------------------------
+      P0S=P0(1)**2+P0(2)**2+P0(3)**2
+      AM0=DSQRT(P0(4)**2-P0S)
+      EPM=P0(4)+AM0
+      PSP0=PS(1)*P0(1)+PS(2)*P0(2)+PS(3)*P0(3)
+      HS=(PSP0/EPM+PS(4))/AM0
+      P(1)=PS(1)+P0(1)*HS
+      P(2)=PS(2)+P0(2)*HS
+      P(3)=PS(3)+P0(3)*HS
+      P(4)=(P0(4)*PS(4)+PSP0)/AM0
+      RETURN
+      END
+      SUBROUTINE LTRAN12
+C==>calculating particle momentum in PRF {EE,PPX,PPY,PPZ} from
+C-  the momentum of the first particle {E1,P1X,P1Y,P1Z) in NRF
+      IMPLICIT REAL*8 (A-H,O-Z)
+      COMMON/FSI_MOM/P1X,P1Y,P1Z,E1,P1,  !part. momenta in NRF
+     1               P2X,P2Y,P2Z,E2,P2
+      COMMON/FSI_PRF/PPX,PPY,PPZ,AK,AKS,
+     1               X,Y,Z,T,RP,RPS
+      COMMON/FSI_POC/AMN,AM1,AM2,CN,C1,C2,AC1,AC2
+      COMMON/FSI_P12/P12X,P12Y,P12Z,E12,P12,AM12,EPM
+      COMMON/FSI_COOR/X1,Y1,Z1,T1,R1, !4-coord. of emis. points in NRF
+     1                X2,Y2,Z2,T2,R2
+      COMMON/FSI_CONS/PI,PI2,SPI,DR,W
+C   fm --> 1/GeV
+      X1=X1*W
+      Y1=Y1*W
+      Z1=Z1*W
+      T1=T1*W
+      X2=X2*W
+      Y2=Y2*W
+      Z2=Z2*W
+      T2=T2*W
+C   calculating Ri, Pi and Ei
+      R1=DSQRT(X1*X1+Y1*Y1+Z1*Z1)
+      R2=DSQRT(X2*X2+Y2*Y2+Z2*Z2)
+      P1S=P1X*P1X+P1Y*P1Y+P1Z*P1Z
+      P2S=P2X*P2X+P2Y*P2Y+P2Z*P2Z
+      P1=DSQRT(P1S)
+      P2=DSQRT(P2S)
+      E1=DSQRT(AM1*AM1+P1S)
+      E2=DSQRT(AM2*AM2+P2S)
+C-----------------------------------------------------------------------
+      E12=E1+E2
+      P12X=P1X+P2X
+      P12Y=P1Y+P2Y
+      P12Z=P1Z+P2Z
+      P12S=P12X**2+P12Y**2+P12Z**2
+      AM12=DSQRT(E12**2-P12S)
+      EPM=E12+AM12
+      P12=DSQRT(P12S)
+      P112=P1X*P12X+P1Y*P12Y+P1Z*P12Z
+      H1=(P112/EPM-E1)/AM12
+      PPX=P1X+P12X*H1
+      PPY=P1Y+P12Y*H1
+      PPZ=P1Z+P12Z*H1
+      EE=(E12*E1-P112)/AM12
+      AKS=EE**2-AM1**2
+      AK=DSQRT(AKS)
+
+CW      WRITE(6,38)'AK ',AK,'K ',PPX,PPY,PPZ,EE
+38    FORMAT(A7,E11.4,A7,4E11.4)
+      RETURN
+      END
+      SUBROUTINE FSIPN(WEIF)
+C  calculating particle-nucleus Coulomb Wave functions FFij
+      IMPLICIT REAL*8 (A-H,O-Z)
+      COMMON/FSI_POC/AMN,AM1,AM2,CN,C1,C2,AC1,AC2
+      COMMON/FSI_MOM/P1X,P1Y,P1Z,E1,P1,  !part. momenta in NRF
+     1               P2X,P2Y,P2Z,E2,P2
+      COMMON/FSI_COOR/X1,Y1,Z1,T1,R1, ! 4-coord. of emis. points in NRF
+     1                X2,Y2,Z2,T2,R2
+      COMMON/FSI_NS/LL,NS,ICH,ISI,IQS,I3C,I3S
+      COMMON/FSI_ACH/HPR,AC,ACH,ACHR,ISPIN,MSPIN
+      COMMON/FSI_ICH1/ICH1
+      COMMON/FSI_ETA/ETA
+      COMMON/FSI_FFPN/FF12,FF21
+      COMPLEX*16 FF1,FF12,FF21
+      FF12=DCMPLX(1.D0,0.D0)
+      FF21=DCMPLX(1.D0,0.D0)
+C      ACH=1.D0
+C      WEIF=1.D0
+      IF(I3C.EQ.0)RETURN
+      ICH1=IDINT(C1)
+      IF(ICH1.EQ.0)GOTO 11
+      XH=AC1*P1
+      ACH=ACP(XH)
+      ACHR=DSQRT(ACH)
+      ETA=0.D0
+      IF(XH.NE.0.D0)ETA=1/XH
+      RHOS=P1*R1
+      HS=X1*P1X+Y1*P1Y+Z1*P1Z
+      FF12=FF12*FF1(RHOS,HS)
+      IF(IQS.EQ.0)GOTO 11
+      RHOS=P1*R2
+      HS=X2*P1X+Y2*P1Y+Z2*P1Z
+      FF21=FF21*FF1(RHOS,HS)
+ 11   ICH1=IDINT(C2)
+      IF(ICH1.EQ.0)GOTO 10
+      XH=AC2*P2
+      ACH=ACP(XH)
+      ACHR=DSQRT(ACH)
+      ETA=0.D0
+      IF(XH.NE.0.D0)ETA=1/XH
+      RHOS=P2*R2
+      HS=X2*P2X+Y2*P2Y+Z2*P2Z
+      FF12=FF12*FF1(RHOS,HS)
+CW      WRITE(6,41)'AC2 ',AC2,'ACH ',ACH,'ETA ',ETA,'RHOS ',RHOS,'HS ',HS
+41    FORMAT(5(A5,E11.4))
+CW      WRITE(6,40)'FF12 ',DREAL(FF12),DIMAG(FF12)
+      IF(IQS.EQ.0)GOTO 10
+      RHOS=P2*R1
+      HS=X1*P2X+Y1*P2Y+Z1*P2Z
+      FF21=FF21*FF1(RHOS,HS)
+CW      WRITE(6,41)'AC1 ',AC1,'ACH ',ACH,'ETA ',ETA,'RHOS ',RHOS,'HS ',HS
+CW      WRITE(6,40)'FF21 ',DREAL(FF21),DIMAG(FF21)
+40    FORMAT(A7,2E12.4)
+ 10   CONTINUE
+C  WEIF = the weight due to the Coulomb particle-nucleus interaction
+      WEIF=DREAL(FF12)**2+DIMAG(FF12)**2
+      IF(IQS.EQ.1)WEIF=0.5D0*(WEIF+DREAL(FF21)**2+DIMAG(FF21)**2)
+      RETURN
+      END
+      FUNCTION GPIPI(X,J)
+C--- GPIPI = k*COTG(DELTA), X=k^2
+C--  J=1(2) corresponds to isospin=0(2)
+      IMPLICIT REAL*8 (A-H,O-Z)
+      COMMON/FSI_AAPI/AAPI(20,2)
+      COMMON/FSI_C/HELP(20),AM,AMS,DM
+      OM=DSQRT(X+AMS)
+      XX=X/AMS
+      GPIPI=OM/AAPI(1,J)
+      GPIPI=GPIPI*(1+(AAPI(3,J)-AAPI(1,J)**2)*XX+AAPI(4,J)*XX*XX)
+      GPIPI=GPIPI/(1+(AAPI(3,J)+AAPI(2,J)/AAPI(1,J))*XX)
+      RETURN
+      END
+      
+      FUNCTION GPIN(X,J)
+C--- GPIN = k*COTG(DELTA), X=k^2
+C--  J=1(2) corresponds to piN isospin=1/2(3/2)
+      IMPLICIT REAL*8 (A-H,O-Z)
+      COMMON/FSI_AAPIN/AAPIN(20,2)
+      GPIN=1/AAPIN(1,J)+.5D0*AAPIN(2,J)*X
+      RETURN
+      END
+      
+      FUNCTION GND(X,J)
+C--- GND = k*COTG(DELTA), X=k^2
+C--- J=1(2) corresp. to nd(pd), S=1/2,
+C--- J=3(4) corresp. to nd(pd), S=3/2
+      IMPLICIT REAL*8 (A-H,O-Z)
+      COMMON/FSI_AAND/AAND(20,4)
+      XX=X
+      GND=1/AAND(1,J)+.5D0*AAND(2,J)*X
+      DO 1 I=4,4
+      XX=XX*X
+   1  GND=GND+AAND(I,J)*XX
+      GND=GND/(1+AAND(3,J)*X)
+      RETURN
+      END
+      FUNCTION GDD(X,J)
+C--- GDD = k*COTG(DELTA), X=k^2
+C--- J=1,2,3 corresp. to S=0,1,2
+      IMPLICIT REAL*8 (A-H,O-Z)
+      COMMON/FSI_AADD/AADD(20,3)
+      COMMON/FSI_C/C(10),AM,AMS,DM
+      COMMON/FSI_CONS/PI,PI2,SPI,DR,W
+      COMPLEX*16 C
+      E=X/2/AM
+      ER=DSQRT(E)
+      IF(J.EQ.1)THEN
+       GDD=ER*(AADD(1,1)*DEXP(-E/AADD(2,1))-AADD(3,1))
+       GDD=GDD/DR   ! from degree to radian
+       TAND=DTAN(GDD)
+       IF(TAND.EQ.0.D0)TAND=1.D-10
+       GDD=DSQRT(X)/TAND
+      END IF
+      IF(J.EQ.2)THEN
+       GDD=1.D10   
+      END IF
+      IF(J.EQ.3)THEN
+       GDD=ER*(AADD(1,3)+AADD(2,3)*E)
+       GDD=GDD/DR    ! from degree to radian
+       TAND=DTAN(GDD)
+       IF(TAND.EQ.0.D0)TAND=1.D-10
+       GDD=DSQRT(X)/TAND
+      END IF      
+      RETURN
+      END
+      BLOCK DATA
+      IMPLICIT REAL*8 (A-H,O-Z)
+      COMMON/FSI_AAPI/AAPI(20,2)/FSI_AAND/AAND(20,4)
+      COMMON/FSI_AADD/AADD(20,3)/FSI_AAPIN/AAPIN(20,2)
+      COMMON/FSI_AAKK/AAKK(9)/FSI_AAPAP/AAPAPR(3,2),AAPAPI(3,2)
+C---Parameters for GPIPI (I,J), J=1,2 -> isospin=0,2
+      DATA AAPI/.2600D00, .2500D00, .3480D00,-.0637D00, 16*0.D0,
+     1         -.0280D00,-.0820D00, .2795D00,-.0086D00, 16*0.D0/
+C---Parameters for GPIN (I,J), J=1,2 -> piN isospin=1/2,3/2
+      DATA AAPIN/ .12265D1, .1563D2,     18*0.D0,
+     1            -.750D0,  .7688D2,     18*0.D0/
+C---Parameters for GND (I,J), J=1(2) corresp. to nd(pd), S=1/2,
+C---                          J=3(4) corresp. to nd(pd), S=3/2
+      DATA AAND/-.3295D1,-.8819D3, .4537D4, .28645D5, 16*0.D0,
+     1          -.13837D2, .11505D2, .0D0, .10416D2,  16*0.D0,
+     2          -.32180D2, .1014D2,  .0D0, .0D0,      16*0.D0,
+     3          -.60213D2, .1333D2,  .0D0,-.70309D2,  16*0.D0/
+      DATA AADD/ .10617D4, .3194D-2, .56849D3, 17*0.D0,
+     1           20*0.D0,
+     2          -.1085D4, .1987D5, 18*0.D0/
+C--- AAKK= m_K^2, m_pi^2, m_eta^2, m_S*^2, m_delta^2,
+C---       gam(S*-->KK-b), gam(S*-->pipi), gam(delta-->KK-b),
+C---       gam(delta-->pi eta)       
+      DATA AAKK/.247677D00,.01947977D00,.2997015D00,.9604D00,
+     1          .96511D00,
+cc     2          .792D00, .199D00, .333D00, .222D00/ ! Martin (77)
+     2          .094D00, .110D00, .333D00, .222D00/ ! Morgan (93) 
+C---Parameters for PAP (I,J), j=1,2 -> isospin I=0,2
+C---                          i=1-3 -> a_singlet, a_triplet, d [fm]
+C---    Im a_IS (I=isospin, S=spin) are fixed by atomic data and 
+C       n-bar survival time up to one free parameter, e.g. Im a_00 
+C---    Batty (89), Kerbikov (93):
+C--- Ima_10=1.96-Ima_00, Ima_01=0.367-Ima_00/3, Ima_11=0.453+Ima_00/3
+C---       In DATA we put Ima_00=0.3.
+C---    Re a_IS are fixed by atomic data up to three free parameters
+C---    Batty (89):
+C---         Rea_aver(pp-bar)=Re[(a_00+a_10)+3(a_01+a_11)]/8=-0.9
+C---       In DATA we used Rea_IS from Paris potential Pignone (94) 
+C---       rescaled by 1.67 to satisfy the atomic constraint.
+C---    Effective radius is is taken independent of IS from the phase
+C---    shift fit by Pirner et al. (91). 
+      DATA AAPAPR/-0.94D0, -1.98D0,  .1D0,
+     1            -1.40D0,  0.37D0,  .1D0/ ! Re
+      DATA AAPAPI/ 0.3 D0,  .267D0,-.01D0,
+     1             1.66D0,  .553D0,-.01D0/ ! Im
+      END
+      SUBROUTINE CKKB  ! calculates KK-b scattering amplitude,
+                       ! saturated by S*(980) and delta(982) resonances
+      IMPLICIT REAL*8 (A-H,O-Z)
+      COMMON/FSI_PRF/PPX,PPY,PPZ,AK,AKS,
+     1               X,Y,Z,T,RP,RPS
+      COMMON/FSI_AAKK/AAKK(9)
+      COMMON/FSI_C/C(10),AM,AMS,DM
+      COMPLEX*16 C
+      S4=AKS+AAKK(1)
+      S=4*S4
+      AKPIPI=DSQRT(S4-AAKK(2))
+      EETA2=(S+AAKK(3)-AAKK(2))**2/4/S
+      AKPIETA=DSQRT(EETA2-AAKK(3))
+      C(1)=AAKK(6)/2/DCMPLX(AAKK(4)-S,
+     ,-AK*AAKK(6)-AKPIPI*AAKK(7))
+      C(1)=C(1)+AAKK(8)/2/DCMPLX(AAKK(5)-S,
+     ,-AK*AAKK(8)-AKPIETA*AAKK(9))
+      RETURN
+      END 
+      SUBROUTINE CPAP           ! calculates pp-bar scattering amplitude
+                                ! accounting for nn-bar->pp-bar channel
+      IMPLICIT REAL*8 (A-H,O-Z)
+      COMMON/FSI_ACH/HPR,AC,ACH,ACHR,ISPIN,MSPIN
+      COMMON/FSI_PRF/PPX,PPY,PPZ,AK,AKS,
+     1     X,Y,Z,T,RP,RPS
+      COMMON/FSI_AAPAP/AAPAPR(3,2),AAPAPI(3,2)
+      COMMON/FSI_C/C(10),AM,AMS,DM
+      COMMON/FSI_2CHA/AK2,AK2S,AAK,HCP2,AMU2_AMU1 ! k* (kappa) for 2-nd channel
+      COMPLEX*16 C
+      DATA AM2/.93956563D0/
+      AMU2_AMU1=AM2/AM          ! AM2=2*mu(nn-bar), AM=2*mu(pp-bar)
+      AK2S0=AMU2_AMU1*AKS 
+      AK2S =AK2S0-2*AM2*(AM2-AM)
+      IF(AK2S.GE.0.D0)THEN
+         AK2=DCMPLX(DSQRT(AK2S),0.D0) !  k2
+      ELSE
+         AK2=DCMPLX(0.D0,DSQRT(-AK2S)) !  kappa2
+      ENDIF
+      C(10)=C(6+(ISPIN-1)*2)+
+     +     DCMPLX(AAPAPR(3,ISPIN)*AKS/2-0.016D0-HCP2,
+     ,     AAPAPI(3,ISPIN)*AKS/2-AAK) ! (1/f)11
+      C(5)=C(6+(ISPIN-1)*2)+
+     +     DCMPLX(AAPAPR(3,ISPIN)*AK2S0/2,
+     ,     AAPAPI(3,ISPIN)*AK2S0/2)         
+      IF(AK2S.GE.0.D0)THEN
+         C(5)=C(5)-DCMPLX(0.D0,AK2)  
+      ELSE
+         C(5)=C(5)+DCMPLX(AK2,0.D0) ! (1/f)22 
+      ENDIF
+      C(10)=C(10)*C(5)-C(7+(ISPIN-1)*2)*C(7+(ISPIN-1)*2)
+      C(ISPIN)=C(5)/C(10)       ! f11
+      C(ISPIN+2)=-C(7+(ISPIN-1)*2)/C(10) ! f12
+      RETURN
+      END 
+      
+      SUBROUTINE FSIIN(I_ITEST,I_ICH,I_IQS,I_ISI,I_I3C)
+C          SUBROUTINE FSIINI
+C---Note:
+C-- ICH= 0 (1) if the Coulomb interaction is absent (present);
+C-- ISPIN= JJ= 1,2,..,MSPIN denote increasing values of the pair
+C-- total spin S.
+C-- To calculate the CF of two particles (with masses m1, m2 and
+C-- charges C1, C2) the following information is required:
+C-- AM= twice the reduced mass= 2*m1*m2/(m1+m2) in GeV/c^2,
+C-- DM= (m1-m2)/(m1+m2), required if NS=2;
+C-- AC= Bohr radius= 2*137.036*0.1973/(C1*C2*AMH) in fm;
+C-- AC > 1.D9 if C1*C2= 0, AC < 0 if C1*C2 < 0;
+C-- MSPIN= MSPINH(LL)= number of the values of the total pair spin S;
+C-- FD= FDH(LL,JJ), RD= RDH(LL,JJ)= scattering length and effective
+C-- radius for each value of the total pair spin S, JJ= 1,..,MSPIN;     ;
+C-- the corresponding square well parameters EB= EBH(LL,JJ), RB=
+C-- RBH(LL,JJ) (required if NS=1) may be calculated by sear.f;
+C-- if the effective range approximation is not valid (as is the case,
+C-- e.g., for two-pion system) a code for calculation of the scattering
+C-- amplitude should be supplemented;
+C-- RHO= RHOH(LL,JJ), SF= SFH(LL,JJ), SE= SEH(LL) are spin factors;
+C-- RHO= the probability that the spins j1 and j2 of the two particles
+C-- will combine in a total spin S;
+C-- RHO= (2*S+1)/[(2j1+1)*(2j2+1)] for unpolarized particles;
+C-- RHO= (1-P1*P2)/4 and (3+P1*P2)/4 correspond to S=0 and 1 in the
+C-- case of spin-1/2 particles with polarizations P1 and P2;
+C-----------------------------------------------------------------------
+      IMPLICIT REAL*8 (A-H,O-Z)
+      COMMON/FSI_POC/AMN,AM1,AM2,CN,C1,C2,AC1,AC2
+      COMMON/FSI_PRF/PPX,PPY,PPZ,AK,AKS,
+     1               X,Y,Z,T,RP,RPS
+      COMMON/FSI_SPIN/RHO(10)
+      COMMON/FSI_ACH/HPR,AC,ACH,ACHR,ISPIN,MSPIN
+      COMMON/FSI_NS/LL,NS,ICH,ISI,IQS,I3C,I3S
+      COMMON/FSI_FD/FD(10),RD(10)
+      COMMON/FSI_C/C(10),AM,AMS,DM
+      COMMON/FSI_CONS/PI,PI2,SPI,DR,W
+      COMPLEX*16 C
+      COMMON/FSI_AA/AA
+      COMMON/FSI_AAPI/AAPI(20,2)/FSI_AAND/AAND(20,4)
+      COMMON/FSI_AAPIN/AAPIN(20,2)
+      COMMON/FSI_AAPAP/AAPAPR(3,2),AAPAPI(3,2)
+      COMMON/FSI_SW/RB(10),EB(10),BK(10),CDK(10),SDK(10),
+     1              SBKRB(10),SDKK(10)
+      COMMON/FSI_FDH/FDH(30,10),RDH(30,10),EBH(30,10),RBH(30,10)
+      COMMON/FSI_RHOH/RHOH(30,10)
+      COMMON/FSI_AMCH/AM1H(30),AM2H(30),C1H(30),C2H(30),MSPINH(30)
+C============= declarations pour l'appel de READ_FILE()============
+c      CHARACTER*10 KEY
+c      CHARACTER*8  CH8
+c      INTEGER*4    INT4
+c      REAL*8       REAL8
+c      INTEGER*4    IERR
+C
+C--- mass of the first and second particle
+      DATA AM1H/.93956563D0,.93827231D0,.93956563D0,3.72737978D0,
+     C          .13957D0,.13498D0,.13957D0, .93956563D0, .93827231D0,
+     C          4*.13957D0,4*.493677D0,
+     C          2*1.87561339D0,2*2.80892165D0,2*.497672D0,
+     C          1.87561339D0,3*.93827231D0,.93956563D0, 
+     C          1.115684D0,.93827231D0/
+      DATA AM2H/.93956563D0,.93827231D0,.93827231D0,3.72737978D0,
+     C          .13957D0,.13498D0,.13957D0, 2*1.87561339D0,
+     C          2*.493677D0,2*.93827231D0,
+     C          2*.493677D0,2*.93827231D0,
+     C          1.87561339D0,3.72737978D0,2.80892165D0,3.72737978D0,
+     C          2*.497672D0,2*2.80892165D0,3.72737978D0,
+     C          3*1.115684D0,.93827231D0/
+c--------|---------|---------|---------|---------|---------|---------|----------
+C---  charge of the first and second particle
+      DATA C1H/0.D0,1.D0,0.D0,2.D0, 1.D0,0.D0,1.D0,0.D0,1.D0,
+     C         3*1.D0,-1.D0,3*1.D0,-1.D0,
+     C         4*1.D0,2*0.D0,4*1.D0,2*0.D0, 1.D0/
+      DATA C2H/0.D0,1.D0,1.D0,2.D0,-1.D0,0.D0,3*1.D0,
+     C         -1.D0,3*1.D0,-1.D0,3*1.D0,
+     C         1.D0,2.D0,1.D0,2.D0,2*0.D0,2*1.D0,2.D0,3*0.D0,-1.D0/
+C---MSPIN vs (LL)
+      DATA MSPINH/3*2,4*1,2*2,8*1,3,1,2,1,2*1,2*2,1,3*2, 2/
+C---Spin factors <RHO vs (LL,ISPIN)
+      DATA RHOH/3*.25D0, 4*1.D0, 2*.3333D0, 8*1.D0, 
+     1          .1111D0,1.D0,.25D0,1.D0,2*1.D0,
+     1          .3333D0,.25D0,1.D0,3*.25D0, .25D0,
+     2          3*.75D0, 4*0.D0, 2*.6667D0, 8*0.D0, 
+     2          .3333D0,.0D0,.75D0,.0D0,2*0.D0,
+     2          .6667D0,.75D0,0.D0,3*.75D0, .75D0, 
+     3          17*.0D0,.5556D0,3*0.D0, 8*0.D0,1*0.D0,210*0.D0/
+C---Scattering length FD and effective radius RD in fm vs (LL,ISPIN)
+      DATA FDH/
+     1            17.0D0,7.8D0,23.7D0,2230.1218D0,.225D0,.081D0,-.063D0,
+     1     -.65D0,-2.73D0,
+     1     .137D0,-.071D0,-.148D0,.112D0,2*1.D-6,-.360D0,
+     1     2*1.D-6,1.344D0,6*1.D-6,-5.628D0,2.18D0,2.40D0, 
+     1     2.81D0,              ! ND potential 
+C     1     0.50D0,              ! NSC97e potential lam-lam
+     1     1*0.001D0,        
+C     c     2 -10.8D0,2*-5.4D0,4*0.D0,-6.35D0,-11.88D0,8*0.D0,9*0.D0,
+     2     3*-5.4D0,4*0.D0,-6.35D0,-11.88D0,8*0.D0,9*0.D0,
+     2     1.93D0,1.84D0,
+     2     0.50D0,              ! triplet f0 lam-lam=singlet f0 ND
+                                ! not contributing in s-wave FSI approx.
+     2     1*0.001D0,
+     3     240*0.D0/
+c--------|---------|---------|---------|---------|---------|---------|----------     
+      DATA RDH/
+     1     2.7D0,2.8D0,2.7D0,1.12139906D0,-44.36D0,64.0D0,784.9D0,
+     1     477.9D0, 2.27D0, 9*0.D0,-69.973D0, 6*0.D0,3.529D0,
+     1     3.19D0,3.15D0,
+     1     2.95D0,              ! ND potential lam-lam
+C     1  10.6D0, ! NSC97e potential lam-lam
+     1     1*0.D0,  
+     2     3*1.7D0,4*0.D0,2.0D0,2.63D0, 17*0.D0,3.35D0,3.37D0, 
+     2     2.95D0,              ! triplet d0 lam-lam=singlet d0 ND
+                                ! not contributing in s-wave approx.  
+     2     1*0.D0, 
+     3     240*0.D0/
+C---  Corresponding square well parameters RB (width in fm) and
+C--   EB =SQRT(-AM*U) (in GeV/c); U is the well height
+      DATA RBH/2.545739D0,   2.779789D0, 2.585795D0, 5.023544D0,
+     1     .124673D0, .3925180D0,.09D0, 2.D0, 4.058058D0, 17*0.D0, 
+     1     2.252623D0, 2.278575D0, 
+     1     2.234089D0,          ! ND potential lam-lam
+C     1  3.065796D0, ! NSC97e potential lam-lam
+     1     1*0.001D0,  
+     2     3*2.003144D0,
+     2     4*0.D0, 2.D0, 4.132163D0, 17*0.D0, 
+     2     2.272703D0, 2.256355D0, 
+     2     2.234089D0,          ! triplet potential lam-lam=singlet ND
+                                ! not contributing in s-wave FSI approx.  
+     2     1*0.001D0, 
+     3     240*0.D0/
+      DATA EBH/.1149517D0,    .1046257D0,   .1148757D0, .1186010D0,
+     1     .7947389D0,2.281208D0,8.7D0,.4D0,.1561219D0,17*0.D0,
+     1     .1013293D0, .1020966D0, 
+     1     .1080476D0,          ! ND potential lam-lam
+C     1    .04115994D0, ! NSC97e potential lam-lam
+     1     1*0.001D0,    
+     2     3*.1847221D0,
+     2     4*0.D0, .4D0, .1150687D0, 17*0.D0, 
+     2     .09736083D0, .09708310D0, 
+     2     .1080476D0,          ! triplet potential lam-lam= singlet ND 
+                                ! not contributing in s-wave FSI approx. 
+     2     1*0.001D0, 
+     3     240*0.D0/
+
+C++----- add to be able to call several time-------
+      integer ifirst
+      data ifirst/0/
+      ifirst=ifirst+1
+
+C=======< constants >========================
+      W=1/.1973D0    ! from fm to 1/GeV
+      PI=4*DATAN(1.D0)
+      PI2=2*PI
+      SPI=DSQRT(PI)
+      DR=180.D0/PI   ! from radian to degree
+      AC1=1.D10
+      AC2=1.D10
+C=======< condition de calculs >=============
+      NUNIT=11 ! for IBM in Nantes
+C      NUNIT=4 ! for SUN in Prague
+C++      CALL readint4(NUNIT,'ITEST     ',ITEST)      
+C++      CALL readint4(NUNIT,'NS        ',NS) 
+      ITEST=I_ITEST
+      IF(ITEST.EQ.1)THEN
+C++      CALL readint4(NUNIT,'ICH       ',ICH)
+C++      CALL readint4(NUNIT,'IQS       ',IQS)
+C++      CALL readint4(NUNIT,'ISI       ',ISI)
+C++      CALL readint4(NUNIT,'I3C       ',I3C)
+       ICH=I_ICH
+       IQS=I_IQS
+       ISI=I_ISI
+       I3C=I_I3C
+      ENDIF
+C============================================
+      IF (IFIRST.LE.1) THEN
+         DO 3 J1=1,30
+            DO 3 J2=1,10
+               FDH(J1,J2)=FDH(J1,J2)*W
+               RDH(J1,J2)=RDH(J1,J2)*W
+ 3             RBH(J1,J2)=RBH(J1,J2)*W   
+C     print *,"FD,RD,EB,RB: ",FDH(J1,J2),RDH(J1,J2),EBH(J1,J2),RBH(J1,J2)
+               
+      ENDIF
+C===================================
+      RETURN
+      END
+C
+      SUBROUTINE LLINI(lll,I_NS,I_ITEST)
+C===> Initialisation for a given LL value.
+C     ===========================================      
+      IMPLICIT REAL*8 (A-H,O-Z)
+      COMMON/FSI_POC/AMN,AM1,AM2,CN,C1,C2,AC1,AC2
+      COMMON/FSI_SPIN/RHO(10)
+      COMMON/FSI_ACH/HPR,AC,ACH,ACHR,ISPIN,MSPIN
+      COMMON/FSI_NS/LL,NS,ICH,ISI,IQS,I3C,I3S
+      COMMON/FSI_FD/FD(10),RD(10)
+      COMMON/FSI_C/C(10),AM,AMS,DM
+      COMMON/FSI_CONS/PI,PI2,SPI,DR,W
+      COMPLEX*16 C
+      COMMON/FSI_AA/AA
+      COMMON/FSI_PRF/PPX,PPY,PPZ,AK,AKS,
+     1               X,Y,Z,T,RP,RPS
+      COMMON/FSI_AAPI/AAPI(20,2)/FSI_AAND/AAND(20,4)
+      COMMON/FSI_AAPIN/AAPIN(20,2)
+      COMMON/FSI_SW/RB(10),EB(10),BK(10),CDK(10),SDK(10),
+     1              SBKRB(10),SDKK(10)
+      COMMON/FSI_FDH/FDH(30,10),RDH(30,10),EBH(30,10),RBH(30,10)
+      COMMON/FSI_RHOH/RHOH(30,10)
+      COMMON/FSI_AMCH/AM1H(30),AM2H(30),C1H(30),C2H(30),MSPINH(30)
+      COMMON/FSI_AAKK/AAKK(9)/FSI_AAPAP/AAPAPR(3,2),AAPAPI(3,2)
+
+C++----- add to be able to call several time-------
+      integer ifirst
+      data ifirst/0/
+      ifirst=ifirst+1
+
+C===> LL - Initialisation ========================================
+C---- Setting particle masses and charges
+      LL=lll
+      NS=I_NS
+      AM1=AM1H(LL)
+      AM2=AM2H(LL)
+      C1=C1H(LL)
+      C2=C2H(LL)
+C      print *,"llini: ",AM1,AM2,C1,C2
+C---> Switches:
+C     ISI=1(0)  the strong interaction between the two particles ON (OFF)
+C     IQS=1(0)  the quantum statistics ON (OFF);
+C               should be OFF for nonidentical particles
+C     I3C=1(0)  the Coulomb interaction with the nucleus ON (OFF)
+C     I3S=1(0)  the strong interaction with the nucleus ON (OFF)
+C     ICH=1(0)  if C1*C2 is different from 0 (is equal to 0)
+C-    To switch off the Coulomb force between the two particles
+C     put ICH=0 and substitute the strong amplitude parameters by
+C     the ones not affected by Coulomb interaction
+C---- --------------------------------------------------------------------
+      IF (I_ITEST.NE.1) THEN
+         ICH=0
+         IF(C1*C2.NE.0.D0) ICH=1
+         IQS=0
+         IF(C1+AM1.EQ.C2+AM2) IQS=1
+         I3S=0                  ! only this option is available
+         ISI=1
+         I3C=1
+      ENDIF
+C---> Calcul. twice the reduced mass (AM), the relative 
+C     mass difference (DM) and the Bohr radius (AC)
+      AM=2*AM1*AM2/(AM1+AM2)
+      AMS=AM*AM
+      DM=(AM1-AM2)/(AM1+AM2)
+      AC=1.D10
+      C12=C1*C2
+      IF(C12.NE.0.D0)AC=2*137.036D0/(C12*AM)
+C---Setting spin factors
+      MSPIN=MSPINH(LL)
+C      print *,"MSPIN: ",MSPIN
+      MSP=MSPIN
+      DO 91 ISPIN=1,10
+ 91      RHO(ISPIN)=RHOH(LL,ISPIN)
+C 91      print *,"RHO: ",ISPIN,RHO(ISPIN)
+C---> Integration limit AA in the spherical wave approximation
+      AA=0.D0
+cc      IF(NS.EQ.2.OR.NS.EQ.4)AA=.5D0 !!in 1/GeV --> 0.1 fm
+      IF(NS.EQ.2.OR.NS.EQ.4)AA=6.D0 !!in 1/GeV --> 1.2 fm
+C---> Setting scatt. length (FD), eff. radius (RD) and, if possible,
+C--   also the corresp. square well parameters (EB, RB)
+      DO 55 JJ=1,MSP
+         ISPIN=JJ
+         FD(JJ)=FDH(LL,JJ)
+         RD(JJ)=RDH(LL,JJ)
+         EB(JJ)=EBH(LL,JJ)
+         RB(JJ)=RBH(LL,JJ)
+C         print *,"FD,RD,EB,RB: ",FD(JJ),RD(JJ),EB(JJ),RB(JJ)
+C---Resets FD and RD for a nucleon-deuteron system (LL=8,9)
+      IF(LL.EQ.8.OR.LL.EQ.9)THEN
+       JH=LL-7+2*JJ-2
+       FD(JJ)=AAND(1,JH)
+       RD(JJ)=AAND(2,JH)-2*AAND(3,JH)/AAND(1,JH)
+      ENDIF
+C---Resets FD and RD for a pion-pion system (LL=5,6,7)
+      IF(LL.EQ.5.OR.LL.EQ.6.OR.LL.EQ.7)THEN
+       IF(LL.EQ.7)FD(JJ)=AAPI(1,2)/AM
+       IF(LL.EQ.5)FD(JJ)=(.6667D0*AAPI(1,1)+.3333D0*AAPI(1,2))/AM
+       IF(LL.EQ.6)FD(JJ)=(.3333D0*AAPI(1,1)+.6667D0*AAPI(1,2))/AM
+       AKS=0.D0
+       DAKS=1.D-5
+       AKSH=AKS+DAKS
+       AKH=DSQRT(AKSH)
+       GPI1H=GPIPI(AKSH,1)
+       GPI2H=GPIPI(AKSH,2)
+       H=1/FD(JJ)
+       IF(LL.EQ.7)C(JJ)=1/DCMPLX(GPI2H,-AKH)
+       IF(LL.EQ.5)
+     + C(JJ)=.6667D0/DCMPLX(GPI1H,-AKH)+.3333D0/DCMPLX(GPI2H,-AKH)
+       IF(LL.EQ.6)
+     + C(JJ)=.3333D0/DCMPLX(GPI1H,-AKH)+.6667D0/DCMPLX(GPI2H,-AKH)
+       HH=DREAL(1/C(JJ))
+       RD(JJ)=2*(HH-H)/DAKS
+      ENDIF
+C---Resets FD and RD for a pion-nucleon system (LL=12,13) 
+      IF(LL.EQ.12.OR.LL.EQ.13)THEN
+       IF(LL.EQ.12)FD(JJ)=AAPIN(1,2)
+       IF(LL.EQ.13)FD(JJ)=(.6667D0*AAPIN(1,1)+.3333D0*AAPIN(1,2))
+       AKS=0.D0
+       DAKS=1.D-5
+       AKSH=AKS+DAKS
+       AKH=DSQRT(AKSH)
+       GPI1H=GPIN(AKSH,1)
+       GPI2H=GPIN(AKSH,2)
+       H=1/FD(JJ)
+       IF(LL.EQ.12)C(JJ)=1/DCMPLX(GPI2H,-AKH)
+       IF(LL.EQ.13)
+     + C(JJ)=.6667D0/DCMPLX(GPI1H,-AKH)+.3333D0/DCMPLX(GPI2H,-AKH)
+       HH=DREAL(1/C(JJ))
+       RD(JJ)=2*(HH-H)/DAKS
+      ENDIF
+C---fm to 1/GeV for pp-bar system
+      IF(LL.EQ.30)THEN
+         IF(IFIRST.LE.1)THEN
+            DO 4 I3=1,3
+               AAPAPR(I3,JJ)=AAPAPR(I3,JJ)*W
+ 4             AAPAPI(I3,JJ)=AAPAPI(I3,JJ)*W
+C     4       print *,"AAPAPR,AAPAPI: ",AAPAPR(I3,JJ),AAPAPI(I3,JJ)
+C---  Calculates complex elements M11=M22=C(6), M12=M21=C(7) for I=0
+C---  at k*=0                  M11=M22=C(8), M12=M21=C(9) for I=1   
+          C(7+(JJ-1)*2)=2*DCMPLX(AAPAPR(1,JJ),AAPAPI(1,JJ))*
+     *         DCMPLX(AAPAPR(2,JJ),AAPAPI(2,JJ)) ! 2a_0Sa_1S
+          C(6+(JJ-1)*2)=DCMPLX(AAPAPR(1,JJ)+AAPAPR(2,JJ),
+     ,         AAPAPI(1,JJ)+AAPAPI(2,JJ))/
+     /         C(7+(JJ-1)*2)    ! M11=M22
+          C(7+(JJ-1)*2)=-DCMPLX(AAPAPR(1,JJ)-AAPAPR(2,JJ),
+     ,         AAPAPI(1,JJ)-AAPAPI(2,JJ))/
+     /         C(7+(JJ-1)*2)    ! M12=M21      
+        ENDIF
+      ENDIF
+C---Calculation continues for any system (any LL)
+ 55   CONTINUE
+      RETURN
+      END 
+C=======================================================
+C
+
+c++  This routine is used to init mass and charge of the nucleus.
+
+      SUBROUTINE FSINUCL(R_AMN,R_CN)
+
+      IMPLICIT REAL*8 (A-H,O-Z)
+      COMMON/FSI_POC/AMN,AM1,AM2,CN,C1,C2,AC1,AC2
+
+      AMN=R_AMN
+      CN=R_CN
+      
+      RETURN
+      END
+      
+C======================================================
+C
+
+      SUBROUTINE FSIMOMENTUM(PP1,PP2)
+      
+      IMPLICIT REAL*8 (A-H,O-Z)
+      COMMON/FSI_MOM/P1X,P1Y,P1Z,E1,P1,  ! particle momenta in NRF
+     1               P2X,P2Y,P2Z,E2,P2 
+
+
+      REAL*8 PP1(3),PP2(3)
+c      Print *,"momentum",pp1,pp2
+      P1X=PP1(1)
+      P1Y=PP1(2)
+      P1Z=PP1(3)
+      P2X=PP2(1)
+      P2Y=PP2(2)
+      P2Z=PP2(3)
+      RETURN
+      END
+      
+
+
+C======================================================
+C
+
+      SUBROUTINE FSIPOSITION(XT1,XT2)
+      
+      IMPLICIT REAL*8 (A-H,O-Z)
+      COMMON/FSI_COOR/X1,Y1,Z1,T1,R1, !4-coord. of emis. points in NRF
+     1                X2,Y2,Z2,T2,R2
+
+      REAL*8 XT1(4),XT2(4)
+clc      print *,'fsi',xt1,xt2
+      X1=XT1(1)
+      Y1=XT1(2)
+      Z1=XT1(3)
+      T1=XT1(4)
+      X2=XT2(1)
+      Y2=XT2(2)
+      Z2=XT2(3)
+      T2=XT2(4)
+      RETURN
+      END
+      
+
+C======================================================
+C======================================================
+C
+      subroutine BoostToPrf()
+      IMPLICIT REAL*8 (A-H,O-Z)
+      COMMON/FSI_CVK/V,CVK
+      COMMON/FSI_MOM/P1X,P1Y,P1Z,E1,P1,  !part. momenta in NRF
+     1               P2X,P2Y,P2Z,E2,P2
+      COMMON/FSI_PRF/PPX,PPY,PPZ,AK,AKS,
+     1               X,Y,Z,T,RP,RPS
+      COMMON/FSI_COOR/X1,Y1,Z1,T1,R1, ! 4-coord. of emis. points in NRF
+     1                X2,Y2,Z2,T2,R2
+      COMMON/FSI_P12/P12X,P12Y,P12Z,E12,P12,AM12,EPM
+
+      XS=X1-X2
+      YS=Y1-Y2
+      ZS=Z1-Z2
+      TS=T1-T2
+      RS12=XS*P12X+YS*P12Y+ZS*P12Z
+      H1=(RS12/EPM-TS)/AM12
+      X=XS+P12X*H1
+      Y=YS+P12Y*H1
+      Z=ZS+P12Z*H1
+      T=(E12*TS-RS12)/AM12
+      RPS=X*X+Y*Y+Z*Z
+      RP=DSQRT(RPS)
+CW      WRITE(6,38)'RP ',RP,'X ',X,Y,Z,T
+38    FORMAT(A7,E11.4,A7,4E11.4)
+      CVK=(P12X*PPX+P12Y*PPY+P12Z*PPZ)/(P12*AK)
+      V=P12/E12
+      return 
+      end
+
+      SUBROUTINE FSIWF(WEI)
+C==> Prepares necessary quantities and call VZ(WEI) to calculate
+C    the weight due to FSI
+      IMPLICIT REAL*8 (A-H,O-Z)
+      COMMON/FSI_CVK/V,CVK
+      COMMON/FSI_MOM/P1X,P1Y,P1Z,E1,P1,  !part. momenta in NRF
+     1               P2X,P2Y,P2Z,E2,P2
+      COMMON/FSI_PRF/PPX,PPY,PPZ,AK,AKS,
+     1               X,Y,Z,T,RP,RPS
+      COMMON/FSI_COOR/X1,Y1,Z1,T1,R1, ! 4-coord. of emis. points in NRF
+     1                X2,Y2,Z2,T2,R2
+      COMMON/FSI_POC/AMN,AM1,AM2,CN,C1,C2,AC1,AC2
+      COMMON/FSI_SPIN/RHO(10)
+      COMMON/FSI_BP/B,P
+      COMMON/FSI_ETA/ETA
+      COMMON/FSI_ACH/HPR,AC,ACH,ACHR,ISPIN,MSPIN
+      COMMON/FSI_SW/RB(10),EB(10),BK(10),CDK(10),SDK(10),
+     1              SBKRB(10),SDKK(10)
+      COMMON/FSI_NS/LL,NS,ICH,ISI,IQS,I3C,I3S
+      COMMON/FSI_RR/F(10)
+      COMMON/FSI_FD/FD(10),RD(10)
+      COMMON/FSI_C/C(10),AM,AMS,DM
+      COMPLEX*16 C,F
+      COMMON/FSI_AA/AA
+      COMMON/FSI_SHH/SH,CHH
+      COMMON/FSI_AAPI/AAPI(20,2)/FSI_AAND/AAND(20,4)
+      COMMON/FSI_AAPIN/AAPIN(20,2)
+      COMMON/FSI_P12/P12X,P12Y,P12Z,E12,P12,AM12,EPM
+      COMMON/FSI_2CHA/AK2,AK2S,AAK,HCP2,AMU2_AMU1 ! k* (kappa) for 2-nd channel
+C==>calculating relative 4-coordinates of the particles in PRF
+C-  {T,X,Y,Z} from the relative coordinates {TS,XS,YS,ZS} in NRF
+      XS=X1-X2
+      YS=Y1-Y2
+      ZS=Z1-Z2
+      TS=T1-T2
+      RS12=XS*P12X+YS*P12Y+ZS*P12Z
+      H1=(RS12/EPM-TS)/AM12
+      X=XS+P12X*H1
+      Y=YS+P12Y*H1
+      Z=ZS+P12Z*H1
+      T=(E12*TS-RS12)/AM12
+      RPS=X*X+Y*Y+Z*Z
+      RP=DSQRT(RPS)
+CW      WRITE(6,38)'RP ',RP,'X ',X,Y,Z,T
+38    FORMAT(A7,E11.4,A7,4E11.4)
+      CVK=(P12X*PPX+P12Y*PPY+P12Z*PPZ)/(P12*AK)
+      V=P12/E12
+
+C      ACH=1.D0 
+      IF(ICH.EQ.0)GOTO 21
+      XH=AC*AK
+      ACH=ACP(XH)
+      ACHR=DSQRT(ACH)
+      ETA=0.D0
+      IF(XH.NE.0.D0)ETA=1/XH
+C---HCP, HPR needed (e.g. in GST) if ICH=1
+      HCP=HC(XH)
+      HPR=HCP+.1544313298D0
+C      AAK=ACH*AK    !
+C      HCP2=2*HCP/AC ! needed to calculate C(JJ) for charged particles
+  21  CONTINUE
+      MSP=MSPIN
+      DO 30 JJ=1,MSP
+      ISPIN=JJ
+      IF(NS.NE.1)GOTO22
+C---Calc. quantities for the square well potential;
+C-- for LL=6-26 the square well potential is not possible or available
+      IF(LL.EQ.4)GOTO 22
+      BK(JJ)=DSQRT(EB(JJ)**2+AKS)
+      XRA=2*RB(JJ)/AC
+      HRA=BK(JJ)*RB(JJ)
+      CALL SEQ(XRA,HRA)
+      SBKRB(JJ)=HRA*B
+      HRA=AK*RB(JJ)
+      CALL GST(XRA,HRA)
+      SDK(JJ)=SH
+      CDK(JJ)=CHH
+      SDKK(JJ)=RB(JJ)
+      IF(AK.NE.0.D0)SDKK(JJ)=SH/AK
+      IF(ICH.EQ.1)SDK(JJ)=ACH*SDK(JJ)
+  22  CONTINUE
+C-----------------------------------------------------------------------
+C---Calc. the strong s-wave scattering amplitude = C(JJ)
+C-- divided by Coulomb penetration factor squared (if ICH=1)
+      IF(NS.NE.1)GOTO 230
+      IF(LL.NE.4)GOTO 230 ! SW scat. amplitude used for alfa-alfa only
+      GAK=G(AK)
+      AKACH=AK
+      IF(ICH.EQ.1)AKACH=AK*ACH
+      C(JJ)=1/DCMPLX(GAK,-AKACH) ! amplitude for the SW-potential
+      GOTO 30
+ 230  IF(LL.EQ.5.OR.LL.EQ.6.OR.LL.EQ.7)GOTO20    ! pipi  
+      IF(LL.EQ.12.OR.LL.EQ.13)GOTO20             ! piN 
+      IF(LL.EQ.8.OR.LL.EQ.9.OR.LL.EQ.18)GOTO20   ! Nd, dd
+      IF(LL.EQ.14.OR.LL.EQ.17.OR.LL.EQ.23)GOTO27 ! K+K-, K-p, K0K0-b
+       IF(LL.EQ.30)GOTO 28                        ! pp-bar
+      A1=RD(JJ)*FD(JJ)*AKS
+      A2=1+.5D0*A1
+      IF(ICH.EQ.1)A2=A2-2*HCP*FD(JJ)/AC
+      AKF=AK*FD(JJ)
+      IF(ICH.EQ.1)AKF=AKF*ACH
+      C(JJ)=FD(JJ)/DCMPLX(A2,-AKF)
+      GOTO30
+ 20   CONTINUE
+C---Calc. scatt. ampl. C(JJ) for pipi, piN and Nd, dd
+      JH=LL-7+2*JJ-2
+      IF(LL.EQ.8.OR.LL.EQ.9)GPI2=GND(AKS,JH)
+      IF(LL.EQ.18)GPI2=GDD(AKS,JJ)
+      IF(LL.EQ.5.OR.LL.EQ.6.OR.LL.EQ.7)GPI2=GPIPI(AKS,2)
+      IF(LL.EQ.12.OR.LL.EQ.13)GPI2=GPIN(AKS,2)
+      C(JJ)=1.D0/DCMPLX(GPI2,-AK) !pi+pi+, nd, pd, pi+p, dd
+      IF(LL.NE.5.AND.LL.NE.6.AND.LL.NE.13)GOTO27
+      IF(LL.EQ.5.OR.LL.EQ.6)GPI1=GPIPI(AKS,1)
+      IF(LL.EQ.13)GPI1=GPIN(AKS,1)
+      IF(LL.EQ.5.OR.LL.EQ.13)
+     c           C(JJ)=.6667D0/DCMPLX(GPI1,-AK)+.3333D0*C(JJ) !pi+pi-,pi-p
+      IF(LL.EQ.6)C(JJ)=.3333D0/DCMPLX(GPI1,-AK)+.6667D0*C(JJ) !pi0pi0
+ 27   CONTINUE
+C---Calc. K+K-, K0K0-b or K-p s-wave scatt. ampl.
+      IF(LL.EQ.14.OR.LL.EQ.23)CALL CKKB
+c      IF(LL.EQ.17)C(JJ)=DCMPLX(-3.29D0,3.55D0)     ! Martin'76 (K-p)
+c      IF(LL.EQ.17)C(JJ)=DCMPLX(3.29D0,3.55D0)     ! Martin'76 (K-p) WRONG SIGN!!!
+      IF(LL.EQ.17)C(JJ)=DCMPLX(-2.585D0,4.156D0)   ! Borasoy'04 (K-p)
+c      IF(LL.EQ.17)C(JJ)=DCMPLX(-3.371D0,3.244D0)   ! Martin'81 (K-p)
+C---Calc. pi+pi-, pi+pi+, pd, pi+p, pi-p, K+K- or K-p s-wave scatt. ampl.
+C-- divided by Coulomb penetration factor squared (if ICH=1)
+      IF(ICH.EQ.0)GOTO 30
+      AAK=ACH*AK    !
+      HCP2=2*HCP/AC ! needed to calculate C(JJ) for charged particles
+      C(JJ)=1/(1/C(JJ)-HCP2+DCMPLX(0.D0,AK-AAK))
+      GOTO 30
+ 28   CONTINUE
+C---Calc. pp-bar s-wave scatt. ampl.
+      CALL CPAP
+ 30   CONTINUE
+C***********************************************************************
+      CALL VZ(WEI)
+      RETURN
+      END
+      SUBROUTINE VZ(WEI)
+C==> Calculates the weight WEI due to FSI
+      IMPLICIT REAL*8 (A-H,O-Z)
+      COMMON/FSI_JR/JRAT
+      COMMON/FSI_PRF/PPX,PPY,PPZ,AK,AKS,
+     1               X,Y,Z,T,RP,RPS
+      COMMON/FSI_SPIN/RHO(10)
+      COMMON/FSI_ETA/ETA
+      COMMON/FSI_AA/AA
+      COMMON/FSI_FFF/F12,F21
+      COMMON/FSI_ACH/HPR,AC,ACH,ACHR,ISPIN,MSPIN
+      COMMON/FSI_NS/LL,NS,ICH,ISI,IQS,I3C,I3S
+      COMMON/FSI_FD/FD(10),RD(10)
+      COMMON/FSI_RR/F(10)
+      COMMON/FSI_C/C(10),AM,AMS,DM
+      COMMON/FSI_COULPH/EIDC
+      COMPLEX*16 F,C,G,PSI12,PSI21
+      COMPLEX*16 F12,F21
+      COMPLEX*16 EIDC
+      COMPLEX*8 Z8,CGAMMA
+      COMMON/FSI_FFPN/FF12,FF21
+      COMPLEX*16 FF12,FF21
+      COMMON/FSI_2CHA/AK2,AK2S,AAK,HCP2,AMU2_AMU1 ! k* (kappa) for 2-nd channel
+      WEI=0.D0
+      IF(JRAT.EQ.1)GOTO 11
+      RHOS=AK*RP
+      HS=X*PPX+Y*PPY+Z*PPZ
+      IF(RHOS.LT.15.D0.AND.RHOS+DABS(HS).LT.20.D0)GOTO 2
+C---Calc. EIDC=exp(i*Coul.Ph.);
+C-- used in calc. of hypergeom. f-s in SEQA, FAS at k*R > 15, 20
+      Z8=CMPLX(1.,SNGL(ETA))
+      Z8=CGAMMA(Z8)
+      EIDC=Z8/CABS(Z8)
+ 2    CALL FF(RHOS,HS)
+ 11   MSP=MSPIN
+      IF(ISI.EQ.0)GOTO 4  ! the strong interaction ON (OFF) if ISI=1(0)
+      IF(RP.LT.AA)GOTO 4
+      IF(JRAT.NE.1) CALL FIRT
+      IF(IQS.EQ.0)GOTO 5  ! the quantum statistics ON (OFF) if IQS=1(0)
+      JSIGN=-1
+      DO 1 JJ=1,MSP
+      JSIGN=-JSIGN
+      G=F(JJ)*C(JJ)
+      IF(ICH.EQ.1)G=G*ACHR
+      PSI12=FF12*(F12+G)
+      PSI21=FF21*(F21+G)
+      G=PSI12+JSIGN*PSI21
+ 1    WEI=WEI+RHO(JJ)*(DREAL(G)**2+DIMAG(G)**2)
+      GOTO 8
+ 5    DO 6 JJ=1,MSP
+      G=F(JJ)*C(JJ)
+      IF(ICH.EQ.1)G=G*ACHR
+CW      WRITE(6,38)'JJ ',JJ,'F ',DREAL(F(JJ)),DIMAG(F(JJ))
+CW      WRITE(6,38)'JJ ',JJ,'C ',DREAL(C(JJ)),DIMAG(C(JJ))
+CW      WRITE(6,38)'JJ ',JJ,'G ',DREAL(G),DIMAG(G)
+CW      WRITE(6,38)'JJ ',JJ,'F12+G ',DREAL(F12+G),DIMAG(F12+G)
+CW      WRITE(6,38)'JJ ',JJ,'F21+G ',DREAL(F21+G),DIMAG(F21+G)
+38    FORMAT(A7,I3,A7,2E11.4)
+      PSI12=FF12*(F12+G)
+ 6    WEI=WEI+RHO(JJ)*(DREAL(PSI12)**2+DIMAG(PSI12)**2)
+c--- Account for nn-bar->pp-bar channel ---------------------------
+      IF(LL.EQ.30)THEN
+      DO 61 JJ=1,MSP
+       HH=RHO(JJ)*(DREAL(C(JJ+2))**2+DIMAG(C(JJ+2))**2)*
+     * AMU2_AMU1*ACH/RPS
+       IF(AK2S.LT.0)HH=HH*DEXP(-2*RP*AK2)
+ 61   WEI=WEI+HH
+       ENDIF
+c------------------------------------------------------------------
+      RETURN
+ 4    PSI12=FF12*F12
+      IF(IQS.EQ.0)GOTO 50 ! the quantum statistics ON (OFF) if IQS=1(0)
+      PSI21=FF21*F21
+      JSIGN=-1
+      DO 3 JJ=1,MSP
+      JSIGN=-JSIGN
+      G=PSI12+JSIGN*PSI21
+ 3    WEI=WEI+RHO(JJ)*(DREAL(G)**2+DIMAG(G)**2)
+      GOTO 8
+ 50   WEI=DREAL(PSI12)**2+DIMAG(PSI12)**2
+      RETURN
+ 8    WEI=WEI/2
+      RETURN
+      END
+      SUBROUTINE FIRT
+C---CALC. THE F(JJ)
+C-- F(JJ)*C(JJ)= DEVIATION OF THE BETHE-SALPETER AMPL. FROM PLANE WAVE
+      IMPLICIT REAL*8 (A-H,O-Z)
+      COMMON/FSI_PRF/PPX,PPY,PPZ,AK,AKS,
+     1               X,Y,Z,T,RP,RPS
+      COMMON/FSI_SHH/SH,CHH
+      COMMON/FSI_BP/B,P
+      COMMON/FSI_ACH/HPR,AC,ACH,ACHR,ISPIN,MSPIN
+      COMMON/FSI_C/C(10),AM,AMS,DM
+      COMMON/FSI_SW/RB(10),EB(10),BK(10),CDK(10),SDK(10),
+     1              SBKRB(10),SDKK(10)
+      COMMON/FSI_NS/LL,NS,ICH,ISI,IQS,I3C,I3S
+      COMMON/FSI_RR/F(10)
+      EQUIVALENCE(RSS,RP),(TSS,T)
+      COMPLEX*16 F,C,CH1
+      MSP=MSPIN
+      DO 10 JJ=1,MSP
+      IF(JJ.GT.1)GOTO 3
+      XRA=2*RSS/AC
+      IF(AK.NE.0.D0)GOTO2
+      SHK=1.D0
+      SH=.0D0
+      SHH=SH
+      CHH=1/RSS
+      GOTO3
+  2   H=AK*RSS
+      CALL GST(XRA,H)
+      SH=SH/RSS
+      CHH=CHH/RSS
+      SHH=SH
+      IF(ICH.EQ.1) SHH=ACH*SH
+  3   IF(NS.EQ.2)GOTO1
+C---F= ASYMPTOTIC FORMULA (T= 0 APPROX.); NS= 4
+  6   F(JJ)=DCMPLX(CHH,SHH)
+      IF(NS.NE.1)GOTO 10
+C---F INSIDE THE SQUARE-WELL (T= 0 APPROX.); NS= 1
+      IF(RSS.GE.RB(JJ)) GOTO 10
+      IF(AK.NE.0.D0.AND.JJ.EQ.1)SHK=SH/AK
+      H=BK(JJ)*RSS
+      CALL GST(XRA,H)
+      SKR=B*BK(JJ)
+      F(JJ)=DCMPLX(CDK(JJ),SDK(JJ))*SKR
+      CH1=(SDKK(JJ)*SKR-SHK*SBKRB(JJ))/C(JJ)
+      F(JJ)=(F(JJ)+CH1)/SBKRB(JJ)
+      GOTO 10
+  1   CONTINUE
+C---F= ASYMPTOTIC FORMULA (T= 0 NOT REQUIRED); NS= 2
+      IF(JJ.GT.1)GOTO 8
+      IF(TSS.EQ.0.D0)GOTO6
+      TSSA=DABS(TSS)
+      IF(DM.NE.0.D0)GOTO 11
+      H=AM*.5D0/TSSA
+      IF(AK.NE.0.D0)GOTO4
+      HM=H*RPS
+      IF(HM.GE.3.D15)GOTO6
+      FS1=DFRSIN(HM)
+      FC1=DFRCOS(HM)
+      FC2=FC1
+      FS2=FS1
+      GOTO5
+  4   CONTINUE
+      H1=AK*TSSA/AM
+      HM=H*(RSS-H1)**2
+      HP=H*(RSS+H1)**2
+      IF(HP.GE.3.D15)GOTO6
+      FS1=DFRSIN(HM)
+      FC1=DFRCOS(HM)
+      FS2=DFRSIN(HP)
+      FC2=DFRCOS(HP)
+      GOTO 5
+  11  CONTINUE
+      FS1=0.D0
+      FS2=0.D0
+      FC1=0.D0
+      FC2=0.D0
+      DO 13 I=1,2
+      IF(I.EQ.1)TSSH=TSSA*(1+DM)
+      IF(I.EQ.2)TSSH=TSSA*(1-DM)
+      H=AM*.5D0/TSSH
+      IF(AK.NE.0.D0)GOTO 12
+      HM=H*RPS
+      IF(HM.GE.3.D15)GOTO6
+      FS1=FS1+DFRSIN(HM)/2
+      FC1=FC1+DFRCOS(HM)/2
+      IF(I.EQ.1)GOTO 13
+      FC2=FC1
+      FS2=FS1
+      GOTO 13
+  12  CONTINUE
+      H1=AK*TSSH/AM
+      HM=H*(RSS-H1)**2
+      HP=H*(RSS+H1)**2
+      IF(HP.GE.3.D15)GOTO6
+      FS1=FS1+DFRSIN(HM)/2
+      FC1=FC1+DFRCOS(HM)/2
+      FS2=FS2+DFRSIN(HP)/2
+      FC2=FC2+DFRCOS(HP)/2
+  13  CONTINUE
+  5   C12=FC1+FS2
+      S12=FS1+FC2
+      A12=FS1-FC2
+      A21=FS2-FC1
+      A2=.5D0*(CHH*(A12+A21)+SH*(A12-A21))+SHH
+      A1=.5D0*(CHH*(C12+S12)+SH*(C12-S12))
+      F(JJ)=.3989422D0*DCMPLX(A1,A2)
+      GOTO 10
+  8   F(JJ)=F(1)
+ 10   CONTINUE
+      RETURN
+      END
+      FUNCTION EXF(X)
+      IMPLICIT REAL*8 (A-H,O-Z)
+      IF(X.LT.-15.D0) GO TO 1
+      EXF=DEXP(X)
+      RETURN
+  1   EXF=.0D0
+      RETURN
+      END
+      SUBROUTINE SEQ(X,H)
+C---CALC. FUNCTIONS B, P (EQS. (17) OF G-K-L-L);
+C-- NEEDED TO CALC. THE CONFLUENT HYPERGEOMETRIC FUNCTION GST.
+      IMPLICIT REAL*8 (A-H,O-Z)
+      COMMON/FSI_BP/B,P
+      DIMENSION BH(3),PH(3)
+      DATA ERR/1.D-7/
+      BH(1)=1.D0
+      PH(1)=1.D0
+      PH(2)=.0D0
+      BH(2)=.5D0*X
+      B=1+BH(2)
+      P=1.D0
+      HS=H*H
+      J=0
+  2   J=J+1
+      BH(3)=(X*BH(2)-HS*BH(1))/((J+1)*(J+2))
+      PH(3)=(X*PH(2)-HS*PH(1)-(2*J+1)*X*BH(2))/(J*(J+1))
+      B=B+BH(3)
+      P=P+PH(3)
+      Z=DABS(BH(2))+DABS(BH(3))+DABS(PH(2))+DABS(PH(3))
+      IF(Z.LT.ERR)RETURN
+      BH(1)=BH(2)
+      BH(2)=BH(3)
+      PH(1)=PH(2)
+      PH(2)=PH(3)
+      GOTO 2
+      END
+      SUBROUTINE SEQA(X,H)
+C---CALC. FUNCTIONS CHH=REAL(GST), SH=IMAG(GST)/ACH, B=SH/H
+C-- IN THE ASYMPTOTIC REGION H=K*R >> 1.
+      IMPLICIT REAL*8 (A-H,O-Z)
+      COMMON/FSI_BP/B,P
+      COMMON/FSI_SHH/SH,CHH
+      COMMON/FSI_ETA/ETA
+      COMMON/FSI_ACH/HPR,AC,ACH,ACHR,ISPIN,MSPIN
+      COMMON/FSI_COULPH/EIDC
+      COMPLEX*16 EIDC,GST
+      ARG=H-ETA*DLOG(2*H)
+      GST=DCMPLX(DCOS(ARG),DSIN(ARG))
+      GST=ACHR*EIDC*GST
+      CHH=DREAL(GST)
+      SH=DIMAG(GST)/ACH
+      B=SH/H
+      RETURN
+      END
+      SUBROUTINE FF(RHO,H)
+C---Calc. F12, F21;
+C-- F12= FF0* plane wave,  FF0=F*ACHR,
+C---F is the confluent hypergeometric function,
+C-- ACHR=sqrt(ACH), where ACH is the Coulomb factor
+      IMPLICIT REAL*8 (A-H,O-Z)
+      COMMON/FSI_ACH/HPR,AC,ACH,ACHR,ISPIN,MSPIN
+      COMMON/FSI_NS/LL,NS,ICH,ISI,IQS,I3C,I3S
+      COMMON/FSI_ETA/ETA
+      COMMON/FSI_FFF/F12,F21
+      COMPLEX*16 FF0,F12,F21
+      C=DCOS(H)
+      S=DSIN(H)
+      F12=DCMPLX(C,-S)
+      F21=DCMPLX(C,S)
+      IF(ICH.EQ.0)RETURN
+      RHOP=RHO+H
+      RHOM=RHO-H
+      F12=FF0(RHO,H)*F12
+      F21=FF0(RHO,-H)*F21
+      RETURN
+      END
+      FUNCTION FAS(RKS)
+C-- FAS=F*ACHR
+C---F is the confluent hypergeometric function at k*r >> 1
+C-- ACHR=sqrt(ACH), where ACH is the Coulomb factor
+      IMPLICIT REAL*8 (A-H,O-Z)
+      COMPLEX*16 FAS,EIDC,ZZ1
+      COMMON/FSI_ACH/HPR,AC,ACH,ACHR,ISPIN,MSPIN
+      COMMON/FSI_ETA/ETA
+      COMMON/FSI_COULPH/EIDC
+      D1=DLOG(RKS)*ETA
+      D2=ETA*ETA/RKS
+      ZZ1=DCMPLX(DCOS(D1),DSIN(D1))/EIDC
+      FAS=DCMPLX(1.D0,-D2)*ZZ1
+      FAS=FAS-DCMPLX(DCOS(RKS),DSIN(RKS))*ETA/RKS/ZZ1
+      RETURN
+      END
+      FUNCTION FF0(RHO,H)
+C-- FF0=F*ACHR
+C-- F is the confluent hypergeometric function
+C-- (Eq. (15) of G-K-L-L), F= 1 at r* << AC
+C-- ACHR=sqrt(ACH), where ACH is the Coulomb factor
+      IMPLICIT REAL*8 (A-H,O-Z)
+      COMMON/FSI_ACH/HPR,AC,ACH,ACHR,ISPIN,MSPIN
+      COMMON/FSI_NS/LL,NS,ICH,ISI,IQS,I3C,I3S
+      COMMON/FSI_ETA/ETA
+      COMPLEX*16 ALF,ALF1,Z,S,A,FF0,FAS
+      DATA ERR/1.D-5/
+      S=DCMPLX(1.D0,0.D0)
+      FF0=S
+      RHOP=RHO+H
+CC      GOTO 5 ! rejects the approx. calcul. of hyperg. f-ion F
+      IF(RHOP.LT.20.D0)GOTO5
+      FF0=FAS(RHOP) ! approx. calc.
+      RETURN
+  5   ALF=DCMPLX(.0D0,-ETA)
+      ALF1=ALF-1
+      Z=DCMPLX(.0D0,RHOP)
+      J=0
+  3   J=J+1
+      A=(ALF1+J)/(J*J)
+      S=S*A*Z
+      FF0=FF0+S
+      ZR=DABS(DREAL(S))
+      ZI=DABS(DIMAG(S))
+      IF((ZR+ZI).GT.ERR)GOTO3
+      FF0=FF0*ACHR
+      RETURN
+      END
+      FUNCTION HC(XA)
+C---HC = h-function of Landau-Lifshitz: h(x)=Re[psi(1-i/x)]+ln(x)
+C-- psi(x) is the digamma function (the logarithmic derivative of
+C-- the gamma function)
+      IMPLICIT REAL*8 (A-H,O-Z)
+      DIMENSION BN(15)
+      DATA BN/.8333333333D-1,.8333333333D-2,.396825396825D-2,
+     1        .4166666667D-2,.7575757576D-2,.2109279609D-1,
+     2        .8333333333D-1,.4432598039D0 ,.305395433D1,
+     3        .2645621212D2, .2814601449D3, .3607510546D4,
+     4        .5482758333D5, .9749368235D6, .200526958D8/
+      X=DABS(XA)
+      IF(X.LT..33D0) GOTO 1
+CC      IF(X.GE.3.5D0) GO TO 2
+      S=.0D0
+      N=0
+   3  N=N+1
+      DS=1.D0/N/((N*X)**2+1)
+      S=S+DS
+      IF(DS.GT.0.1D-12) GOTO 3
+C---Provides 7 digit accuracy
+      HC=S-.5772156649D0+DLOG(X)
+      RETURN
+CC   2  HC=1.2D0/X**2+DLOG(X)-.5772156649 D0
+CC      RETURN
+   1  X2=X*X
+      XP=X2
+      HC=0.D0
+      IMA=9
+      IF(X.LT.0.1D0)IMA=3
+      DO 4 I=1,IMA
+      HC=HC+XP*BN(I)
+   4  XP=X2*XP
+      RETURN
+      END
+      FUNCTION ACP(X)
+C--- ACP = COULOMB PENETRATION FACTOR
+      IMPLICIT REAL*8 (A-H,O-Z)
+      IF(X.LT.0.05D0.AND.X.GE.0.D0) GO TO 1
+      Y=6.2831853D0/X
+      ACP=Y/(EXF(Y)-1)
+      RETURN
+   1  ACP=1.D-6
+      RETURN
+      END
+      SUBROUTINE GST(X,H)
+C---CALC. THE CONFL. HYPERGEOM. F-N = CHH+i*SH
+C-- AND THE COULOMB F-S B, P (CALLS SEQ OR SEQA).
+      IMPLICIT REAL*8 (A-H,O-Z)
+      COMMON/FSI_ACH/HPR,AC,ACH,ACHR,ISPIN,MSPIN
+      COMMON/FSI_NS/LL,NS,ICH,ISI,IQS,I3C,I3S
+      COMMON/FSI_SHH/SH,CHH
+      COMMON/FSI_BP/B,P
+  1   IF(ICH.EQ.1)GOTO 2
+  3   SH=DSIN(H)
+      CHH=DCOS(H)
+      B=1.D0
+      IF(H.NE.0.D0)B=SH/H
+      P=CHH
+      RETURN
+  2   CONTINUE
+      IF(H.GT.15.D0)GOTO4 ! comment out if you want to reject
+                   ! the approximate calculation of hyperg. f-ion G
+      CALL SEQ(X,H) ! exact calculation
+      SH=H*B
+      CHH=P+B*X*(DLOG(DABS(X))+HPR)
+      RETURN
+  4   CALL SEQA(X,H)
+      RETURN
+      END
+      FUNCTION FF1(RHO,H)
+C---FF1=FF0; used for particle-nucleus system
+C-- FF0=F12*ACHR
+C-- F12 is the confluent hypergeometric function
+C-- (Eq. (15) of G-K-L-L), F12= 1 at r* << AC
+C-- ACHR=sqrt(ACH), where ACH is the Coulomb factor
+      IMPLICIT REAL*8 (A-H,O-Z)
+      COMMON/FSI_ACH/HPR,AC,ACH,ACHR,ISPIN,MSPIN
+      COMMON/FSI_NS/LL,NS,ICH,ISI,IQS,I3C,I3S
+      COMMON/FSI_ETA/ETA
+      COMMON/FSI_COULPH/EIDC
+      COMMON/FSI_ICH1/ICH1
+      COMPLEX*16 FF0,FF1
+      COMPLEX*16 EIDC
+      COMPLEX*8 Z8,CGAMMA
+      FF1=DCMPLX(1.D0,0.D0)
+      IF(ICH1.EQ.0)GOTO 2
+      IF(RHO.LT.15.D0.AND.RHO+H.LT.20.D0)GOTO 2
+C---Calc. EIDC=exp(i*Coul.Ph.);
+C-- used in calc. of hypergeom. f-s in SEQA, FAS at k*R > 15, 20
+      Z8=CMPLX(1.,SNGL(ETA))
+      Z8=CGAMMA(Z8)
+      EIDC=Z8/CABS(Z8)
+ 2    FF1=FF0(RHO,H)
+      RETURN
+      END
+      FUNCTION G(AK)
+C---Used to calculate SW scattering amplitude for alpa-alpha system
+C-- and for sear.f (square well potential search)
+C---NOTE THAT SCATT. AMPL.= 1/CMPLX(G(AK),-AK*ACH)
+      IMPLICIT REAL*8 (A-H,O-Z)
+      COMMON/FSI_SW/RB(10),EB(10),BK(10),CDK(10),SDK(10),
+     1              SBKRB(10),SDKK(10)
+      COMMON/FSI_NS/LL,NS,ICH,ISI,IQS,I3C,I3S
+      COMMON/FSI_ACH/HPR,AC,ACH,ACHR,JJ,MSPIN
+      COMMON/FSI_BP/B,P/FSI_DERIV/BPR,PPR/FSI_SHH/SH,CHH
+      COMMON/FSI_DAK/DAK,HAC,IFUN
+      HAC=.0D0
+      ACH=1.D0
+      IF(ICH.EQ.0)GOTO 1
+      XH=AC*AK
+      HCP=HC(XH)
+      HPR=HCP+.1544313298D0
+      ACH=ACP(XH)
+      HAC=2*HCP/AC
+   1  AKS=AK**2
+      BK(JJ)=DSQRT(AKS+EB(JJ)**2) ! kappa=kp
+      X=2*RB(JJ)/AC
+      H=BK(JJ)*RB(JJ)             ! kp*d
+      CALL GST(X,H)
+      BRHO=B                      ! B(kp,d)
+      SBKRB(JJ)=SH                ! kp*d*B(kp,d)
+      CALL DERIW(X,H)
+      BRHOP=BPR                   ! B'(kp,d)= dB(kp,r)/dln(r) at r=d
+      H=AK*RB(JJ)
+      CALL GST(X,H)
+      CDK(JJ)=CHH                 ! ReG(k,d)
+      BRHOS=B                     !  B(k,d)
+      PRHOS=P                     !  P(k,d)
+      SDK(JJ)=SH
+      IF(ICH.EQ.0)GOTO 2
+      SDK(JJ)=ACH*SH              ! ImG(k,d)
+      IF(AK.EQ.0.D0.AND.AC.LT.0.D0)SDK(JJ)=3.14159*X*B
+   2  SDKK(JJ)=RB(JJ)
+      IF(AK.NE.0.D0)SDKK(JJ)=SH/AK ! d*B(k,d)
+      CALL DERIW(X,H)              ! PPR=P'(k,d)= dP(k,r)/dln(r) at r=d
+      ZZ=PPR-PRHOS
+      IF(ICH.EQ.1)ZZ=ZZ+X*(BRHOS+BPR*(DLOG(DABS(X))+HPR))
+C   ZZ= P'(k,d)-P(k,d)+x*{B(k,d)+B'(k,d)*[ln!x!+2*C-1+h(k*ac)]}
+      GG=(BRHOP*CDK(JJ)-BRHO*ZZ)/RB(JJ)
+C   GG= [B'(kp,d)*ReG(k,d)-B(kp,d)*ZZ]/d
+      G=GG/(BRHO*BPR-BRHOP*BRHOS)
+C    G= GG/[B(kp,d)*B'(k,d)-B'(kp,d)*B(k,d)]
+      RETURN
+      END
+      SUBROUTINE DERIW(X,H)
+C---CALLED BY F-N G(AK)
+      IMPLICIT REAL*8 (A-H,O-Z)
+      COMMON/FSI_NS/LL,NS,ICH,ISI,IQS,I3C,I3S 
+      COMMON/FSI_BP/B,P/FSI_DERIV/BPR,PPR
+      HH=.1D-3
+      CALL GST(X,H-HH)
+      Q1=P
+      B1=B
+      CALL GST(X,H+HH)
+      HHH=HH+HH
+      BPR=H*(B-B1)/HHH
+      PPR=H*(P-Q1)/HHH
+      IF(ICH.EQ.0)RETURN
+      CALL GST(X-HH,H)
+      Q1=P
+      B1=B
+      CALL GST(X+HH,H)
+      BPR=BPR+X*(B-B1)/HHH
+      PPR=PPR+X*(P-Q1)/HHH
+      RETURN
+      END
+C================================================================
+      SUBROUTINE READ_FILE(KEY,CH8,INT4,REAL8,IERR,NUNIT)
+C     ==========
+C
+C     Routine to read one parameter of the program in the file
+C     DATA NUNIT defined in FSI3B EXEC
+C     NUNIT=11 for IBM in Nantes, 4 for SUN in Prague
+C
+C     INPUT  : KEY (CHARACTER*10) :
+C     OUTPUT : case of KEY : CH8   : (CHARACTER*8)
+C                            INT4  : (INTEGER*4)
+C                            REAL8 : (REAL*8)
+C                     (only one of them)
+C              IERR (INTEGER) : 0 : no error
+C                               1 : key not found
+      CHARACTER*10 KEY,TEST
+      CHARACTER*4  TYPE
+      CHARACTER*8  CH8
+      INTEGER*4    INT4
+      REAL*8       REAL8
+      INTEGER*4    IERR
+      IERR=0
+      REWIND(NUNIT)
+1     READ(NUNIT,FMT='(A10,2X,A4)')TEST,TYPE
+      IF (TEST.EQ.KEY) THEN
+        BACKSPACE(NUNIT)
+        IF (TYPE.EQ.'CHAR') READ(NUNIT,FMT='(18X,A8,54X)')CH8
+        IF (TYPE.EQ.'INT4') READ(NUNIT,FMT='(18X,I8,54X)')INT4
+        IF (TYPE.EQ.'REA8') READ(NUNIT,FMT='(18X,F10.5,52X)')REAL8
+      ELSE
+        IF (TEST.NE.'* E.O.F. *') THEN
+          GOTO 1
+        ELSE
+          IERR=1
+        ENDIF
+      ENDIF
+c      IF(IERR.EQ.1)STOP 
+      RETURN
+      END
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoHelix.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoHelix.h
new file mode 100644 (file)
index 0000000..c63bfb0
--- /dev/null
@@ -0,0 +1,40 @@
+/***************************************************************************
+ *
+ * $Id$
+ *
+ * Author: Frank Laue, BNL, laue@bnl.gov
+ ***************************************************************************
+ *
+ ***************************************************************************
+ *
+ * $Log$
+ * Revision 1.1.1.1  2007/04/25 15:38:41  panos
+ * Importing the HBT code dir
+ *
+ * Revision 1.1.1.1  2007/03/07 10:14:49  mchojnacki
+ * First version on CVS
+ *
+ * Revision 1.1  2001/06/21 19:15:45  laue
+ * Modified fiels:
+ *   CTH.h : new constructor added
+ *   AliFemtoEvent, AliFemtoKink, AliFemtoTrack : constructors from the persistent
+ *                                   (TTree) classes added
+ *   AliFemtoLikeSignAnalysis : minor changes, for debugging
+ *   AliFemtoTypes: split into different files
+ * Added files: for the new TTree muDst's
+ *   StExceptions.cxx StExceptions.h AliFemtoEnumeration.h
+ *   AliFemtoHelix.h AliFemtoHisto.h AliFemtoString.h AliFemtoTFile.h
+ *   AliFemtoTTreeEvent.cxx AliFemtoTTreeEvent.h AliFemtoTTreeKink.cxx
+ *   AliFemtoTTreeKink.h AliFemtoTTreeTrack.cxx AliFemtoTTreeTrack.h
+ *   AliFemtoTTreeV0.cxx AliFemtoTTreeV0.h AliFemtoVector.h
+ *
+ *
+ ***************************************************************************/
+#ifndef AliFemtoHelix_hh
+#define AliFemtoHelix_hh
+
+#include "AliFmHelix.h"
+typedef AliFmHelix AliFemtoHelix;//!
+#include "AliFmPhysicalHelixD.h"
+typedef AliFmPhysicalHelixD AliFemtoPhysicalHelix;//!
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoHiddenInfo.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoHiddenInfo.h
new file mode 100644 (file)
index 0000000..f6256b2
--- /dev/null
@@ -0,0 +1,32 @@
+////////////////////////////////////////////////////////////////////////////////
+/// AliFemtoHiddenInfo - pure virtual base class for the hidden info         ///
+/// Hidden info stores additional information, which is not in a standard    ///
+/// track. 
+////////////////////////////////////////////////////////////////////////////////
+
+#ifndef AliFemtoHiddenInfo_hh
+#define AliFemtoHiddenInfo_hh
+
+#include "AliFemtoTypes.h"
+
+class AliFemtoHiddenInfo{
+
+ public:
+  AliFemtoHiddenInfo(){/* no-op */};
+  virtual ~AliFemtoHiddenInfo(){/* no-op */};
+  
+  // !!! MANDATORY !!!
+  // --- Copy the hidden info from AliFemtoTrack to AliFemtoParticle
+  virtual AliFemtoHiddenInfo* Clone() const;
+  
+ protected:
+  virtual AliFemtoHiddenInfo* GetParticleHiddenInfo() const =0;
+
+};
+//_______________________________________
+inline AliFemtoHiddenInfo* AliFemtoHiddenInfo::Clone() const{
+  // return exact copy of this hidden info
+  return GetParticleHiddenInfo();
+}
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoKTPairCut.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoKTPairCut.cxx
new file mode 100644 (file)
index 0000000..fddd0f0
--- /dev/null
@@ -0,0 +1,211 @@
+/////////////////////////////////////////////////////////////////////////////
+//                                                                         //
+// AliFemtoKTPairCut - a pair cut which selects pairs based on their       //
+// transverse momentum kT                                                  //
+//                                                                         //
+/////////////////////////////////////////////////////////////////////////////
+/***************************************************************************
+ *
+ * $Id: AliFemtoKTPairCut.cxx,v 1.1.2.2 2007/11/09 11:20:35 akisiel Exp $
+ *
+ * Author: Adam Kisiel, Ohio State, kisiel@mps.ohio-state.edu
+ ***************************************************************************
+ *
+ * Description: part of STAR HBT Framework: AliFemtoMaker package
+ *   a cut to remove "shared" and "split" pairs
+ *
+ ***************************************************************************
+ *
+ *
+ **************************************************************************/
+#include "AliFemtoKTPairCut.h"
+#include <string>
+#include <cstdio>
+#include <TMath.h>
+
+#ifdef __ROOT__
+ClassImp(AliFemtoKTPairCut)
+#endif
+
+//__________________
+AliFemtoKTPairCut::AliFemtoKTPairCut():
+  AliFemtoPairCut(),
+  fKTMin(0),
+  fKTMax(1.0e6),
+  fPhiMin(0),
+  fPhiMax(360.0),
+  fPtMin(0.0),
+  fPtMax(1000.0)
+{
+  fKTMin = 0;
+   fKTMax = 1.0e6;
+}
+//__________________
+AliFemtoKTPairCut::AliFemtoKTPairCut(double lo, double hi) :
+  AliFemtoPairCut(),
+  fKTMin(lo),
+  fKTMax(hi),
+  fPhiMin(0),
+  fPhiMax(360),
+  fPtMin(0.0),
+  fPtMax(1000.0)
+{
+}
+//__________________
+AliFemtoKTPairCut::AliFemtoKTPairCut(const AliFemtoKTPairCut& c) : 
+  AliFemtoPairCut(c),
+  fKTMin(0),
+  fKTMax(1.0e6),
+  fPhiMin(0),
+  fPhiMax(360),
+  fPtMin(0.0),
+  fPtMax(1000.0)
+{ 
+  fKTMin = c.fKTMin;
+  fKTMax = c.fKTMax;
+  fPhiMin = c.fPhiMin;
+  fPhiMax = c.fPhiMax;
+  fPtMin = c.fPtMin;
+  fPtMax = c.fPtMax;
+}
+
+//__________________
+AliFemtoKTPairCut::~AliFemtoKTPairCut(){
+  /* no-op */
+}
+AliFemtoKTPairCut& AliFemtoKTPairCut::operator=(const AliFemtoKTPairCut& c)
+{
+  if (this != &c) {
+    fKTMin = c.fKTMin;
+    fKTMax = c.fKTMax;
+    fPhiMin = c.fPhiMin;
+    fPhiMax = c.fPhiMax;
+    fPtMin = c.fPtMin;
+    fPtMax = c.fPtMax;
+  }
+
+  return *this;
+}
+//__________________
+/*bool AliFemtoKTPairCut::Pass(const AliFemtoPair* pair){
+  bool temp = true;
+  
+  if (pair->KT() < fKTMin)
+    temp = false;
+
+  if (pair->KT() > fKTMax)
+    temp = false;
+
+  return temp;
+}*/
+//__________________
+AliFemtoString AliFemtoKTPairCut::Report(){
+  // Prepare a report from the execution
+  string stemp = "AliFemtoKT Pair Cut \n";  char ctemp[100];
+  snprintf(ctemp , 100, "Accept pair with kT in range %f , %f",fKTMin,fKTMax);
+  snprintf(ctemp , 100, "Accept pair with angle in range %f , %f",fPhiMin,fPhiMax);
+  stemp += ctemp;
+  AliFemtoString returnThis = stemp;
+  return returnThis;}
+//__________________
+
+TList *AliFemtoKTPairCut::ListSettings()
+{
+  // return a list of settings in a writable form
+  TList *tListSetttings =  new TList();
+  char buf[200];
+  snprintf(buf, 200, "AliFemtoKTPairCut.ktmax=%f", fKTMax);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoKTPairCut.ktmin=%f", fKTMin);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoKTPairCut.phimax=%f", fPhiMax);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoKTPairCut.phimin=%f", fPhiMin);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoKTPairCut.ptmin=%f", fPtMin);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoKTPairCut.ptmax=%f", fPtMax);
+  tListSetttings->AddLast(new TObjString(buf));
+
+  return tListSetttings;
+}
+
+void AliFemtoKTPairCut::SetKTRange(double ktmin, double ktmax)
+{
+  fKTMin = ktmin;
+  fKTMax = ktmax;
+}
+
+void AliFemtoKTPairCut::SetPhiRange(double phimin, double phimax)
+{
+  fPhiMin = phimin;
+  fPhiMax = phimax;
+}
+
+void AliFemtoKTPairCut::SetPTMin(double ptmin, double ptmax)
+{
+  fPtMin = ptmin;
+  fPtMax = ptmax;
+}
+
+//______________________________________________________
+bool AliFemtoKTPairCut::Pass(const AliFemtoPair* pair)
+{
+  bool temp = true;
+
+//Taking care of the Kt cut
+  if (pair->KT() < fKTMin)
+    temp = false;
+
+  if (pair->KT() > fKTMax)
+    temp = false;
+
+  if (!temp) return temp;
+
+  if ((fPtMin > 0.0) || (fPtMax<1000.0)) {
+//     double px1 = pair->Track1()->Track()->P().x();
+//     double py1 = pair->Track1()->Track()->P().y();
+
+//     double px2 = pair->Track2()->Track()->P().x();
+//     double py2 = pair->Track2()->Track()->P().y();
+    
+//     double pt1 = TMath::Hypot(px1, py1);
+//     double pt2 = TMath::Hypot(px2, py2);
+    
+//     if ((pt1<fPtMin) || (pt1>fPtMax)) return false;
+//     if ((pt2<fPtMin) || (pt2>fPtMax)) return false;
+    if ((pair->Track1()->Track()->Pt()<fPtMin) || (pair->Track1()->Track()->Pt()>fPtMax)) return false;
+    if ((pair->Track2()->Track()->Pt()<fPtMin) || (pair->Track2()->Track()->Pt()>fPtMax)) return false;
+  }
+
+//Taking care of the Phi cut
+//   double rpangle = (pair->GetPairAngleEP())*180/TMath::Pi();
+  double rpangle = pair->GetPairAngleEP();
+
+  if (rpangle > 180.0) rpangle -= 180.0;
+  if (rpangle < 0.0) rpangle += 180.0;
+  
+  if (fPhiMin < 0) {
+    if ((rpangle > fPhiMax) && (rpangle < 180.0+fPhiMin)) 
+      temp = false;
+  }
+  else {
+    if ((rpangle < fPhiMin) || (rpangle > fPhiMax))
+      temp = false;
+  }
+  return temp;
+}
+
+//_____________________________________
+bool AliFemtoKTPairCut::Pass(const AliFemtoPair* pair, double aRPAngle)
+{
+//The same as above, but it is defined with RP Angle as input in all the Correlatin function classes.
+
+  bool temp = (aRPAngle > 0.);
+  aRPAngle = true;
+   
+  if (!Pass(pair))
+       temp = false;
+
+  return temp;
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoKTPairCut.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoKTPairCut.h
new file mode 100644 (file)
index 0000000..2f42379
--- /dev/null
@@ -0,0 +1,64 @@
+/////////////////////////////////////////////////////////////////////////////
+//                                                                         //
+// AliFemtoKTPairCut - a pair cut which selects pairs based on their       //
+// transverse momentum kT                                                  //
+//                                                                         //
+/////////////////////////////////////////////////////////////////////////////
+/***************************************************************************
+ *
+ * $Id: AliFemtoKTPairCut.h,v 1.1.2.1 2007/10/19 13:28:14 akisiel Exp $
+ *
+ * Author: Adam Kisiel, Ohio State University, kisiel@mps.ohio-state.edu
+ ***************************************************************************
+ *
+ * Description: part of STAR HBT Framework: AliFemtoMaker package
+ *   a cut to remove "shared" and "split" pairs
+ *
+ ***************************************************************************
+ *
+ *
+ **************************************************************************/
+
+#ifndef ALIFEMTOKTPAIRCUT_H
+#define ALIFEMTOKTPAIRCUT_H
+
+// do I need these lines ?
+//#ifndef StMaker_H
+//#include "StMaker.h"
+//#endif
+
+#include "AliFemtoPairCut.h"
+
+class AliFemtoKTPairCut : public AliFemtoPairCut{
+public:
+  AliFemtoKTPairCut();
+  AliFemtoKTPairCut(double lo, double hi);
+  AliFemtoKTPairCut(const AliFemtoKTPairCut& c);
+  virtual ~AliFemtoKTPairCut();
+  AliFemtoKTPairCut& operator=(const AliFemtoKTPairCut& c);
+
+  virtual AliFemtoString Report();
+  virtual TList *ListSettings();
+  AliFemtoPairCut* Clone();
+  void SetKTRange(double ktmin, double ktmax);
+  void SetPhiRange(double phimin, double phimax);
+  void SetPTMin(double ptmin, double ptmax=1000.0);
+  virtual bool Pass(const AliFemtoPair* pair);
+  virtual bool Pass(const AliFemtoPair* pair, double aRPAngle);
+
+ protected:
+  Double_t fKTMin;          // Minimum allowed pair transverse momentum
+  Double_t fKTMax;          // Maximum allowed pair transverse momentum 
+  Double_t fPhiMin;         // Minimum angle vs. reaction plane 
+  Double_t fPhiMax;         // Maximum angle vs. reaction plane
+  Double_t fPtMin;          // Minimum per-particle pT
+  Double_t fPtMax;          // Maximum per-particle pT
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoKTPairCut, 0)
+#endif
+};
+
+inline AliFemtoPairCut* AliFemtoKTPairCut::Clone() { AliFemtoKTPairCut* c = new AliFemtoKTPairCut(*this); return c;}
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoKink.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoKink.cxx
new file mode 100644 (file)
index 0000000..663ad06
--- /dev/null
@@ -0,0 +1,170 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFemtoKink: main class holding all the necessary information        //
+// about a kink (before the identification) that is required during      //
+// femtoscopic analysis. This class is filled with information from the  //
+// input stream by the reader. A particle has a link back to the Kink    //
+// it was created from, so we do not copy the information.               //
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+/***********************************************************************
+ *
+ * $Id$
+ *
+ * Author: Mike Lisa, Ohio State, 23May2001
+ *
+ ***********************************************************************
+ *
+ * Description: Kink class with information gotten from the StKinkVertex
+ *              of Wenshen Deng and Spiros Margetis
+ *
+ ***********************************************************************
+ *
+ * $Log$
+ * Revision 1.4  2007/05/03 09:42:29  akisiel
+ * Fixing Effective C++ warnings
+ *
+ * Revision 1.3  2007/04/27 07:24:34  akisiel
+ * Make revisions needed for compilation from the main AliRoot tree
+ *
+ * Revision 1.1.1.1  2007/04/25 15:38:41  panos
+ * Importing the HBT code dir
+ *
+ * Revision 1.1.1.1  2007/03/07 10:14:49  mchojnacki
+ * First version on CVS
+ *
+ * Revision 1.4  2001/11/14 21:07:21  lisa
+ * Fixed several small things (mostly discarded const) that caused fatal errors with gcc2.95.3
+ *
+ * Revision 1.3  2001/09/05 21:55:23  laue
+ * typo fixed
+ *
+ * Revision 1.2  2001/06/21 19:15:46  laue
+ * Modified fiels:
+ *   CTH.h : new constructor added
+ *   AliFemtoEvent, AliFemtoKink, AliFemtoTrack : constructors from the persistent
+ *                                   (TTree) classes added
+ *   AliFemtoLikeSignAnalysis : minor changes, for debugging
+ *   AliFemtoTypes: split into different files
+ * Added files: for the new TTree muDst's
+ *   StExceptions.cxx StExceptions.h AliFemtoEnumeration.h
+ *   AliFemtoHelix.h AliFemtoHisto.h AliFemtoString.h AliFemtoTFile.h
+ *   AliFemtoTTreeEvent.cxx AliFemtoTTreeEvent.h AliFemtoTTreeKink.cxx
+ *   AliFemtoTTreeKink.h AliFemtoTTreeTrack.cxx AliFemtoTTreeTrack.h
+ *   AliFemtoTTreeV0.cxx AliFemtoTTreeV0.h AliFemtoVector.h
+ *
+ * Revision 1.1  2001/05/25 23:23:59  lisa
+ * Added in AliFemtoKink stuff
+ *
+ * 
+ *
+ ***********************************************************************/
+
+#include "AliFemtoKink.h"
+#include "phys_constants.h"
+#include "AliFemtoTrack.h"
+// -----------------------------------------------------------------------
+AliFemtoKink::AliFemtoKink():
+  fDcaParentDaughter(0), fDcaDaughterPrimaryVertex(0), 
+  fDcaParentPrimaryVertex(0), fHitDistanceParentDaughter(0),  
+  fHitDistanceParentVertex(0),
+  fDecayAngle(0), fDecayAngleCM(0),             
+  fDaughter(),            
+  fParent(),               
+  fPosition(0,0,0)        
+{
+  for (int id=0; id<3; id++) fDeltaEnergy[id] = 0.0;
+}
+// -----------------------------------------------------------------------
+AliFemtoKink::AliFemtoKink(const AliFemtoKink& k):
+  fDcaParentDaughter(0), fDcaDaughterPrimaryVertex(0), 
+  fDcaParentPrimaryVertex(0), fHitDistanceParentDaughter(0),  
+  fHitDistanceParentVertex(0),
+  fDecayAngle(0), fDecayAngleCM(0),             
+  fDaughter(),            
+  fParent(),               
+  fPosition(0,0,0)        
+{ // copy constructor
+
+  fDcaParentDaughter          =   k.fDcaParentDaughter;           
+  fDcaDaughterPrimaryVertex   =   k.fDcaDaughterPrimaryVertex;    
+  fDcaParentPrimaryVertex     =   k.fDcaParentPrimaryVertex;      
+  fHitDistanceParentDaughter  =   k.fHitDistanceParentDaughter;   
+  fHitDistanceParentVertex    =   k.fHitDistanceParentVertex;     
+  fDeltaEnergy[0]             =   k.fDeltaEnergy[0];              
+  fDeltaEnergy[1]             =   k.fDeltaEnergy[1];              
+  fDeltaEnergy[2]             =   k.fDeltaEnergy[2];              
+  fDecayAngle                 =   k.fDecayAngle;                  
+  fDecayAngleCM               =   k.fDecayAngleCM;                
+  fDaughter                   =   k.fDaughter;                    
+  fParent                     =   k.fParent;                      
+  fPosition                   =   k.fPosition;                
+
+}
+// -----------------------------------------------------------------------
+AliFemtoKink& AliFemtoKink::operator=( const AliFemtoKink& k)
+{
+  if (this != &k) {
+    fDcaParentDaughter          =   k.fDcaParentDaughter;           
+    fDcaDaughterPrimaryVertex   =   k.fDcaDaughterPrimaryVertex;    
+    fDcaParentPrimaryVertex     =   k.fDcaParentPrimaryVertex;      
+    fHitDistanceParentDaughter  =   k.fHitDistanceParentDaughter;   
+    fHitDistanceParentVertex    =   k.fHitDistanceParentVertex;     
+    fDeltaEnergy[0]             =   k.fDeltaEnergy[0];              
+    fDeltaEnergy[1]             =   k.fDeltaEnergy[1];              
+    fDeltaEnergy[2]             =   k.fDeltaEnergy[2];              
+    fDecayAngle                 =   k.fDecayAngle;                  
+    fDecayAngleCM               =   k.fDecayAngleCM;                
+    fDaughter                   =   k.fDaughter;                    
+    fParent                     =   k.fParent;                      
+    fPosition                   =   k.fPosition;                
+  }
+
+  return *this;
+}
+
+
+//--------------------- below here is ONLY star ----------------
+#ifndef __NO_STAR_DEPENDENCE_ALLOWED__
+#ifdef __ROOT__
+#include "StEvent/StTrack.h"
+#include "StEvent/StKinkVertex.h"
+AliFemtoKink::AliFemtoKink( const StKinkVertex& SKV, AliFemtoThreeVector PrimaryVertex )
+{ 
+
+  fDcaParentDaughter          = SKV.dcaParentDaughter();
+  fDcaDaughterPrimaryVertex   = SKV.dcaDaughterPrimaryVertex();
+  fDcaParentPrimaryVertex     = SKV.dcaParentPrimaryVertex();
+  fHitDistanceParentDaughter  = SKV.hitDistanceParentDaughter();
+  fHitDistanceParentVertex    = SKV.hitDistanceParentVertex();
+  fDeltaEnergy[0]             = SKV.dE(0);
+  fDeltaEnergy[1]             = SKV.dE(1);
+  fDeltaEnergy[2]             = SKV.dE(2);
+  fDecayAngle                 = SKV.decayAngle();
+  fDecayAngleCM               = SKV.decayAngleCM();
+
+  // now fill member AliFemtoTrack data...
+  const StTrack* StTrk;
+  AliFemtoTrack* HbtTrk;
+  // Daughter
+  StTrk = SKV.daughter(0);
+  HbtTrk = new AliFemtoTrack(StTrk,PrimaryVertex); // generate NEW HbtTrack from StTrack
+  fDaughter = *HbtTrk;                         // invoke copy ctr of AliFemtoTrack
+  delete HbtTrk;                               // get rid of the NEW HbtTrack - we are done with that
+  // Parent
+  StTrk = SKV.parent();
+  HbtTrk = new AliFemtoTrack(StTrk,PrimaryVertex); // generate NEW HbtTrack from StTrack
+  fParent = *HbtTrk;                           // invoke copy ctr of AliFemtoTrack
+  delete HbtTrk;                               // get rid of the NEW HbtTrack - we are done with that
+
+  // finally, the kink position
+  fPosition.setX(SKV.position().x());
+  fPosition.setY(SKV.position().y());
+  fPosition.setZ(SKV.position().z());
+
+}
+
+// mike removed all AliFemtoTTree stuff 21apr2006
+
+#endif // __ROOT__
+#endif  // __NO_STAR_DEPENDENCE_ALLOWED__
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoKink.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoKink.h
new file mode 100644 (file)
index 0000000..b7873ef
--- /dev/null
@@ -0,0 +1,145 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFemtoKink: main class holding all the necessary information        //
+// about a kink (before the identification) that is required during      //
+// femtoscopic analysis. This class is filled with information from the  //
+// input stream by the reader. A particle has a link back to the Kink    //
+// it was created from, so we do not copy the information.               //
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+/***********************************************************************
+ *
+ * $Id$
+ *
+ * Author: Mike Lisa, Ohio State, 23May2001
+ *
+ ***********************************************************************
+ *
+ * Description: Kink class with information gotten from the StKinkVertex
+ *              of Wenshen Deng and Spiros Margetis
+ *
+ ***********************************************************************
+ *
+ * $Log$
+ * Revision 1.2  2007/05/03 09:42:29  akisiel
+ * Fixing Effective C++ warnings
+ *
+ * Revision 1.1.1.1  2007/04/25 15:38:41  panos
+ * Importing the HBT code dir
+ *
+ * Revision 1.1.1.1  2007/03/07 10:14:49  mchojnacki
+ * First version on CVS
+ *
+ * Revision 1.4  2003/09/02 17:58:32  perev
+ * gcc 3.2 updates + WarnOff
+ *
+ * Revision 1.3  2001/11/14 21:07:21  lisa
+ * Fixed several small things (mostly discarded const) that caused fatal errors with gcc2.95.3
+ *
+ * Revision 1.2  2001/06/21 19:15:46  laue
+ * Modified fiels:
+ *   CTH.h : new constructor added
+ *   AliFemtoEvent, AliFemtoKink, AliFemtoTrack : constructors from the persistent
+ *                                   (TTree) classes added
+ *   AliFemtoLikeSignAnalysis : minor changes, for debugging
+ *   AliFemtoTypes: split into different files
+ * Added files: for the new TTree muDst's
+ *   StExceptions.cxx StExceptions.h AliFemtoEnumeration.h
+ *   AliFemtoHelix.h AliFemtoHisto.h AliFemtoString.h AliFemtoTFile.h
+ *   AliFemtoTTreeEvent.cxx AliFemtoTTreeEvent.h AliFemtoTTreeKink.cxx
+ *   AliFemtoTTreeKink.h AliFemtoTTreeTrack.cxx AliFemtoTTreeTrack.h
+ *   AliFemtoTTreeV0.cxx AliFemtoTTreeV0.h AliFemtoVector.h
+ *
+ * Revision 1.1  2001/05/25 23:23:59  lisa
+ * Added in AliFemtoKink stuff
+ *
+ * 
+ *
+ ***********************************************************************/
+#ifndef ALIFEMTOKINK_H
+#define ALIFEMTOKINK_H
+
+class StKinkVertex;
+//#include "StEvent/StKinkVertex.h"  // from StEvent
+#include "AliFemtoTrack.h"
+
+#include "AliFemtoTypes.h" //same as in AliFemtoTrack.h
+
+class AliFemtoKink {
+public:
+  AliFemtoKink();
+  AliFemtoKink( const AliFemtoKink& k); // copy constructor
+#ifndef __NO_STAR_DEPENDENCE_ALLOWED__
+#ifdef __ROOT__
+  AliFemtoKink( const StKinkVertex&, AliFemtoThreeVector PrimaryVertex); // create a AliFemtoKink from a StKinkVertex
+#endif
+#endif
+  ~AliFemtoKink(){/* no-op */}
+  AliFemtoKink& operator=( const AliFemtoKink& k); // copy constructor
+
+  // Get's
+  float        DcaParentDaughter() const;
+  float        DcaDaughterPrimaryVertex() const;
+  float        DcaParentPrimaryVertex() const;
+  float        HitDistanceParentDaughter() const;
+  float        HitDistanceParentVertex() const;
+  float        DeltaEnergy(int i=0) const;
+  float        DecayAngle() const;
+  float        DecayAngleCM() const;
+  AliFemtoTrack   Daughter() const;
+  AliFemtoTrack   Parent() const;
+  AliFemtoThreeVector Position() const; 
+
+  
+
+protected:
+
+  float        fDcaParentDaughter;           // from StKinkVertex class directly 
+  float        fDcaDaughterPrimaryVertex;    // from StKinkVertex class directly 
+  float        fDcaParentPrimaryVertex;      // from StKinkVertex class directly 
+  float        fHitDistanceParentDaughter;   // from StKinkVertex class directly 
+  float        fHitDistanceParentVertex;     // from StKinkVertex class directly 
+  float        fDeltaEnergy[3];              // from StKinkVertex class directly 
+  float        fDecayAngle;                  // from StKinkVertex class directly 
+  float        fDecayAngleCM;                // from StKinkVertex class directly 
+  AliFemtoTrack   fDaughter;                    // from StKinkVertex class directly 
+  AliFemtoTrack   fParent;                      // from StVertex class (which StKinkVertex inherits from)
+  AliFemtoThreeVector fPosition;                // from StMeasuredPoint class (which StVertex inherits from)
+
+};
+
+// Get's
+inline float        AliFemtoKink::DcaParentDaughter() const {return fDcaParentDaughter;}
+inline float        AliFemtoKink::DcaDaughterPrimaryVertex() const {return fDcaDaughterPrimaryVertex;}
+inline float        AliFemtoKink::DcaParentPrimaryVertex() const {return fDcaParentPrimaryVertex;}
+inline float        AliFemtoKink::HitDistanceParentDaughter() const {return fHitDistanceParentDaughter;}
+inline float        AliFemtoKink::HitDistanceParentVertex() const {return fHitDistanceParentVertex;}
+inline float        AliFemtoKink::DeltaEnergy(int i) const {return fDeltaEnergy[i];}
+inline float        AliFemtoKink::DecayAngle() const {return fDecayAngle;}
+inline float        AliFemtoKink::DecayAngleCM() const {return fDecayAngleCM;}
+inline AliFemtoTrack   AliFemtoKink::Daughter() const {return fDaughter;}
+inline AliFemtoTrack   AliFemtoKink::Parent() const {return fParent;}
+inline AliFemtoThreeVector AliFemtoKink::Position() const {return fPosition;}
+
+
+
+
+#endif
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoKinkCollection.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoKinkCollection.h
new file mode 100644 (file)
index 0000000..c578748
--- /dev/null
@@ -0,0 +1,46 @@
+/***************************************************************************
+ *
+ * $Id$
+ *
+ * Author: Mike Lisa, Ohio State, lisa@mps.ohio-state.edu
+ ***************************************************************************
+ *
+ * Description: part of STAR HBT Framework: AliFemtoMaker package
+ *   The Collection of Kinks is the a component of the HbtEvent,
+ *   which is essentially the transient microDST
+ *
+ ****************************************************************************
+ *
+ * $Log$
+ * Revision 1.1.1.1  2007/04/25 15:38:41  panos
+ * Importing the HBT code dir
+ *
+ * Revision 1.1.1.1  2007/03/07 10:14:49  mchojnacki
+ * First version on CVS
+ *
+ * Revision 1.1  2001/05/25 23:23:59  lisa
+ * Added in AliFemtoKink stuff
+ *
+ *
+ ***************************************************************************/
+
+
+#ifndef AliFemtoKinkCollection_hh
+#define AliFemtoKinkCollection_hh
+#include "AliFemtoKink.h"
+#include <list>
+
+#if !defined(ST_NO_NAMESPACES)
+using std::list;
+#endif
+
+#ifdef ST_NO_TEMPLATE_DEF_ARGS
+typedef list<AliFemtoKink*, allocator<AliFemtoKink*> >            AliFemtoKinkCollection;
+typedef list<AliFemtoKink*, allocator<AliFemtoKink*> >::iterator  AliFemtoKinkIterator;
+#else
+typedef list<AliFemtoKink*>            AliFemtoKinkCollection;
+typedef list<AliFemtoKink*>::iterator  AliFemtoKinkIterator;
+#endif
+
+#endif
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoKinkCut.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoKinkCut.h
new file mode 100644 (file)
index 0000000..ca6d456
--- /dev/null
@@ -0,0 +1,35 @@
+////////////////////////////////////////////////////////////////////////////////
+/// AliFemtoKinkCut - the pure virtual base class for the kink cut           ///
+/// All kink cuts must inherit from this one                                 ///
+////////////////////////////////////////////////////////////////////////////////
+
+#ifndef AliFemtoKinkCut_hh
+#define AliFemtoKinkCut_hh
+
+#include "AliFemtoTypes.h"
+#include "AliFemtoKink.h"
+#include "AliFemtoParticleCut.h"
+
+class AliFemtoKinkCut : public AliFemtoParticleCut {
+
+public:
+
+  AliFemtoKinkCut(){/* no-op */};                       // default constructor. - Users should write their own
+  AliFemtoKinkCut(const AliFemtoKinkCut&);                         // copy constructor
+  virtual ~AliFemtoKinkCut(){/* no-op */};              // destructor
+  AliFemtoKinkCut& operator=(const AliFemtoKinkCut&);                         // copy constructor
+
+  virtual bool Pass(const AliFemtoKink* aKink)=0;               // true if passes, false if not
+
+  virtual AliFemtoParticleType Type(){return hbtKink;}
+  virtual AliFemtoKinkCut* Clone() { return 0;}
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoKinkCut, 0)
+#endif
+};
+//_____________________________
+inline AliFemtoKinkCut::AliFemtoKinkCut(const AliFemtoKinkCut& c) : AliFemtoParticleCut(c) { /* no-op */ } 
+inline AliFemtoKinkCut& AliFemtoKinkCut::operator=(const AliFemtoKinkCut& aCorrFctn) {   if (this != &aCorrFctn) { AliFemtoParticleCut::operator=(aCorrFctn); } return *this; }
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoLikeSignAnalysis.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoLikeSignAnalysis.cxx
new file mode 100644 (file)
index 0000000..9070039
--- /dev/null
@@ -0,0 +1,298 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// This is an analysis which calculated the background from like sign    //
+// pairs in the same event                                               //
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+
+#include "AliFemtoLikeSignAnalysis.h"
+#include "AliFemtoParticleCollection.h"
+#include "AliFemtoPicoEventCollectionVector.h"
+#include "AliFemtoPicoEventCollectionVectorHideAway.h"
+
+#ifdef __ROOT__ 
+ClassImp(AliFemtoLikeSignAnalysis)
+#endif
+
+// this little function used to apply ParticleCuts (TrackCuts or V0Cuts) and fill ParticleCollections of picoEvent
+//  it is called from AliFemtoSimpleAnalysis::ProcessEvent()
+
+
+extern void FillHbtParticleCollection(AliFemtoParticleCut*         partCut,
+                                    AliFemtoEvent*               hbtEvent,
+                                    AliFemtoParticleCollection*  partCollection);
+
+//____________________________
+AliFemtoLikeSignAnalysis::AliFemtoLikeSignAnalysis(unsigned int bins, double min, double max) : 
+  AliFemtoSimpleAnalysis(),
+  fVertexBins(0),
+  fOverFlow(0),  
+  fUnderFlow(0)  
+{
+  // standard constructor
+  fVertexBins = bins;
+  fVertexZ[0] = min;
+  fVertexZ[1] = max;
+  fUnderFlow = 0; 
+  fOverFlow = 0; 
+  if (fMixingBuffer) delete fMixingBuffer;
+  fPicoEventCollectionVectorHideAway = new AliFemtoPicoEventCollectionVectorHideAway(fVertexBins,fVertexZ[0],fVertexZ[1]);
+    /* no-op */
+}
+//____________________________
+AliFemtoLikeSignAnalysis::AliFemtoLikeSignAnalysis(const AliFemtoLikeSignAnalysis& a) : 
+  AliFemtoSimpleAnalysis(a) ,
+  fVertexBins(0),
+  fOverFlow(0),  
+  fUnderFlow(0)  
+{
+  // copy constructor
+  fVertexBins = a.fVertexBins; 
+  fVertexZ[0] = a.fVertexZ[0]; 
+  fVertexZ[1] = a.fVertexZ[1];
+  fUnderFlow = 0; 
+  fOverFlow = 0; 
+  if (fMixingBuffer) delete fMixingBuffer;
+  fPicoEventCollectionVectorHideAway = new AliFemtoPicoEventCollectionVectorHideAway(fVertexBins,fVertexZ[0],fVertexZ[1]);
+ }
+AliFemtoLikeSignAnalysis& AliFemtoLikeSignAnalysis::operator=(const AliFemtoLikeSignAnalysis& OriginalAnalysis)
+{
+  if (this != &OriginalAnalysis) {
+    fVertexBins = OriginalAnalysis.fVertexBins; 
+    fVertexZ[0] = OriginalAnalysis.fVertexZ[0]; 
+    fVertexZ[1] = OriginalAnalysis.fVertexZ[1];
+    fUnderFlow = 0; 
+    fOverFlow = 0; 
+    if (fMixingBuffer) delete fMixingBuffer;
+    if (fPicoEventCollectionVectorHideAway) delete fPicoEventCollectionVectorHideAway;
+    fPicoEventCollectionVectorHideAway = new AliFemtoPicoEventCollectionVectorHideAway(fVertexBins,fVertexZ[0],fVertexZ[1]);
+  }
+
+  return *this;
+
+}
+
+//____________________________ 
+AliFemtoLikeSignAnalysis::~AliFemtoLikeSignAnalysis(){
+  // destructor
+  delete fPicoEventCollectionVectorHideAway; fPicoEventCollectionVectorHideAway=0;
+}
+//____________________________
+AliFemtoString AliFemtoLikeSignAnalysis::Report()
+{  
+  // prepare report
+  char tCtemp[200];
+  cout << "AliFemtoLikeSignAnalysis - constructing Report..."<<endl;
+  AliFemtoString temp = "-----------\nHbt Analysis Report:\n";
+  snprintf(tCtemp , 200, "Events are mixed in %d bins in the range %E cm to %E cm.\n",fVertexBins,fVertexZ[0],fVertexZ[1]);
+  temp += tCtemp;
+  snprintf(tCtemp , 200, "Events underflowing: %d\n",fUnderFlow);
+  temp += tCtemp;
+  snprintf(tCtemp , 200, "Events overflowing: %d\n",fOverFlow);
+  temp += tCtemp;
+  snprintf(tCtemp , 200, "Now adding AliFemtoSimpleAnalysis(base) Report\n");
+  temp += tCtemp; 
+  temp += "Adding AliFemtoSimpleAnalysis(base) Report now:\n";
+  temp += AliFemtoSimpleAnalysis::Report();
+  temp += "-------------\n";
+  AliFemtoString returnThis=temp;
+  return returnThis;
+}
+//_________________________
+void AliFemtoLikeSignAnalysis::ProcessEvent(const AliFemtoEvent* hbtEvent) {
+  // perform all the analysis tasks for a single event
+  // get right mixing buffer
+  double vertexZ = hbtEvent->PrimVertPos().z();
+  fMixingBuffer = fPicoEventCollectionVectorHideAway->PicoEventCollection(vertexZ); 
+  if (!fMixingBuffer) {
+    if ( vertexZ < fVertexZ[0] ) fUnderFlow++;
+    if ( vertexZ > fVertexZ[1] ) fOverFlow++;
+    return;
+  }
+
+  // startup for EbyE 
+  EventBegin(hbtEvent);  
+  // event cut and event cut monitor
+  bool tmpPassEvent = fEventCut->Pass(hbtEvent);
+  fEventCut->FillCutMonitor(hbtEvent, tmpPassEvent);
+  if (tmpPassEvent) {
+      fNeventsProcessed++;
+      cout << "AliFemtoLikeSignAnalysis::ProcessEvent() - " << hbtEvent->TrackCollection()->size();
+      cout << " #track=" << hbtEvent->TrackCollection()->size();
+      // OK, analysis likes the event-- build a pico event from it, using tracks the analysis likes...
+      AliFemtoPicoEvent* picoEvent = new AliFemtoPicoEvent;       // this is what we will make pairs from and put in Mixing Buffer
+      FillHbtParticleCollection(fFirstParticleCut,(AliFemtoEvent*)hbtEvent,picoEvent->FirstParticleCollection());
+      if ( !(AnalyzeIdenticalParticles()) )
+       FillHbtParticleCollection(fSecondParticleCut,(AliFemtoEvent*)hbtEvent,picoEvent->SecondParticleCollection());
+      cout <<"   #particles in First, Second Collections: " <<
+       picoEvent->FirstParticleCollection()->size() << " " <<
+       picoEvent->SecondParticleCollection()->size() << endl;
+      
+      if (picoEvent->SecondParticleCollection()->size()*picoEvent->FirstParticleCollection()->size()==0) {
+       delete picoEvent;
+       cout << "AliFemtoLikeSignAnalysis - picoEvent deleted due to empty collection " <<endl; 
+       return;
+      }
+      // OK, pico event is built
+      // make real pairs...
+      
+      // Fabrice points out that we do not need to keep creating/deleting pairs all the time
+      // We only ever need ONE pair, and we can just keep changing internal pointers
+      // this should help speed things up
+      AliFemtoPair* tThePair = new AliFemtoPair;
+      
+      AliFemtoParticleIterator tPartIter1;
+      AliFemtoParticleIterator tPartIter2;
+      AliFemtoCorrFctnIterator tCorrFctnIter;
+      AliFemtoParticleIterator tStartOuterLoop = picoEvent->FirstParticleCollection()->begin();  // always
+      AliFemtoParticleIterator tEndOuterLoop   = picoEvent->FirstParticleCollection()->end();    // will be one less if identical
+      AliFemtoParticleIterator tStartInnerLoop;
+      AliFemtoParticleIterator tEndInnerLoop;
+      if (AnalyzeIdenticalParticles()) {             // only use First collection
+       tEndOuterLoop--;                                               // outer loop goes to next-to-last particle in First collection
+       tEndInnerLoop = picoEvent->FirstParticleCollection()->end() ;  // inner loop goes to last particle in First collection
+      }
+      else {                                                          // nonidentical - loop over First and Second collections
+       tStartInnerLoop = picoEvent->SecondParticleCollection()->begin(); // inner loop starts at first particle in Second collection
+       tEndInnerLoop   = picoEvent->SecondParticleCollection()->end() ;  // inner loop goes to last particle in Second collection
+      }
+      // real pairs
+      for (tPartIter1=tStartOuterLoop;tPartIter1!=tEndOuterLoop;tPartIter1++){
+       if (AnalyzeIdenticalParticles()){
+         tStartInnerLoop = tPartIter1;
+         tStartInnerLoop++;
+       }
+       tThePair->SetTrack1(*tPartIter1);
+       for (tPartIter2 = tStartInnerLoop; tPartIter2!=tEndInnerLoop;tPartIter2++){
+         tThePair->SetTrack2(*tPartIter2);
+         // The following lines have to be uncommented if you want pairCutMonitors
+         // they are not in for speed reasons
+         // bool tmpPassPair = mPairCut->Pass(tThePair);
+          // mPairCut->FillCutMonitor(tThePair, tmpPassPair);
+         // if ( tmpPassPair ) {
+         if (fPairCut->Pass(tThePair)){
+           for (tCorrFctnIter=fCorrFctnCollection->begin();
+                tCorrFctnIter!=fCorrFctnCollection->end();tCorrFctnIter++){
+             AliFemtoLikeSignCorrFctn* tCorrFctn = dynamic_cast<AliFemtoLikeSignCorrFctn*>(*tCorrFctnIter);
+             if (tCorrFctn) tCorrFctn->AddRealPair(tThePair);
+           }
+         }  // if passed pair cut
+       }    // loop over second particle
+      }      // loop over first particle
+#ifdef STHBTDEBUG
+      cout << "AliFemtoLikeSignAnalysis::ProcessEvent() - reals done" << endl;
+#endif
+
+      AliFemtoParticleIterator nextIter;
+      AliFemtoParticleIterator prevIter;
+
+      // like sign first partilce collection pairs
+      prevIter = tEndOuterLoop;
+      prevIter--;
+      for (tPartIter1=tStartOuterLoop;tPartIter1!=prevIter;tPartIter1++){
+       tThePair->SetTrack1(*tPartIter1);
+       nextIter = tPartIter1;
+       nextIter++;
+       for (tPartIter2 = nextIter; tPartIter2!=tEndOuterLoop;tPartIter2++){
+         tThePair->SetTrack2(*tPartIter2);
+         // The following lines have to be uncommented if you want pairCutMonitors
+         // they are not in for speed reasons
+         // bool tmpPassPair = mPairCut->Pass(tThePair);
+          // mPairCut->FillCutMonitor(tThePair, tmpPassPair);
+         // if ( tmpPassPair ) {
+         if (fPairCut->Pass(tThePair)){
+           for (tCorrFctnIter=fCorrFctnCollection->begin();
+                tCorrFctnIter!=fCorrFctnCollection->end();tCorrFctnIter++){
+             AliFemtoLikeSignCorrFctn* tCorrFctn = dynamic_cast<AliFemtoLikeSignCorrFctn*>(*tCorrFctnIter);
+             if (tCorrFctn) tCorrFctn->AddLikeSignPositivePair(tThePair);
+           }
+         }  // if passed pair cut
+       }    // loop over second particle
+      }      // loop over first particle
+#ifdef STHBTDEBUG
+      cout << "AliFemtoLikeSignAnalysis::ProcessEvent() - like sign first collection done" << endl;
+#endif
+      // like sign second partilce collection pairs
+      prevIter = tEndInnerLoop;
+      prevIter--;
+      for (tPartIter1=tStartInnerLoop;tPartIter1!=prevIter;tPartIter1++){
+       tThePair->SetTrack1(*tPartIter1);
+       nextIter = tPartIter1;
+       nextIter++;
+       for (tPartIter2 = nextIter; tPartIter2!=tEndInnerLoop;tPartIter2++){
+         tThePair->SetTrack2(*tPartIter2);
+         // The following lines have to be uncommented if you want pairCutMonitors
+         // they are not in for speed reasons
+         // bool tmpPassPair = mPairCut->Pass(tThePair);
+          // mPairCut->FillCutMonitor(tThePair, tmpPassPair);
+         // if ( tmpPassPair ) {
+         if (fPairCut->Pass(tThePair)){
+           for (tCorrFctnIter=fCorrFctnCollection->begin();
+                tCorrFctnIter!=fCorrFctnCollection->end();tCorrFctnIter++){
+             AliFemtoLikeSignCorrFctn* tCorrFctn = dynamic_cast<AliFemtoLikeSignCorrFctn*>(*tCorrFctnIter);
+             if (tCorrFctn) tCorrFctn->AddLikeSignNegativePair(tThePair);
+           }
+         }  // if passed pair cut
+       }    // loop over second particle
+      }      // loop over first particle
+#ifdef STHBTDEBUG
+      cout << "AliFemtoLikeSignAnalysis::ProcessEvent() - like sign second collection done" << endl;
+#endif
+      
+      if (MixingBufferFull()){
+#ifdef STHBTDEBUG
+       cout << "Mixing Buffer is full - lets rock and roll" << endl;
+#endif
+      }
+      else {
+       cout << "Mixing Buffer not full -gotta wait " << MixingBuffer()->size() << endl;
+      }
+      if (MixingBufferFull()){
+       tStartOuterLoop = picoEvent->FirstParticleCollection()->begin();
+       tEndOuterLoop   = picoEvent->FirstParticleCollection()->end();
+       AliFemtoPicoEvent* storedEvent;
+       AliFemtoPicoEventIterator picoEventIter;
+       for (picoEventIter=MixingBuffer()->begin();picoEventIter!=MixingBuffer()->end();picoEventIter++){
+         storedEvent = *picoEventIter;
+         if (AnalyzeIdenticalParticles()){
+           tStartInnerLoop = storedEvent->FirstParticleCollection()->begin();
+           tEndInnerLoop = storedEvent->FirstParticleCollection()->end();
+         }
+         else{
+           tStartInnerLoop = storedEvent->SecondParticleCollection()->begin();
+           tEndInnerLoop = storedEvent->SecondParticleCollection()->end();
+         }
+         for (tPartIter1=tStartOuterLoop;tPartIter1!=tEndOuterLoop;tPartIter1++){
+           tThePair->SetTrack1(*tPartIter1);
+           for (tPartIter2=tStartInnerLoop;tPartIter2!=tEndInnerLoop;tPartIter2++){
+             tThePair->SetTrack2(*tPartIter2);
+             // testing...           cout << "tThePair defined... going to pair cut... ";
+             if (fPairCut->Pass(tThePair)){
+               // testing...           cout << " tThePair passed PairCut... ";
+               for (tCorrFctnIter=fCorrFctnCollection->begin();
+                    tCorrFctnIter!=fCorrFctnCollection->end();tCorrFctnIter++){
+                 AliFemtoLikeSignCorrFctn* tCorrFctn = dynamic_cast<AliFemtoLikeSignCorrFctn*>(*tCorrFctnIter);
+                 if (tCorrFctn) { 
+                   tCorrFctn->AddMixedPair(tThePair);
+                   //cout << " tThePair has been added to MixedPair method " << endl;
+                 }
+               }
+             }  // if passed pair cut
+           }    // loop over second particle
+         }      // loop over first particle
+       }        // loop over pico-events stored in Mixing buffer
+       // Now get rid of oldest stored pico-event in buffer.
+       // This means (1) delete the event from memory, (2) "pop" the pointer to it from the MixingBuffer
+       delete MixingBuffer()->back();
+       MixingBuffer()->pop_back();
+      }  // if mixing buffer is full
+      delete tThePair;
+      MixingBuffer()->push_front(picoEvent);  // store the current pico-event in buffer
+    }   // if currentEvent is accepted by currentAnalysis
+    EventEnd(hbtEvent);  // cleanup for EbyE 
+    //    cout << "AliFemtoLikeSignAnalysis::ProcessEvent() - return to caller ... " << endl;
+}
+
+
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoLikeSignAnalysis.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoLikeSignAnalysis.h
new file mode 100644 (file)
index 0000000..b1d5c4b
--- /dev/null
@@ -0,0 +1,53 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// This is an analysis which calculated the background from like sign    //
+// pairs in the same event                                               //
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+#ifndef ALIFEMTOLIKESIGNANALYSIS_H
+#define ALIFEMTOLIKESIGNANALYSIS_H
+//#ifndef StMaker_H
+//#include "StMaker.h"
+//#endif
+
+#include "AliFemtoAnalysis.h"        // base analysis class
+#include "AliFemtoTypes.h"
+//#include "AliFemtoEventCut.h"             // base class 
+//#include "AliFemtoParticleCut.h"          // base class
+//#include "AliFemtoPairCut.h"              // base class
+#include "AliFemtoLikeSignCorrFctn.h"    // base class
+#include "AliFemtoSimpleAnalysis.h"
+#include "AliFemtoCorrFctnCollection.h"
+
+class AliFemtoEventCut;
+class AliFemtoParticleCut;
+class AliFemtoPairCut;
+
+class AliFemtoLikeSignAnalysis : public AliFemtoSimpleAnalysis {
+
+public: 
+
+  AliFemtoLikeSignAnalysis(unsigned int bins=20, double min=-100., double max=100.);
+  AliFemtoLikeSignAnalysis(const AliFemtoLikeSignAnalysis& OriginalAnalysis);  // copy constructor
+  AliFemtoLikeSignAnalysis& operator=(const AliFemtoLikeSignAnalysis& OriginalAnalysis);  
+  virtual ~AliFemtoLikeSignAnalysis();
+
+  virtual void ProcessEvent(const AliFemtoEvent* TheEventToBeProcessed);
+  virtual AliFemtoString Report();
+  virtual unsigned int Overflow() { return fOverFlow;}
+  virtual unsigned int Underflow() { return fUnderFlow;}
+
+protected:
+  double fVertexZ[2];           /* min/max z-vertex position allowed to be processed */
+  unsigned int fVertexBins;     /* number of mixing bins in z-vertex in EventMixing Buffer */
+  unsigned int fOverFlow;       /* number of events encountered which had too large z-vertex */
+  unsigned int fUnderFlow;      /* number of events encountered which had too small z-vertex */
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoLikeSignAnalysis, 0)
+#endif
+
+};
+
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoLikeSignCorrFctn.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoLikeSignCorrFctn.h
new file mode 100644 (file)
index 0000000..1df5396
--- /dev/null
@@ -0,0 +1,35 @@
+////////////////////////////////////////////////////////////////////////////////
+/// AliFemtoLikeSignCorrFctn - the pure virtual base class for the like sign ///
+/// correlation function. All like sign correlation functions  must inherit  ///
+/// from this one                                                            ///
+////////////////////////////////////////////////////////////////////////////////
+#ifndef AliFemtoLikeSignCorrFctn_hh
+#define AliFemtoLikeSignCorrFctn_hh
+
+class AliFemtoPair;
+#include "AliFemtoCorrFctn.h"
+
+class AliFemtoLikeSignCorrFctn : public AliFemtoCorrFctn {
+
+  friend class AliFemtoLikeSignAnalysis;
+
+public:
+  AliFemtoLikeSignCorrFctn():AliFemtoCorrFctn() {/* no-op */};
+  AliFemtoLikeSignCorrFctn(const AliFemtoLikeSignCorrFctn& aCorrFctn);
+  virtual ~AliFemtoLikeSignCorrFctn(){/* no-op */};
+  AliFemtoLikeSignCorrFctn& operator=(const AliFemtoLikeSignCorrFctn& aCorrFctn);
+
+  virtual void AddLikeSignPositivePair(const AliFemtoPair* aPair) = 0;
+  virtual void AddLikeSignNegativePair(const AliFemtoPair* aPair) = 0;
+
+  virtual AliFemtoLikeSignCorrFctn* Clone() { return 0;}
+  virtual TList* GetOutputList() = 0;
+
+  // the following allows "back-pointing" from the CorrFctn to the "parent" Analysis
+};
+//________________________________________
+inline AliFemtoLikeSignCorrFctn::AliFemtoLikeSignCorrFctn(const AliFemtoLikeSignCorrFctn& /* c */):AliFemtoCorrFctn() { fyAnalysis =0; }
+inline AliFemtoLikeSignCorrFctn& AliFemtoLikeSignCorrFctn::operator=(const AliFemtoLikeSignCorrFctn& aCorrFctn) {   if (this != &aCorrFctn) { AliFemtoCorrFctn::operator=(aCorrFctn); } return *this; }
+
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoLorentzVector.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoLorentzVector.h
new file mode 100644 (file)
index 0000000..17d4122
--- /dev/null
@@ -0,0 +1,743 @@
+/***************************************************************************
+ *
+ * $Id$
+ *
+ * Author: Brian Lasiuk, Thomas Ullrich, April 1998
+ ***************************************************************************
+ *
+ * Description:
+ *
+ * Remarks:   Since not all compilers support member templates
+ *            we have to specialize the templated member on these
+ *            platforms. If member templates are not supported the
+ *            ST_NO_MEMBER_TEMPLATES flag has to be set. tu.
+ *
+ *            In the near future when all compilers can handle member
+ *            templates this class should be cleaned up. A lot of
+ *            redundant code can be removed as soon as the compilers
+ *            are up-to-date. tu
+ *
+ ***************************************************************************
+ *
+ * $Log$
+ * Revision 1.1.1.1  2007/04/25 15:38:41  panos
+ * Importing the HBT code dir
+ *
+ * Revision 1.1.1.1  2007/03/07 10:14:49  mchojnacki
+ * First version on CVS
+ *
+ * Revision 1.11  2005/09/22 20:09:20  fisyak
+ * Make AliFemtoLorentzVector persistent
+ *
+ * Revision 1.10  2005/07/06 18:49:56  fisyak
+ * Replace AliFemtoHelixD, AliFemtoLorentzVectorD,AliFemtoLorentzVectorF,AliFemtoMatrixD,AliFemtoMatrixF,AliFemtoPhysicalHelixD,AliFemtoThreeVectorD,AliFemtoThreeVectorF by templated version
+ *
+ * Revision 1.9  2005/03/28 06:02:45  perev
+ * Defence FPE added
+ *
+ * Revision 1.8  2003/09/02 17:59:35  perev
+ * gcc 3.2 updates + WarnOff
+ *
+ * Revision 1.7  2003/05/01 19:24:31  ullrich
+ * Corrected problem in boost().
+ *
+ * Revision 1.6  1999/10/15 15:56:36  ullrich
+ * Changed output format in operator<<, added operator>>
+ *
+ * Revision 1.5  1999/06/04 18:01:36  ullrich
+ * New operators operator() and operator[] which can be used
+ * as lvalues.
+ *
+ * Revision 1.4  1999/04/14 23:12:07  fisyak
+ * Add __CINT__ to handle references
+ *
+ * Revision 1.3  1999/02/17 11:38:36  ullrich
+ * Removed specialization for 'long double'.
+ *
+ * Revision 1.2  1999/02/14 23:11:42  fisyak
+ * Fixes for Rootcint
+ *
+ * Revision 1.1  1999/01/30 03:59:02  fisyak
+ * Root Version of AliFemtoarClassLibrary
+ *
+ * Revision 1.1  1999/01/23 00:27:52  ullrich
+ * Initial Revision
+ *
+ **************************************************************************/
+/*//
+//// General class for a Lorentz four-vector
+///*/
+#ifndef ST_LORENTZ_VECTOR_HH
+#define ST_LORENTZ_VECTOR_HH
+
+#include "AliFemtoThreeVector.h"
+template<class T> class AliFemtoLorentzVector {
+public:
+    AliFemtoLorentzVector(T = 0, T = 0, T = 0, T = 0);
+    virtual ~AliFemtoLorentzVector();
+    
+#ifndef ST_NO_MEMBER_TEMPLATES
+    template<class X> AliFemtoLorentzVector(const AliFemtoThreeVector<X>&, T);
+    template<class X> AliFemtoLorentzVector(T, const AliFemtoThreeVector<X>&);   
+
+    template<class X> AliFemtoLorentzVector(const AliFemtoLorentzVector<X>&);
+    template<class X> AliFemtoLorentzVector<T>& operator=(const AliFemtoLorentzVector<X>&);
+    // AliFemtoLorentzVector(const AliFemtoLorentzVector<T>&);                use default
+    // AliFemtoLorentzVector<T>& operator=(const AliFemtoLorentzVector<T>&);  use default
+#else
+    AliFemtoLorentzVector(const AliFemtoThreeVector<float>&, T);
+    AliFemtoLorentzVector(T, const AliFemtoThreeVector<float>&);   
+    AliFemtoLorentzVector(const AliFemtoLorentzVector<float>&);
+    
+    AliFemtoLorentzVector(const AliFemtoThreeVector<double>&, T);
+    AliFemtoLorentzVector(T, const AliFemtoThreeVector<double>&);   
+    AliFemtoLorentzVector(const AliFemtoLorentzVector<double>&);
+        
+    AliFemtoLorentzVector<T>& operator=(const AliFemtoLorentzVector<float>&);
+    AliFemtoLorentzVector<T>& operator=(const AliFemtoLorentzVector<double>&);
+#endif
+    
+    T x()                     const;
+    T y()                     const;
+    T z()                     const;
+    T t()                     const;
+    T px()                    const;
+    T py()                    const;
+    T pz()                    const;
+    T e()                     const;
+    T operator()  (size_t)    const;
+    T operator[]  (size_t)    const;
+    
+    T& operator()  (size_t);
+    T& operator[]  (size_t);
+
+    const AliFemtoThreeVector<T>& vect() const;    
+    
+    void SetX(T);
+    void SetY(T);
+    void SetZ(T);
+    void SetPx(T);
+    void SetPy(T);
+    void SetPz(T);
+    void SetE(T);
+    void SetT(T);
+    
+#ifndef ST_NO_MEMBER_TEMPLATES
+    template <class X> void SetVect(const AliFemtoThreeVector<X>&);
+#else
+    void SetVect(const AliFemtoThreeVector<float>&);
+    void SetVect(const AliFemtoThreeVector<double>&);
+#endif   
+
+    T Perp()               const;
+    T Perp2()              const;
+    T PseudoRapidity()     const;
+    T Phi()                const;
+    T Theta()              const;
+    T CosTheta()           const;
+    
+    T Plus()               const;
+    T Minus()              const;
+    
+    T m()                  const; 
+    T m2()                 const; 
+    T mt()                 const;
+    T mt2()                const;
+    T Rapidity()           const;
+    
+#ifndef ST_NO_MEMBER_TEMPLATES
+    template<class X> AliFemtoLorentzVector<T> boost(const AliFemtoLorentzVector<X>&) const;
+#else
+    AliFemtoLorentzVector<T> boost(const AliFemtoLorentzVector<float>&) const;
+    AliFemtoLorentzVector<T> boost(const AliFemtoLorentzVector<double>&) const;
+#endif   
+    
+    AliFemtoLorentzVector<T>  operator- ();
+    AliFemtoLorentzVector<T>  operator+ ();
+    AliFemtoLorentzVector<T>& operator*= (double);
+    AliFemtoLorentzVector<T>& operator/= (double);
+
+#ifndef ST_NO_MEMBER_TEMPLATES
+    template<class X> bool operator == (const AliFemtoLorentzVector<X>&) const;
+    template<class X> bool operator != (const AliFemtoLorentzVector<X>&) const;
+    template<class X> AliFemtoLorentzVector<T>& operator+= (const AliFemtoLorentzVector<X>&);
+    template<class X> AliFemtoLorentzVector<T>& operator-= (const AliFemtoLorentzVector<X>&);
+#else    
+    bool operator == (const AliFemtoLorentzVector<float>&) const;
+    bool operator != (const AliFemtoLorentzVector<float>&) const;
+    bool operator == (const AliFemtoLorentzVector<double>&) const;
+    bool operator != (const AliFemtoLorentzVector<double>&) const;
+
+    AliFemtoLorentzVector<T>& operator+= (const AliFemtoLorentzVector<float>&);
+    AliFemtoLorentzVector<T>& operator-= (const AliFemtoLorentzVector<float>&);
+    AliFemtoLorentzVector<T>& operator+= (const AliFemtoLorentzVector<double>&);
+    AliFemtoLorentzVector<T>& operator-= (const AliFemtoLorentzVector<double>&);
+#endif
+
+protected:
+    AliFemtoThreeVector<T> fThreeVector; // The three-vector component
+    T               fX4;                // The fourth component
+#ifdef __ROOT__
+  ClassDef(AliFemtoLorentzVector,3)
+#endif
+};
+#ifndef __CINT__
+//
+//        Implementation of member functions
+//
+template<class T>
+AliFemtoLorentzVector<T>::AliFemtoLorentzVector(T x, T y, T z, T t)
+    : fThreeVector(x, y, z), fX4(t) { /* nop */ }
+
+template<class T>
+AliFemtoLorentzVector<T>::~AliFemtoLorentzVector() { /* nopt */ }    
+
+template<class T>
+const AliFemtoThreeVector<T>& AliFemtoLorentzVector<T>::vect() const 
+{
+    return fThreeVector;
+}
+
+template<class T>
+T AliFemtoLorentzVector<T>::m2() const
+{
+    return (fX4*fX4 - fThreeVector*fThreeVector);    
+}
+
+template<class T>
+T AliFemtoLorentzVector<T>::Plus() const { return (e() + pz()); }
+
+template<class T>
+T AliFemtoLorentzVector<T>::Minus() const { return (e() - pz()); }
+
+template<class T>
+T AliFemtoLorentzVector<T>::m() const
+{
+    T mass2 = m2();
+    if (mass2 < 0)
+       return -::sqrt(-mass2);
+    else
+       return ::sqrt(mass2);
+}
+
+template<class T>
+T AliFemtoLorentzVector<T>::mt2() const
+{
+    return this->Perp2() + m2();
+}
+
+template<class T>
+T AliFemtoLorentzVector<T>::mt() const
+{
+    //
+    // change to more optimal code ?
+    // return e()*e() - pz()*pz();
+    T massPerp2 = mt2();
+    if (massPerp2 < 0)
+       return -::sqrt(-massPerp2);
+    else
+       return ::sqrt(massPerp2);
+}
+
+template<class T>
+void AliFemtoLorentzVector<T>::SetPx(T x) {fThreeVector.SetX(x);}
+
+template<class T>
+void AliFemtoLorentzVector<T>::SetPy(T y) {fThreeVector.SetY(y);}
+
+template<class T>
+void AliFemtoLorentzVector<T>::SetPz(T z) {fThreeVector.SetZ(z);}
+
+template<class T>
+void AliFemtoLorentzVector<T>::SetX(T x) {fThreeVector.SetX(x);}
+
+template<class T>
+void AliFemtoLorentzVector<T>::SetY(T y) {fThreeVector.SetY(y);}
+
+template<class T>
+void AliFemtoLorentzVector<T>::SetZ(T z) {fThreeVector.SetZ(z);}
+
+template<class T>
+void AliFemtoLorentzVector<T>::SetT(T t) {fX4 = t;}
+
+template<class T>
+void AliFemtoLorentzVector<T>::SetE(T e) {fX4 = e;}
+
+template<class T>
+T AliFemtoLorentzVector<T>::x() const {return fThreeVector.x();}
+
+template<class T>
+T AliFemtoLorentzVector<T>::y() const {return fThreeVector.y();}
+
+template<class T>
+T AliFemtoLorentzVector<T>::z() const {return fThreeVector.z();}
+
+template<class T>
+T AliFemtoLorentzVector<T>::px() const {return fThreeVector.x();}
+
+template<class T>
+T AliFemtoLorentzVector<T>::py() const {return fThreeVector.y();}
+
+template<class T>
+T AliFemtoLorentzVector<T>::pz() const {return fThreeVector.z();}
+
+template<class T>
+T AliFemtoLorentzVector<T>::e() const {return fX4;}
+
+template<class T>
+T AliFemtoLorentzVector<T>::t() const {return fX4;}
+
+template<class T>
+T AliFemtoLorentzVector<T>::Perp() const {return fThreeVector.Perp();}
+
+template<class T>
+T AliFemtoLorentzVector<T>::Perp2() const {return fThreeVector.Perp2();}
+
+template<class T>
+T AliFemtoLorentzVector<T>::PseudoRapidity() const {return fThreeVector.PseudoRapidity();}
+
+template<class T>
+T AliFemtoLorentzVector<T>::Phi() const {return fThreeVector.Phi();}
+
+template<class T>
+T AliFemtoLorentzVector<T>::Theta() const {return fThreeVector.Theta();}
+
+template<class T>
+T AliFemtoLorentzVector<T>::CosTheta() const {return fThreeVector.CosTheta();}
+
+template<class T>
+T AliFemtoLorentzVector<T>::operator() (size_t i) const
+{
+    if (i < 3)
+        return fThreeVector(i);
+    else if (i == 3)
+        return fX4;
+    else {
+#ifndef ST_NO_EXCEPTIONS
+      throw out_of_range("AliFemtoLorentzVector<T>::operator(): bad index");  
+#else
+      cerr << "AliFemtoLorentzVector<T>::operator(): bad index." << endl;
+#endif
+      return 0;
+    }
+}
+
+template<class T>
+T& AliFemtoLorentzVector<T>::operator() (size_t i)
+{
+    if (i < 3)
+        return fThreeVector(i);
+    else if (i == 3)
+        return fX4;
+    else {
+#ifndef ST_NO_EXCEPTIONS
+      throw out_of_range("AliFemtoLorentzVector<T>::operator(): bad index");  
+#else
+      cerr << "AliFemtoLorentzVector<T>::operator(): bad index." << endl;
+#endif
+      return fX4;
+    }
+}
+
+template<class T>
+T AliFemtoLorentzVector<T>::operator[] (size_t i) const
+{
+    if (i < 3)
+        return fThreeVector[i];
+    else if (i == 3)
+        return fX4;
+    else {
+#ifndef ST_NO_EXCEPTIONS
+      throw out_of_range("AliFemtoLorentzVector<T>::operator[]: bad index"); 
+#else
+      cerr << "AliFemtoLorentzVector<T>::operator[]: bad index." << endl;
+#endif
+      return 0;
+    }
+}
+
+template<class T>
+T& AliFemtoLorentzVector<T>::operator[] (size_t i)
+{
+    if (i < 3)
+        return fThreeVector[i];
+    else if (i == 3)
+        return fX4;
+    else {
+#ifndef ST_NO_EXCEPTIONS
+      throw out_of_range("AliFemtoLorentzVector<T>::operator[]: bad index"); 
+#else
+      cerr << "AliFemtoLorentzVector<T>::operator[]: bad index." << endl;
+#endif
+      return fX4;
+    }
+}
+
+template<class T>
+T AliFemtoLorentzVector<T>::Rapidity() const
+{
+    return 0.5*::log((fX4+fThreeVector.z())/(fX4-fThreeVector.z())+1e-20);
+}
+
+template<class T>
+AliFemtoLorentzVector<T> AliFemtoLorentzVector<T>::operator- ()
+{
+    return AliFemtoLorentzVector<T>(-fX4,-fThreeVector);
+}
+
+template<class T>
+AliFemtoLorentzVector<T> AliFemtoLorentzVector<T>::operator+ ()
+{
+    return *this;
+}
+
+template<class T>
+AliFemtoLorentzVector<T>& AliFemtoLorentzVector<T>::operator*= (double c)
+{
+    fThreeVector *= c;
+    fX4 *= c;
+    return *this;
+}
+
+template<class T>
+AliFemtoLorentzVector<T>& AliFemtoLorentzVector<T>::operator/= (double c)
+{
+    fThreeVector /= c;
+    fX4 /= c;
+    return *this;
+}
+
+#ifndef ST_NO_MEMBER_TEMPLATES
+#ifndef WIN32
+
+template<class T>
+template<class X>
+AliFemtoLorentzVector<T>::AliFemtoLorentzVector(const AliFemtoThreeVector<X> &vec, T t)
+       : fThreeVector(vec), fX4(t) { /* nop */ }
+
+template<class T>
+template<class X>
+AliFemtoLorentzVector<T>::AliFemtoLorentzVector(T t, const AliFemtoThreeVector<X> &vec)
+       : fThreeVector(vec), fX4(t) { /* nop */ }
+
+template<class T>
+template<class X>
+AliFemtoLorentzVector<T>::AliFemtoLorentzVector(const AliFemtoLorentzVector<X> &vec)
+       : fThreeVector(vec.vect()), fX4(vec.t()) { /* nop */ }
+
+template<class T>
+template<class X>
+AliFemtoLorentzVector<T>
+AliFemtoLorentzVector<T>::boost(const AliFemtoLorentzVector<X>& pframe) const
+{
+    T mass               = abs(pframe);
+    AliFemtoThreeVector<T> eta = (-1./mass)*pframe.vect();            // gamma*beta
+    T gamma              = fabs(pframe.e())/mass;
+    AliFemtoThreeVector<T> pl  = ((this->vect()*eta)/(eta*eta))*eta;  // longitudinal momentum
+    return AliFemtoLorentzVector<T>(gamma*this->e() - this->vect()*eta,
+                              this->vect() + (gamma-1.)*pl - this->e()*eta);
+}
+
+template<class T>
+template<class X>
+void AliFemtoLorentzVector<T>::SetVect(const AliFemtoThreeVector<X>& v)
+{
+    fThreeVector = v;
+}
+
+template<class T>
+template<class X>
+AliFemtoLorentzVector<T>&
+AliFemtoLorentzVector<T>::operator=(const AliFemtoLorentzVector<X>& vec)
+{
+  if(this != &vec) {
+    fThreeVector = vec.vect();
+    fX4 = vec.t();
+  }
+  return *this;
+}
+
+template<class T>
+template<class X>
+bool
+AliFemtoLorentzVector<T>::operator== (const AliFemtoLorentzVector<X>& v) const
+{
+    return (fThreeVector == v.vect()) && (fX4 == v.t());
+}
+
+template<class T>
+template<class X>
+bool
+AliFemtoLorentzVector<T>::operator!= (const AliFemtoLorentzVector<X>& v) const
+{
+    return !(*this == v);
+}
+
+template<class T>
+template<class X>
+AliFemtoLorentzVector<T>&
+AliFemtoLorentzVector<T>::operator+= (const AliFemtoLorentzVector<X>& v)
+{
+    fThreeVector += v.vect();
+    fX4 += v.t();
+    return *this;
+}
+
+template<class T>
+template<class X>
+AliFemtoLorentzVector<T>&
+AliFemtoLorentzVector<T>::operator-= (const AliFemtoLorentzVector<X>& v)
+{
+    fThreeVector -= v.vect();
+    fX4 -= v.t();
+    return *this;
+}
+
+#endif 
+#else
+
+template<class T>
+AliFemtoLorentzVector<T>::AliFemtoLorentzVector(const AliFemtoThreeVector<float> &vec, T t)
+       : fThreeVector(vec), fX4(t) { /* nop */ }
+
+template<class T>
+AliFemtoLorentzVector<T>::AliFemtoLorentzVector(const AliFemtoThreeVector<double> &vec, T t)
+       : fThreeVector(vec), fX4(t) { /* nop */ }
+
+template<class T>
+AliFemtoLorentzVector<T>::AliFemtoLorentzVector(T t, const AliFemtoThreeVector<float> &vec)
+       : fThreeVector(vec), fX4(t) { /* nop */ }
+
+template<class T>
+AliFemtoLorentzVector<T>::AliFemtoLorentzVector(T t, const AliFemtoThreeVector<double> &vec)
+       : fThreeVector(vec), fX4(t) { /* nop */ }
+
+template<class T>
+AliFemtoLorentzVector<T>::AliFemtoLorentzVector(const AliFemtoLorentzVector<float> &vec)
+       : fThreeVector(vec.vect()), fX4(vec.t()) { /* nop */ }
+    
+template<class T>
+AliFemtoLorentzVector<T>::AliFemtoLorentzVector(const AliFemtoLorentzVector<double> &vec)
+       : fThreeVector(vec.vect()), fX4(vec.t()) { /* nop */ }
+    
+template<class T>
+AliFemtoLorentzVector<T>
+AliFemtoLorentzVector<T>::boost(const AliFemtoLorentzVector<float>& pframe) const
+{
+    T mass               = abs(pframe);
+    AliFemtoThreeVector<T> eta = (-1./mass)*pframe.vect();            // gamma*beta
+    T gamma              = fabs(pframe.e())/mass;
+    AliFemtoThreeVector<T> pl  = ((this->vect()*eta)/(eta*eta))*eta;  // longitudinal momentum
+    return AliFemtoLorentzVector<T>(gamma*this->e() - this->vect()*eta,
+                              this->vect() + (gamma-1.)*pl - this->e()*eta);
+}
+
+template<class T>
+AliFemtoLorentzVector<T>
+AliFemtoLorentzVector<T>::boost(const AliFemtoLorentzVector<double>& pframe) const
+{
+    T mass               = abs(pframe);
+    AliFemtoThreeVector<T> eta = (-1./mass)*pframe.vect();            // gamma*beta
+    T gamma              = fabs(pframe.e())/mass;
+    AliFemtoThreeVector<T> pl  = ((this->vect()*eta)/(eta*eta))*eta;  // longitudinal momentum
+    return AliFemtoLorentzVector<T>(gamma*this->e() - this->vect()*eta,
+                              this->vect() + (gamma-1.)*pl - this->e()*eta);
+}
+
+template<class T>
+void AliFemtoLorentzVector<T>::SetVect(const AliFemtoThreeVector<float>& v)
+{
+    fThreeVector = v;
+}
+
+template<class T>
+void AliFemtoLorentzVector<T>::SetVect(const AliFemtoThreeVector<double>& v)
+{
+    fThreeVector = v;
+}
+
+template<class T>
+AliFemtoLorentzVector<T>&
+AliFemtoLorentzVector<T>::operator=(const AliFemtoLorentzVector<float>& vec)
+{
+    fThreeVector = vec.vect();
+    fX4 = vec.t();
+    return *this;
+}
+
+template<class T>
+AliFemtoLorentzVector<T>&
+AliFemtoLorentzVector<T>::operator=(const AliFemtoLorentzVector<double>& vec)
+{
+    fThreeVector = vec.vect();
+    fX4 = vec.t();
+    return *this;
+}
+
+template<class T>
+bool
+AliFemtoLorentzVector<T>::operator== (const AliFemtoLorentzVector<float>& v) const
+{
+    return (this->vect() == v.vect()) && (fX4 == v.t());
+}
+
+template<class T>
+bool
+AliFemtoLorentzVector<T>::operator== (const AliFemtoLorentzVector<double>& v) const
+{
+    return (fThreeVector == v.vect()) && (fX4 == v.t());
+}
+
+template<class T>
+bool
+AliFemtoLorentzVector<T>::operator!= (const AliFemtoLorentzVector<float>& v) const
+{
+    return !(*this == v);
+}
+
+template<class T>
+bool
+AliFemtoLorentzVector<T>::operator!= (const AliFemtoLorentzVector<double>& v) const
+{
+    return !(*this == v);
+}
+
+template<class T>
+AliFemtoLorentzVector<T>&
+AliFemtoLorentzVector<T>::operator+= (const AliFemtoLorentzVector<float>& v)
+{
+    fThreeVector += v.vect();
+    fX4 += v.t();
+    return *this;
+}
+
+template<class T>
+AliFemtoLorentzVector<T>&
+AliFemtoLorentzVector<T>::operator+= (const AliFemtoLorentzVector<double>& v)
+{
+    fThreeVector += v.vect();
+    fX4 += v.t();
+    return *this;
+}
+
+template<class T>
+AliFemtoLorentzVector<T>&
+AliFemtoLorentzVector<T>::operator-= (const AliFemtoLorentzVector<float>& v)
+{
+    fThreeVector -= v.vect();
+    fX4 -= v.t();
+    return *this;
+}
+
+template<class T>
+AliFemtoLorentzVector<T>&
+AliFemtoLorentzVector<T>::operator-= (const AliFemtoLorentzVector<double>& v)
+{
+    fThreeVector -= v.vect();
+    fX4 -= v.t();
+    return *this;
+}
+
+#endif // ST_NO_MEMBER_TEMPLATES
+#endif /* ! __CINT__ */
+#ifdef __CINT__
+template<> AliFemtoLorentzVector<double> operator+ (const AliFemtoLorentzVector<double>& v1, const AliFemtoLorentzVector<double>& v2);
+template<> AliFemtoLorentzVector<double> operator+ (const AliFemtoLorentzVector<double>& v1, const AliFemtoLorentzVector<float>& v2);
+template<> AliFemtoLorentzVector<double> operator+ (const AliFemtoLorentzVector<float>&  v1, const AliFemtoLorentzVector<double>& v2);
+template<> AliFemtoLorentzVector<float>  operator+ (const AliFemtoLorentzVector<float>&  v1, const AliFemtoLorentzVector<float>& v2);
+template<> AliFemtoLorentzVector<double> operator- (const AliFemtoLorentzVector<double>& v1, const AliFemtoLorentzVector<double>& v2);
+template<> AliFemtoLorentzVector<double> operator- (const AliFemtoLorentzVector<double>& v1, const AliFemtoLorentzVector<float>& v2);
+template<> AliFemtoLorentzVector<double> operator- (const AliFemtoLorentzVector<float>&  v1, const AliFemtoLorentzVector<double>& v2);
+template<> AliFemtoLorentzVector<float>  operator- (const AliFemtoLorentzVector<float>&  v1, const AliFemtoLorentzVector<float>& v2);
+template<> AliFemtoLorentzVector<double> operator* (const AliFemtoLorentzVector<double>& v1, const AliFemtoLorentzVector<double>& v2);
+template<> AliFemtoLorentzVector<double> operator* (const AliFemtoLorentzVector<double>& v1, const AliFemtoLorentzVector<float>& v2);
+template<> AliFemtoLorentzVector<double> operator* (const AliFemtoLorentzVector<float>&  v1, const AliFemtoLorentzVector<double>& v2);
+template<> AliFemtoLorentzVector<float>  operator* (const AliFemtoLorentzVector<float>&  v1, const AliFemtoLorentzVector<float>& v2);
+template<> AliFemtoLorentzVector<double> operator* (const              double v1, const AliFemtoLorentzVector<double>& v2);
+template<> AliFemtoLorentzVector<double> operator* (const              double v1, const AliFemtoLorentzVector<float>&  v2);
+template<> AliFemtoLorentzVector<double> operator* (const AliFemtoLorentzVector<double>& v1, const double              v2);
+template<> AliFemtoLorentzVector<double> operator* (const AliFemtoLorentzVector<float>&  v1, const double              v2);
+template<> AliFemtoLorentzVector<double> operator/ (const AliFemtoLorentzVector<double>& v1, const AliFemtoLorentzVector<double>& v2);
+template<> AliFemtoLorentzVector<double> operator/ (const AliFemtoLorentzVector<double>& v1, const AliFemtoLorentzVector<float>& v2);
+template<> AliFemtoLorentzVector<double> operator/ (const AliFemtoLorentzVector<float>&  v1, const AliFemtoLorentzVector<double>& v2);
+template<> AliFemtoLorentzVector<float>  operator/ (const AliFemtoLorentzVector<float>&  v1, const AliFemtoLorentzVector<float>& v2);
+template<> AliFemtoLorentzVector<double> operator/ (const              double v1, const AliFemtoLorentzVector<double>& v2);
+template<> AliFemtoLorentzVector<double> operator/ (const              double v1, const AliFemtoLorentzVector<float>&  v2);
+template<> AliFemtoLorentzVector<double> operator/ (const AliFemtoLorentzVector<double>& v1, const double              v2);
+template<> AliFemtoLorentzVector<double> operator/ (const AliFemtoLorentzVector<float>&  v1, const double              v2);
+template<> istream& operator>> (istream& is, const AliFemtoLorentzVector<double>& v);
+template<> ostream& operator<< (ostream& os, const AliFemtoLorentzVector<double>& v);
+template<> istream& operator>> (istream& is, const AliFemtoLorentzVector<float>& v);
+template<> ostream& operator<< (ostream& os, const AliFemtoLorentzVector<float>& v);
+template<> double abs(const AliFemtoLorentzVector<double>& v);
+template<> float  abs(const AliFemtoLorentzVector<float>& v);
+#else
+//
+//   Non-member operators
+//
+template<class T, class X>
+AliFemtoLorentzVector<T>
+operator+ (const AliFemtoLorentzVector<T>& v1, const AliFemtoLorentzVector<X>& v2)
+{
+    return AliFemtoLorentzVector<T>(v1) += v2;
+}
+
+template<class T, class X>
+AliFemtoLorentzVector<T>
+operator- (const AliFemtoLorentzVector<T>& v1, const AliFemtoLorentzVector<X>& v2)
+{
+    return AliFemtoLorentzVector<T>(v1) -= v2;
+}
+
+template<class T, class X>
+T
+operator* (const AliFemtoLorentzVector<T>& v1, const AliFemtoLorentzVector<X>& v2)
+{
+    return v1.t()*v2.t() - v1.vect()*v2.vect();
+}
+
+template<class T>
+AliFemtoLorentzVector<T>
+operator* (const AliFemtoLorentzVector<T>& v, double c)
+{
+    return AliFemtoLorentzVector<T>(v) *= c;
+}
+
+template<class T>
+AliFemtoLorentzVector<T> operator* (double c, const AliFemtoLorentzVector<T>& v)
+{
+    return AliFemtoLorentzVector<T>(v) *= c;
+}
+
+template<class T, class X>
+AliFemtoLorentzVector<T> operator/ (const AliFemtoLorentzVector<T>& v, X c)
+{
+    return AliFemtoLorentzVector<T>(v) /= c;
+}
+
+template<class T>
+ostream& operator<< (ostream& os, const AliFemtoLorentzVector<T>& v)
+{
+    return os << v.vect() << "\t\t" << v.t();
+}
+
+template<class T>
+istream&  operator>>(istream& is, AliFemtoLorentzVector<T>& v)
+{
+    T  x, y, z, t;
+    is >> x >> y >> z >> t;
+    v.SetX(x);
+    v.SetY(y);
+    v.SetZ(z);
+    v.SetT(t);
+    return is;
+}
+
+//
+//        Non-member functions
+//
+template<class T>
+T abs(const AliFemtoLorentzVector<T>& v) {return v.m();}
+
+#endif /*  __CINT__ */
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoLorentzVectorD.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoLorentzVectorD.h
new file mode 100644 (file)
index 0000000..bbfab85
--- /dev/null
@@ -0,0 +1,22 @@
+/***************************************************************************
+ *
+ * $Id$
+ * $Log$
+ * Revision 1.1.1.1  2007/04/25 15:38:41  panos
+ * Importing the HBT code dir
+ *
+ * Revision 1.1.1.1  2007/03/07 10:14:49  mchojnacki
+ * First version on CVS
+ *
+ * Revision 1.6  2005/07/06 18:49:56  fisyak
+ * Replace AliFemtoHelixD, AliFemtoLorentzVectorD,AliFemtoLorentzVectorF,AliFemtoMatrixD,AliFemtoMatrixF,AliFemtoPhysicalHelixD,AliFemtoThreeVectorD,AliFemtoThreeVectorF by templated version
+ *
+
+****************************************************************************/
+#ifndef ALIFM_LORENTZ_VECTOR_D_HH
+#define ALIFM_LORENTZ_VECTOR_D_HH
+//#include "AliFemtoThreeVectorF.hh"
+#include "AliFmThreeVectorD.h"
+#include "AliFmLorentzVector.h"
+typedef AliFmLorentzVector<double> AliFmLorentzVectorD;
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoMCTrackCut.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoMCTrackCut.cxx
new file mode 100644 (file)
index 0000000..49139eb
--- /dev/null
@@ -0,0 +1,186 @@
+/////////////////////////////////////////////////////////////////////////////////////
+//                                                                                 //
+// AliFemtoMCTrackCut: A basic track cut that used information from                //
+// ALICE MC to accept or reject the track.                                         //  
+// Enables the selection on charge, transverse momentum, rapidity,                 //
+// and PDG of the particle                                                        //
+// Authors: Malgorzata Janik, Warsaw University of Technology, majanik@cern.ch     //
+//          Lukasz Graczykowski, Warsaw University of Technology, lgraczyk@cern.ch //
+//                                                                                //
+/////////////////////////////////////////////////////////////////////////////////////
+
+
+
+#include "AliFemtoMCTrackCut.h"
+#include <cstdio>
+
+#ifdef __ROOT__ 
+ClassImp(AliFemtoMCTrackCut)
+#endif
+
+
+AliFemtoMCTrackCut::AliFemtoMCTrackCut() :
+    fCharge(0),
+    fLabel(0),
+    fPDGcode(211),
+    fNTracksPassed(0),
+    fNTracksFailed(0)
+{
+  // Default constructor
+  fNTracksPassed = fNTracksFailed = 0;
+  fCharge = 0;  // takes both charges 0
+  fPt[0]=0.0;              fPt[1] = 100.0;//100
+  fPDGcode = 0;
+  fRapidity[0]=-2;       fRapidity[1]=2;//-2 2
+  fEta[0]=-2;       fEta[1]=2;//-2 2
+  fLabel=false;
+}
+//------------------------------
+AliFemtoMCTrackCut::~AliFemtoMCTrackCut(){
+  /* noop */
+}
+//------------------------------
+bool AliFemtoMCTrackCut::Pass(const AliFemtoTrack* track)
+{
+
+  if (fLabel)
+    {
+      if(track->Label()<0)
+       {
+         fNTracksFailed++;
+         return false;
+       }    
+    }
+
+   if (fCharge!=0)
+    {               
+    if (fCharge==10)   
+       {
+       if(track->Charge()==0){
+         fNTracksFailed++;
+         return false;
+         }
+       } 
+      else if (track->Charge()!= fCharge)      
+       {
+         fNTracksFailed++;
+         return false;
+       }
+    }
+
+   if (fPDGcode!=0)
+     {
+     
+     if(fPDGcode==11 || fPDGcode==-11 )
+     { if(!fMass) fMass=0.000511;
+        if (track->PidProbElectron()!=1000)
+          {
+            fNTracksFailed++;
+            return false;
+          }
+          }
+       if(fPDGcode==13 || fPDGcode==-13)
+       {
+        if (track->PidProbMuon()!=1000)
+          {if(!fMass) fMass=0.105658;
+            fNTracksFailed++;
+            return false;
+          }
+          }
+       if(fPDGcode==211 || fPDGcode==-211 )
+       {
+        if (track->PidProbPion()!=1000)
+          {if(!fMass) fMass= 0.1395699;
+            fNTracksFailed++;
+            return false;
+          }
+          }
+       if(fPDGcode==2212 || fPDGcode==-2212 )
+       { if(!fMass) fMass=0.938272013;
+        if (track->PidProbProton()!=1000)
+          {
+            fNTracksFailed++;
+            return false;
+          }
+          }
+      if(fPDGcode==321 || fPDGcode==-321 )
+      { if(!fMass) fMass=0.493677;
+        if (track->PidProbKaon()!=1000)
+          {
+            fNTracksFailed++;
+            return false;
+          }
+          }
+     }
+
+  float tEnergy = ::sqrt(track->P().Mag2()+fMass*fMass);
+  //cout<<"MCTrackCut: tEnergy: "<<tEnergy<<endl;
+  //cout<<"MCTrackCut: track->P().z(): "<<track->P().z()<<endl;
+  //cout<<"MCTrackCut: tEnergy-track->P().z(): "<<tEnergy-track->P().z()<<endl;
+  float tRapidity;
+  if(tEnergy-track->P().z() == 0 || (tEnergy+track->P().z())/(tEnergy-track->P().z()) == 0)
+    {
+    fNTracksFailed++;
+    return false;
+    }
+  else
+    tRapidity = 0.5*::log((tEnergy+track->P().z())/(tEnergy-track->P().z()));
+  float tPt = ::sqrt((track->P().x())*(track->P().x())+(track->P().y())*(track->P().y()));
+  float tEta = track->P().PseudoRapidity();
+
+  if ((tRapidity<fRapidity[0])||(tRapidity>fRapidity[1]))
+    {
+      fNTracksFailed++;
+      return false;
+    }
+  if ((tEta<fEta[0])||(tEta>fEta[1]))
+    {
+      fNTracksFailed++;
+      return false;
+    }
+  if ((tPt<fPt[0])||(tPt>fPt[1]))
+    {
+      fNTracksFailed++;
+      return false;
+    }
+
+  fNTracksPassed++ ;
+  return true;
+    
+    
+}
+//------------------------------
+AliFemtoString AliFemtoMCTrackCut::Report()
+{
+  // Prepare report from the execution
+  string tStemp;
+  char tCtemp[100];
+  snprintf(tCtemp,100,"Particle mass:\t%E\n",this->Mass());
+  tStemp=tCtemp;
+  snprintf(tCtemp,100,"Particle charge:\t%d\n",fCharge);
+  tStemp+=tCtemp;
+  snprintf(tCtemp,100,"Particle pT:\t%E - %E\n",fPt[0],fPt[1]);
+  tStemp+=tCtemp;
+  snprintf(tCtemp,100,"Particle rapidity:\t%E - %E\n",fRapidity[0],fRapidity[1]);
+  tStemp+=tCtemp; 
+  snprintf(tCtemp,100,"Particle eta:\t%E - %E\n",fEta[0],fEta[1]);
+  tStemp+=tCtemp;
+  snprintf(tCtemp,100,"Number of tracks which passed:\t%ld  Number which failed:\t%ld\n",fNTracksPassed,fNTracksFailed);
+  tStemp += tCtemp;
+  AliFemtoString returnThis = tStemp;
+  return returnThis;
+}
+TList *AliFemtoMCTrackCut::ListSettings()
+{
+  // return a list of settings in a writable form
+  TList *tListSetttings = new TList();
+  char buf[200];
+  snprintf(buf, 200, "AliFemtoMCTrackCut.mass=%f", this->Mass());
+  tListSetttings->AddLast(new TObjString(buf));
+
+  snprintf(buf, 200, "AliFemtoMCTrackCut.charge=%i", fCharge);
+  tListSetttings->AddLast(new TObjString(buf));
+  return tListSetttings;
+}
+
+                           
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoMCTrackCut.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoMCTrackCut.h
new file mode 100644 (file)
index 0000000..61c54d0
--- /dev/null
@@ -0,0 +1,68 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFemtoMCTrackCut: A basic track cut that used information from     //
+// ALICE MC to accept or reject the track.                              //  
+// Enables the selection on charge, transverse momentum, rapidity,       //
+// and PDG of the particle                                                                                      //
+// Authors: Malgorzata Janik (WUT)    majanik@cern.ch                                  //
+//                     Lukasz Graczykowski (WUT) lgraczyk@cern.ch                                       //
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+
+#ifndef ALIFEMTOMCTRACKCUT_H
+#define ALIFEMTOMCTRACKCUT_H
+
+
+#include "AliFemtoTrackCut.h"
+
+class AliFemtoMCTrackCut : public AliFemtoTrackCut 
+{
+
+ public:
+  AliFemtoMCTrackCut();
+  virtual ~AliFemtoMCTrackCut();
+
+  virtual bool Pass(const AliFemtoTrack* aTrack);
+
+  virtual AliFemtoString Report();
+  virtual TList *ListSettings();
+  virtual AliFemtoParticleType Type(){return hbtTrack;}
+
+  void SetPt(const float& lo, const float& hi);
+  void SetRapidity(const float& lo, const float& hi);
+  void SetEta(const float& lo, const float& hi);
+  void SetCharge(const int& ch);
+  void SetPDG(const int& pdg);
+  void SetLabel(const bool& flag);
+
+
+ private:   // here are the quantities I want to cut on...
+
+  int               fCharge;             // particle charge
+  float             fPt[2];              // bounds for transverse momentum
+  float             fRapidity[2];        // bounds for rapidity
+  float             fEta[2];             // bounds for pseudorapidity
+  bool              fLabel;              // if true label<0 will not pass throught 
+  int               fPDGcode;            // PDG code of the particle
+  long              fNTracksPassed;      // passed tracks count
+  long              fNTracksFailed;      // failed tracks count
+
+
+
+#ifdef __ROOT__ 
+  ClassDef(AliFemtoMCTrackCut, 1)
+#endif
+    };
+
+
+inline void AliFemtoMCTrackCut::SetPt(const float& lo, const float& hi){fPt[0]=lo; fPt[1]=hi;}
+inline void AliFemtoMCTrackCut::SetRapidity(const float& lo,const float& hi){fRapidity[0]=lo; fRapidity[1]=hi;}
+inline void AliFemtoMCTrackCut::SetEta(const float& lo,const float& hi){fEta[0]=lo; fEta[1]=hi;}
+inline void AliFemtoMCTrackCut::SetCharge(const int& ch){fCharge = ch;}
+inline void AliFemtoMCTrackCut::SetPDG(const int& pdg){fPDGcode = pdg;}
+inline void AliFemtoMCTrackCut::SetLabel(const bool& flag){fLabel=flag;}
+
+
+#endif
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoManager.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoManager.cxx
new file mode 100644 (file)
index 0000000..76a86c9
--- /dev/null
@@ -0,0 +1,254 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFemtoManager: main class managing femtoscopic analysis             //
+// The Manager is the top-level object that coordinates activities       //
+// and performs event, particle, and pair loops, and checks the          //
+// various Cuts of the Analyses in its AnalysisCollection                //
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+
+#include "AliFemtoManager.h"
+//#include "AliFemtoParticleCollection.h"
+//#include "AliFemtoTrackCut.h"
+//#include "AliFemtoV0Cut.h"
+#include <cstdio>
+
+#ifdef __ROOT__
+ClassImp(AliFemtoManager)
+#endif
+
+
+
+//____________________________
+AliFemtoManager::AliFemtoManager():
+  fAnalysisCollection(0),
+  fEventReader(0),
+  fEventWriterCollection(0)
+{
+  // default constructor
+  fAnalysisCollection = new AliFemtoAnalysisCollection;
+  fEventWriterCollection = new AliFemtoEventWriterCollection;
+  fEventReader = 0;
+}
+//____________________________
+AliFemtoManager::AliFemtoManager(const AliFemtoManager& aManager) :
+  fAnalysisCollection(0),
+  fEventReader(0),
+  fEventWriterCollection(0)
+{
+  // copy constructor
+  fEventReader = aManager.fEventReader;
+  AliFemtoSimpleAnalysisIterator tAnalysisIter;
+  fAnalysisCollection = new AliFemtoAnalysisCollection;
+  for (tAnalysisIter=aManager.fAnalysisCollection->begin();tAnalysisIter!=aManager.fAnalysisCollection->end();tAnalysisIter++){
+    fAnalysisCollection->push_back(*tAnalysisIter);
+  }
+  AliFemtoEventWriterIterator tEventWriterIter;
+  fEventWriterCollection = new AliFemtoEventWriterCollection;
+  for (tEventWriterIter=aManager.fEventWriterCollection->begin();tEventWriterIter!=aManager.fEventWriterCollection->end();tEventWriterIter++){
+    fEventWriterCollection->push_back(*tEventWriterIter);
+  }
+}
+
+//____________________________
+AliFemtoManager::~AliFemtoManager(){
+  // destructor
+  delete fEventReader;
+  // now delete each Analysis in the Collection, and then the Collection itself
+  AliFemtoSimpleAnalysisIterator tAnalysisIter;
+  for (tAnalysisIter=fAnalysisCollection->begin();tAnalysisIter!=fAnalysisCollection->end();tAnalysisIter++){
+    delete *tAnalysisIter;
+    *tAnalysisIter = 0;
+  }
+  delete fAnalysisCollection;
+  // now delete each EventWriter in the Collection, and then the Collection itself
+  AliFemtoEventWriterIterator tEventWriterIter;
+  for (tEventWriterIter=fEventWriterCollection->begin();tEventWriterIter!=fEventWriterCollection->end();tEventWriterIter++){
+    delete *tEventWriterIter;
+    *tEventWriterIter = 0;
+  }
+  delete fEventWriterCollection;
+}
+//____________________________
+AliFemtoManager& AliFemtoManager::operator=(const AliFemtoManager& aManager)
+{
+  // assignment operator
+  if (this == &aManager)
+    return *this;
+
+  fEventReader = aManager.fEventReader;
+  AliFemtoSimpleAnalysisIterator tAnalysisIter;
+  if (fAnalysisCollection) {
+    for (tAnalysisIter=fAnalysisCollection->begin();tAnalysisIter!=fAnalysisCollection->end();tAnalysisIter++){
+      delete *tAnalysisIter;
+      *tAnalysisIter = 0;
+    }
+    delete fAnalysisCollection;
+  }
+  // now delete each EventWriter in the Collection, and then the Collection itself
+  AliFemtoEventWriterIterator tEventWriterIter;
+  if (fEventWriterCollection) {
+    for (tEventWriterIter=fEventWriterCollection->begin();tEventWriterIter!=fEventWriterCollection->end();tEventWriterIter++){
+      delete *tEventWriterIter;
+      *tEventWriterIter = 0;
+    }
+    delete fEventWriterCollection;
+  }
+
+  fAnalysisCollection = new AliFemtoAnalysisCollection;
+  for (tAnalysisIter=aManager.fAnalysisCollection->begin();tAnalysisIter!=aManager.fAnalysisCollection->end();tAnalysisIter++){
+    fAnalysisCollection->push_back(*tAnalysisIter);
+  }
+
+  fEventWriterCollection = new AliFemtoEventWriterCollection;
+  for (tEventWriterIter=aManager.fEventWriterCollection->begin();tEventWriterIter!=aManager.fEventWriterCollection->end();tEventWriterIter++){
+    fEventWriterCollection->push_back(*tEventWriterIter);
+  }
+  return *this;
+}
+
+//____________________________
+int AliFemtoManager::Init(){
+  // Execute initialization procedures
+  AliFemtoString readerMessage;
+  readerMessage += "*** *** *** *** *** *** *** *** *** *** *** *** \n";
+  // EventReader
+  if (fEventReader) {
+    if (fEventReader->Init("r",readerMessage)){
+      cout << " AliFemtoManager::Init() - Reader initialization failed " << endl;
+      return (1);
+    }
+    readerMessage += fEventReader->Report();
+  }
+  // EventWriters
+  AliFemtoEventWriterIterator tEventWriterIter;
+  for (tEventWriterIter=fEventWriterCollection->begin();tEventWriterIter!=fEventWriterCollection->end();tEventWriterIter++){
+    //cout << "*EventWriterIter " << *EventWriterIter << endl;
+    // The message (AliFemtoString) passed into Init will be at the file header.
+    // for that reason take the readerReport, add my own report and pass as message 
+    AliFemtoString writerMessage = readerMessage;
+    writerMessage += "*** *** *** *** *** *** *** *** *** *** *** *** \n";
+    writerMessage += (*tEventWriterIter)->Report();
+    if (*tEventWriterIter) {
+      if ( (*tEventWriterIter)->Init("w",writerMessage)){ // yes, the message from the reader is passed into the writer
+       cout << " AliFemtoManager::Init() - Writer initialization failed " << endl;
+       return (1);
+      }
+    }
+  }
+  
+  
+  return (0);
+}
+//____________________________
+void AliFemtoManager::Finish(){
+  // Initialize finish procedures
+  // EventReader
+  if (fEventReader) fEventReader->Finish();
+  // EventWriters
+  AliFemtoEventWriterIterator tEventWriterIter;
+  AliFemtoEventWriter* currentEventWriter;
+  for (tEventWriterIter=fEventWriterCollection->begin();tEventWriterIter!=fEventWriterCollection->end();tEventWriterIter++){
+    currentEventWriter = *tEventWriterIter;
+    currentEventWriter->Finish();
+  }
+  // Analyses
+  AliFemtoSimpleAnalysisIterator tAnalysisIter;
+  AliFemtoAnalysis* currentAnalysis;
+  for (tAnalysisIter=fAnalysisCollection->begin();tAnalysisIter!=fAnalysisCollection->end();tAnalysisIter++){
+    currentAnalysis = *tAnalysisIter;
+    currentAnalysis->Finish();
+  }
+}
+//____________________________
+AliFemtoString AliFemtoManager::Report(){
+  // Construct a report from all the classes
+  string stemp;
+  char ctemp[100];
+  // EventReader
+  stemp = fEventReader->Report();
+  // EventWriters
+  snprintf(ctemp , 100, "\nAliFemtoManager Reporting %u EventWriters\n",(unsigned int) fEventWriterCollection->size());
+  stemp += ctemp;
+  AliFemtoEventWriterIterator tEventWriterIter;
+  AliFemtoEventWriter* currentEventWriter;
+  for (tEventWriterIter=fEventWriterCollection->begin();tEventWriterIter!=fEventWriterCollection->end();tEventWriterIter++){
+    //    cout << "AliFemtoManager - asking for EventWriter Report" << endl;
+    currentEventWriter = *tEventWriterIter;
+    stemp+=currentEventWriter->Report();
+  }
+  // Analyses
+  snprintf(ctemp , 100, "\nAliFemtoManager Reporting %u Analyses\n",(unsigned int) fAnalysisCollection->size());
+  stemp += ctemp;
+  AliFemtoSimpleAnalysisIterator tAnalysisIter;
+  AliFemtoAnalysis* currentAnalysis;
+  for (tAnalysisIter=fAnalysisCollection->begin();tAnalysisIter!=fAnalysisCollection->end();tAnalysisIter++){
+    //    cout << "AliFemtoManager - asking for Analysis Report" << endl;
+    currentAnalysis = *tAnalysisIter;
+    stemp+=currentAnalysis->Report();
+  }
+
+  AliFemtoString returnThis = stemp;
+  return returnThis;
+}
+//____________________________
+AliFemtoAnalysis* AliFemtoManager::Analysis( int n ){  // return pointer to n-th analysis
+  // return analysis number n
+  if ( n<0 || n > (int) fAnalysisCollection->size() )
+    return NULL;
+  AliFemtoSimpleAnalysisIterator iter = fAnalysisCollection->begin();
+  for (int i=0; i<n ;i++){
+    iter++;
+  }
+  return *iter;
+}
+//____________________________
+AliFemtoEventWriter* AliFemtoManager::EventWriter( int n ){  // return pointer to n-th analysis
+  // return event writern number n
+  if ( n<0 || n > (int) fEventWriterCollection->size() )
+    return NULL;
+  AliFemtoEventWriterIterator iter = fEventWriterCollection->begin();
+  for (int i=0; i<n ;i++){
+    iter++;
+  }
+  return *iter;
+}
+ //____________________________
+int AliFemtoManager::ProcessEvent(){
+  // process a single event by reading it and passing it to each
+  // analysis and event writer
+  //  cout << "AliFemtoManager::ProcessEvent" << endl;
+  // NOTE - this ReturnHbtEvent makes a *new* AliFemtoEvent - delete it when done!
+  AliFemtoEvent* currentHbtEvent = fEventReader->ReturnHbtEvent();
+  //  cout << "Event reader has returned control to manager" << endl;
+  
+  // if no HbtEvent is returned, then we abort processing.
+  // the question is now: do we try again next time (i.e. there may be an HbtEvent next time)
+  // or are we at EOF or something?  If Reader says Status=0, then that means try again later.
+  // so, we just return the Reader's Status.
+  if (!currentHbtEvent){
+    cout << "AliFemtoManager::ProcessEvent() - Reader::ReturnHbtEvent() has returned null pointer\n";
+    return fEventReader->Status();
+  }
+  
+  // loop over all the EventWriters
+  AliFemtoEventWriterIterator tEventWriterIter;
+  for (tEventWriterIter=fEventWriterCollection->begin();tEventWriterIter!=fEventWriterCollection->end();tEventWriterIter++){
+#ifdef STHBRDEBUG
+    cout << " *tEventWriterIter " <<  *tEventWriterIter << endl;
+#endif
+    (*tEventWriterIter)->WriteHbtEvent(currentHbtEvent);
+  } 
+
+  // loop over all the Analysis
+  AliFemtoSimpleAnalysisIterator tAnalysisIter;
+  for (tAnalysisIter=fAnalysisCollection->begin();tAnalysisIter!=fAnalysisCollection->end();tAnalysisIter++){
+    (*tAnalysisIter)->ProcessEvent(currentHbtEvent);
+  } 
+
+  if (currentHbtEvent) delete currentHbtEvent;
+#ifdef STHBRDEBUG
+  cout << "AliFemtoManager::ProcessEvent() - return to caller ... " << endl;
+#endif
+  return 0;    // 0 = "good return"
+}       // ProcessEvent
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoManager.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoManager.h
new file mode 100644 (file)
index 0000000..df4edcc
--- /dev/null
@@ -0,0 +1,71 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFemtoManager: main class managing femtoscopic analysis             //
+// The Manager is the top-level object that coordinates activities       //
+// and performs event, particle, and pair loops, and checks the          //
+// various Cuts of the Analyses in its AnalysisCollection                //
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+
+#ifndef ALIFEMTOMANAGER_H
+#define ALIFEMTOMANAGER_H
+
+
+#include "AliFemtoTypes.h"
+#include "AliFemtoAnalysisCollection.h"
+#include "AliFemtoEventWriterCollection.h"
+#include "AliFemtoEvent.h"
+#include "AliFemtoAnalysis.h"
+#include "AliFemtoEventReader.h"
+#include "AliFemtoEventWriter.h"
+
+class AliFemtoManager{
+
+private:
+  AliFemtoAnalysisCollection* fAnalysisCollection;       // Collection of analyzes
+  AliFemtoEventReader*        fEventReader;              // Event reader
+  AliFemtoEventWriterCollection* fEventWriterCollection; // Event writer collection
+
+public:
+  AliFemtoManager();
+  AliFemtoManager(const AliFemtoManager& aManager);
+  virtual ~AliFemtoManager();
+
+  AliFemtoManager& operator=(const AliFemtoManager& aManager);
+
+  // Gets and Sets...
+  AliFemtoAnalysisCollection* AnalysisCollection();
+  AliFemtoAnalysis* Analysis(int n);  // Access to Analysis within Collection
+  void AddAnalysis(AliFemtoAnalysis* a);
+
+  AliFemtoEventWriterCollection* EventWriterCollection();
+  AliFemtoEventWriter* EventWriter(int n);// Access to EventWriter within Collection
+  void SetEventWriter(AliFemtoEventWriter* w);  // just for historic reasons
+  void AddEventWriter(AliFemtoEventWriter* w);
+
+  AliFemtoEventReader* EventReader();
+  void SetEventReader(AliFemtoEventReader* r);
+
+  int Init();
+  int ProcessEvent();   // a "0" return value means success - otherwise quit
+  void Finish();
+
+  AliFemtoString Report(); //!
+#ifdef __ROOT__
+  ClassDef(AliFemtoManager, 0)
+#endif
+};
+
+inline AliFemtoAnalysisCollection* AliFemtoManager::AnalysisCollection(){return fAnalysisCollection;}
+inline void AliFemtoManager::AddAnalysis(AliFemtoAnalysis* anal){fAnalysisCollection->push_back(anal);}
+
+inline AliFemtoEventWriterCollection* AliFemtoManager::EventWriterCollection(){return fEventWriterCollection;}
+inline void AliFemtoManager::AddEventWriter(AliFemtoEventWriter* writer){fEventWriterCollection->push_back(writer);}
+inline void AliFemtoManager::SetEventWriter(AliFemtoEventWriter* writer){fEventWriterCollection->push_back(writer);}
+
+inline AliFemtoEventReader* AliFemtoManager::EventReader(){return fEventReader;}
+inline void AliFemtoManager::SetEventReader(AliFemtoEventReader* reader){fEventReader = reader;}
+
+
+#endif
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelCorrFctn.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelCorrFctn.cxx
new file mode 100644 (file)
index 0000000..2d3b4aa
--- /dev/null
@@ -0,0 +1,174 @@
+////////////////////////////////////////////////////////////////////////////////
+///                                                                          ///
+/// AliFemtoModelCorrFctn - the base class for correlation function which    ///
+/// uses the model framework and weight generation                           ///
+///                                                                          ///
+////////////////////////////////////////////////////////////////////////////////
+#ifdef __ROOT__
+  ClassImp(AliFemtoModelCorrFctn, 1)
+#endif
+
+#include "AliFemtoModelGausLCMSFreezeOutGenerator.h"
+#include "AliFemtoModelHiddenInfo.h"
+#include "AliFemtoModelCorrFctn.h"
+#include "AliFemtoPair.h"
+#include "AliFemtoModelManager.h"
+#include <TH1D.h>
+    
+//_______________________
+AliFemtoModelCorrFctn::AliFemtoModelCorrFctn(): 
+  AliFemtoCorrFctn(),
+  fManager(0),
+  fNumeratorTrue(0),
+  fNumeratorFake(0),
+  fDenominator(0)
+{
+  // Default constructor
+  fNumeratorTrue = new TH1D("ModelNumTrue","ModelNumTrue",50,0.0,0.5);
+  fNumeratorFake = new TH1D("ModelNumFake","ModelNumFake",50,0.0,0.5);
+  fDenominator = new TH1D("ModelDen","ModelDen",50,0.0,0.5);
+
+  fNumeratorTrue->Sumw2();
+  fNumeratorFake->Sumw2();
+  fDenominator->Sumw2();
+}
+//_______________________
+AliFemtoModelCorrFctn::AliFemtoModelCorrFctn(const char *title, Int_t aNbins, Double_t aQinvLo, Double_t aQinvHi):
+  AliFemtoCorrFctn(),
+  fManager(0),
+  fNumeratorTrue(0),
+  fNumeratorFake(0),
+  fDenominator(0)
+{
+  // Normal constructor
+  char buf[100];
+  snprintf(buf , 100,  "NumTrue%s", title);
+  fNumeratorTrue = new TH1D(buf,buf,aNbins,aQinvLo,aQinvHi);
+  snprintf(buf , 100,  "NumFake%s", title);
+  fNumeratorFake = new TH1D(buf,buf,aNbins,aQinvLo,aQinvHi);
+  snprintf(buf , 100,  "Den%s", title);
+  fDenominator = new TH1D(buf,buf,aNbins,aQinvLo,aQinvHi);
+
+  fNumeratorTrue->Sumw2();
+  fNumeratorFake->Sumw2();
+  fDenominator->Sumw2();
+}
+//_______________________
+AliFemtoModelCorrFctn::AliFemtoModelCorrFctn(const AliFemtoModelCorrFctn& aCorrFctn) :
+  AliFemtoCorrFctn(),
+  fManager(0),
+  fNumeratorTrue(0),
+  fNumeratorFake(0),
+  fDenominator(0)
+{
+  // Copy constructor
+  if (aCorrFctn.fNumeratorTrue)
+    fNumeratorTrue = new TH1D(*(aCorrFctn.fNumeratorTrue));
+  if (aCorrFctn.fNumeratorFake)
+    fNumeratorFake = new TH1D(*(aCorrFctn.fNumeratorFake));
+  if (aCorrFctn.fDenominator)
+    fDenominator = new TH1D(*(aCorrFctn.fDenominator));
+  fManager = aCorrFctn.fManager;
+}
+//_______________________
+AliFemtoModelCorrFctn::~AliFemtoModelCorrFctn()
+{
+  // Destructor
+  if (fNumeratorTrue) delete fNumeratorTrue;
+  if (fNumeratorFake) delete fNumeratorFake;
+  if (fDenominator) delete fDenominator;
+}
+//_______________________
+AliFemtoModelCorrFctn& AliFemtoModelCorrFctn::operator=(const AliFemtoModelCorrFctn& aCorrFctn)
+{
+  // Assignment operator
+  if (this == &aCorrFctn)
+    return *this;
+  
+  if (aCorrFctn.fNumeratorTrue)
+    fNumeratorTrue = new TH1D(*(aCorrFctn.fNumeratorTrue));
+  else
+    fNumeratorTrue = 0;
+  if (aCorrFctn.fNumeratorFake)
+    fNumeratorFake = new TH1D(*(aCorrFctn.fNumeratorFake));
+  else
+    fNumeratorFake = 0;
+  if (aCorrFctn.fDenominator)
+    fDenominator = new TH1D(*(aCorrFctn.fDenominator));
+  else
+    fDenominator = 0;
+  fManager = aCorrFctn.fManager;
+
+  return *this;
+}
+//_______________________
+void AliFemtoModelCorrFctn::ConnectToManager(AliFemtoModelManager *aManager)
+{
+  fManager = aManager;
+}
+
+//_______________________
+AliFemtoString AliFemtoModelCorrFctn::Report()
+{
+  // Prepare report
+  AliFemtoString tStr = "AliFemtoModelCorrFctn report";
+
+  return tStr;
+}
+
+//_______________________
+void AliFemtoModelCorrFctn::AddRealPair(AliFemtoPair* aPair)
+{
+  Double_t weight = fManager->GetWeight(aPair);
+  fNumeratorTrue->Fill(aPair->QInv(), weight);
+}
+//_______________________
+void AliFemtoModelCorrFctn::AddMixedPair(AliFemtoPair* aPair)
+{
+  Double_t weight = fManager->GetWeight(aPair);
+  fNumeratorFake->Fill(aPair->QInv(), weight);
+  fDenominator->Fill(aPair->QInv(), 1.0);
+}
+//_______________________
+void AliFemtoModelCorrFctn::EventBegin(const AliFemtoEvent* /* aEvent */)
+{
+  /* Do nothing */
+}
+//_______________________
+void AliFemtoModelCorrFctn::EventEnd(const AliFemtoEvent* /* aEvent */)
+{
+  /* Do nothing */
+}
+//_______________________
+void AliFemtoModelCorrFctn::Finish()
+{
+  /* Do nothing */
+}
+//_______________________
+void AliFemtoModelCorrFctn::Write()
+{
+  // Write out data histos
+  fNumeratorTrue->Write();
+  fNumeratorFake->Write();
+  fDenominator->Write();
+}
+//_______________________
+AliFemtoModelCorrFctn* AliFemtoModelCorrFctn::Clone()
+{
+  // Create clone
+  AliFemtoModelCorrFctn *tCopy = new AliFemtoModelCorrFctn(*this);
+  
+  return tCopy;
+}
+//_________________________
+TList* AliFemtoModelCorrFctn::GetOutputList()
+{
+  // Prepare the list of objects to be written to the output
+  TList *tOutputList = new TList();
+
+  tOutputList->Add(fNumeratorTrue); 
+  tOutputList->Add(fNumeratorFake); 
+  tOutputList->Add(fDenominator); 
+
+  return tOutputList;
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelCorrFctn.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelCorrFctn.h
new file mode 100644 (file)
index 0000000..0e0aa79
--- /dev/null
@@ -0,0 +1,55 @@
+////////////////////////////////////////////////////////////////////////////////
+///                                                                          ///
+/// AliFemtoModelCorrFctn - the base class for correlation function which    ///
+/// uses the model framework and weight generation                           ///
+///                                                                          ///
+////////////////////////////////////////////////////////////////////////////////
+#ifndef ALIFEMTOMODELCORRFCTN_H
+#define ALIFEMTOMODELCORRFCTN_H
+
+#include "AliFemtoCorrFctn.h"
+class AliFemtoPair;
+class AliFemtoModelManager;
+class TH1D;
+
+class AliFemtoModelCorrFctn: public AliFemtoCorrFctn {
+
+public:
+  AliFemtoModelCorrFctn();
+  AliFemtoModelCorrFctn(const char *title, Int_t aNbins, Double_t aQinvLo, Double_t aQinvHi);
+  AliFemtoModelCorrFctn(const AliFemtoModelCorrFctn& aCorrFctn);
+  virtual ~AliFemtoModelCorrFctn();
+
+  AliFemtoModelCorrFctn& operator=(const AliFemtoModelCorrFctn& aCorrFctn);
+
+  virtual void ConnectToManager(AliFemtoModelManager *aManager);
+
+  virtual AliFemtoString Report();
+
+  virtual void AddRealPair(AliFemtoPair* aPair);
+  virtual void AddMixedPair(AliFemtoPair* aPir);
+
+  virtual void EventBegin(const AliFemtoEvent* aEvent);
+  virtual void EventEnd(const AliFemtoEvent* aEvent);
+  virtual void Finish();
+
+  virtual TList* GetOutputList();
+  virtual void Write();
+
+  virtual AliFemtoModelCorrFctn* Clone();
+
+protected:
+  AliFemtoModelManager *fManager; // Link back to the manager to get the weights
+  
+  TH1D *fNumeratorTrue; // Numerator made with pairs from the same event
+  TH1D *fNumeratorFake; // Numerator made with pairs from different events (mixed pairs)
+  TH1D *fDenominator;   // Denominator made with mixed pairs
+
+private:
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoModelCorrFctn, 1)
+#endif
+};
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelFreezeOutGenerator.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelFreezeOutGenerator.cxx
new file mode 100644 (file)
index 0000000..063fa6d
--- /dev/null
@@ -0,0 +1,44 @@
+////////////////////////////////////////////////////////////////////////////////
+///                                                                          ///
+/// AliFemtoModelFreezeOutGenerator - abstract base class for freeze-out     ///
+/// coordinates generator                                                    ///
+/// Authors: Adam Kisiel kisiel@mps.ohio-state.edu                           ///
+///                                                                          ///
+////////////////////////////////////////////////////////////////////////////////
+#ifdef __ROOT__
+  ClassImp(AliFemtoModelFreezeOutGenerator, 1)
+#endif
+
+#include "AliFemtoModelFreezeOutGenerator.h"
+
+//____________________________
+AliFemtoModelFreezeOutGenerator::AliFemtoModelFreezeOutGenerator(): 
+  fRandom(0) 
+{ /* no-op */ }
+//____________________________
+AliFemtoModelFreezeOutGenerator::AliFemtoModelFreezeOutGenerator(const AliFemtoModelFreezeOutGenerator &/* aModel */): 
+  fRandom(0)
+{/* no-op */}
+//____________________________
+AliFemtoModelFreezeOutGenerator::~AliFemtoModelFreezeOutGenerator()
+{
+  if (fRandom) delete fRandom;
+}
+//____________________________
+AliFemtoModelFreezeOutGenerator& AliFemtoModelFreezeOutGenerator::operator=(const AliFemtoModelFreezeOutGenerator& aGen) 
+{ 
+  if (this == &aGen) return *this; 
+  if (aGen.fRandom) 
+    fRandom = new TRandom2(*aGen.fRandom);
+  else 
+    fRandom=0; 
+  return *this; 
+}
+//____________________________
+AliFemtoModelFreezeOutGenerator* AliFemtoModelFreezeOutGenerator::Clone() const 
+{ 
+  return 0; 
+}
+
+
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelFreezeOutGenerator.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelFreezeOutGenerator.h
new file mode 100644 (file)
index 0000000..ac8229d
--- /dev/null
@@ -0,0 +1,40 @@
+////////////////////////////////////////////////////////////////////////////////
+///                                                                          ///
+/// AliFemtoModelFreezeOutGenerator - abstract base class for freeze-out     ///
+/// coordinates generator                                                    ///
+/// Authors: Adam Kisiel kisiel@mps.ohio-state.edu                           ///
+///                                                                          ///
+////////////////////////////////////////////////////////////////////////////////
+#ifndef AliFemtoModelFreezeOutGenerator_hh
+#define AliFemtoModelFreezeOutGenerator_hh
+
+#include "TRandom2.h"
+#include "AliFemtoPair.h"
+
+class AliFemtoModelFreezeOutGenerator 
+{
+ public:
+  AliFemtoModelFreezeOutGenerator();
+  AliFemtoModelFreezeOutGenerator(const AliFemtoModelFreezeOutGenerator &aModel);
+  
+  AliFemtoModelFreezeOutGenerator& operator=(const AliFemtoModelFreezeOutGenerator& aGen);
+  
+  virtual ~AliFemtoModelFreezeOutGenerator();
+  virtual void GenerateFreezeOut(AliFemtoPair *aPair) = 0;
+  
+  virtual AliFemtoModelFreezeOutGenerator* Clone() const;
+  
+ protected:
+  TRandom2 *fRandom;
+  
+ private:
+  
+#ifdef __ROOT__
+  ClassDef(AliFemtoModelFreezeOutGenerator, 1)
+#endif
+    
+};
+
+#endif
+
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelGausLCMSFreezeOutGenerator.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelGausLCMSFreezeOutGenerator.cxx
new file mode 100644 (file)
index 0000000..2472a79
--- /dev/null
@@ -0,0 +1,145 @@
+////////////////////////////////////////////////////////////////////////////////
+///                                                                          ///
+/// AliFemtoModelGausLCMSFreezeOutGenerator - freeze-out                     ///
+/// coordinates generator, generating a 3D gaussian ellipsoid in LCMS        ///
+/// Authors: Adam Kisiel kisiel@mps.ohio-state.edu                           ///
+///                                                                          ///
+////////////////////////////////////////////////////////////////////////////////
+#ifdef __ROOT__
+  ClassImp(AliFemtoModelGausLCMSFreezeOutGenerator, 1)
+#endif
+
+#include "math.h"
+#include "AliFemtoModelGausLCMSFreezeOutGenerator.h"
+#include "AliFemtoModelHiddenInfo.h"
+#include "AliFemtoLorentzVector.h"
+#include <TMath.h>
+
+//_______________________
+AliFemtoModelGausLCMSFreezeOutGenerator::AliFemtoModelGausLCMSFreezeOutGenerator() :
+  fSizeOut(0), fSizeSide(0), fSizeLong(0)
+{
+  // Default constructor
+  fRandom = new TRandom2();
+}
+
+//_______________________
+AliFemtoModelGausLCMSFreezeOutGenerator::AliFemtoModelGausLCMSFreezeOutGenerator(const AliFemtoModelGausLCMSFreezeOutGenerator &aModel):
+  AliFemtoModelFreezeOutGenerator(aModel),
+  fSizeOut(0), fSizeSide(0), fSizeLong(0)
+{
+  // Copy constructor
+  fRandom = new TRandom2();
+  SetSizeOut(aModel.GetSizeOut());
+  SetSizeSide(aModel.GetSizeSide());
+  SetSizeLong(aModel.GetSizeLong());
+}
+//_______________________
+AliFemtoModelGausLCMSFreezeOutGenerator::~AliFemtoModelGausLCMSFreezeOutGenerator()
+{
+  if (fRandom) delete fRandom;
+}
+//_______________________
+AliFemtoModelGausLCMSFreezeOutGenerator& AliFemtoModelGausLCMSFreezeOutGenerator::operator=(const AliFemtoModelGausLCMSFreezeOutGenerator &aModel)
+{
+  if (this != &aModel) {
+    fRandom = new TRandom2();
+    SetSizeOut(aModel.GetSizeOut());
+    SetSizeSide(aModel.GetSizeSide());
+    SetSizeLong(aModel.GetSizeLong());
+  }
+
+  return *this;
+}
+//_______________________
+void AliFemtoModelGausLCMSFreezeOutGenerator::GenerateFreezeOut(AliFemtoPair *aPair)
+{
+  // Generate two particle emission points with respect
+  // to their pair momentum 
+  // The source is the 3D Gaussian ellipsoid in the LCMS frame
+  AliFemtoModelHiddenInfo *inf1 = (AliFemtoModelHiddenInfo *) aPair->Track1()->HiddenInfo();
+  AliFemtoModelHiddenInfo *inf2 = (AliFemtoModelHiddenInfo *) aPair->Track2()->HiddenInfo();
+
+  if ((!inf1) || (!inf2)) { cout << "Hidden info not created! "  << endl; exit(kFALSE); }
+
+  Double_t tPx = inf1->GetTrueMomentum()->x() + inf2->GetTrueMomentum()->x();
+  Double_t tPy = inf1->GetTrueMomentum()->y() + inf2->GetTrueMomentum()->y();
+  Double_t tPz = inf1->GetTrueMomentum()->z() + inf2->GetTrueMomentum()->z();
+  Double_t tM1 = inf1->GetMass();
+  Double_t tM2 = inf2->GetMass();
+  Double_t tE1 = sqrt(tM1*tM1 + inf1->GetTrueMomentum()->Mag2());
+  Double_t tE2 = sqrt(tM2*tM2 + inf2->GetTrueMomentum()->Mag2());
+  Double_t tEs = tE1 + tE2;
+
+  Double_t tPt = sqrt(tPx*tPx + tPy*tPy);
+
+  Double_t tRout = fRandom->Gaus(0.0, fSizeOut);
+  Double_t tRside = fRandom->Gaus(0.0, fSizeSide);
+  Double_t tRlong = fRandom->Gaus(0.0, fSizeLong);
+  
+  Double_t tXout = (tPx * tRout + tPy * tRside)/tPt;
+  Double_t tXside = (tPy * tRout - tPx * tRside)/tPt;
+
+  Double_t tBetaz = tPz/tEs;
+  Double_t tGammaz = 1.0/TMath::Sqrt(1-tBetaz*tBetaz);
+  
+  Double_t tXlong = tGammaz * (tRlong + tBetaz * 0);
+  Double_t tXtime = tGammaz * (0 + tBetaz * tRlong);
+  
+  if (!(inf1->GetEmissionPoint())) {
+    AliFemtoLorentzVector *tPos = new AliFemtoLorentzVector(0,0,0,0);
+    inf1->SetEmissionPoint(tPos);
+    delete tPos;
+  }
+  else
+    inf1->SetEmissionPoint(0,0,0,0);
+  if (!(inf2->GetEmissionPoint())) {
+    AliFemtoLorentzVector *tPos = new AliFemtoLorentzVector(tXout,tXside,tXlong,tXtime);
+    inf2->SetEmissionPoint(tPos);
+    delete tPos;
+  }
+  else
+    inf2->SetEmissionPoint(tXout, tXside, tXlong, tXtime);
+}
+
+//_______________________
+void AliFemtoModelGausLCMSFreezeOutGenerator::SetSizeOut(Double_t aSizeOut)
+{
+  fSizeOut = aSizeOut;
+}
+//_______________________
+void AliFemtoModelGausLCMSFreezeOutGenerator::SetSizeSide(Double_t aSizeSide)
+{
+  fSizeSide = aSizeSide;
+}
+//_______________________
+void AliFemtoModelGausLCMSFreezeOutGenerator::SetSizeLong(Double_t aSizeLong)
+{
+  fSizeLong = aSizeLong;
+}
+
+//_______________________
+Double_t AliFemtoModelGausLCMSFreezeOutGenerator::GetSizeOut() const
+{
+  return fSizeOut;
+}
+//_______________________
+Double_t AliFemtoModelGausLCMSFreezeOutGenerator::GetSizeSide() const
+{
+  return fSizeSide;
+}
+//_______________________
+Double_t AliFemtoModelGausLCMSFreezeOutGenerator::GetSizeLong() const
+{
+  return fSizeLong;
+}
+//_______________________
+AliFemtoModelFreezeOutGenerator* AliFemtoModelGausLCMSFreezeOutGenerator::Clone() const
+{ 
+  return GetGenerator(); 
+}
+//_______________________
+AliFemtoModelFreezeOutGenerator* AliFemtoModelGausLCMSFreezeOutGenerator::GetGenerator() const 
+{ 
+  AliFemtoModelFreezeOutGenerator* tModel = new AliFemtoModelGausLCMSFreezeOutGenerator(*this); return tModel; 
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelGausLCMSFreezeOutGenerator.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelGausLCMSFreezeOutGenerator.h
new file mode 100644 (file)
index 0000000..d86c0ae
--- /dev/null
@@ -0,0 +1,50 @@
+////////////////////////////////////////////////////////////////////////////////
+///                                                                          ///
+/// AliFemtoModelGausLCMSFreezeOutGenerator - freeze-out                     ///
+/// coordinates generator, generating a 3D gaussian ellipsoid in LCMS        ///
+/// Authors: Adam Kisiel kisiel@mps.ohio-state.edu                           ///
+///                                                                          ///
+////////////////////////////////////////////////////////////////////////////////
+#ifndef ALIFEMTOMODELGAUSLCMSFREEZEOUTGENERATOR_H
+#define ALIFEMTOMODELGAUSLCMSFREEZEOUTGENERATOR_H
+
+#include "AliFemtoModelFreezeOutGenerator.h"
+
+#include "TRandom.h"
+
+class AliFemtoModelGausLCMSFreezeOutGenerator : public AliFemtoModelFreezeOutGenerator
+{
+ public:
+  AliFemtoModelGausLCMSFreezeOutGenerator();
+  AliFemtoModelGausLCMSFreezeOutGenerator(const AliFemtoModelGausLCMSFreezeOutGenerator &aModel);
+  virtual ~AliFemtoModelGausLCMSFreezeOutGenerator();
+  AliFemtoModelGausLCMSFreezeOutGenerator& operator=(const AliFemtoModelGausLCMSFreezeOutGenerator &aModel);
+  virtual void GenerateFreezeOut(AliFemtoPair *aPair);
+
+  void SetSizeOut(Double_t aSizeOut);
+  void SetSizeSide(Double_t aSizeSide);
+  void SetSizeLong(Double_t aSizeLong);
+  
+  Double_t GetSizeOut() const;
+  Double_t GetSizeSide() const;
+  Double_t GetSizeLong() const;
+
+  virtual AliFemtoModelFreezeOutGenerator* Clone() const;
+
+ protected:
+  Double_t fSizeOut;  // Size of the source in the out direction
+  Double_t fSizeSide; // Size of the source in the side direction
+  Double_t fSizeLong; // Size of the source in the long direction
+
+ private:
+  AliFemtoModelFreezeOutGenerator* GetGenerator() const;
+               
+#ifdef __ROOT__
+  ClassDef(AliFemtoModelGausLCMSFreezeOutGenerator, 1)
+#endif
+
+    };
+  
+#endif
+
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelGlobalHiddenInfo.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelGlobalHiddenInfo.cxx
new file mode 100644 (file)
index 0000000..8934971
--- /dev/null
@@ -0,0 +1,96 @@
+////////////////////////////////////////////////////////////////////////////////
+///                                                                          ///
+/// AliFemtoModelGlobalHiddenInfo - the hidden info for model calculations    //
+/// Stores information needed for the weight generation - the true           ///
+/// simulated momenta, freeze-out coordinates from model and particle PID    ///
+///                                                                          ///
+////////////////////////////////////////////////////////////////////////////////
+#include "AliFemtoModelGlobalHiddenInfo.h"
+
+//_____________________________________________
+AliFemtoModelGlobalHiddenInfo::AliFemtoModelGlobalHiddenInfo() :
+  AliFemtoModelHiddenInfo(),
+  fGlobalEmissionPoint(0)
+{
+  // Default constructor
+}
+//_____________________________________________
+AliFemtoModelGlobalHiddenInfo::AliFemtoModelGlobalHiddenInfo(const AliFemtoModelGlobalHiddenInfo &aInfo) :
+  AliFemtoModelHiddenInfo(aInfo),
+  fGlobalEmissionPoint(0)
+{
+  // Copy constructor
+  if (aInfo.GetGlobalEmissionPoint())
+    SetGlobalEmissionPoint((*aInfo.GetGlobalEmissionPoint()));
+}
+//_____________________________________________
+AliFemtoModelGlobalHiddenInfo::~AliFemtoModelGlobalHiddenInfo()
+{
+  // Destructor
+//   if (fTrueMomentum) delete fTrueMomentum;
+//   if (fEmissionPoint) delete fEmissionPoint;
+  if (fGlobalEmissionPoint) delete fGlobalEmissionPoint;
+}
+//_____________________________________________
+AliFemtoModelGlobalHiddenInfo& AliFemtoModelGlobalHiddenInfo::operator=(const AliFemtoModelGlobalHiddenInfo& aInfo)
+{
+  // assignment operator
+  if (this == &aInfo)
+    return *this;
+
+  if (fTrueMomentum) delete fTrueMomentum;
+  if (aInfo.GetTrueMomentum())
+    SetTrueMomentum(aInfo.GetTrueMomentum());
+  else SetTrueMomentum(0);
+  if (fEmissionPoint) delete fEmissionPoint;
+  if (aInfo.GetEmissionPoint())
+    SetEmissionPoint(aInfo.GetEmissionPoint());
+  else SetEmissionPoint(0);
+  if (fGlobalEmissionPoint) delete fGlobalEmissionPoint;
+  if (aInfo.GetGlobalEmissionPoint())
+    SetGlobalEmissionPoint(*aInfo.GetGlobalEmissionPoint());
+  else fGlobalEmissionPoint = 0;
+  fPDGPid = aInfo.GetPDGPid();
+  fMass = aInfo.GetMass();
+
+  return *this;
+}
+//_____________________________________________
+AliFemtoThreeVector *AliFemtoModelGlobalHiddenInfo::GetGlobalEmissionPoint() const
+{
+  return fGlobalEmissionPoint;
+}
+//_____________________________________________
+void                   AliFemtoModelGlobalHiddenInfo::SetGlobalEmissionPoint(const AliFemtoThreeVector& aPos)
+{
+  // set position from vector
+  if (fGlobalEmissionPoint) {
+    fGlobalEmissionPoint->SetX(aPos.x());
+    fGlobalEmissionPoint->SetY(aPos.y());
+    fGlobalEmissionPoint->SetZ(aPos.z());
+  }
+  else {
+    fGlobalEmissionPoint = new AliFemtoThreeVector();
+    *fGlobalEmissionPoint = aPos;
+  }
+}
+//_____________________________________________
+void                   AliFemtoModelGlobalHiddenInfo::SetGlobalEmissionPoint(Double_t aRx, Double_t aRy, Double_t aRz)
+{
+  // Set position from components
+  if (fGlobalEmissionPoint) {
+    fGlobalEmissionPoint->SetX(aRx);
+    fGlobalEmissionPoint->SetY(aRy);
+    fGlobalEmissionPoint->SetZ(aRz);
+  }
+  else {
+    fGlobalEmissionPoint = new AliFemtoThreeVector(aRx, aRy, aRz); 
+  }
+}
+//_____________________________________________
+ AliFemtoHiddenInfo* AliFemtoModelGlobalHiddenInfo::GetParticleHiddenInfo() const
+{
+  // return copy of this hidden info
+  AliFemtoModelGlobalHiddenInfo* tBuf = new AliFemtoModelGlobalHiddenInfo(*this);
+  return tBuf;
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelGlobalHiddenInfo.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelGlobalHiddenInfo.h
new file mode 100644 (file)
index 0000000..083a848
--- /dev/null
@@ -0,0 +1,48 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoModelGlobalHiddenInfo - the hidden info for model calculations     //
+// Stores information needed for the weight generation - the true             //
+// simulated momenta, freeze-out coordinates from model and particle PID      //
+// and global creation point                                                  //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+
+#ifndef ALIFEMTOMODELGLOBALHIDDENINFO_H
+#define ALIFEMTOMODELGLOBALHIDDENINFO_H
+
+#include <TH1D.h>
+#include "AliFemtoTypes.h"
+#include "AliFemtoThreeVector.h"
+#include "AliFemtoLorentzVector.h"
+#include "AliFemtoHiddenInfo.h"
+#include "AliFemtoModelHiddenInfo.h"
+
+class AliFemtoModelGlobalHiddenInfo : public AliFemtoModelHiddenInfo{
+
+public:
+  AliFemtoModelGlobalHiddenInfo();
+  AliFemtoModelGlobalHiddenInfo(const AliFemtoModelGlobalHiddenInfo &aInfo);
+  virtual ~AliFemtoModelGlobalHiddenInfo();
+
+  AliFemtoModelGlobalHiddenInfo& operator=(const AliFemtoModelGlobalHiddenInfo& aInfo);
+
+  AliFemtoThreeVector   *GetGlobalEmissionPoint() const;
+  void                   SetGlobalEmissionPoint(const AliFemtoThreeVector& aPos);
+  void                   SetGlobalEmissionPoint(Double_t aRx, Double_t aRy, Double_t aRz);
+
+// !!! MANDATORY !!!
+// --- Copy the hidden info from AliFemtoTrack to AliFemtoParticle
+  virtual AliFemtoHiddenInfo* Clone() const;
+  
+ protected:
+  virtual AliFemtoHiddenInfo* GetParticleHiddenInfo() const;
+
+  AliFemtoThreeVector   *fGlobalEmissionPoint;
+};
+//_______________________________________
+inline AliFemtoHiddenInfo* AliFemtoModelGlobalHiddenInfo::Clone() const{
+  // return exact copy of this hidden info
+  return GetParticleHiddenInfo();
+}
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelHiddenInfo.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelHiddenInfo.cxx
new file mode 100644 (file)
index 0000000..dbf599a
--- /dev/null
@@ -0,0 +1,177 @@
+////////////////////////////////////////////////////////////////////////////////
+///                                                                          ///
+/// AliFemtoModelHiddenInfo - the hidden info for model calculations         ///
+/// Stores information needed for the weight generation - the true           ///
+/// simulated momenta, freeze-out coordinates from model and particle PID    ///
+///                                                                          ///
+////////////////////////////////////////////////////////////////////////////////
+#include "AliFemtoModelHiddenInfo.h"
+
+//_____________________________________________
+AliFemtoModelHiddenInfo::AliFemtoModelHiddenInfo() :
+  fTrueMomentum(0),
+  fEmissionPoint(0),
+  fPDGPid(0),
+  fMass(0)
+{
+  // Default constructor
+}
+//_____________________________________________
+AliFemtoModelHiddenInfo::AliFemtoModelHiddenInfo(const AliFemtoModelHiddenInfo &aInfo) :
+  AliFemtoHiddenInfo(aInfo),
+  fTrueMomentum(0),
+  fEmissionPoint(0),
+  fPDGPid(0),
+  fMass(0)
+{
+  // Copy constructor
+  if (aInfo.GetTrueMomentum())
+    SetTrueMomentum(aInfo.GetTrueMomentum());
+  if (aInfo.GetEmissionPoint())
+    SetEmissionPoint(aInfo.GetEmissionPoint());
+  fPDGPid = aInfo.GetPDGPid();
+  fMass = aInfo.GetMass();
+}
+//_____________________________________________
+AliFemtoModelHiddenInfo::~AliFemtoModelHiddenInfo()
+{
+  // Destructor
+  if (fTrueMomentum) delete fTrueMomentum;
+  if (fEmissionPoint) delete fEmissionPoint;
+}
+//_____________________________________________
+AliFemtoModelHiddenInfo& AliFemtoModelHiddenInfo::operator=(const AliFemtoModelHiddenInfo& aInfo)
+{
+  // assignment operator
+  if (this == &aInfo)
+    return *this;
+
+  if (fTrueMomentum) delete fTrueMomentum;
+  if (aInfo.GetTrueMomentum())
+    SetTrueMomentum(aInfo.GetTrueMomentum());
+  else SetTrueMomentum(0);
+  if (fEmissionPoint) delete fEmissionPoint;
+  if (aInfo.GetEmissionPoint())
+    SetEmissionPoint(aInfo.GetEmissionPoint());
+  else SetEmissionPoint(0);
+  fPDGPid = aInfo.GetPDGPid();
+  fMass = aInfo.GetMass();
+
+  return *this;
+}
+//_____________________________________________
+AliFemtoThreeVector   *AliFemtoModelHiddenInfo::GetTrueMomentum() const
+{
+  return fTrueMomentum;
+}
+//_____________________________________________
+AliFemtoLorentzVector *AliFemtoModelHiddenInfo::GetEmissionPoint() const
+{
+  return fEmissionPoint;
+}
+//_____________________________________________
+Int_t                  AliFemtoModelHiddenInfo::GetPDGPid() const
+{
+  return fPDGPid;
+}
+//_____________________________________________
+Double_t                  AliFemtoModelHiddenInfo::GetMass() const
+{
+  return fMass;
+}
+//_____________________________________________
+void                   AliFemtoModelHiddenInfo::SetTrueMomentum(AliFemtoThreeVector *aMom)
+{
+  // Set momentum from vector
+  if (fTrueMomentum) {
+    fTrueMomentum->SetX(aMom->x());
+    fTrueMomentum->SetY(aMom->y());
+    fTrueMomentum->SetZ(aMom->z());
+  }
+  else {
+    fTrueMomentum = new AliFemtoThreeVector(*aMom);
+  }
+}
+//_____________________________________________
+void                   AliFemtoModelHiddenInfo::SetTrueMomentum(const AliFemtoThreeVector& aMom)
+{
+  // Set momentum from vector
+  if (fTrueMomentum) {
+    fTrueMomentum->SetX(aMom.x());
+    fTrueMomentum->SetY(aMom.y());
+    fTrueMomentum->SetZ(aMom.z());
+  }
+  else {
+    fTrueMomentum = new AliFemtoThreeVector();
+    *fTrueMomentum = aMom;
+  }
+}
+//_____________________________________________
+void                   AliFemtoModelHiddenInfo::SetTrueMomentum(Double_t aPx, Double_t aPy, Double_t aPz)
+{
+  // Set momentum from components
+  if (!fTrueMomentum) fTrueMomentum = new AliFemtoThreeVector();
+    fTrueMomentum->SetX(aPx);
+    fTrueMomentum->SetY(aPy);
+    fTrueMomentum->SetZ(aPz);
+}
+//_____________________________________________
+void                   AliFemtoModelHiddenInfo::SetEmissionPoint(AliFemtoLorentzVector *aPos)
+{
+  // Set position from vector
+  if (fEmissionPoint) {
+    fEmissionPoint->SetX(aPos->px());
+    fEmissionPoint->SetY(aPos->py());
+    fEmissionPoint->SetZ(aPos->pz());
+    fEmissionPoint->SetT(aPos->e());
+  }
+  else {
+    fEmissionPoint = new AliFemtoLorentzVector(*aPos);
+  }
+}
+//_____________________________________________
+void                   AliFemtoModelHiddenInfo::SetEmissionPoint(const AliFemtoLorentzVector& aPos)
+{
+  // Set position from vector
+  if (fEmissionPoint) {
+    fEmissionPoint->SetX(aPos.px());
+    fEmissionPoint->SetY(aPos.py());
+    fEmissionPoint->SetZ(aPos.pz());
+    fEmissionPoint->SetT(aPos.e());
+  }
+  else {
+    fEmissionPoint = new AliFemtoLorentzVector();
+    *fEmissionPoint = aPos;
+  }
+}
+//_____________________________________________
+void                   AliFemtoModelHiddenInfo::SetPDGPid(Int_t aPid)
+{
+  fPDGPid = aPid;
+}
+//_____________________________________________
+void                   AliFemtoModelHiddenInfo::SetMass(Double_t aMass)
+{
+  fMass = aMass;
+}
+//_____________________________________________
+void                   AliFemtoModelHiddenInfo::SetEmissionPoint(Double_t aRx, Double_t aRy, Double_t aRz, Double_t aT)
+{
+  // Set position from components
+  if (fEmissionPoint) {
+    fEmissionPoint->SetX(aRx);
+    fEmissionPoint->SetY(aRy);
+    fEmissionPoint->SetZ(aRz);
+    fEmissionPoint->SetT(aT);
+  }
+  else {
+    fEmissionPoint = new AliFemtoLorentzVector(aRx, aRy, aRz, aT); 
+  }
+}
+//_____________________________________________
+ AliFemtoHiddenInfo* AliFemtoModelHiddenInfo::GetParticleHiddenInfo() const
+{
+  // return copy of this hidden info
+  AliFemtoModelHiddenInfo* tBuf = new AliFemtoModelHiddenInfo(*this);
+  return tBuf;
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelHiddenInfo.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelHiddenInfo.h
new file mode 100644 (file)
index 0000000..2fb0361
--- /dev/null
@@ -0,0 +1,58 @@
+////////////////////////////////////////////////////////////////////////////////
+///                                                                          ///
+/// AliFemtoModelHiddenInfo - the hidden info for model calculations         ///
+/// Stores information needed for the weight generation - the true           ///
+/// simulated momenta, freeze-out coordinates from model and particle PID    ///
+///                                                                          ///
+////////////////////////////////////////////////////////////////////////////////
+
+#ifndef ALIFEMTOMODELHIDDENINFO_H
+#define ALIFEMTOMODELHIDDENINFO_H
+
+#include <TH1D.h>
+#include "AliFemtoTypes.h"
+#include "AliFemtoThreeVector.h"
+#include "AliFemtoLorentzVector.h"
+#include "AliFemtoHiddenInfo.h"
+
+class AliFemtoModelHiddenInfo : public AliFemtoHiddenInfo{
+
+public:
+  AliFemtoModelHiddenInfo();
+  AliFemtoModelHiddenInfo(const AliFemtoModelHiddenInfo &aInfo);
+  virtual ~AliFemtoModelHiddenInfo();
+
+  AliFemtoModelHiddenInfo& operator=(const AliFemtoModelHiddenInfo& aInfo);
+  AliFemtoThreeVector   *GetTrueMomentum() const;
+  AliFemtoLorentzVector *GetEmissionPoint() const;
+  Int_t                  GetPDGPid() const;
+  Double_t               GetMass() const;
+
+  void                   SetTrueMomentum(AliFemtoThreeVector *aMom);
+  void                   SetTrueMomentum(const AliFemtoThreeVector& aMom);
+  void                   SetTrueMomentum(Double_t aPx, Double_t aPy, Double_t aPz);
+  void                   SetEmissionPoint(AliFemtoLorentzVector *aPos);
+  void                   SetEmissionPoint(const AliFemtoLorentzVector& aPos);
+  void                   SetEmissionPoint(Double_t aRx, Double_t aRy, Double_t aRz, Double_t aT);
+  void                   SetPDGPid(Int_t aPid);
+  void                   SetMass(Double_t aMass);
+
+// !!! MANDATORY !!!
+// --- Copy the hidden info from AliFemtoTrack to AliFemtoParticle
+  virtual AliFemtoHiddenInfo* Clone() const;
+  
+ protected:
+  virtual AliFemtoHiddenInfo* GetParticleHiddenInfo() const;
+
+  AliFemtoThreeVector   *fTrueMomentum;  // True (simulated) momentum
+  AliFemtoLorentzVector *fEmissionPoint; // Emission point coordinates
+  Int_t                  fPDGPid;        // True PID of the particle
+  Double_t               fMass;          // True particle mass
+};
+//_______________________________________
+inline AliFemtoHiddenInfo* AliFemtoModelHiddenInfo::Clone() const{
+  // return exact copy of this hidden info
+  return GetParticleHiddenInfo();
+}
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelManager.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelManager.cxx
new file mode 100644 (file)
index 0000000..63aeab9
--- /dev/null
@@ -0,0 +1,190 @@
+////////////////////////////////////////////////////////////////////////////////
+///                                                                          ///
+/// AliFemtoModelManager - main helper class for femtoscopy calculations     ///
+/// Manages weight generation, freeze-out coordinates generation             ///
+/// Authors: Adam Kisiel kisiel@mps.ohio-state.edu                           ///
+///                                                                          ///
+////////////////////////////////////////////////////////////////////////////////
+#ifdef __ROOT__
+  ClassImp(AliFemtoModelManager, 1)
+#endif
+
+#include "AliFemtoModelManager.h"
+#include "AliFemtoModelHiddenInfo.h"
+
+//_____________________________________________
+AliFemtoModelManager::AliFemtoModelManager():
+  fFreezeOutGenerator(0),
+  fWeightGenerator(0),
+  fCreateCopyHiddenInfo(kFALSE)
+{
+}
+//_____________________________________________
+AliFemtoModelManager::AliFemtoModelManager(const AliFemtoModelManager& aManager):
+  fFreezeOutGenerator(0),
+  fWeightGenerator(0),
+  fCreateCopyHiddenInfo(aManager.fCreateCopyHiddenInfo)
+{
+  if (aManager.fFreezeOutGenerator) {
+    fFreezeOutGenerator = aManager.fFreezeOutGenerator->Clone();
+  }
+  if (aManager.fWeightGenerator) {
+    fWeightGenerator = aManager.fWeightGenerator->Clone();
+  }
+}
+//_____________________________________________
+AliFemtoModelManager::~AliFemtoModelManager()
+{
+  if (fFreezeOutGenerator) delete fFreezeOutGenerator;
+  if (fWeightGenerator) delete fWeightGenerator;
+}
+//_____________________________________________
+AliFemtoModelManager& AliFemtoModelManager::operator=(const AliFemtoModelManager& aManager)
+{
+  if (this == &aManager)
+    return *this;
+  if (aManager.fFreezeOutGenerator) {
+    fFreezeOutGenerator = aManager.fFreezeOutGenerator->Clone();
+  }
+  else fFreezeOutGenerator = 0;
+  if (aManager.fWeightGenerator) {
+    fWeightGenerator = aManager.fWeightGenerator->Clone();
+  }
+  else fWeightGenerator = 0;
+  fCreateCopyHiddenInfo = aManager.fCreateCopyHiddenInfo;
+  
+  return *this;
+}
+//_____________________________________________
+void AliFemtoModelManager::AcceptFreezeOutGenerator(AliFemtoModelFreezeOutGenerator *aFreeze)
+{
+  fFreezeOutGenerator = aFreeze;
+}
+//_____________________________________________
+void AliFemtoModelManager::AcceptWeightGenerator(AliFemtoModelWeightGenerator *aWeight)
+{
+  fWeightGenerator = aWeight;
+}
+//_____________________________________________
+Double_t AliFemtoModelManager::GetWeight(AliFemtoPair *aPair)
+{
+  if (!fWeightGenerator) {
+    cout << "No weight generator set! Cannot calculate weight" << endl;
+    exit(0);
+  }
+  // Return femtoscopic weight for a given pair
+  if (fCreateCopyHiddenInfo) {
+    // Try to guess particle masses and pid from the weight generator
+    Double_t tMass1=0.0001, tMass2=0.0001;
+    Int_t tPid1=0, tPid2=0;
+    if (fWeightGenerator->GetPairType() == AliFemtoModelWeightGenerator::PionPlusPionPlus()) {
+      tMass1 = 0.13957;
+      tMass2 = 0.13957;
+      tPid1 = 211;
+      tPid2 = 211;
+    }
+    if (fWeightGenerator->GetPairType() == AliFemtoModelWeightGenerator::PionPlusPionMinus()) {
+      tMass1 = 0.13957;
+      tMass2 = 0.13957;
+      tPid1 = 211;
+      tPid2 = -211;
+    }
+    if (fWeightGenerator->GetPairType() == AliFemtoModelWeightGenerator::KaonPlusKaonPlus()) {
+      tMass1 = 0.493677;
+      tMass2 = 0.493677;
+      tPid1 = 321;
+      tPid2 = 321;
+    }
+    if (fWeightGenerator->GetPairType() == AliFemtoModelWeightGenerator::KaonPlusKaonMinus()) {
+      tMass1 = 0.493677;
+      tMass2 = 0.493677;
+      tPid1 = 321;
+      tPid2 = -321;
+    }
+    if (fWeightGenerator->GetPairType() == AliFemtoModelWeightGenerator::ProtonProton()) {
+      tMass1 = 0.938272;
+      tMass2 = 0.938272;
+      tPid1 = 2212;
+      tPid2 = 2212;
+    }
+    if (fWeightGenerator->GetPairType() == AliFemtoModelWeightGenerator::ProtonAntiproton()) {
+      tMass1 = 0.938272;
+      tMass2 = 0.938272;
+      tPid1 = 2212;
+      tPid2 = -2212;
+    }
+    if (fWeightGenerator->GetPairType() == AliFemtoModelWeightGenerator::PionPlusKaonPlus()) {
+      tMass1 = 0.13957;
+      tMass2 = 0.493677;
+      tPid1 = 211;
+      tPid2 = 321;
+    }
+    if (fWeightGenerator->GetPairType() == AliFemtoModelWeightGenerator::PionPlusKaonMinus()) {
+      tMass1 = 0.13957;
+      tMass2 = 0.493677;
+      tPid1 = 211;
+      tPid2 = -321;
+    }
+    if (fWeightGenerator->GetPairType() == AliFemtoModelWeightGenerator::PionPlusProton()) {
+      tMass1 = 0.13957;
+      tMass2 = 0.938272;
+      tPid1 = 211;
+      tPid2 = 2212;
+    }
+    if (fWeightGenerator->GetPairType() == AliFemtoModelWeightGenerator::PionPlusAntiproton()) {
+      tMass1 = 0.13957;
+      tMass2 = 0.938272;
+      tPid1 = 211;
+      tPid2 = -2212;
+    }
+    if (fWeightGenerator->GetPairType() == AliFemtoModelWeightGenerator::KaonPlusProton()) {
+      tMass1 = 0.493677;
+      tMass2 = 0.938272;
+      tPid1 = 321;
+      tPid2 = 2212;
+    }
+    if (fWeightGenerator->GetPairType() == AliFemtoModelWeightGenerator::KaonPlusAntiproton()) {
+      tMass1 = 0.493677;
+      tMass2 = 0.938272;
+      tPid1 = 321;
+      tPid2 = -2212;
+    }
+
+    if (!(aPair->Track1()->HiddenInfo())) {
+      AliFemtoModelHiddenInfo *inf1 = new AliFemtoModelHiddenInfo();
+      inf1->SetTrueMomentum(aPair->Track1()->Track()->P());
+      inf1->SetMass(tMass1);
+      inf1->SetPDGPid(tPid1);
+      aPair->Track1()->SetHiddenInfo(inf1);
+      delete inf1;
+    }
+    if (!(aPair->Track2()->HiddenInfo())) {
+      AliFemtoModelHiddenInfo *inf2 = new AliFemtoModelHiddenInfo();
+      inf2->SetTrueMomentum(aPair->Track2()->Track()->P());
+      inf2->SetMass(tMass2);
+      inf2->SetPDGPid(tPid2);
+      aPair->Track2()->SetHiddenInfo(inf2);
+      delete inf2;
+    }
+  }
+
+  if (fFreezeOutGenerator) {
+    fFreezeOutGenerator->GenerateFreezeOut(aPair);
+  }
+  return fWeightGenerator->GenerateWeight(aPair);
+}
+//_____________________________________________
+void AliFemtoModelManager::CreateCopyHiddenInfo(Bool_t aCopy)
+{
+  fCreateCopyHiddenInfo = aCopy;
+}
+//_____________________________________________
+AliFemtoModelFreezeOutGenerator* AliFemtoModelManager::GetFreezeOutGenerator()
+{
+  return fFreezeOutGenerator;
+}
+//_____________________________________________
+AliFemtoModelWeightGenerator*    AliFemtoModelManager::GetWeightGenerator()
+{
+  return fWeightGenerator;
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelManager.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelManager.h
new file mode 100644 (file)
index 0000000..58b4ee7
--- /dev/null
@@ -0,0 +1,48 @@
+////////////////////////////////////////////////////////////////////////////////
+///                                                                          ///
+/// AliFemtoModelManager - main helper class for femtoscopy calculations     ///
+/// Manages weight generation, freeze-out coordinates generation             ///
+/// Authors: Adam Kisiel kisiel@mps.ohio-state.edu                           ///
+///                                                                          ///
+////////////////////////////////////////////////////////////////////////////////
+#ifndef AliFemtoModelManager_hh
+#define AliFemtoModelManager_hh
+
+#include "AliFemtoEnumeration.h"
+#include "AliFemtoModelWeightGenerator.h"
+#include "AliFemtoModelFreezeOutGenerator.h"
+
+class AliFemtoModelManager 
+{
+ public:
+  AliFemtoModelManager();
+  AliFemtoModelManager(const AliFemtoModelManager& aManager);
+  virtual  ~AliFemtoModelManager();
+
+  AliFemtoModelManager& operator=(const AliFemtoModelManager& aManager);
+
+  void AcceptFreezeOutGenerator(AliFemtoModelFreezeOutGenerator *aFreeze);
+  void AcceptWeightGenerator(AliFemtoModelWeightGenerator *aWeight);
+  void CreateCopyHiddenInfo(Bool_t aCopy=kTRUE);
+
+  AliFemtoModelFreezeOutGenerator* GetFreezeOutGenerator();
+  AliFemtoModelWeightGenerator*    GetWeightGenerator();
+
+  virtual Double_t GetWeight(AliFemtoPair *aPair);
+  
+ protected:
+  AliFemtoModelFreezeOutGenerator *fFreezeOutGenerator;   // Freeze-out coordinates generator
+  AliFemtoModelWeightGenerator    *fWeightGenerator;      // Femtoscopic weight generator
+  Bool_t                           fCreateCopyHiddenInfo; // Switch to turn on hidden-info generation
+
+ private:
+               
+#ifdef __ROOT__
+  ClassDef(AliFemtoModelManager, 1)
+#endif
+
+    };
+  
+#endif
+
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelWeightGenerator.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelWeightGenerator.cxx
new file mode 100644 (file)
index 0000000..c6a6906
--- /dev/null
@@ -0,0 +1,129 @@
+////////////////////////////////////////////////////////////////////////////////
+///                                                                          ///
+/// AliFemtoModelWeightGenerator - abstract base class for femtoscopic       ///
+/// weight generator                                                         ///
+/// Authors: Adam Kisiel kisiel@mps.ohio-state.edu                           ///
+///                                                                          ///
+////////////////////////////////////////////////////////////////////////////////
+#ifdef __ROOT__
+  ClassImp(AliFemtoModelGausLCMSFreezeOutGenerator, 1)
+#endif
+
+#include "AliFemtoPair.h"
+
+#include "AliFemtoModelWeightGenerator.h"
+#include "AliFemtoModelHiddenInfo.h"
+
+const Int_t AliFemtoModelWeightGenerator::fgkPairTypeNone = 0;
+const Int_t AliFemtoModelWeightGenerator::fgkPionPlusPionPlus = 1;
+const Int_t AliFemtoModelWeightGenerator::fgkPionPlusPionMinus = 2;
+const Int_t AliFemtoModelWeightGenerator::fgkKaonPlusKaonPlus = 3;
+const Int_t AliFemtoModelWeightGenerator::fgkKaonPlusKaonMinus = 4;
+const Int_t AliFemtoModelWeightGenerator::fgkProtonProton = 5;
+const Int_t AliFemtoModelWeightGenerator::fgkProtonAntiproton = 6;
+const Int_t AliFemtoModelWeightGenerator::fgkPionPlusKaonPlus = 7;
+const Int_t AliFemtoModelWeightGenerator::fgkPionPlusKaonMinus = 8;
+const Int_t AliFemtoModelWeightGenerator::fgkPionPlusProton = 9;
+const Int_t AliFemtoModelWeightGenerator::fgkPionPlusAntiproton = 10;
+const Int_t AliFemtoModelWeightGenerator::fgkKaonPlusProton = 11;
+const Int_t AliFemtoModelWeightGenerator::fgkKaonPlusAntiproton = 12;
+
+//_____________________________________________
+AliFemtoModelWeightGenerator::AliFemtoModelWeightGenerator() :
+  fPairType(0), 
+  fKStarOut(0), fKStarSide(0), fKStarLong(0), fKStar(0), 
+  fRStarOut(0), fRStarSide(0), fRStarLong(0), fRStar(0)
+{}
+//_____________________________________________
+AliFemtoModelWeightGenerator::AliFemtoModelWeightGenerator(const AliFemtoModelWeightGenerator &aModel) :
+  fPairType(0), 
+  fKStarOut(0), fKStarSide(0), fKStarLong(0), fKStar(0), 
+  fRStarOut(0), fRStarSide(0), fRStarLong(0), fRStar(0)
+{
+  fPairType = aModel.fPairType;
+}
+//_____________________________________________
+AliFemtoModelWeightGenerator::~AliFemtoModelWeightGenerator(){/* no-op */}
+//_____________________________________________
+AliFemtoModelWeightGenerator& AliFemtoModelWeightGenerator::operator=(const AliFemtoModelWeightGenerator &aModel)
+{
+  if (this != &aModel) {
+    fPairType = aModel.fPairType;
+  }
+
+  return *this;
+}
+//_____________________________________________
+void     AliFemtoModelWeightGenerator::SetPairType(Int_t aPairType)
+{
+  fPairType = aPairType;
+}
+
+//_____________________________________________
+Int_t    AliFemtoModelWeightGenerator::GetPairType() const
+{
+  return fPairType;
+}
+
+//_____________________________________________
+void     AliFemtoModelWeightGenerator::SetPairTypeFromPair(AliFemtoPair *aPair)
+{
+  fPairType = GetPairTypeFromPair(aPair);
+}
+//_____________________________________________
+Int_t    AliFemtoModelWeightGenerator::GetPairTypeFromPair(AliFemtoPair *aPair)
+{
+  // Get the type of pair from PID of particles in the pair
+  AliFemtoModelHiddenInfo *inf1 = ( AliFemtoModelHiddenInfo *) aPair->Track1()->HiddenInfo();
+  AliFemtoModelHiddenInfo *inf2 = ( AliFemtoModelHiddenInfo *) aPair->Track2()->HiddenInfo();
+
+  Int_t tPairType = fgkPairTypeNone;
+
+  const Int_t ktPid1 = inf1->GetPDGPid();
+  const Int_t ktPid2 = inf2->GetPDGPid();
+
+  if      (((ktPid1 ==   211) && (ktPid2 ==   211)) ||
+           ((ktPid1 ==  -211) && (ktPid2 ==  -211)))
+    tPairType = fgkPionPlusPionPlus;
+  else if (((ktPid1 ==  -211) && (ktPid2 ==   211)) ||
+           ((ktPid1 ==   211) && (ktPid2 ==  -211)))
+    tPairType = fgkPionPlusPionMinus;
+  else if (((ktPid1 ==   321) && (ktPid2 ==   321)) ||
+           ((ktPid1 ==  -321) && (ktPid2 ==  -321)))
+    tPairType = fgkKaonPlusKaonPlus;
+  else if (((ktPid1 ==  -321) && (ktPid2 ==   321)) ||
+           ((ktPid1 ==   321) && (ktPid2 ==  -321)))
+    tPairType = fgkKaonPlusKaonMinus;
+  else if (((ktPid1 ==  2212) && (ktPid2 ==  2212)) ||
+           ((ktPid1 == -2212) && (ktPid2 == -2212)))
+    tPairType = fgkProtonProton;
+  else if (((ktPid1 == -2212) && (ktPid2 ==  2212)) ||
+           ((ktPid1 ==  2212) && (ktPid2 == -2212)))
+    tPairType = fgkProtonAntiproton;
+  else if (((ktPid1 ==   211) && (ktPid2 ==   321)) ||
+           ((ktPid1 ==  -211) && (ktPid2 ==  -321)))
+    tPairType = fgkPionPlusKaonPlus;
+  else if (((ktPid1 ==  -211) && (ktPid2 ==   321)) ||
+           ((ktPid1 ==   211) && (ktPid2 ==  -321)))
+    tPairType = fgkPionPlusKaonMinus;
+  else if (((ktPid1 ==   211) && (ktPid2 ==  2212)) ||
+           ((ktPid1 ==  -211) && (ktPid2 == -2212)))
+    tPairType = fgkPionPlusProton;
+  else if (((ktPid1 ==  -211) && (ktPid2 ==  2212)) ||
+           ((ktPid1 ==   211) && (ktPid2 == -2212)))
+    tPairType = fgkPionPlusAntiproton;
+  else if (((ktPid1 ==   321) && (ktPid2 ==  2212)) ||
+           ((ktPid1 ==  -321) && (ktPid2 == -2212)))
+    tPairType = fgkKaonPlusProton;
+  else if (((ktPid1 ==  -321) && (ktPid2 ==  2212)) ||
+           ((ktPid1 ==   321) && (ktPid2 == -2212)))
+    tPairType = fgkKaonPlusAntiproton;
+
+  return tPairType;
+}
+
+//_____________________________________________
+AliFemtoModelWeightGenerator* AliFemtoModelWeightGenerator::Clone() const
+{
+  return 0;
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelWeightGenerator.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelWeightGenerator.h
new file mode 100644 (file)
index 0000000..ce0df50
--- /dev/null
@@ -0,0 +1,112 @@
+////////////////////////////////////////////////////////////////////////////////
+///                                                                          ///
+/// AliFemtoModelWeightGenerator - abstract base class for femtoscopic       ///
+/// weight generator                                                         ///
+/// Authors: Adam Kisiel kisiel@mps.ohio-state.edu                           ///
+///                                                                          ///
+////////////////////////////////////////////////////////////////////////////////
+#ifndef ALIFEMTOMODELWEIGHTGENERATOR_H
+#define ALIFEMTOMODELWEIGHTGENERATOR_H
+
+#include "TRandom2.h"
+class AliFemtoPair;
+
+class AliFemtoModelWeightGenerator 
+{
+ public:
+  AliFemtoModelWeightGenerator();
+  AliFemtoModelWeightGenerator(const AliFemtoModelWeightGenerator &aModel);
+  virtual ~AliFemtoModelWeightGenerator();
+  AliFemtoModelWeightGenerator& operator=(const AliFemtoModelWeightGenerator &aModel);
+  virtual Double_t GenerateWeight(AliFemtoPair *aPair) = 0;
+
+  virtual void     SetPairType(Int_t aPairType);
+  virtual void     SetPairTypeFromPair(AliFemtoPair *aPair);
+  virtual Int_t    GetPairType() const;
+  virtual Int_t    GetPairTypeFromPair(AliFemtoPair *aPair);
+
+  virtual Double_t GetKStar() const;
+  virtual Double_t GetKStarOut() const;
+  virtual Double_t GetKStarSide() const;
+  virtual Double_t GetKStarLong() const;
+  virtual Double_t GetRStar() const;
+  virtual Double_t GetRStarOut() const;
+  virtual Double_t GetRStarSide() const;
+  virtual Double_t GetRStarLong() const;
+
+  virtual AliFemtoModelWeightGenerator* Clone() const;
+
+  static Int_t PionPlusPionPlus();  
+  static Int_t PionPlusPionMinus(); 
+  static Int_t KaonPlusKaonPlus();  
+  static Int_t KaonPlusKaonMinus(); 
+  static Int_t ProtonProton();      
+  static Int_t ProtonAntiproton();  
+  static Int_t PionPlusKaonPlus();  
+  static Int_t PionPlusKaonMinus(); 
+  static Int_t PionPlusProton();    
+  static Int_t PionPlusAntiproton();
+  static Int_t KaonPlusProton();    
+  static Int_t KaonPlusAntiproton();
+  static Int_t PairTypeNone();
+
+ protected:
+  static const Int_t fgkPairTypeNone;      // no pair type set - read from model
+  static const Int_t fgkPionPlusPionPlus;  // identical pion pair
+  static const Int_t fgkPionPlusPionMinus; // non-identical pion pair
+  static const Int_t fgkKaonPlusKaonPlus;  // identical kaon pair
+  static const Int_t fgkKaonPlusKaonMinus; // non-identical kaon pair
+  static const Int_t fgkProtonProton;      // identical proton pair
+  static const Int_t fgkProtonAntiproton;  // non-identical proton pair
+  static const Int_t fgkPionPlusKaonPlus;  // same-charge pion kaon pair
+  static const Int_t fgkPionPlusKaonMinus; // opposite-charge pion kaon pair
+  static const Int_t fgkPionPlusProton;    // same-charge pion proton pair
+  static const Int_t fgkPionPlusAntiproton;// opposite-chare pion proton pair
+  static const Int_t fgkKaonPlusProton;    // same-charge kaon proton pair
+  static const Int_t fgkKaonPlusAntiproton;// opposite-charge kaon proton pair
+
+  Int_t fPairType;     // Type of the pair for which the calculation is done
+
+  Double_t fKStarOut;  // relative momentum out component in PRF
+  Double_t fKStarSide; // relative momentum side component in PRF
+  Double_t fKStarLong; // relative momentum long component in PRF
+  Double_t fKStar;     // relative momentum magnitude
+
+  Double_t fRStarOut;  // relative separation out component in PRF
+  Double_t fRStarSide; // relative separation side component in PRF
+  Double_t fRStarLong; // relative separation long component in PRF
+  Double_t fRStar;     // relative separation magnitude
+ private:
+  
+#ifdef __ROOT__
+  ClassDef(AliFemtoModelWeightGenerator, 1)
+#endif
+
+    };
+  
+inline Double_t AliFemtoModelWeightGenerator::GetKStar() const { return fKStar; }
+inline Double_t AliFemtoModelWeightGenerator::GetKStarOut() const { return fKStarOut; }
+inline Double_t AliFemtoModelWeightGenerator::GetKStarSide() const { return fKStarSide; }
+inline Double_t AliFemtoModelWeightGenerator::GetKStarLong() const { return fKStarLong; }
+inline Double_t AliFemtoModelWeightGenerator::GetRStar() const { return fRStar; }
+inline Double_t AliFemtoModelWeightGenerator::GetRStarOut() const { return fRStarOut; }
+inline Double_t AliFemtoModelWeightGenerator::GetRStarSide() const { return fRStarSide; }
+inline Double_t AliFemtoModelWeightGenerator::GetRStarLong() const { return fRStarLong; }
+
+inline Int_t AliFemtoModelWeightGenerator::PairTypeNone() { return fgkPairTypeNone; }  
+inline Int_t AliFemtoModelWeightGenerator::PionPlusPionPlus() { return fgkPionPlusPionPlus; }  
+inline Int_t AliFemtoModelWeightGenerator::PionPlusPionMinus() { return fgkPionPlusPionMinus; } 
+inline Int_t AliFemtoModelWeightGenerator::KaonPlusKaonPlus() { return fgkKaonPlusKaonPlus; }  
+inline Int_t AliFemtoModelWeightGenerator::KaonPlusKaonMinus() { return fgkKaonPlusKaonMinus; } 
+inline Int_t AliFemtoModelWeightGenerator::ProtonProton() { return fgkProtonProton; }      
+inline Int_t AliFemtoModelWeightGenerator::ProtonAntiproton() { return fgkProtonAntiproton; }  
+inline Int_t AliFemtoModelWeightGenerator::PionPlusKaonPlus() { return fgkPionPlusKaonPlus; }  
+inline Int_t AliFemtoModelWeightGenerator::PionPlusKaonMinus() { return fgkPionPlusKaonMinus; } 
+inline Int_t AliFemtoModelWeightGenerator::PionPlusProton() { return fgkPionPlusProton; }    
+inline Int_t AliFemtoModelWeightGenerator::PionPlusAntiproton() { return fgkPionPlusAntiproton; }
+inline Int_t AliFemtoModelWeightGenerator::KaonPlusProton() { return fgkKaonPlusProton; }    
+inline Int_t AliFemtoModelWeightGenerator::KaonPlusAntiproton() { return fgkKaonPlusAntiproton; }
+
+#endif
+
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelWeightGeneratorBasic.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelWeightGeneratorBasic.cxx
new file mode 100644 (file)
index 0000000..5c61f85
--- /dev/null
@@ -0,0 +1,200 @@
+////////////////////////////////////////////////////////////////////////////////
+///                                                                          ///
+/// AliFemtoModelWeightGeneratorBasic -  basic femtoscopic weight generator  ///
+/// only return a simple                                                          ///
+/// Authors: Adam Kisiel kisiel@mps.ohio-state.edu                           ///
+///                                                                          ///
+////////////////////////////////////////////////////////////////////////////////
+#ifdef __ROOT__
+  ClassImp(AliFemtoModelWeightGeneratorBasic, 1)
+#endif
+
+#include "AliFemtoModelWeightGeneratorBasic.h"
+#include "AliFemtoModelHiddenInfo.h"
+
+//________________________
+AliFemtoModelWeightGeneratorBasic::AliFemtoModelWeightGeneratorBasic():
+  AliFemtoModelWeightGenerator()
+{
+  /* no-op */
+}
+//________________________
+AliFemtoModelWeightGeneratorBasic::AliFemtoModelWeightGeneratorBasic(const AliFemtoModelWeightGeneratorBasic &aModel) :
+  AliFemtoModelWeightGenerator(aModel)
+{
+  /* no-op */
+}
+
+//________________________
+AliFemtoModelWeightGeneratorBasic::~AliFemtoModelWeightGeneratorBasic()
+{
+  /* no-op */
+}
+
+AliFemtoModelWeightGeneratorBasic& AliFemtoModelWeightGeneratorBasic::operator=(const AliFemtoModelWeightGeneratorBasic &aModel)
+{
+  if (this != &aModel) {
+    AliFemtoModelWeightGenerator::operator=(aModel);
+  }
+  
+  return *this;
+}
+
+//________________________
+Double_t AliFemtoModelWeightGeneratorBasic::GenerateWeight(AliFemtoPair *aPair)
+{
+  // Generate a simple femtoscopic weight coming only from 
+  // quantum statistics - symmetrization or anti-symmetrization
+  // of the pair wave function
+
+  // Get hidden information pointers
+  AliFemtoModelHiddenInfo *inf1 = (AliFemtoModelHiddenInfo *) aPair->Track1()->HiddenInfo();
+  AliFemtoModelHiddenInfo *inf2 = (AliFemtoModelHiddenInfo *) aPair->Track2()->HiddenInfo();
+
+  // Calculate pair variables
+  Double_t tPx = inf1->GetTrueMomentum()->x()+inf2->GetTrueMomentum()->x();
+  Double_t tPy = inf1->GetTrueMomentum()->y()+inf2->GetTrueMomentum()->y();
+  Double_t tPz = inf1->GetTrueMomentum()->z()+inf2->GetTrueMomentum()->z();
+  //  double tE  = inf1->GetTrueMomentum()->e +inf2->GetTrueMomentum()->.e;
+  Double_t tM1 = inf1->GetMass();
+  Double_t tM2 = inf2->GetMass();
+  Double_t tE1 = sqrt(tM1*tM1 + inf1->GetTrueMomentum()->Mag2());
+  Double_t tE2 = sqrt(tM2*tM2 + inf2->GetTrueMomentum()->Mag2());
+  Double_t tE  = tE1 + tE2;
+  Double_t tPt = tPx*tPx + tPy*tPy;
+  Double_t tMt = tE*tE - tPz*tPz;//mCVK;
+  Double_t tM  = sqrt(tMt - tPt);
+  tMt = sqrt(tMt);
+  tPt = sqrt(tPt);
+  Double_t tBetat = tPt/tMt;
+
+  // Boost to LCMS
+  Double_t tBeta = tPz/tE;
+  Double_t tGamma = tE/tMt;        
+  fKStarLong = tGamma * (inf1->GetTrueMomentum()->z() - tBeta * tE1);
+  Double_t tE1L = tGamma * (tE1  - tBeta * inf1->GetTrueMomentum()->z());
+  
+  // Transform positions to LCMS
+//   Double_t tP1zl = tGamma * (inf1->GetEmissionPoint()->z() - tBeta * inf1->GetEmissionPoint()->t());
+//   Double_t tP1tl = tGamma * (inf1->GetEmissionPoint()->t() - tBeta * inf1->GetEmissionPoint()->z());
+  
+//   Double_t tP2zl = tGamma * (inf2->GetEmissionPoint()->z() - tBeta * inf2->GetEmissionPoint()->t());
+//   Double_t tP2tl = tGamma * (inf2->GetEmissionPoint()->t() - tBeta * inf2->GetEmissionPoint()->z());
+  
+//   Double_t tP1pzl = tGamma * (inf1->GetTrueMomentum()->z() - tBeta * tE1);
+//   Double_t tP1el  = tGamma * (tE1  - tBeta * inf1->GetTrueMomentum()->z());
+  
+//   Double_t tP2pzl = tGamma * (inf2->GetTrueMomentum()->z() - tBeta * tE2);
+//   Double_t tP2el  = tGamma * (tE2  - tBeta * inf2->GetTrueMomentum()->z());
+  
+  // Rotate in transverse plane
+  fKStarOut  = ( inf1->GetTrueMomentum()->x()*tPx + inf1->GetTrueMomentum()->y()*tPy)/tPt;
+  fKStarSide = (-inf1->GetTrueMomentum()->x()*tPy + inf1->GetTrueMomentum()->y()*tPx)/tPt;
+      
+//   Double_t tP1pxl = fKStarOut;
+//   Double_t tP1pyl = fKStarSide;
+  
+//   Double_t tP2pxl = (inf2->GetTrueMomentum()->x()*tPx + inf2->GetTrueMomentum()->y()*tPy)/tPt;
+//   Double_t tP2pyl = (inf2->GetTrueMomentum()->y()*tPx - inf2->GetTrueMomentum()->x()*tPy)/tPt;;
+  
+//   Double_t tKO = tP1pxl - tP2pxl;
+//   Double_t tKS = tP1pyl - tP2pyl;
+//   Double_t tKL = tP1pzl - tP2pzl;
+//   Double_t tDE = tP1el  - tP2el;
+  
+  // save the rotated coordinates in LCMS variables
+//   Double_t tP1xl = ( inf1->GetEmissionPoint()->x()*tPx + inf1->GetEmissionPoint()->y()*tPy)/tPt;
+//   Double_t tP1yl = (-inf1->GetEmissionPoint()->x()*tPy + inf1->GetEmissionPoint()->y()*tPx)/tPt;
+
+//   Double_t tP2xl = ( inf2->GetEmissionPoint()->x()*tPx + inf2->GetEmissionPoint()->y()*tPy)/tPt;
+//   Double_t tP2yl = (-inf2->GetEmissionPoint()->x()*tPy + inf2->GetEmissionPoint()->y()*tPx)/tPt;
+  
+  // Boost to pair cms
+  fKStarOut = tMt/tM * (fKStarOut - tPt/tMt * tE1L);
+  
+  tBetat = tPt/tMt;
+//   Double_t tGammat = 1.0/sqrt(1.0-tBetat*tBetat);
+  
+//   Double_t tP1xp = tGammat*(tP1xl - tBetat*tP1tl);
+//   Double_t tP1tp = tGammat*(tP1tl - tBetat*tP1xl);
+  
+//   Double_t tP2xp = tGammat*(tP2xl - tBetat*tP2tl);
+//   Double_t tP2tp = tGammat*(tP2tl - tBetat*tP2xl);
+  
+//   Double_t tRO = (tP1xl - tP2xl)/0.197327;
+//   Double_t tRS = (tP1yl - tP2yl)/0.197327;
+//   Double_t tRL = (tP1zl - tP2zl)/0.197327;
+//   Double_t tDT = (tP1tl - tP2tl)/0.197327;
+  
+  Double_t tDX = inf1->GetEmissionPoint()->x()-inf2->GetEmissionPoint()->x();
+  Double_t tDY = inf1->GetEmissionPoint()->y()-inf2->GetEmissionPoint()->y();
+  Double_t tRLong = inf1->GetEmissionPoint()->z()-inf2->GetEmissionPoint()->z();
+  Double_t tDTime = inf1->GetEmissionPoint()->t()-inf2->GetEmissionPoint()->t();
+
+  Double_t tROut = (tDX*tPx + tDY*tPy)/tPt;
+  Double_t tRSide = (-tDX*tPy + tDY*tPx)/tPt;
+
+  fRStarSide = tRSide;
+  Double_t tRSS = fRStarSide/0.197327;
+
+  fRStarLong = tGamma*(tRLong - tBeta* tDTime);
+  Double_t tDTimePairLCMS = tGamma*(tDTime - tBeta* tRLong);
+
+  Double_t tRLS = fRStarLong/0.197327;
+  tBeta = tPt/tMt;
+  tGamma = tMt/tM;
+
+  fRStarOut = tGamma*(tROut - tBeta* tDTimePairLCMS);
+  Double_t tROS = fRStarOut/0.197327;
+//   Double_t tDTimePairCMS = tGamma*(tDTimePairLCMS - tBeta* tROut);
+  fRStar = ::sqrt(fRStarOut*fRStarOut + fRStarSide*fRStarSide +
+                          fRStarLong*fRStarLong);
+  fKStar = ::sqrt(fKStarOut*fKStarOut + fKStarSide*fKStarSide + fKStarLong*fKStarLong);
+//   Double_t tRSt = fRStar/0.197327;
+
+  if (fPairType != fgkPairTypeNone) {
+    if ((fPairType == PionPlusPionPlus()) || (fPairType == KaonPlusKaonPlus()))
+      return 1.0 + cos (2*(fKStarOut * tROS + fKStarSide * tRSS + fKStarLong * tRLS));
+    else if (fPairType == ProtonProton())
+      return 1.0 - 0.5 * cos (2*(fKStarOut * tROS + fKStarSide * tRSS + fKStarLong * tRLS));
+    else 
+      return 1.0;
+  }
+  else {
+    Int_t tPairType = GetPairTypeFromPair(aPair);
+    if ((tPairType == PionPlusPionPlus()) || (tPairType == KaonPlusKaonPlus()))
+      return 1.0 + cos (2*(fKStarOut * tROS + fKStarSide * tRSS + fKStarLong * tRLS));
+    else if (tPairType == ProtonProton())
+      return 1.0 - 0.5 * cos (2*(fKStarOut * tROS + fKStarSide * tRSS + fKStarLong * tRLS));
+    else 
+      return 1.0;
+    
+  }
+}
+
+//________________________
+void     AliFemtoModelWeightGeneratorBasic::SetPairType(Int_t aPairType)
+{
+  AliFemtoModelWeightGenerator::SetPairType(aPairType);
+}
+//________________________
+void     AliFemtoModelWeightGeneratorBasic::SetPairTypeFromPair(AliFemtoPair *aPair)
+{
+  AliFemtoModelWeightGenerator::SetPairTypeFromPair(aPair);
+}
+//________________________
+Int_t    AliFemtoModelWeightGeneratorBasic::GetPairType() const
+{
+  return AliFemtoModelWeightGenerator::GetPairType();
+}
+//________________________
+AliFemtoModelWeightGenerator* AliFemtoModelWeightGeneratorBasic::Clone() const
+{
+  return GetGenerator();
+}
+//________________________
+AliFemtoModelWeightGenerator* AliFemtoModelWeightGeneratorBasic::GetGenerator() const
+{
+  AliFemtoModelWeightGeneratorBasic *tGen = new AliFemtoModelWeightGeneratorBasic(*this);
+  return tGen;
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelWeightGeneratorBasic.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelWeightGeneratorBasic.h
new file mode 100644 (file)
index 0000000..e7a6321
--- /dev/null
@@ -0,0 +1,42 @@
+////////////////////////////////////////////////////////////////////////////////
+///                                                                          ///
+/// AliFemtoModelWeightGeneratorBasic -  basic femtoscopic weight generator  ///
+/// only return a simple                                                          ///
+/// Authors: Adam Kisiel kisiel@mps.ohio-state.edu                           ///
+///                                                                          ///
+////////////////////////////////////////////////////////////////////////////////
+#ifndef AliFemtoModelWeightGeneratorBasic_hh
+#define AliFemtoModelWeightGeneratorBasic_hh
+
+#include "TRandom2.h"
+#include "AliFemtoPair.h"
+#include "AliFemtoModelWeightGenerator.h"
+
+class AliFemtoModelWeightGeneratorBasic : public AliFemtoModelWeightGenerator
+{
+ public:
+  AliFemtoModelWeightGeneratorBasic();
+  AliFemtoModelWeightGeneratorBasic(const AliFemtoModelWeightGeneratorBasic &aModel);
+  virtual ~AliFemtoModelWeightGeneratorBasic();
+  AliFemtoModelWeightGeneratorBasic& operator=(const AliFemtoModelWeightGeneratorBasic &aModel);
+  virtual Double_t GenerateWeight(AliFemtoPair *aPair);
+
+  virtual void     SetPairType(Int_t aPairType);
+  virtual void     SetPairTypeFromPair(AliFemtoPair *aPair);
+  virtual Int_t    GetPairType() const; 
+
+  virtual AliFemtoModelWeightGenerator* Clone() const;
+ protected:
+  
+ private:
+  AliFemtoModelWeightGenerator* GetGenerator() const;
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoModelWeightGeneratorBasic, 1)
+#endif
+
+    };
+  
+#endif
+
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelWeightGeneratorLednicky.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelWeightGeneratorLednicky.cxx
new file mode 100644 (file)
index 0000000..83504db
--- /dev/null
@@ -0,0 +1,672 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFemtoModelWeightGeneratorLednicky : the most advanced weight       //
+// generator available. Supports a large number of different pair types  //
+// and interaction types. Can calculate pair weights coming from         //
+// quantum statistics, coulomb interation and strong interaction ot any  //
+// combination of the three, as applicable.                              //
+// This class is a wrapper for the fortran code provided by Richard      //
+// Lednicky.                                                             //
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+
+//#include "StHbtMaker/ThCorrFctn/AliFemtoModelWeightGeneratorLednicky.h"
+#include "AliFemtoModelWeightGeneratorLednicky.h"
+#include "AliFemtoModelHiddenInfo.h"
+#include "AliFemtoPair.h"
+//#include "StarCallf77.h"
+//#include <strstream.h>
+//#include <iomanip.h>
+//#include <stream>
+//#include <iomanip>
+#include <sstream>
+
+#ifdef SOLARIS
+# ifndef false
+typedef int bool;
+#define false 0
+#define true 1
+# endif
+#endif
+
+#ifdef WIN32
+# ifdef CERNLIB_MSSTDCALL
+#  define F77_UCASE
+#  define type_of_call _stdcall
+#  ifndef CERNLIB_QXCAPT
+#    define CERNLIB_QXCAPT
+#  endif
+# else
+#  define F77_LCASE
+#  ifndef CERNLIB_QXNO_SC
+#    define CERNLIB_QXNO_SC
+#  endif
+# endif
+# define type_of_call  _stdcall
+# define DEFCHARD   const char* , const int        
+# define DEFCHARL          
+# define PASSCHARD(string) string, strlen(string) 
+# define PASSCHARL(string) 
+#else
+# define DEFCHARD     const char* 
+# define DEFCHARL   , const int 
+# define PASSCHARD(string) string 
+# define PASSCHARL(string) , strlen(string) 
+#endif
+#ifdef CERNLIB_QXCAPT
+#  define F77_NAME(name,NAME) NAME
+#else
+#  if defined(CERNLIB_QXNO_SC)
+#    define F77_NAME(name,NAME) name
+#  else
+#    define F77_NAME(name,NAME) name##_
+#  endif
+#endif
+#ifndef type_of_call
+# define type_of_call
+#endif
+
+// --- Prototype of the function used in the weight calculator 
+//     (in FsiWeightLedinicky.F)
+#define fsiin F77_NAME(fsiin,FSIIN)
+extern "C" {void type_of_call F77_NAME(fsiin,FSIIN)(const int &itest,const int &ich, const int &iqs, const int &isi,const int &i3c);}
+#define llini F77_NAME(llini,LLINI)
+extern "C" {void type_of_call F77_NAME(llini,LLINI)(const int &lll,const int &ns, const int &itest);}
+
+#define fsinucl F77_NAME(fsinucl,FSINUCL)
+extern "C" {void type_of_call  F77_NAME(fsinucl,FSINUCL)(const double &mn,const double &cn);}
+#define fsimomentum F77_NAME(fsimomentum,FSIMOMENTUM)
+extern "C" {void type_of_call F77_NAME(fsimomentum,FSIMOMENTUM)(double &p1,double &p2);}
+#define fsiposition F77_NAME(fsiposition,FSIPOSITION)
+extern "C" {void type_of_call F77_NAME(fsiposition,FSIPOSITION)(double &x1,double &x2);}
+#define fsiw F77_NAME(fsiw,FSIW)
+extern "C" {void type_of_call F77_NAME(fsiw,FSIW)(const int &i,double &weif,
+                                                 double &wei,double &wein);}
+#define ltran12 F77_NAME(ltran12,LTRAN12)
+extern "C" {void type_of_call ltran12_();}
+
+// Test function for Lambda potential
+//#define printlam F77_NAME(printlam,PRINTLAM)
+//extern "C" {void type_of_call printlam_();}
+//there is not PRINTLAM in *.F file
+
+// --- Additional prototyping of some CERN functions (in FsiTool.F)
+typedef float   REAL;
+typedef struct { REAL re; REAL im; } COMPLEX;
+#define cgamma F77_NAME(cgamma,CGAMMA)
+extern "C" {COMPLEX type_of_call cgamma_(COMPLEX*);}
+
+#ifdef __ROOT__
+ClassImp(AliFemtoModelWeightGeneratorLednicky)
+#endif
+
+AliFemtoModelWeightGeneratorLednicky::AliFemtoModelWeightGeneratorLednicky() : 
+  AliFemtoModelWeightGenerator(),
+  fWei(0), fWein(0), fWeif(0), fWeightDen(0), 
+  fItest(0),fIch(1),fIqs(1),fIsi(1),fI3c(0),
+  fNuclMass(1.),fNuclCharge(0.),
+  fSphereApp(false),fT0App(false) ,
+  fLL(0), fNuclChargeSign(1), fSwap(0), fLLMax(30), fLLName(0), 
+  fNumProcessPair(0), fNumbNonId(0)
+{
+  // default constructor
+  fLLName=new char*[fLLMax+1];
+  fNumProcessPair=new int[fLLMax+1];
+  int i;
+  for (i=1;i<=fLLMax;i++) {fLLName[i]=new char[40];fNumProcessPair[i]=0;}
+  strncpy( fLLName[1],"neutron neutron",40);
+  strncpy( fLLName[2],"proton proton",40);
+  strncpy( fLLName[3],"neutron proton",40);
+  strncpy( fLLName[4],"alpha alpha",40);
+  strncpy( fLLName[5],"pi+ pi-",40);
+  strncpy( fLLName[6],"pi0 pi0",40);
+  strncpy( fLLName[7],"pi+ pi+",40);
+  strncpy( fLLName[8],"neutron deuteron",40);
+  strncpy( fLLName[9],"proton deuteron",40);
+  strncpy( fLLName[10],"pi+ K-",40);
+  strncpy( fLLName[11],"pi+ K+",40);
+  strncpy( fLLName[12],"pi+ proton",40);
+  strncpy( fLLName[13],"pi- proton",40);
+  strncpy( fLLName[14],"K+ K-",40);
+  strncpy( fLLName[15],"K+ K+",40);
+  strncpy( fLLName[16],"K+ proton",40);
+  strncpy( fLLName[17],"K- proton",40);
+  strncpy( fLLName[18],"deuteron deuteron",40);
+  strncpy( fLLName[19],"deuton alpha",40);
+  strncpy( fLLName[20],"triton triton",40);
+  strncpy( fLLName[21],"triton alpha",40);
+  strncpy( fLLName[22],"K0 K0",40);
+  strncpy( fLLName[23],"K0 K0b",40);
+  strncpy( fLLName[24],"deuteron triton",40);
+  strncpy( fLLName[25],"proton triton",40);
+  strncpy( fLLName[26],"proton alpha",40);
+  strncpy( fLLName[27],"proton lambda",40);
+  strncpy( fLLName[28],"neutron lambda",40);
+  strncpy( fLLName[29],"Lambda lambda",40);// gael 21May02
+  strncpy( fLLName[30],"Proton Anti-proton",40);// gael 21May02
+  FsiInit();
+  FsiNucl();
+}
+//______________________
+AliFemtoModelWeightGeneratorLednicky::AliFemtoModelWeightGeneratorLednicky(const AliFemtoModelWeightGeneratorLednicky &aWeight):
+  AliFemtoModelWeightGenerator(),
+  fWei(0), fWein(0), fWeif(0), fWeightDen(0), 
+  fItest(0),fIch(1),fIqs(1),fIsi(1),fI3c(0),
+  fNuclMass(1.),fNuclCharge(0.),
+  fSphereApp(false),fT0App(false) ,
+  fLL(0), fNuclChargeSign(1), fSwap(0), fLLMax(30), fLLName(0), 
+  fNumProcessPair(0), fNumbNonId(0)
+{
+  // copy constructor
+  fWei = aWeight.fWei; 
+  fWein = aWeight.  fWein;
+  fWeif = aWeight. fWeif;
+  fWeightDen = aWeight.fWeightDen;
+  
+  fItest = aWeight.fItest;
+  fIch = aWeight.fIch;
+  fIqs = aWeight.fIqs;
+  fIsi = aWeight.fIsi;
+  fI3c = aWeight.fI3c;
+  fNuclMass = aWeight.fNuclMass;
+  fNuclCharge = aWeight.fNuclCharge;
+  fSphereApp = aWeight.fSphereApp;
+  fT0App = aWeight.fT0App; 
+  fLL = aWeight.fLL;
+  fNuclChargeSign = aWeight.fNuclChargeSign;
+  fSwap = aWeight.fSwap;
+  fLLName = aWeight.fLLName; 
+  fNumProcessPair = aWeight.fNumProcessPair;
+  fNumbNonId = aWeight.fNumbNonId;
+  fLLName=new char*[fLLMax+1];
+  fNumProcessPair=new int[fLLMax+1];
+  int i;
+  for (i=1;i<=fLLMax;i++) {fLLName[i]=new char[40];fNumProcessPair[i]=0;}
+  strncpy( fLLName[1],"neutron neutron",40);
+  strncpy( fLLName[2],"proton proton",40);
+  strncpy( fLLName[3],"neutron proton",40);
+  strncpy( fLLName[4],"alpha alpha",40);
+  strncpy( fLLName[5],"pi+ pi-",40);
+  strncpy( fLLName[6],"pi0 pi0",40);
+  strncpy( fLLName[7],"pi+ pi+",40);
+  strncpy( fLLName[8],"neutron deuteron",40);
+  strncpy( fLLName[9],"proton deuteron",40);
+  strncpy( fLLName[10],"pi+ K-",40);
+  strncpy( fLLName[11],"pi+ K+",40);
+  strncpy( fLLName[12],"pi+ proton",40);
+  strncpy( fLLName[13],"pi- proton",40);
+  strncpy( fLLName[14],"K+ K-",40);
+  strncpy( fLLName[15],"K+ K+",40);
+  strncpy( fLLName[16],"K+ proton",40);
+  strncpy( fLLName[17],"K- proton",40);
+  strncpy( fLLName[18],"deuteron deuteron",40);
+  strncpy( fLLName[19],"deuton alpha",40);
+  strncpy( fLLName[20],"triton triton",40);
+  strncpy( fLLName[21],"triton alpha",40);
+  strncpy( fLLName[22],"K0 K0",40);
+  strncpy( fLLName[23],"K0 K0b",40);
+  strncpy( fLLName[24],"deuteron triton",40);
+  strncpy( fLLName[25],"proton triton",40);
+  strncpy( fLLName[26],"proton alpha",40);
+  strncpy( fLLName[27],"proton lambda",40);
+  strncpy( fLLName[28],"neutron lambda",40);
+  strncpy( fLLName[29],"Lambda lambda",40);// gael 21May02
+  strncpy( fLLName[30],"Proton Anti-proton",40);// gael 21May02
+  FsiInit();
+  FsiNucl();
+}
+
+AliFemtoModelWeightGeneratorLednicky& AliFemtoModelWeightGeneratorLednicky::operator=(const AliFemtoModelWeightGeneratorLednicky& aWeight)
+{
+  // assignment operator
+  if (this == &aWeight)
+    return *this;
+
+  fWei = aWeight.fWei; 
+  fWein = aWeight.  fWein;
+  fWeif = aWeight. fWeif;
+  fWeightDen = aWeight.fWeightDen;
+  
+  fItest = aWeight.fItest;
+  fIch = aWeight.fIch;
+  fIqs = aWeight.fIqs;
+  fIsi = aWeight.fIsi;
+  fI3c = aWeight.fI3c;
+  fNuclMass = aWeight.fNuclMass;
+  fNuclCharge = aWeight.fNuclCharge;
+  fSphereApp = aWeight.fSphereApp;
+  fT0App = aWeight.fT0App; 
+  fLL = aWeight.fLL;
+  fNuclChargeSign = aWeight.fNuclChargeSign;
+  fSwap = aWeight.fSwap;
+  //  fLLName = aWeight.fLLName; 
+  fNumProcessPair = aWeight.fNumProcessPair;
+  fNumbNonId = aWeight.fNumbNonId;
+  if (fLLName) free(fLLName);
+  fLLName=new char*[fLLMax+1];
+  if (fNumProcessPair) free(fNumProcessPair);
+  fNumProcessPair=new int[fLLMax+1];
+  int i;
+  for (i=1;i<=fLLMax;i++) {fLLName[i]=new char[40];fNumProcessPair[i]=0;}
+  strncpy( fLLName[1],"neutron neutron",40);
+  strncpy( fLLName[2],"proton proton",40);
+  strncpy( fLLName[3],"neutron proton",40);
+  strncpy( fLLName[4],"alpha alpha",40);
+  strncpy( fLLName[5],"pi+ pi-",40);
+  strncpy( fLLName[6],"pi0 pi0",40);
+  strncpy( fLLName[7],"pi+ pi+",40);
+  strncpy( fLLName[8],"neutron deuteron",40);
+  strncpy( fLLName[9],"proton deuteron",40);
+  strncpy( fLLName[10],"pi+ K-",40);
+  strncpy( fLLName[11],"pi+ K+",40);
+  strncpy( fLLName[12],"pi+ proton",40);
+  strncpy( fLLName[13],"pi- proton",40);
+  strncpy( fLLName[14],"K+ K-",40);
+  strncpy( fLLName[15],"K+ K+",40);
+  strncpy( fLLName[16],"K+ proton",40);
+  strncpy( fLLName[17],"K- proton",40);
+  strncpy( fLLName[18],"deuteron deuteron",40);
+  strncpy( fLLName[19],"deuton alpha",40);
+  strncpy( fLLName[20],"triton triton",40);
+  strncpy( fLLName[21],"triton alpha",40);
+  strncpy( fLLName[22],"K0 K0",40);
+  strncpy( fLLName[23],"K0 K0b",40);
+  strncpy( fLLName[24],"deuteron triton",40);
+  strncpy( fLLName[25],"proton triton",40);
+  strncpy( fLLName[26],"proton alpha",40);
+  strncpy( fLLName[27],"proton lambda",40);
+  strncpy( fLLName[28],"neutron lambda",40);
+  strncpy( fLLName[29],"Lambda lambda",40);// gael 21May02
+  strncpy( fLLName[30],"Proton Anti-proton",40);// gael 21May02
+  FsiInit();
+  FsiNucl();
+  
+  return *this;
+}
+
+
+double AliFemtoModelWeightGeneratorLednicky::GenerateWeight(AliFemtoPair* aPair)
+{
+  // Get hidden information pointers
+  AliFemtoModelHiddenInfo *inf1 = (AliFemtoModelHiddenInfo *) aPair->Track1()->HiddenInfo();
+  AliFemtoModelHiddenInfo *inf2 = (AliFemtoModelHiddenInfo *) aPair->Track2()->HiddenInfo();
+
+  // Calculate pair variables
+  Double_t tPx = inf1->GetTrueMomentum()->x()+inf2->GetTrueMomentum()->x();
+  Double_t tPy = inf1->GetTrueMomentum()->y()+inf2->GetTrueMomentum()->y();
+  Double_t tPz = inf1->GetTrueMomentum()->z()+inf2->GetTrueMomentum()->z();
+  Double_t tM1 = inf1->GetMass();
+  Double_t tM2 = inf2->GetMass();
+  Double_t tE1 = sqrt(tM1*tM1 + inf1->GetTrueMomentum()->Mag2());
+  Double_t tE2 = sqrt(tM2*tM2 + inf2->GetTrueMomentum()->Mag2());
+  Double_t tE  = tE1 + tE2;
+  Double_t tPt = tPx*tPx + tPy*tPy;
+  Double_t tMt = tE*tE - tPz*tPz;//mCVK;
+  Double_t tM  = sqrt(tMt - tPt);
+  tMt = sqrt(tMt);
+  tPt = sqrt(tPt);
+  Double_t tBetat = tPt/tMt;
+
+  // Boost to LCMS
+  Double_t tBeta = tPz/tE;
+  Double_t tGamma = tE/tMt;        
+  fKStarLong = tGamma * (inf1->GetTrueMomentum()->z() - tBeta * tE1);
+  Double_t tE1L = tGamma * (tE1  - tBeta * inf1->GetTrueMomentum()->z());
+    
+  // Rotate in transverse plane
+  fKStarOut  = ( inf1->GetTrueMomentum()->x()*tPx + inf1->GetTrueMomentum()->y()*tPy)/tPt;
+  fKStarSide = (-inf1->GetTrueMomentum()->x()*tPy + inf1->GetTrueMomentum()->y()*tPx)/tPt;
+      
+  // Boost to pair cms
+  fKStarOut = tMt/tM * (fKStarOut - tPt/tMt * tE1L);
+  
+  tBetat = tPt/tMt;
+  
+  Double_t tDX = inf1->GetEmissionPoint()->x()-inf2->GetEmissionPoint()->x();
+  Double_t tDY = inf1->GetEmissionPoint()->y()-inf2->GetEmissionPoint()->y();
+  Double_t tRLong = inf1->GetEmissionPoint()->z()-inf2->GetEmissionPoint()->z();
+  Double_t tDTime = inf1->GetEmissionPoint()->t()-inf2->GetEmissionPoint()->t();
+
+  Double_t tROut = (tDX*tPx + tDY*tPy)/tPt;
+  Double_t tRSide = (-tDX*tPy + tDY*tPx)/tPt;
+
+//   cout << "Got points 1 " << inf1->GetEmissionPoint()->x() << "  " <<  inf1->GetEmissionPoint()->y() << " "  << inf1->GetEmissionPoint()->z() << "  " << inf1->GetEmissionPoint()->t() << endl;
+
+//   cout << "Got points 2 " << inf2->GetEmissionPoint()->x() << "  " << inf2->GetEmissionPoint()->y() << " " << inf2->GetEmissionPoint()->z() << "  " << inf2->GetEmissionPoint()->t() << endl;
+
+  fRStarSide = tRSide;
+
+  fRStarLong = tGamma*(tRLong - tBeta* tDTime);
+  Double_t tDTimePairLCMS = tGamma*(tDTime - tBeta* tRLong);
+
+  tBeta = tPt/tMt;
+  tGamma = tMt/tM;
+
+  fRStarOut = tGamma*(tROut - tBeta* tDTimePairLCMS);
+  fRStar = ::sqrt(fRStarOut*fRStarOut + fRStarSide*fRStarSide +
+                          fRStarLong*fRStarLong);
+  fKStar = ::sqrt(fKStarOut*fKStarOut + fKStarSide*fKStarSide + fKStarLong*fKStarLong);
+
+//   cout << "Got out side " << fRStarOut << " " << fRStarSide << endl;
+
+  if (!SetPid(inf1->GetPDGPid(),inf2->GetPDGPid())) {
+    fWeightDen=1.;
+    return 1;    
+  } 
+  else { // Good Pid
+    AliFemtoThreeVector*  p;
+    p=(inf1->GetTrueMomentum());
+    double p1[]={p->x(),p->y(),p->z()};
+    p=(inf2->GetTrueMomentum());
+    double p2[]={p->x(),p->y(),p->z()};
+    if ((p1[0]==p2[0])&&(p1[1]==p2[1])&&(p1[2]==p2[2])) {
+      fWeightDen=0.;
+      return 0;  
+    } 
+    if (fSwap) {
+      fsimomentum(*p2,*p1);
+    } else {
+      fsimomentum(*p1,*p2);
+    }
+    AliFemtoLorentzVector* tPoint;
+    tPoint=(inf1->GetEmissionPoint());
+//     cout << "Pid1:dans GetWeight = " << aThPair->GetPid1() << endl;
+//     cout << "Pid2:dans GetWeight = " << aThPair->GetPid2() << endl;
+//     cout << "LL:in GetWeight = " << mLL << endl;
+
+    double x1[]={tPoint->x(),tPoint->y(),tPoint->z(),tPoint->t()};
+    tPoint=(inf2->GetEmissionPoint());
+    double x2[]={tPoint->x(),tPoint->y(),tPoint->z(),tPoint->t()};
+    if ((x1[0]==x2[0])&&(x1[1]==x2[1])&&(x1[2]==x2[2])&&(x1[3]==x2[3])) {
+      fWeightDen=0.;
+      return 0;  
+    } 
+    if (fSwap) {
+      fsiposition(*x2,*x1);
+    } else {
+      fsiposition(*x1,*x2);
+    }
+    FsiSetLL();
+    ltran12();
+    fsiw(1,fWeif,fWei,fWein);
+
+    if (fI3c==0) return fWein;
+    fWeightDen=fWeif;
+    return fWei;
+  }
+}
+
+AliFemtoString AliFemtoModelWeightGeneratorLednicky::Report() {
+  // create report
+  ostringstream tStr; 
+  tStr << "Lednicky afterburner calculation for  Correlation -  Report" << endl;
+  tStr << "    Setting : Quantum : " << ((fIqs) ? "On" : "Off"); 
+  tStr << " - Coulbomb : " << ((fIch) ? "On" : "Off") ;
+  tStr << " - Strong : " << ((fIsi) ? "On" : "Off");
+  tStr << endl;
+  tStr << "              3-Body : " << ((fI3c) ? "On"  : "Off") ;
+  if (fI3c) tStr << " Mass=" <<  fNuclMass << " - Charge= " << fNuclCharge ;
+  tStr << endl;
+  tStr << "    " << fNumProcessPair[0] << " Pairs have been Processed :" << endl;
+  int i;
+  for(i=1;i<=fLLMax;i++) { 
+    if (fNumProcessPair[i])
+      tStr << "         " << fNumProcessPair[i] << " " << fLLName[i] << endl;
+  }
+  if (fNumbNonId)
+    tStr << "         "<< fNumbNonId << " Non Identified" << endl;
+  AliFemtoString returnThis = tStr.str();
+  return returnThis;
+}
+
+void AliFemtoModelWeightGeneratorLednicky::FsiInit(){
+  // Initialize weight generation module
+//   cout << "*******************AliFemtoModelWeightGeneratorLednicky check FsiInit ************" << endl;
+//   cout <<"mItest dans FsiInit() = " << fItest << endl;
+//   cout <<"mIch dans FsiInit() = " << fIch << endl;
+//   cout <<"mIqs dans FsiInit() = " << fIqs << endl;
+//   cout <<"mIsi dans FsiInit() = " << fIsi << endl;
+//   cout <<"mI3c dans FsiInit() = " << fI3c << endl;
+  fsiin(fItest,fIch,fIqs,fIsi,fI3c);
+}
+
+void AliFemtoModelWeightGeneratorLednicky::FsiNucl(){
+  // initialize weight generation taking into account the residual charge
+//   cout << "*******************AliFemtoModelWeightGeneratorLednicky check FsiNucl ************" << endl;
+//   cout <<"fNuclMass dans FsiNucl() = " << fNuclMass << endl;
+//   cout <<"fNuclCharge dans FsiNucl() = " << fNuclCharge << endl;
+//   cout <<"fNuclChargeSign dans FsiNucl() = " << fNuclChargeSign << endl;
+  fsinucl(fNuclMass,fNuclCharge*fNuclChargeSign);
+}
+
+void AliFemtoModelWeightGeneratorLednicky::FsiSetLL(){
+  // set internal pair type for the module
+  int tNS;
+  if (fSphereApp||(fLL>5)) {
+    if (fT0App) { tNS=4;} 
+    else {tNS=2;}
+  } else { tNS=1;}
+   //cout <<"fLL dans FsiSetLL() = "<< fLL << endl;
+   //cout <<"tNS dans FsiSetLL() = "<< tNS << endl;
+   //cout <<"fItest dans FsiSetLL() = "<< fItest << endl;
+  llini(fLL,tNS,fItest);
+  //cout<<" end of FsiSetLL"<<endl;
+}
+         
+bool AliFemtoModelWeightGeneratorLednicky::SetPid(const int aPid1,const int aPid2) {
+  // set calculated system for basing on particles' pids
+  static const int ksPi0Pid=111;
+  static const int ksPionPid=211; 
+  static const int ksK0Pid=311;
+  static const int ksKPid=321;
+  static const int ksNeutPid=2112;
+  static const int ksProtPid=2212;
+  static const int ksLamPid=3122;
+  //  static const int sLamLamPid=3122;
+
+   // cout << "Setting PID to " << aPid1 << " " << aPid2 << endl;
+
+  int tPidl,tPidh;
+  int tChargeFactor=1;
+  
+  if (abs(aPid1)<abs(aPid2)) {
+    if (aPid1<0) tChargeFactor=-1;
+    tPidl=aPid1*tChargeFactor;
+    tPidh=aPid2*tChargeFactor;
+    fSwap=false;
+  } else {
+    if (aPid2<0) tChargeFactor=-1;
+    tPidl=aPid2*tChargeFactor;
+    tPidh=aPid1*tChargeFactor;
+    fSwap=true;
+  }
+  switch (tPidl) {
+  case ksPionPid:
+    switch (tPidh) {
+    case -ksPionPid:   fLL=5; tChargeFactor*=1 ;break;
+    case ksPionPid:    fLL=7; tChargeFactor*=1 ;break;
+    case -ksKPid:      fLL=10;tChargeFactor*=1 ;break;  
+    case ksKPid:       fLL=11;tChargeFactor*=1 ;break;  
+    case ksProtPid:    fLL=12;tChargeFactor*=1 ;break;
+    case -ksProtPid:   fLL=13;tChargeFactor*=-1;break;
+    default: fLL=0;
+    }
+    break;
+  case ksProtPid:
+    switch (tPidh) {
+    case ksProtPid:    fLL=2; tChargeFactor*=1 ;break;
+    case ksLamPid:     fLL=27;tChargeFactor*=1 ;break;
+    case -ksProtPid:   fLL=30;tChargeFactor*=1 ;break;
+    default: fLL=0;
+    }
+    break;
+  case ksKPid:
+    switch (tPidh) {
+    case -ksKPid:      fLL=14;tChargeFactor*=1 ;break;
+    case ksKPid:       fLL=15;tChargeFactor*=1 ;break;
+    case ksProtPid:    fLL=16;tChargeFactor*=1 ;break;
+    case -ksProtPid:   fLL=17;tChargeFactor*=-1 ;break;
+    default: fLL=0;
+    }
+    break;    
+  case ksK0Pid:
+    switch (tPidh) {
+    case ksK0Pid:         fLL=22;tChargeFactor*=1 ;break;
+    case -ksK0Pid:        fLL=23;tChargeFactor*=1 ;break;
+    default: fLL=0;
+    }
+    break;   
+  case ksPi0Pid:
+    switch (tPidh) {
+    case ksPi0Pid:        fLL=6; tChargeFactor*=1 ;break;
+    default: fLL=0;
+    }
+    break;
+  case ksNeutPid:
+    switch (tPidh) {
+    case ksNeutPid:      fLL=1; tChargeFactor*=1 ;break;
+    case ksProtPid:      fLL=3; tChargeFactor*=1 ;break;
+    case ksLamPid:       fLL=28;tChargeFactor*=1 ;break;
+    default: fLL=0;
+    }
+    break;                                             //Gael 21May02 
+  case ksLamPid:                                        //Gael 21May02 
+    switch (tPidh) {                                   //Gael 21May02 
+    case ksLamPid:       fLL=29;tChargeFactor*=1 ;break;//Gael 21May02  
+    default: fLL=0;                                    //Gael 21May02 
+    }                                                 //Gael 21May02 
+    break;                                             //Gael 21May02 
+  default: fLL=0;
+  }
+  if (tChargeFactor!=fNuclChargeSign) {
+    fNuclChargeSign=tChargeFactor;
+    FsiNucl();
+  }
+  (fNumProcessPair[0])++;
+  if (fLL) {
+    (fNumProcessPair[fLL])++;
+    return true;
+  } else {
+    fNumbNonId++;
+    return false;
+  }
+//   cout << "*******************AliFemtoModelWeightGeneratorLednicky check SetPid ************" << endl;
+//   cout << "fLL=="<< fLL << endl;
+//   cout << "fNuclCharge=="<< fNuclCharge << endl;
+
+}    
+AliFemtoModelWeightGeneratorLednicky::~AliFemtoModelWeightGeneratorLednicky() 
+{ 
+  if (fLLName) delete [] fLLName;
+  if (fNumProcessPair) delete [] fNumProcessPair;
+/* no-op */ 
+}
+
+//_____________________________________________
+void     AliFemtoModelWeightGeneratorLednicky::SetPairType(Int_t aPairType)
+{
+  // set calculated system basing on the pair type
+  fPairType = aPairType;
+  if (fPairType == fgkPionPlusPionPlus) SetPid(211,211);
+  if (fPairType == fgkPionPlusPionMinus ) SetPid(211, -211);
+  if (fPairType == fgkKaonPlusKaonPlus ) SetPid(321, 321);
+  if (fPairType == fgkKaonPlusKaonMinus ) SetPid(321, -321);
+  if (fPairType == fgkProtonProton ) SetPid(2212, 2212);
+  if (fPairType == fgkProtonAntiproton ) SetPid(2212, -2212);
+  if (fPairType == fgkPionPlusKaonPlus ) SetPid(211, 321);
+  if (fPairType == fgkPionPlusKaonMinus ) SetPid(211, -321);
+  if (fPairType == fgkPionPlusProton ) SetPid(211, 2212);
+  if (fPairType == fgkPionPlusAntiproton ) SetPid(211, -2212);
+  if (fPairType == fgkKaonPlusProton ) SetPid(321, 2212);
+  if (fPairType == fgkKaonPlusAntiproton ) SetPid(321, -2212);
+}
+
+//_____________________________________________
+Int_t    AliFemtoModelWeightGeneratorLednicky::GetPairType() const
+{
+  // return pair type
+  return fPairType;
+}
+
+//_____________________________________________
+void     AliFemtoModelWeightGeneratorLednicky::SetPairTypeFromPair(AliFemtoPair *aPair)
+{
+  // set calculated system based on the hidden info in the pair
+  AliFemtoModelHiddenInfo *inf1 = ( AliFemtoModelHiddenInfo *) aPair->Track1()->HiddenInfo();
+  AliFemtoModelHiddenInfo *inf2 = ( AliFemtoModelHiddenInfo *) aPair->Track2()->HiddenInfo();
+
+  const Int_t ktPid1 = inf1->GetPDGPid();
+  const Int_t ktPid2 = inf2->GetPDGPid();
+
+  if      (((ktPid1 ==   211) && (ktPid2 ==   211)) ||
+           ((ktPid1 ==  -211) && (ktPid2 ==  -211)))
+    fPairType = fgkPionPlusPionPlus;
+  else if (((ktPid1 ==  -211) && (ktPid2 ==   211)) ||
+           ((ktPid1 ==   211) && (ktPid2 ==  -211)))
+    fPairType = fgkPionPlusPionMinus;
+  else if (((ktPid1 ==   321) && (ktPid2 ==   321)) ||
+           ((ktPid1 ==  -321) && (ktPid2 ==  -321)))
+    fPairType = fgkKaonPlusKaonPlus;
+  else if (((ktPid1 ==  -321) && (ktPid2 ==   321)) ||
+           ((ktPid1 ==   321) && (ktPid2 ==  -321)))
+    fPairType = fgkKaonPlusKaonMinus;
+  else if (((ktPid1 ==  2212) && (ktPid2 ==  2212)) ||
+           ((ktPid1 == -2212) && (ktPid2 == -2212)))
+    fPairType = fgkProtonProton;
+  else if (((ktPid1 == -2212) && (ktPid2 ==  2212)) ||
+           ((ktPid1 ==  2212) && (ktPid2 == -2212)))
+    fPairType = fgkProtonAntiproton;
+  else if (((ktPid1 ==   211) && (ktPid2 ==   321)) ||
+           ((ktPid1 ==  -211) && (ktPid2 ==  -321)))
+    fPairType = fgkPionPlusKaonPlus;
+  else if (((ktPid1 ==  -211) && (ktPid2 ==   321)) ||
+           ((ktPid1 ==   211) && (ktPid2 ==  -321)))
+    fPairType = fgkPionPlusKaonMinus;
+  else if (((ktPid1 ==   211) && (ktPid2 ==  2212)) ||
+           ((ktPid1 ==  -211) && (ktPid2 == -2212)))
+    fPairType = fgkPionPlusProton;
+  else if (((ktPid1 ==  -211) && (ktPid2 ==  2212)) ||
+           ((ktPid1 ==   211) && (ktPid2 == -2212)))
+    fPairType = fgkPionPlusAntiproton;
+  else if (((ktPid1 ==   321) && (ktPid2 ==  2212)) ||
+           ((ktPid1 ==  -321) && (ktPid2 == -2212)))
+    fPairType = fgkKaonPlusProton;
+  else if (((ktPid1 ==  -321) && (ktPid2 ==  2212)) ||
+           ((ktPid1 ==   321) && (ktPid2 == -2212)))
+    fPairType = fgkKaonPlusAntiproton;
+  SetPid(ktPid1, ktPid2);
+}
+
+void AliFemtoModelWeightGeneratorLednicky::SetNuclCharge(const double aNuclCharge) {fNuclCharge=aNuclCharge;FsiNucl();}
+void AliFemtoModelWeightGeneratorLednicky::SetNuclMass(const double aNuclMass){fNuclMass=aNuclMass;FsiNucl();}
+
+void AliFemtoModelWeightGeneratorLednicky::SetSphere(){fSphereApp=true;}
+void AliFemtoModelWeightGeneratorLednicky::SetSquare(){fSphereApp=false;}
+void AliFemtoModelWeightGeneratorLednicky::SetT0ApproxOn(){ fT0App=true;}
+void AliFemtoModelWeightGeneratorLednicky::SetT0ApproxOff(){ fT0App=false;}
+void AliFemtoModelWeightGeneratorLednicky::SetDefaultCalcPar(){
+  fItest=1;fIqs=1;fIsi=1;fI3c=0;fIch=1;FsiInit();
+  fSphereApp=false;fT0App=false;}
+
+void AliFemtoModelWeightGeneratorLednicky::SetCoulOn()    {fItest=1;fIch=1;FsiInit();}
+void AliFemtoModelWeightGeneratorLednicky::SetCoulOff()   {fItest=1;fIch=0;FsiInit();}
+void AliFemtoModelWeightGeneratorLednicky::SetQuantumOn() {fItest=1;fIqs=1;FsiInit();}
+void AliFemtoModelWeightGeneratorLednicky::SetQuantumOff(){fItest=1;fIqs=0;FsiInit();}
+void AliFemtoModelWeightGeneratorLednicky::SetStrongOn()  {fItest=1;fIsi=1;FsiInit();}
+void AliFemtoModelWeightGeneratorLednicky::SetStrongOff() {fItest=1;fIsi=0;FsiInit();}
+void AliFemtoModelWeightGeneratorLednicky::Set3BodyOn()   {fItest=1;fI3c=1;FsiInit();FsiNucl();}
+void AliFemtoModelWeightGeneratorLednicky::Set3BodyOff()  {fItest=1;fI3c=0;FsiInit();fWeightDen=1.;FsiNucl();}
+
+Double_t AliFemtoModelWeightGeneratorLednicky::GetKStar() const {return AliFemtoModelWeightGenerator::GetKStar();}
+Double_t AliFemtoModelWeightGeneratorLednicky::GetKStarOut() const { return AliFemtoModelWeightGenerator::GetKStarOut(); }
+Double_t AliFemtoModelWeightGeneratorLednicky::GetKStarSide() const { return AliFemtoModelWeightGenerator::GetKStarSide(); }
+Double_t AliFemtoModelWeightGeneratorLednicky::GetKStarLong() const { return AliFemtoModelWeightGenerator::GetKStarLong(); }
+Double_t AliFemtoModelWeightGeneratorLednicky::GetRStar() const { return AliFemtoModelWeightGenerator::GetRStar(); }
+Double_t AliFemtoModelWeightGeneratorLednicky::GetRStarOut() const { return AliFemtoModelWeightGenerator::GetRStarOut(); }
+Double_t AliFemtoModelWeightGeneratorLednicky::GetRStarSide() const { return AliFemtoModelWeightGenerator::GetRStarSide(); }
+Double_t AliFemtoModelWeightGeneratorLednicky::GetRStarLong() const { return AliFemtoModelWeightGenerator::GetRStarLong(); }
+
+AliFemtoModelWeightGenerator* AliFemtoModelWeightGeneratorLednicky::Clone() const {
+  AliFemtoModelWeightGenerator* tmp = new AliFemtoModelWeightGeneratorLednicky(*this);
+  return tmp;
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelWeightGeneratorLednicky.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoModelWeightGeneratorLednicky.h
new file mode 100644 (file)
index 0000000..fb4b153
--- /dev/null
@@ -0,0 +1,110 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFemtoModelWeightGeneratorLednicky : the most advanced weight       //
+// generator available. Supports a large number of different pair types  //
+// and interaction types. Can calculate pair weights coming from         //
+// quantum statistics, coulomb interation and strong interaction ot any  //
+// combination of the three, as applicable.                              //
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+
+#ifndef ALIFEMTOMODELWEIGHTGENERATORLEDNICKY_H
+#define ALIFEMTOMODELWEIGHTGENERATORLEDNICKY_H
+
+#include "AliFemtoTypes.h"
+#include "AliFemtoModelWeightGenerator.h"
+
+class AliFemtoModelWeightGeneratorLednicky : public  AliFemtoModelWeightGenerator {
+ public: 
+// --- Constructor
+  AliFemtoModelWeightGeneratorLednicky(); // call SetDefaultCalcPar
+  AliFemtoModelWeightGeneratorLednicky(const AliFemtoModelWeightGeneratorLednicky &aWeight); // call SetDefaultCalcPar
+// --- Destructor : nothing to explicitly delete
+  AliFemtoModelWeightGeneratorLednicky& operator=(const AliFemtoModelWeightGeneratorLednicky& aWeight);
+  ~AliFemtoModelWeightGeneratorLednicky();
+
+  virtual Double_t GenerateWeight(AliFemtoPair *aPair);
+
+  virtual void     SetPairType(Int_t aPairType);
+  virtual void     SetPairTypeFromPair(AliFemtoPair *aPair);
+  virtual Int_t    GetPairType() const;
+
+  virtual Double_t GetKStar() const;
+  virtual Double_t GetKStarOut() const;
+  virtual Double_t GetKStarSide() const;
+  virtual Double_t GetKStarLong() const;
+  virtual Double_t GetRStar() const;
+  virtual Double_t GetRStarOut() const;
+  virtual Double_t GetRStarSide() const;
+  virtual Double_t GetRStarLong() const;
+
+  virtual AliFemtoModelWeightGenerator* Clone() const;
+
+// --- Setting
+
+// >>> Calculation mode
+  void SetDefaultCalcPar(); // Default is CoulOn, QuantumOn, StrongOn, 3BodyOff, Square, T0ApproxOff
+  void SetCoulOn();
+  void SetCoulOff();
+
+  void SetQuantumOn();
+  void SetQuantumOff();
+  void SetStrongOn();
+  void SetStrongOff();
+  void Set3BodyOn();
+  void Set3BodyOff();
+  void SetSphere(); // use Spherical wave approximation
+  void SetSquare(); // use use Square potential (only for p-p and pi+Pi-) otherwise, use spherical wave approx
+  void SetT0ApproxOff();//only with  Spherical wave Approximation - this is default mode
+  void SetT0ApproxOn(); 
+// Test Lambda parameters
+  void PrintLambdas(){;}
+  
+  void SetNuclCharge(const double aNuclCharge); // for 3-body calculation
+  void SetNuclMass(const double aNuclMass);
+
+  virtual AliFemtoString Report();
+
+protected:
+  // Fsi weight output
+  double  fWei;  // normal weight
+  double  fWein; // weight with nuclear influence
+  double  fWeif; // weight
+  double  fWeightDen; // weight for the denominator
+
+  // Setting parameters
+  int fItest;    // if set to 1 default parameters will be used
+
+  //int mNs;
+  int    fIch;        // switch coulomb interaction on/off
+  int    fIqs;        // switch quantum statistics on/off
+  int    fIsi;        // switch strong interaction on/off
+  int    fI3c;        // switch 3rd body influence on/off
+  double fNuclMass;   // mass of the third body
+  double fNuclCharge; // charge of the third body
+
+  bool   fSphereApp;       // use spherical approximation
+  bool   fT0App;           // use square well approximation
+
+  //Pair identification
+  int       fLL;             // internal pair type code
+  short     fNuclChargeSign; // sign of the 3rd body charge
+  bool      fSwap;           // are particle in right order ? 
+  int const fLLMax;          // number of supported pairs
+  char**    fLLName;         // name of the system
+  int *     fNumProcessPair; // number of process pairs of each type
+  int       fNumbNonId;      // Number of unidentified pairs
+
+  // Interface to the fortran functions
+  void FsiInit();
+  void FsiSetLL();
+  void FsiNucl();
+  bool SetPid(const int aPid1,const int aPid2);
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoModelWeightGeneratorLednicky,1)
+#endif
+};
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoPair.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoPair.cxx
new file mode 100644 (file)
index 0000000..4481ae0
--- /dev/null
@@ -0,0 +1,1212 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFemtoPair: the Pair object is passed to the PairCuts for           //
+// verification, and then to the AddRealPair and AddMixedPair methods of //
+// the Correlation Functions. It holds pair-specific variables like      //
+// relative momenta and has links to the particles and tracks that form  //
+// the pair.                                                             //
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+#include <TMath.h>
+#include "AliFemtoPair.h"
+
+double AliFemtoPair::fgMaxDuInner = .8;
+double AliFemtoPair::fgMaxDzInner = 3.;
+double AliFemtoPair::fgMaxDuOuter = 1.4;
+double AliFemtoPair::fgMaxDzOuter = 3.2;
+
+
+AliFemtoPair::AliFemtoPair() :
+  fTrack1(0), fTrack2(0),
+  fPairAngleEP(0),
+  fNonIdParNotCalculated(0),
+  fDKSide(0),
+  fDKOut(0),
+  fDKLong(0),
+  fCVK(0),
+  fKStarCalc(0),
+  fNonIdParNotCalculatedGlobal(0),
+  fMergingParNotCalculated(0),
+  fWeightedAvSep(0),
+  fFracOfMergedRow(0),
+  fClosestRowAtDCA(0),
+  fMergingParNotCalculatedTrkV0Pos(0),
+  fFracOfMergedRowTrkV0Pos(0),
+  fClosestRowAtDCATrkV0Pos(0),
+  fMergingParNotCalculatedTrkV0Neg(0),
+  fFracOfMergedRowTrkV0Neg(0),
+  fClosestRowAtDCATrkV0Neg(0),
+  fMergingParNotCalculatedV0PosV0Neg(0),
+  fFracOfMergedRowV0PosV0Neg(0),
+  fClosestRowAtDCAV0PosV0Neg(0),
+  fMergingParNotCalculatedV0NegV0Pos(0),
+  fFracOfMergedRowV0NegV0Pos(0),
+  fClosestRowAtDCAV0NegV0Pos(0),
+  fMergingParNotCalculatedV0PosV0Pos(0),
+  fFracOfMergedRowV0PosV0Pos(0),
+  fClosestRowAtDCAV0PosV0Pos(0),
+  fMergingParNotCalculatedV0NegV0Neg(0),
+  fFracOfMergedRowV0NegV0Neg(0),
+  fClosestRowAtDCAV0NegV0Neg(0)
+{
+  // Default constructor
+  fTrack1 = 0;
+  fTrack2 = 0;
+  SetDefaultHalfFieldMergingPar();
+}
+
+AliFemtoPair::AliFemtoPair(AliFemtoParticle* a, AliFemtoParticle* b)
+  : fTrack1(a), fTrack2(b),
+  fPairAngleEP(0),
+  fNonIdParNotCalculated(0),
+  fDKSide(0),
+  fDKOut(0),
+  fDKLong(0),
+  fCVK(0),
+  fKStarCalc(0),
+  fNonIdParNotCalculatedGlobal(0),
+  fMergingParNotCalculated(0),
+  fWeightedAvSep(0),
+  fFracOfMergedRow(0),
+  fClosestRowAtDCA(0),
+  fMergingParNotCalculatedTrkV0Pos(0),
+  fFracOfMergedRowTrkV0Pos(0),
+  fClosestRowAtDCATrkV0Pos(0),
+  fMergingParNotCalculatedTrkV0Neg(0),
+  fFracOfMergedRowTrkV0Neg(0),
+  fClosestRowAtDCATrkV0Neg(0),
+  fMergingParNotCalculatedV0PosV0Neg(0),
+  fFracOfMergedRowV0PosV0Neg(0),
+  fClosestRowAtDCAV0PosV0Neg(0),
+  fMergingParNotCalculatedV0NegV0Pos(0),
+  fFracOfMergedRowV0NegV0Pos(0),
+  fClosestRowAtDCAV0NegV0Pos(0),
+  fMergingParNotCalculatedV0PosV0Pos(0),
+  fFracOfMergedRowV0PosV0Pos(0),
+  fClosestRowAtDCAV0PosV0Pos(0),
+  fMergingParNotCalculatedV0NegV0Neg(0),
+  fFracOfMergedRowV0NegV0Neg(0),
+  fClosestRowAtDCAV0NegV0Neg(0)
+{ 
+  // Construct a pair from two particles
+  SetDefaultHalfFieldMergingPar();
+}
+
+void AliFemtoPair::SetDefaultHalfFieldMergingPar(){
+  fgMaxDuInner = 3;
+  fgMaxDzInner = 4.;
+  fgMaxDuOuter = 4.;
+  fgMaxDzOuter = 6.;
+}
+void AliFemtoPair::SetDefaultFullFieldMergingPar(){
+  // Set default TPC merging parameters for STAR TPC
+  fgMaxDuInner = 0.8;
+  fgMaxDzInner = 3.;
+  fgMaxDuOuter = 1.4;
+  fgMaxDzOuter = 3.2;
+}
+void AliFemtoPair::SetMergingPar(double aMaxDuInner, double aMaxDzInner,
+                             double aMaxDuOuter, double aMaxDzOuter)
+{
+  // Set TPC merging parameters for STAR TPC
+  fgMaxDuInner = aMaxDuInner;
+  fgMaxDzInner = aMaxDzInner;
+  fgMaxDuOuter = aMaxDuOuter;
+  fgMaxDzOuter = aMaxDzOuter;
+}
+
+AliFemtoPair::~AliFemtoPair() {
+  // Destructor
+/* no-op */
+}
+
+AliFemtoPair::AliFemtoPair(const AliFemtoPair &aPair):
+  fTrack1(0), fTrack2(0),
+  fPairAngleEP(0),
+  fNonIdParNotCalculated(0),
+  fDKSide(0),
+  fDKOut(0),
+  fDKLong(0),
+  fCVK(0),
+  fKStarCalc(0),
+  fNonIdParNotCalculatedGlobal(0),
+  fMergingParNotCalculated(0),
+  fWeightedAvSep(0),
+  fFracOfMergedRow(0),
+  fClosestRowAtDCA(0),
+  fMergingParNotCalculatedTrkV0Pos(0),
+  fFracOfMergedRowTrkV0Pos(0),
+  fClosestRowAtDCATrkV0Pos(0),
+  fMergingParNotCalculatedTrkV0Neg(0),
+  fFracOfMergedRowTrkV0Neg(0),
+  fClosestRowAtDCATrkV0Neg(0),
+  fMergingParNotCalculatedV0PosV0Neg(0),
+  fFracOfMergedRowV0PosV0Neg(0),
+  fClosestRowAtDCAV0PosV0Neg(0),
+  fMergingParNotCalculatedV0NegV0Pos(0),
+  fFracOfMergedRowV0NegV0Pos(0),
+  fClosestRowAtDCAV0NegV0Pos(0),
+  fMergingParNotCalculatedV0PosV0Pos(0),
+  fFracOfMergedRowV0PosV0Pos(0),
+  fClosestRowAtDCAV0PosV0Pos(0),
+  fMergingParNotCalculatedV0NegV0Neg(0),
+  fFracOfMergedRowV0NegV0Neg(0),
+  fClosestRowAtDCAV0NegV0Neg(0)
+{
+  // Copy constructor
+  fTrack1 = aPair.fTrack1;
+  fTrack2 = aPair.fTrack2;
+
+  fNonIdParNotCalculated = aPair.fNonIdParNotCalculated;
+  fDKSide = aPair.fDKSide;
+  fDKOut = aPair.fDKOut;
+  fDKLong = aPair.fDKLong;
+  fCVK = aPair.fCVK;
+  fKStarCalc = aPair.fKStarCalc;
+
+  fNonIdParNotCalculatedGlobal = aPair.fNonIdParNotCalculatedGlobal;
+
+  fMergingParNotCalculated = aPair.fMergingParNotCalculated;
+  fWeightedAvSep = aPair.fWeightedAvSep;
+  fFracOfMergedRow = aPair.fFracOfMergedRow;
+  fClosestRowAtDCA = aPair.fClosestRowAtDCA;
+
+  fMergingParNotCalculatedTrkV0Pos = aPair.fMergingParNotCalculatedTrkV0Pos;
+  fFracOfMergedRowTrkV0Pos = aPair.fFracOfMergedRowTrkV0Pos;
+  fClosestRowAtDCATrkV0Pos = aPair.fClosestRowAtDCATrkV0Pos;
+
+  fMergingParNotCalculatedTrkV0Neg = aPair.fMergingParNotCalculatedTrkV0Neg;
+  fFracOfMergedRowTrkV0Neg = aPair.fFracOfMergedRowTrkV0Neg;
+  fClosestRowAtDCATrkV0Neg = aPair.fClosestRowAtDCATrkV0Neg;
+
+  fMergingParNotCalculatedV0PosV0Neg = aPair.fMergingParNotCalculatedV0PosV0Neg;
+  fFracOfMergedRowV0PosV0Neg = aPair.fFracOfMergedRowV0PosV0Neg;
+  fClosestRowAtDCAV0PosV0Neg = aPair.fClosestRowAtDCAV0PosV0Neg;
+
+  fMergingParNotCalculatedV0NegV0Pos = aPair.fMergingParNotCalculatedV0NegV0Pos;
+  fFracOfMergedRowV0NegV0Pos = aPair.fFracOfMergedRowV0NegV0Pos;
+  fClosestRowAtDCAV0NegV0Pos = aPair.fClosestRowAtDCAV0NegV0Pos;
+
+  fMergingParNotCalculatedV0PosV0Pos = aPair.fMergingParNotCalculatedV0PosV0Pos;
+  fFracOfMergedRowV0PosV0Pos = aPair.fFracOfMergedRowV0PosV0Pos;
+  fClosestRowAtDCAV0PosV0Pos = aPair.fClosestRowAtDCAV0PosV0Pos;
+
+  fMergingParNotCalculatedV0NegV0Neg = aPair.fMergingParNotCalculatedV0NegV0Neg;
+  fFracOfMergedRowV0NegV0Neg = aPair.fFracOfMergedRowV0NegV0Neg;
+  fClosestRowAtDCAV0NegV0Neg = aPair.fClosestRowAtDCAV0NegV0Neg;
+}
+
+AliFemtoPair& AliFemtoPair::operator=(const AliFemtoPair &aPair)
+{
+  // Assignment operator
+  if (this == &aPair)
+    return *this;
+
+  fTrack1 = aPair.fTrack1;
+  fTrack2 = aPair.fTrack2;
+
+  fNonIdParNotCalculated = aPair.fNonIdParNotCalculated;
+  fDKSide = aPair.fDKSide;
+  fDKOut = aPair.fDKOut;
+  fDKLong = aPair.fDKLong;
+  fCVK = aPair.fCVK;
+  fKStarCalc = aPair.fKStarCalc;
+
+  fNonIdParNotCalculatedGlobal = aPair.fNonIdParNotCalculatedGlobal;
+
+  fMergingParNotCalculated = aPair.fMergingParNotCalculated;
+  fWeightedAvSep = aPair.fWeightedAvSep;
+  fFracOfMergedRow = aPair.fFracOfMergedRow;
+  fClosestRowAtDCA = aPair.fClosestRowAtDCA;
+
+  fMergingParNotCalculatedTrkV0Pos = aPair.fMergingParNotCalculatedTrkV0Pos;
+  fFracOfMergedRowTrkV0Pos = aPair.fFracOfMergedRowTrkV0Pos;
+  fClosestRowAtDCATrkV0Pos = aPair.fClosestRowAtDCATrkV0Pos;
+
+  fMergingParNotCalculatedTrkV0Neg = aPair.fMergingParNotCalculatedTrkV0Neg;
+  fFracOfMergedRowTrkV0Neg = aPair.fFracOfMergedRowTrkV0Neg;
+  fClosestRowAtDCATrkV0Neg = aPair.fClosestRowAtDCATrkV0Neg;
+
+  fMergingParNotCalculatedV0PosV0Neg = aPair.fMergingParNotCalculatedV0PosV0Neg;
+  fFracOfMergedRowV0PosV0Neg = aPair.fFracOfMergedRowV0PosV0Neg;
+  fClosestRowAtDCAV0PosV0Neg = aPair.fClosestRowAtDCAV0PosV0Neg;
+
+  fMergingParNotCalculatedV0NegV0Pos = aPair.fMergingParNotCalculatedV0NegV0Pos;
+  fFracOfMergedRowV0NegV0Pos = aPair.fFracOfMergedRowV0NegV0Pos;
+  fClosestRowAtDCAV0NegV0Pos = aPair.fClosestRowAtDCAV0NegV0Pos;
+
+  fMergingParNotCalculatedV0PosV0Pos = aPair.fMergingParNotCalculatedV0PosV0Pos;
+  fFracOfMergedRowV0PosV0Pos = aPair.fFracOfMergedRowV0PosV0Pos;
+  fClosestRowAtDCAV0PosV0Pos = aPair.fClosestRowAtDCAV0PosV0Pos;
+
+  fMergingParNotCalculatedV0NegV0Neg = aPair.fMergingParNotCalculatedV0NegV0Neg;
+  fFracOfMergedRowV0NegV0Neg = aPair.fFracOfMergedRowV0NegV0Neg;
+  fClosestRowAtDCAV0NegV0Neg = aPair.fClosestRowAtDCAV0NegV0Neg;
+
+  return *this;
+}
+
+//________________________
+double AliFemtoPair::GetPairAngleEP() const
+{
+       return fPairAngleEP;
+}
+//_________________
+double AliFemtoPair::MInv() const
+{
+  // invariant mass
+    double tInvariantMass = abs(fTrack1->FourMomentum() + fTrack2->FourMomentum());
+    return (tInvariantMass);
+}
+//_________________
+double AliFemtoPair::KT() const
+{
+  // transverse momentum
+  double  tmp = 
+    (fTrack1->FourMomentum() + fTrack2->FourMomentum()).Perp();
+  tmp *= .5;
+
+  return (tmp);
+}
+//_________________
+double AliFemtoPair::Rap() const
+{
+  // longitudinal pair rapidity : Y = 0.5 ::log( E1 + E2 + pz1 + pz2 / E1 + E2 - pz1 - pz2 )
+  double  tmp = 0.5 * log (
+                          (fTrack1->FourMomentum().e() + fTrack2->FourMomentum().e() + fTrack1->FourMomentum().z() + fTrack2->FourMomentum().z()) / 
+                          (fTrack1->FourMomentum().e() + fTrack2->FourMomentum().e() - fTrack1->FourMomentum().z() - fTrack2->FourMomentum().z()) 
+                          ) ;
+  return (tmp);
+}
+//_________________
+double AliFemtoPair::EmissionAngle() const {
+  // emission angle
+  double pxTotal = this->FourMomentumSum().x();
+  double pyTotal = this->FourMomentumSum().y();
+  double angle = atan2(pyTotal,pxTotal)*180.0/3.1415926536;
+  if (angle<0.0) angle+=360.0;
+  return angle;
+}
+//_________________
+// get rid of ambiguously-named method fourMomentum() and replace it with
+// fourMomentumSum() and fourMomentumDiff() - mal 13feb2000
+AliFemtoLorentzVector AliFemtoPair::FourMomentumSum() const
+{
+  // total momentum
+  AliFemtoLorentzVector temp = fTrack1->FourMomentum()+fTrack2->FourMomentum();
+  return temp;
+}
+AliFemtoLorentzVector AliFemtoPair::FourMomentumDiff() const
+{
+  // momentum difference
+  AliFemtoLorentzVector temp = fTrack1->FourMomentum()-fTrack2->FourMomentum();
+  return temp;
+}
+//__________________________________
+void AliFemtoPair::QYKPCMS(double& qP, double& qT, double& q0) const
+{
+  // Yano-Koonin-Podgoretskii Parametrisation in CMS
+  ////
+  // calculate momentum difference in source rest frame (= lab frame)
+  ////
+  AliFemtoLorentzVector l1 = fTrack1->FourMomentum() ;
+  AliFemtoLorentzVector l2 = fTrack2->FourMomentum() ;
+  AliFemtoLorentzVector  l ;
+  // random ordering of the particles
+  if ( rand()/(double)RAND_MAX > 0.50 )  
+    { l = l1-l2 ; } 
+  else 
+    { l = l2-l1 ; } ;
+  // fill momentum differences into return variables
+  qP = l.z() ;
+  qT = l.vect().Perp() ;
+  q0 = l.e() ;
+}
+//___________________________________
+void AliFemtoPair::QYKPLCMS(double& qP, double& qT, double& q0) const
+{
+  // Yano-Koonin-Podgoretskii Parametrisation in LCMS
+  ////
+  //  calculate momentum difference in LCMS : frame where pz1 + pz2 = 0
+  ////
+  AliFemtoLorentzVector l1 = fTrack1->FourMomentum() ;
+  AliFemtoLorentzVector l2 = fTrack2->FourMomentum() ;
+  // determine beta to LCMS
+  double beta = (l1.z()+l2.z()) / (l1.e()+l2.e()) ;
+  double beta2 =  beta*beta ;
+  // unfortunately STAR Class lib knows only boost(particle) not boost(beta) :(
+  // -> create particle with velocity beta and mass 1.0
+  // actually this is : dummyPz = ::sqrt( (dummyMass*dummyMass*beta2) / (1-beta2) ) ; 
+  double dummyPz = ::sqrt( (beta2) / (1-beta2) ) ;
+  // boost in the correct direction
+  if (beta>0.0) { dummyPz = -dummyPz; } ;
+  // create dummy particle
+  AliFemtoLorentzVector  l(0.0, 0.0, dummyPz) ; 
+  double dummyMass = 1.0 ;
+  l.SetE(l.vect().MassHypothesis(dummyMass) );
+  // boost particles along the beam into a frame with velocity beta 
+  AliFemtoLorentzVector l1boosted = l1.boost(l) ;
+  AliFemtoLorentzVector l2boosted = l2.boost(l) ;
+  // caculate the momentum difference with random ordering of the particle
+  if ( rand()/(double)RAND_MAX >0.50)  
+    { l = l1boosted-l2boosted ; } 
+  else 
+    { l = l2boosted-l1boosted ;} ;
+  // fill momentum differences into return variables
+  qP = l.z() ;
+  qT = l.vect().Perp() ;
+  q0 = l.e() ;
+}
+//___________________________________
+// Yano-Koonin-Podgoretskii Parametrisation in pair rest frame
+void AliFemtoPair::QYKPPF(double& qP, double& qT, double& q0) const
+{
+  ////
+  //  calculate momentum difference in pair rest frame : frame where (pz1 + pz2, py1 + py2, px1 + px2) = (0,0,0)
+  ////
+  AliFemtoLorentzVector l1 = fTrack1->FourMomentum() ;
+  AliFemtoLorentzVector l2 = fTrack2->FourMomentum() ;
+  // the center of gravity of the pair travels with l
+  AliFemtoLorentzVector  l = l1 + l2 ; 
+  l = -l ;
+  l.SetE(-l.e()) ;
+  // boost particles  
+  AliFemtoLorentzVector l1boosted = l1.boost(l) ;
+  AliFemtoLorentzVector l2boosted = l2.boost(l) ;
+  // caculate the momentum difference with random ordering of the particle
+  if ( rand()/(double)RAND_MAX > 0.50)  
+    { l = l1boosted-l2boosted ; } 
+  else 
+    { l = l2boosted-l1boosted ;} ;
+  // fill momentum differences into return variables
+  qP = l.z();
+  qT = l.vect().Perp();
+  q0 = l.e();
+}
+//_________________
+double AliFemtoPair::QOutCMS() const
+{
+  // relative momentum out component in lab frame
+    AliFemtoThreeVector tmp1 = fTrack1->FourMomentum().vect();
+    AliFemtoThreeVector tmp2 = fTrack2->FourMomentum().vect();
+
+    double dx = tmp1.x() - tmp2.x();
+    double xt = tmp1.x() + tmp2.x();
+    
+    double dy = tmp1.y() - tmp2.y();
+    double yt = tmp1.y() + tmp2.y();
+
+    double k1 = (::sqrt(xt*xt+yt*yt));
+    double k2 = (dx*xt+dy*yt);
+    double tmp = k2/k1;
+    return (tmp);
+}
+//_________________
+double AliFemtoPair::QSideCMS() const
+{
+  // relative momentum side component in lab frame
+    AliFemtoThreeVector tmp1 = fTrack1->FourMomentum().vect();
+    AliFemtoThreeVector tmp2 = fTrack2->FourMomentum().vect();
+
+    double x1 = tmp1.x();  double y1 = tmp1.y();
+    double x2 = tmp2.x();  double y2 = tmp2.y();
+
+    double xt = x1+x2;  double yt = y1+y2;
+    double k1 = ::sqrt(xt*xt+yt*yt);
+
+    double tmp = 2.0*(x2*y1-x1*y2)/k1;
+    return (tmp);
+}
+
+//_________________________
+double AliFemtoPair::QLongCMS() const
+{
+  // relative momentum component in lab frame
+    AliFemtoLorentzVector tmp1 = fTrack1->FourMomentum();
+    AliFemtoLorentzVector tmp2 = fTrack2->FourMomentum();
+
+    double dz = tmp1.z() - tmp2.z();
+    double zz = tmp1.z() + tmp2.z();
+
+    double dt = tmp1.t() - tmp2.t();
+    double tt = tmp1.t() + tmp2.t();
+
+    double beta = zz/tt;
+    double gamma = 1.0/TMath::Sqrt((1.-beta)*(1.+beta));
+
+    double temp = gamma*(dz - beta*dt);
+    return (temp);
+}
+
+//________________________________
+double AliFemtoPair::QOutPf() const
+{
+  // relative momentum out component in pair frame
+  AliFemtoLorentzVector tmp1 = fTrack1->FourMomentum();
+  AliFemtoLorentzVector tmp2 = fTrack2->FourMomentum();
+  
+  double dt = tmp1.t() - tmp2.t();
+  double tt = tmp1.t() + tmp2.t();
+  
+  double xt = tmp1.x() + tmp2.x();
+  double yt = tmp1.y() + tmp2.y();
+  
+  double k1 = ::sqrt(xt*xt + yt*yt);
+  double bOut = k1/tt;
+  double gOut = 1.0/TMath::Sqrt((1.-bOut)*(1.+bOut));
+  
+  double temp = gOut*(QOutCMS() - bOut*dt);
+  return (temp);
+}
+
+//___________________________________
+double AliFemtoPair::QSidePf() const
+{
+  // relative momentum side component in pair frame
+
+ return(this->QSideCMS());
+}
+
+//___________________________________
+
+double AliFemtoPair::QLongPf() const
+{
+  // relative momentum long component in pair frame
+
+  return(this->QLongCMS());
+}
+
+//___________________________________
+double AliFemtoPair::QOutBf(double /* beta */) const
+{
+  // relative momentum out component
+ return(this->QOutCMS());
+}
+
+//___________________________________
+
+double AliFemtoPair::QSideBf(double /* beta */) const
+{
+  // relative momentum side component 
+ return(this->QSideCMS());
+}
+
+//___________________________________
+double AliFemtoPair::QLongBf(double beta) const
+{
+  // relative momentum long component 
+    AliFemtoLorentzVector tmp1 = fTrack1->FourMomentum();
+    AliFemtoLorentzVector tmp2 = fTrack2->FourMomentum();
+
+    double dz = tmp1.z() - tmp2.z();
+    double dt = tmp1.t() + tmp2.t();
+
+    double gamma = 1.0/::sqrt((1.-beta)*(1.+beta));
+
+    double temp = gamma*(dz - beta*dt);
+    return (temp);
+}
+
+double AliFemtoPair::Quality() const {
+  // Calculate split quality of the pair
+  unsigned long mapMask0 = 0xFFFFFF00;
+  unsigned long mapMask1 = 0x1FFFFF;
+  unsigned long padRow1To24Track1 = fTrack1->TopologyMap(0) & mapMask0;
+  unsigned long padRow25To45Track1 = fTrack1->TopologyMap(1) & mapMask1;
+  unsigned long padRow1To24Track2 = fTrack2->TopologyMap(0) & mapMask0;
+  unsigned long padRow25To45Track2 = fTrack2->TopologyMap(1) & mapMask1;
+  // AND logic
+  unsigned long bothPads1To24 = padRow1To24Track1 & padRow1To24Track2;
+  unsigned long bothPads25To45 = padRow25To45Track1 & padRow25To45Track2;
+  // XOR logic
+  unsigned long onePad1To24 = padRow1To24Track1 ^ padRow1To24Track2;
+  unsigned long onePad25To45 = padRow25To45Track1 ^ padRow25To45Track2;
+  unsigned long bitI;
+  int ibits;
+  int tQuality = 0;
+  double normQual = 0.0;
+  int tMaxQuality = fTrack1->NumberOfHits() + fTrack2->NumberOfHits();
+  for (ibits=8;ibits<=31;ibits++) {
+    bitI = 0;
+    bitI |= 1UL<<(ibits);
+    if ( onePad1To24 & bitI ) {
+      tQuality++;
+      continue;
+    }
+    else{
+      if ( bothPads1To24 & bitI ) tQuality--;
+    }
+  }
+  for (ibits=0;ibits<=20;ibits++) {
+    bitI = 0;
+    bitI |= 1UL<<(ibits);
+    if ( onePad25To45 & bitI ) {
+      tQuality++;
+      continue;
+    }
+    else{
+      if ( bothPads25To45 & bitI ) tQuality--;
+    }
+  }
+  normQual = (double)tQuality/( (double) tMaxQuality );
+  return ( normQual );
+
+}
+
+double AliFemtoPair::Quality2() const {
+  // second implementation of split quality
+  unsigned long mapMask0 = 0xFFFFFF00;
+  unsigned long mapMask1 = 0x1FFFFF;
+  unsigned long padRow1To24Track1 = fTrack1->TopologyMap(0) & mapMask0;
+  unsigned long padRow25To45Track1 = fTrack1->TopologyMap(1) & mapMask1;
+  unsigned long padRow1To24Track2 = fTrack2->TopologyMap(0) & mapMask0;
+  unsigned long padRow25To45Track2 = fTrack2->TopologyMap(1) & mapMask1;
+
+  // AND logic
+  //unsigned long bothPads1To24 = padRow1To24Track1 & padRow1To24Track2;
+  //unsigned long bothPads25To45 = padRow25To45Track1 & padRow25To45Track2;
+
+  // XOR logic
+  unsigned long onePad1To24 = padRow1To24Track1 ^ padRow1To24Track2;
+  unsigned long onePad25To45 = padRow25To45Track1 ^ padRow25To45Track2;
+  unsigned long bitI;
+  int ibits;
+  int tQuality = 0;
+  double normQual = 0.0;
+  int tMaxQuality = fTrack1->NumberOfHits() + fTrack2->NumberOfHits();
+  for (ibits=8;ibits<=31;ibits++) {
+    bitI = 0;
+    bitI |= 1UL<<(ibits);
+    if ( onePad1To24 & bitI ) {
+      tQuality++;
+      continue;
+    }
+    //else{
+    //if ( bothPads1To24 & bitI ) tQuality--;
+    //}
+  }
+  for (ibits=0;ibits<=20;ibits++) {
+    bitI = 0;
+    bitI |= 1UL<<(ibits);
+    if ( onePad25To45 & bitI ) {
+      tQuality++;
+      continue;
+    }
+    //else{
+    //if ( bothPads25To45 & bitI ) tQuality--;
+    //}
+  }
+  normQual = (double)tQuality/( (double) tMaxQuality );
+  return ( normQual );
+
+}
+
+
+double AliFemtoPair::NominalTpcExitSeparation() const {
+  // separation at exit from STAR TPC
+  AliFemtoThreeVector diff = fTrack1->Track()->NominalTpcExitPoint() - fTrack2->Track()->NominalTpcExitPoint();
+  return (diff.Mag());
+}
+
+double AliFemtoPair::NominalTpcEntranceSeparation() const {
+  // separation at entrance to STAR TPC
+  AliFemtoThreeVector diff = fTrack1->Track()->NominalTpcEntrancePoint() - fTrack2->Track()->NominalTpcEntrancePoint();
+  return (diff.Mag());
+}
+
+// double AliFemtoPair::NominalTpcAverageSeparation() const {
+//   // average separation in STAR TPC
+//   AliFemtoThreeVector diff;
+//   double tAveSep = 0.0;
+//   int ipt = 0;
+//   if (fTrack1->fNominalPosSample && fTrack2->fNominalPosSample){
+//   while (fabs(fTrack1->fNominalPosSample[ipt].x())<9999. &&
+//      fabs(fTrack1->fNominalPosSample[ipt].y())<9999. && 
+//      fabs(fTrack1->fNominalPosSample[ipt].z())<9999. &&
+//      fabs(fTrack2->fNominalPosSample[ipt].x())<9999. &&
+//      fabs(fTrack2->fNominalPosSample[ipt].y())<9999. && 
+//      fabs(fTrack2->fNominalPosSample[ipt].z())<9999. &&
+//      ipt<11
+//      ){
+//     //  for (int ipt=0; ipt<11; ipt++){
+//     diff = fTrack1->fNominalPosSample[ipt] - fTrack2->fNominalPosSample[ipt];
+//     ipt++;
+//     tAveSep += diff.Mag();
+//   }
+//   tAveSep = tAveSep/(ipt+1.);
+//   return (tAveSep);}
+//   else return -1;
+// }
+
+double AliFemtoPair::OpeningAngle() const {
+  // opening angle
+ return 57.296* fTrack1->FourMomentum().vect().Angle( fTrack2->FourMomentum().vect() );
+//   AliFemtoThreeVector p1 = fTrack1->FourMomentum().vect();
+//   AliFemtoThreeVector p2 = fTrack2->FourMomentum().vect();
+//   return 57.296*(p1.phi()-p2.phi());
+//   //double dAngInv = 57.296*acos((p1.dot(p2))/(p1.Mag()*p2.Mag()));
+//   //return (dAngInv);
+}
+//_________________
+
+
+double AliFemtoPair::KStarFlipped() const {
+  // kstar with sign flipped
+  AliFemtoLorentzVector tP1 = fTrack1->FourMomentum();
+
+  AliFmThreeVectorD qwe = tP1.vect();
+  qwe *= -1.; // flip it
+  tP1.SetVect(qwe);
+  
+  AliFemtoLorentzVector tSum = (tP1+fTrack2->FourMomentum());
+  double tMass = abs(tSum);
+  AliFmThreeVectorD tGammaBeta = (1./tMass)*tSum.vect(); 
+  double tGamma = tSum.e()/tMass;
+  AliFmThreeVectorD tLongMom  = ((tP1.vect()*tGammaBeta)/
+                             (tGammaBeta*tGammaBeta))*tGammaBeta;
+  AliFmLorentzVectorD tK(tGamma*tP1.e() - tP1.vect()*tGammaBeta,
+                     tP1.vect() + (tGamma-1.)*tLongMom - tP1.e()*tGammaBeta);
+//VP  tP1.vect() *= -1.; // unflip it
+  return tK.vect().Mag();
+}
+
+//double AliFemtoPair::CVK() const{
+//const AliFemtoLorentzVector& tP1 = fTrack1->FourMomentum();
+//AliFemtoLorentzVector tSum = (tP1+fTrack2->FourMomentum());
+//double tMass = abs(tSum);
+//AliFmThreeVectorD tGammaBeta = (1./tMass)*tSum.vect(); 
+//double tGamma = tSum.e()/tMass;
+//AliFmThreeVectorD tLongMom  = ((tP1.vect()*tGammaBeta)/
+//                   (tGammaBeta*tGammaBeta))*tGammaBeta;
+//AliFmLorentzVectorD tK(tGamma*tP1.e() - tP1.vect()*tGammaBeta,
+//           tP1.vect() + (tGamma-1.)*tLongMom - tP1.e()*tGammaBeta);
+//return (tK.vect())*tGammaBeta/tK.vect().Magnitude()/tGammaBeta.Magnitude();
+//}
+
+double AliFemtoPair::CVKFlipped() const{
+  // CVK with sign flipped
+  AliFemtoLorentzVector tP1 = fTrack1->FourMomentum();
+  AliFmThreeVectorD qwe = tP1.vect();
+  qwe *= -1.; // flip it
+  tP1.SetVect(qwe);
+  
+  AliFemtoLorentzVector tSum = (tP1+fTrack2->FourMomentum());
+  double tMass = abs(tSum);
+  AliFmThreeVectorD tGammaBeta = (1./tMass)*tSum.vect(); 
+  double tGamma = tSum.e()/tMass;
+  AliFmThreeVectorD tLongMom  = ((tP1.vect()*tGammaBeta)/
+                             (tGammaBeta*tGammaBeta))*tGammaBeta;
+  AliFmLorentzVectorD tK(tGamma*tP1.e() - tP1.vect()*tGammaBeta,
+                     tP1.vect() + (tGamma-1.)*tLongMom - tP1.e()*tGammaBeta);
+//VP  tP1.vect() *= -1.; // unflip it
+  return (tK.vect())*tGammaBeta/tGamma;
+}
+
+double AliFemtoPair::PInv() const{
+  // invariant total momentum
+  AliFemtoLorentzVector tP1 = fTrack1->FourMomentum();
+  AliFemtoLorentzVector tP2 = fTrack2->FourMomentum();
+  double tP = (tP1.px()+tP2.px())*(tP1.px()+tP2.px())+
+              (tP1.py()+tP2.py())*(tP1.py()+tP2.py())+
+              (tP1.pz()+tP2.pz())*(tP1.pz()+tP2.pz())-
+              (tP1.e() -tP2.e() )*(tP1.e() -tP2.e() );
+  return ::sqrt(fabs(tP));
+}
+
+double AliFemtoPair::QInvFlippedXY() const{
+  // qinv with X and Y flipped
+  AliFemtoLorentzVector tP1 = fTrack1->FourMomentum();
+  tP1.SetX(-1.*tP1.x());
+  tP1.SetY(-1.*tP1.y());
+  AliFemtoLorentzVector tDiff = (tP1-fTrack2->FourMomentum());
+  return ( -1.* tDiff.m());
+}
+
+void AliFemtoPair::CalcNonIdPar() const{ // fortran like function! faster?
+  // Calculate generalized relative mometum 
+  // Use this instead of qXYZ() function when calculating
+  // anything for non-identical particles
+  fNonIdParNotCalculated=0;
+  double px1 = fTrack1->FourMomentum().vect().x();
+  double py1 = fTrack1->FourMomentum().vect().y();
+  double pz1 = fTrack1->FourMomentum().vect().z();
+  double pE1  = fTrack1->FourMomentum().e();
+  double tParticle1Mass = ::sqrt(pE1*pE1 - px1*px1 - py1*py1 - pz1*pz1);
+  double px2 = fTrack2->FourMomentum().vect().x();
+  double py2 = fTrack2->FourMomentum().vect().y();
+  double pz2 = fTrack2->FourMomentum().vect().z();
+  double pE2  = fTrack2->FourMomentum().e();
+  double tParticle2Mass = ::sqrt(pE2*pE2 - px2*px2 - py2*py2 - pz2*pz2);
+
+  double tPx = px1+px2;
+  double tPy = py1+py2;
+  double tPz = pz1+pz2;
+  double tPE = pE1+pE2;
+      
+  double tPtrans = tPx*tPx + tPy*tPy;
+  double tMtrans = tPE*tPE - tPz*tPz;
+  double tPinv =   ::sqrt(tMtrans - tPtrans);
+  tMtrans = ::sqrt(tMtrans);
+  tPtrans = ::sqrt(tPtrans);
+       
+  double tQinvL = (pE1-pE2)*(pE1-pE2) - (px1-px2)*(px1-px2) -
+    (py1-py2)*(py1-py2) - (pz1-pz2)*(pz1-pz2);
+
+  double tQ = (tParticle1Mass*tParticle1Mass - tParticle2Mass*tParticle2Mass)/tPinv;
+  tQ = sqrt ( tQ*tQ - tQinvL);
+         
+  fKStarCalc = tQ/2;
+
+  // ad 1) go to LCMS
+  double beta = tPz/tPE;
+  double gamma = tPE/tMtrans;
+           
+  double pz1L = gamma * (pz1 - beta * pE1);
+  double pE1L = gamma * (pE1 - beta * pz1);
+  
+  // fill histogram for beam projection ( z - axis )
+  fDKLong = pz1L;
+
+  // ad 2) rotation px -> tPt
+  double px1R = (px1*tPx + py1*tPy)/tPtrans;
+  double py1R = (-px1*tPy + py1*tPx)/tPtrans;
+  
+  //fill histograms for side projection ( y - axis )
+  fDKSide = py1R;
+
+  // ad 3) go from LCMS to CMS
+  beta = tPtrans/tMtrans;
+  gamma = tMtrans/tPinv;
+  
+  double px1C = gamma * (px1R - beta * pE1L);
+  
+  // fill histogram for out projection ( x - axis )
+  fDKOut  = px1C;
+
+  fCVK = (fDKOut*tPtrans + fDKLong*tPz)/fKStarCalc/::sqrt(tPtrans*tPtrans+tPz*tPz);
+}
+
+
+/*void AliFemtoPair::calcNonIdParGlobal() const{ // fortran like function! faster?
+  fNonIdParNotCalculatedGlobal=0;
+  double px1 = fTrack1->Track()->PGlobal().x();
+  double py1 = fTrack1->Track()->PGlobal().y();
+  double pz1 = fTrack1->Track()->PGlobal().z();
+  double tParticle1Mass =  fTrack1->FourMomentum().m2();
+  double pE1  = ::sqrt(tParticle1Mass + px1*px1 + py1*py1 + pz1*pz1);
+  tParticle1Mass = ::sqrt(tParticle1Mass);
+
+  double px2 = fTrack2->Track()->PGlobal().x();
+  double py2 = fTrack2->Track()->PGlobal().y();
+  double pz2 = fTrack2->Track()->PGlobal().z();
+  double tParticle2Mass =  fTrack2->FourMomentum().m2();
+  double pE2  = ::sqrt(tParticle2Mass + px2*px2 + py2*py2 + pz2*pz2);
+  tParticle2Mass = ::sqrt(tParticle2Mass);
+
+  double Px = px1+px2;
+  double Py = py1+py2;
+  double Pz = pz1+pz2;
+  double PE = pE1+pE2;
+      
+  double Ptrans = Px*Px + Py*Py;
+  double Mtrans = PE*PE - Pz*Pz;
+  double Pinv =   ::sqrt(Mtrans - Ptrans);
+  Mtrans = ::sqrt(Mtrans);
+  Ptrans = ::sqrt(Ptrans);
+       
+  double QinvL = (pE1-pE2)*(pE1-pE2) - (px1-px2)*(px1-px2) -
+    (py1-py2)*(py1-py2) - (pz1-pz2)*(pz1-pz2);
+
+  double Q = (tParticle1Mass*tParticle1Mass - tParticle2Mass*tParticle2Mass)/Pinv;
+  Q = sqrt ( Q*Q - QinvL);
+         
+  kStarCalcGlobal = Q/2;
+
+  // ad 1) go to LCMS
+  double beta = Pz/PE;
+  double gamma = PE/Mtrans;
+           
+  double pz1L = gamma * (pz1 - beta * pE1);
+  double pE1L = gamma * (pE1 - beta * pz1);
+  
+  // fill histogram for beam projection ( z - axis )
+  fDKLongGlobal = pz1L;
+
+  // ad 2) rotation px -> Pt
+  double px1R = (px1*Px + py1*Py)/Ptrans;
+  double py1R = (-px1*Py + py1*Px)/Ptrans;
+  
+  //fill histograms for side projection ( y - axis )
+  fDKSideGlobal = py1R;
+
+  // ad 3) go from LCMS to CMS
+  beta = Ptrans/Mtrans;
+  gamma = Mtrans/Pinv;
+  
+  double px1C = gamma * (px1R - beta * pE1L);
+  
+  // fill histogram for out projection ( x - axis )
+  fDKOutGlobal  = px1C;
+
+  fCVKGlobal = (fDKOutGlobal*Ptrans + fDKLongGlobal*Pz)/
+    kStarCalcGlobal/::sqrt(Ptrans*Ptrans+Pz*Pz);
+}*/
+
+
+
+// double AliFemtoPair::DcaInsideTpc() const{
+//   // dcs inside the STAR TPC
+//   double tMinDist=NominalTpcEntranceSeparation();
+//   double tExit = NominalTpcExitSeparation();
+//   tMinDist = (tExit>tMinDist) ? tMinDist : tExit;
+//   double tInsideDist;
+//   //tMinDist = 999.;
+
+//   double rMin = 60.;
+//   double rMax = 190.;
+//   const AliFmPhysicalHelixD& tHelix1 = fTrack1->Helix();
+//   const AliFmPhysicalHelixD& tHelix2 = fTrack2->Helix();
+//   // --- One is a line and other one a helix
+//   //if (tHelix1.mSingularity != tHelix2.mSingularity) return -999.;
+//   // --- 2 lines : don't care right now
+//   //if (tHelix1.mSingularity)  return -999.;
+//   // --- 2 helix
+//   double dx = tHelix2.XCenter() - tHelix1.XCenter();
+//   double dy = tHelix2.YCenter() - tHelix1.YCenter();
+//   double dd = ::sqrt(dx*dx + dy*dy);
+//   double r1 = 1/tHelix1.Curvature();
+//   double r2 = 1/tHelix2.Curvature();
+//   double cosAlpha = (r1*r1 + dd*dd - r2*r2)/(2*r1*dd);
+    
+//   double x, y, r;
+//   double s;
+//   if (fabs(cosAlpha) < 1) {           // two solutions
+//     double sinAlpha = sin(acos(cosAlpha));
+//     x = tHelix1.XCenter() + r1*(cosAlpha*dx - sinAlpha*dy)/dd;
+//     y = tHelix1.YCenter() + r1*(sinAlpha*dx + cosAlpha*dy)/dd;
+//     r = ::sqrt(x*x+y*y);
+//     if( r > rMin &&  r < rMax && 
+//     fabs(atan2(y,x)-fTrack1->Track()->NominalTpcEntrancePoint().phi())< 0.5
+//     ){ // first solution inside
+//       s = tHelix1.PathLength(x, y);
+//       tInsideDist=tHelix2.Distance(tHelix1.At(s));
+//       if(tInsideDist<tMinDist) tMinDist = tInsideDist;
+//     }
+//     else{ 
+//       x = tHelix1.XCenter() + r1*(cosAlpha*dx + sinAlpha*dy)/dd;
+//       y = tHelix1.YCenter() + r1*(cosAlpha*dy - sinAlpha*dx)/dd;
+//       r = ::sqrt(x*x+y*y);
+//       if( r > rMin &&  r < rMax &&
+//       fabs(atan2(y,x)-fTrack1->Track()->NominalTpcEntrancePoint().phi())< 0.5
+//       ) {  // second solution inside
+//         s = tHelix1.PathLength(x, y);
+//         tInsideDist=tHelix2.Distance(tHelix1.At(s));
+//         if(tInsideDist<tMinDist) tMinDist = tInsideDist;
+//       }     
+//     }
+//   }
+//   return tMinDist;
+// }
+
+// void AliFemtoPair::CalcMergingPar() const{
+//   // Calculate merging factor for the pair in STAR TPC
+//   fMergingParNotCalculated=0;
+
+//   double tDu, tDz;
+//   int tN = 0;
+//   fFracOfMergedRow = 0.;
+//   fWeightedAvSep =0.;
+//   double tDist;
+//   double tDistMax = 200.;
+//   for(int ti=0 ; ti<45 ; ti++){
+//     if(fTrack1->fSect[ti]==fTrack2->fSect[ti] && fTrack1->fSect[ti]!=-1){
+//       tDu = fabs(fTrack1->fU[ti]-fTrack2->fU[ti]);
+//       tDz = fabs(fTrack1->fZ[ti]-fTrack2->fZ[ti]);
+//       tN++;
+//       if(ti<13){
+//     fFracOfMergedRow += (tDu<fgMaxDuInner && tDz<fgMaxDzInner);
+//     tDist = ::sqrt(tDu*tDu/fgMaxDuInner/fgMaxDuInner+
+//                  tDz*tDz/fgMaxDzInner/fgMaxDzInner);
+//     //fFracOfMergedRow += (tDu<fgMaxDuInner && tDz<fgMaxDzInner);
+//       }
+//       else{
+//     fFracOfMergedRow += (tDu<fgMaxDuOuter && tDz<fgMaxDzOuter);
+//     tDist = ::sqrt(tDu*tDu/fgMaxDuOuter/fgMaxDuOuter+
+//                  tDz*tDz/fgMaxDzOuter/fgMaxDzOuter);
+//     //fFracOfMergedRow += (tDu<fgMaxDuOuter && tDz<fgMaxDzOuter);
+//       }
+//       if(tDist<tDistMax){
+//     fClosestRowAtDCA = ti+1;
+//     tDistMax = tDist;
+//       }
+//       fWeightedAvSep += tDist;
+//     }
+//   }
+//   if(tN>0){
+//     fWeightedAvSep /= tN;
+//     fFracOfMergedRow /= tN;
+//   }
+//   else{
+//     fClosestRowAtDCA = -1;
+//     fFracOfMergedRow = -1.;
+//     fWeightedAvSep = -1.;
+//   }
+// }
+// double AliFemtoPair::TpcExitSeparationTrackV0Pos() const {
+// //________________V0 daughters exit/entrance/average separation calc.
+// //_______1st part is a track 2nd is a V0 considering Pos daughter
+  
+//   AliFemtoThreeVector diff = fTrack1->Track()->NominalTpcExitPoint() - fTrack2->TpcV0PosExitPoint();
+//   return (diff.Mag());
+// }
+
+// double AliFemtoPair::TpcEntranceSeparationTrackV0Pos() const {
+// //________________V0 daughters exit/entrance/average separation calc.
+// //_______1st part is a track 2nd is a V0 considering Pos daughter
+//   AliFemtoThreeVector diff = fTrack1->Track()->NominalTpcEntrancePoint() - fTrack2->TpcV0PosEntrancePoint();
+//   return (diff.Mag());
+// }
+
+// double AliFemtoPair::TpcAverageSeparationTrackV0Pos() const {
+// //________________V0 daughters exit/entrance/average separation calc.
+// //_______1st part is a track 2nd is a V0 considering Pos daughter
+//   AliFemtoThreeVector diff;
+//   double tAveSep = 0.0;
+//   int ipt = 0;
+//   if (fTrack1->fNominalPosSample && fTrack2->fNominalPosSample){
+//   while (fabs(fTrack1->fNominalPosSample[ipt].x())<9999. &&
+//      fabs(fTrack1->fNominalPosSample[ipt].y())<9999. && 
+//      fabs(fTrack1->fNominalPosSample[ipt].z())<9999. &&
+//      fabs(fTrack2->fNominalPosSample[ipt].x())<9999. &&
+//      fabs(fTrack2->fNominalPosSample[ipt].y())<9999. && 
+//      fabs(fTrack2->fNominalPosSample[ipt].z())<9999. &&
+//      (ipt<11)
+//      ){
+//     diff = fTrack1->fNominalPosSample[ipt] - fTrack2->fNominalPosSample[ipt];
+//     ipt++;
+//     tAveSep += diff.Mag();
+//   }
+//   tAveSep = tAveSep/(ipt+1.);
+//   return (tAveSep);}
+//   else return -1;
+// }
+// double AliFemtoPair::TpcExitSeparationTrackV0Neg() const {
+// //_______1st part is a track 2nd is a V0 considering Neg daughter
+//   AliFemtoThreeVector diff = fTrack1->Track()->NominalTpcExitPoint() - fTrack2->TpcV0NegExitPoint();
+//   return (diff.Mag());
+// }
+
+// double AliFemtoPair::TpcEntranceSeparationTrackV0Neg() const {
+// //_______1st part is a track 2nd is a V0 considering Neg daughter
+//   AliFemtoThreeVector diff = fTrack1->Track()->NominalTpcEntrancePoint() - fTrack2->TpcV0NegEntrancePoint();
+//   return (diff.Mag());
+// }
+
+// double AliFemtoPair::TpcAverageSeparationTrackV0Neg() const {
+// //_______1st part is a track 2nd is a V0 considering Neg daughter
+//   AliFemtoThreeVector diff;
+//   double tAveSep = 0.0;
+//   int ipt = 0;
+//   if (fTrack1->fNominalPosSample && fTrack2->fTpcV0NegPosSample){
+//   while (fabs(fTrack1->fNominalPosSample[ipt].x())<9999. &&
+//      fabs(fTrack1->fNominalPosSample[ipt].y())<9999. && 
+//      fabs(fTrack1->fNominalPosSample[ipt].z())<9999. &&
+//      fabs(fTrack2->fTpcV0NegPosSample[ipt].x())<9999. &&
+//      fabs(fTrack2->fTpcV0NegPosSample[ipt].y())<9999. && 
+//      fabs(fTrack2->fTpcV0NegPosSample[ipt].z())<9999. &&
+//      (ipt<11)
+//      ){
+//     diff = fTrack1->fNominalPosSample[ipt] - fTrack2->fTpcV0NegPosSample[ipt];
+//     ipt++;
+//     tAveSep += diff.Mag();
+//   }
+//   tAveSep = tAveSep/(ipt+1.);
+//   return (tAveSep);}
+//   else return -1;
+// }
+
+// double AliFemtoPair::TpcExitSeparationV0PosV0Pos() const {
+// //_______1st part is a V0 considering Pos daughter 2nd is a V0 considering Pos daughter
+//   AliFemtoThreeVector diff = fTrack1->TpcV0PosExitPoint() - fTrack2->TpcV0PosExitPoint();
+//   return (diff.Mag());
+// }
+
+// double AliFemtoPair::TpcEntranceSeparationV0PosV0Pos() const {
+// //_______1st part is a V0 considering Pos daughter 2nd is a V0 considering Pos daughter
+//   AliFemtoThreeVector diff = fTrack1->TpcV0PosEntrancePoint() - fTrack2->TpcV0PosEntrancePoint();
+//   return (diff.Mag());
+// }
+// double AliFemtoPair::TpcAverageSeparationV0PosV0Pos() const {
+// //_______1st part is a V0 considering Pos daughter 2nd is a V0 considering Pos daughter
+//   AliFemtoThreeVector diff;
+//   double tAveSep = 0.0;
+//   int ipt=0;
+//   if (fTrack1->fNominalPosSample && (fTrack2->fNominalPosSample)){
+//     while ((fabs(fTrack1->fNominalPosSample[ipt].x())<9999.) &&
+//     (fabs(fTrack1->fNominalPosSample[ipt].y())<9999.) &&
+//     (fabs(fTrack1->fNominalPosSample[ipt].z())<9999.) &&
+//     (fabs(fTrack2->fNominalPosSample[ipt].x())<9999.) &&
+//     (fabs(fTrack2->fNominalPosSample[ipt].y())<9999.) &&
+//     (fabs(fTrack2->fNominalPosSample[ipt].z())<9999.) &&
+//      (ipt<11)  
+//     ){
+//       diff = fTrack1->fNominalPosSample[ipt] - fTrack2->fNominalPosSample[ipt];
+//       ipt++;
+//       tAveSep += diff.Mag();
+//     }
+//     tAveSep = tAveSep/(ipt+1);
+//     return (tAveSep);}
+//   else return -1;
+// }
+
+// double AliFemtoPair::TpcExitSeparationV0PosV0Neg() const {
+// //_______1st part is a V0 considering Pos daughter 2nd is a V0 considering Neg daughter
+//   AliFemtoThreeVector diff = fTrack1->TpcV0PosExitPoint() - fTrack2->TpcV0NegExitPoint();
+//   return (diff.Mag());
+// }
+
+// double AliFemtoPair::TpcEntranceSeparationV0PosV0Neg() const {
+// //_______1st part is a V0 considering Pos daughter 2nd is a V0 considering Neg daughter
+//   AliFemtoThreeVector diff = fTrack1->TpcV0PosEntrancePoint() - fTrack2->TpcV0NegEntrancePoint();
+//   return (diff.Mag());
+// }
+// double AliFemtoPair::TpcAverageSeparationV0PosV0Neg() const {
+// //_______1st part is a V0 considering Pos daughter 2nd is a V0 considering Neg daughter
+//   AliFemtoThreeVector diff;
+//   double tAveSep = 0.0;
+//   int ipt = 0;
+//   if (fTrack1->fNominalPosSample && fTrack2->fTpcV0NegPosSample){
+//   while (fabs(fTrack1->fNominalPosSample[ipt].x())<9999. &&
+//      fabs(fTrack1->fNominalPosSample[ipt].y())<9999. && 
+//      fabs(fTrack1->fNominalPosSample[ipt].z())<9999. &&
+//      fabs(fTrack2->fTpcV0NegPosSample[ipt].x())<9999. &&
+//      fabs(fTrack2->fTpcV0NegPosSample[ipt].y())<9999. && 
+//      fabs(fTrack2->fTpcV0NegPosSample[ipt].z())<9999. &&
+//      (ipt<11)
+//      ){
+//     diff = fTrack1->fNominalPosSample[ipt] - fTrack2->fTpcV0NegPosSample[ipt];
+//     ipt++;
+//     tAveSep += diff.Mag();
+//   }
+//   tAveSep = tAveSep/(ipt+1.);
+//   return (tAveSep);}
+//   else return -1; 
+// }
+// double AliFemtoPair::TpcExitSeparationV0NegV0Pos() const {
+// //_______1st part is a V0 considering Neg daughter 2nd is a V0 considering Pos daughter
+// // this is to check the upper case
+//   AliFemtoThreeVector diff = fTrack1->TpcV0NegExitPoint() - fTrack2->TpcV0PosExitPoint();
+//   return (diff.Mag());
+// }
+
+// double AliFemtoPair::TpcEntranceSeparationV0NegV0Pos() const {
+// //_______1st part is a V0 considering Neg daughter 2nd is a V0 considering Pos daughter
+// // this is to check the upper case
+//   AliFemtoThreeVector diff = fTrack1->TpcV0NegEntrancePoint() - fTrack2->TpcV0PosEntrancePoint();
+//   return (diff.Mag());
+// }
+// double AliFemtoPair::TpcAverageSeparationV0NegV0Pos() const {
+// //_______1st part is a V0 considering Neg daughter 2nd is a V0 considering Pos daughter
+// // this is to check the upper case
+//    AliFemtoThreeVector diff;
+//    double tAveSep = 0.0;
+//    int ipt = 0;
+//    if ( fTrack1->fTpcV0NegPosSample &&  fTrack2->fNominalPosSample){
+//      while (fabs(fTrack1->fTpcV0NegPosSample[ipt].x())<9999. &&
+//         fabs(fTrack1->fTpcV0NegPosSample[ipt].y())<9999. && 
+//         fabs(fTrack1->fTpcV0NegPosSample[ipt].z())<9999. &&
+//         fabs(fTrack2->fNominalPosSample[ipt].x())<9999. &&
+//         fabs(fTrack2->fNominalPosSample[ipt].y())<9999. && 
+//         fabs(fTrack2->fNominalPosSample[ipt].z())<9999. &&
+//         (ipt<11)
+//         ){
+//        diff = fTrack1->fTpcV0NegPosSample[ipt] - fTrack2->fNominalPosSample[ipt];
+//        ipt++;
+//        tAveSep += diff.Mag();
+//      }
+//      tAveSep = tAveSep/(ipt+1);
+//      return (tAveSep);}
+//      else return -1;
+// }
+// double AliFemtoPair::TpcExitSeparationV0NegV0Neg() const {
+// //_______1st part is a V0 considering Neg daughter 2nd is a V0 considering Neg daughter
+//   AliFemtoThreeVector diff = fTrack1->TpcV0NegExitPoint() - fTrack2->TpcV0NegExitPoint();
+//   return (diff.Mag());
+// }
+
+// double AliFemtoPair::TpcEntranceSeparationV0NegV0Neg() const {
+// //_______1st part is a V0 considering Neg daughter 2nd is a V0 considering Neg daughter
+//   AliFemtoThreeVector diff = fTrack1->TpcV0NegEntrancePoint() - fTrack2->TpcV0NegEntrancePoint();
+//   return (diff.Mag());
+// }
+// double AliFemtoPair::TpcAverageSeparationV0NegV0Neg() const {
+// //_______1st part is a V0 considering Neg daughter 2nd is a V0 considering Neg daughter
+//    AliFemtoThreeVector diff;
+//    double tAveSep = 0.0;
+//    int ipt=0;
+//    if (fTrack1->fTpcV0NegPosSample && fTrack2->fTpcV0NegPosSample){
+//      while (fabs(fTrack1->fTpcV0NegPosSample[ipt].x())<9999. &&
+//         fabs(fTrack1->fTpcV0NegPosSample[ipt].y())<9999. && 
+//         fabs(fTrack1->fTpcV0NegPosSample[ipt].z())<9999. &&
+//         fabs(fTrack2->fTpcV0NegPosSample[ipt].x())<9999. &&
+//         fabs(fTrack2->fTpcV0NegPosSample[ipt].y())<9999. && 
+//         fabs(fTrack2->fTpcV0NegPosSample[ipt].z())<9999. &&
+//         (ipt<11)
+//         ){
+//        diff = fTrack1->fTpcV0NegPosSample[ipt] - fTrack2->fTpcV0NegPosSample[ipt];
+//        ipt++;
+//        tAveSep += diff.Mag();
+//      }
+//      tAveSep = tAveSep/(ipt+1);
+//      return (tAveSep);}
+//    else return -1;
+// }
+
+// void AliFemtoPair::CalcMergingParFctn(short* tmpMergingParNotCalculatedFctn,
+//                                float* tmpZ1,float* tmpU1,
+//                                float* tmpZ2,float* tmpU2,
+//                                int *tmpSect1,int *tmpSect2,
+//                                double* tmpFracOfMergedRow,
+//                                double* tmpClosestRowAtDCA
+//                                ) const{
+// // calculate heper variables for merging 
+//   tmpMergingParNotCalculatedFctn=0;
+//   double tDu, tDz;
+//   int tN = 0;
+//   *tmpFracOfMergedRow = 0.;
+//   *tmpClosestRowAtDCA = 0.;
+//   double tDist;
+//   double tDistMax = 100000000.;
+//   for(int ti=0 ; ti<45 ; ti++){
+//     if(tmpSect1[ti]==tmpSect2[ti] && tmpSect1[ti]!=-1){
+//     tDu = fabs(tmpU1[ti]-tmpU2[ti]);
+//     tDz = fabs(tmpZ1[ti]-tmpZ2[ti]);
+//     tN++;
+//       if(ti<13){
+//     *tmpFracOfMergedRow += (tDu<fgMaxDuInner && tDz<fgMaxDzInner);
+//     tDist = ::sqrt(tDu*tDu/fgMaxDuInner/fgMaxDuInner+
+//                  tDz*tDz/fgMaxDzInner/fgMaxDzInner);
+//       }
+//       else{
+//     *tmpFracOfMergedRow += (tDu<fgMaxDuOuter && tDz<fgMaxDzOuter);
+//     tDist = ::sqrt(tDu*tDu/fgMaxDuOuter/fgMaxDuOuter+
+//                  tDz*tDz/fgMaxDzOuter/fgMaxDzOuter);
+//     }
+//       if(tDist<tDistMax){
+//     fClosestRowAtDCA = ti+1;
+//     tDistMax = tDist;
+//       }
+//       //fWeightedAvSep += tDist; // now, wrong but not used
+//     }       
+//   }
+//   if(tN>0){
+//     //fWeightedAvSep /= tN;
+//     *tmpFracOfMergedRow /= tN;
+//   }
+//   else{
+//     *tmpClosestRowAtDCA = -1;
+//     *tmpFracOfMergedRow = -1.;
+//     //fWeightedAvSep = -1.;
+//   }
+// }
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoPair.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoPair.h
new file mode 100644 (file)
index 0000000..2fad9c7
--- /dev/null
@@ -0,0 +1,414 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFemtoPair: the Pair object is passed to the PairCuts for           //
+// verification, and then to the AddRealPair and AddMixedPair methods of //
+// the Correlation Functions. It holds pair-specific variables like      //
+// relative momenta and has links to the particles and tracks that form  //
+// the pair.                                                             //
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+#ifndef ALIFEMTOPAIR_H
+#define ALIFEMTOPAIR_H
+
+#include <utility>
+
+#include "AliFemtoParticle.h"
+#include "AliFemtoTypes.h"
+
+class AliFemtoPair {
+public:
+  AliFemtoPair();
+  AliFemtoPair(const AliFemtoPair& aPair);
+  AliFemtoPair(AliFemtoParticle*, AliFemtoParticle*);
+  ~AliFemtoPair();
+  AliFemtoPair& operator=(const AliFemtoPair& aPair);
+
+  // track Gets:
+  AliFemtoParticle* Track1() const;
+  AliFemtoParticle* Track2() const;
+  // track Sets:
+  void SetTrack1(const AliFemtoParticle* trkPtr);
+  void SetTrack2(const AliFemtoParticle* trkPtr);
+
+  AliFemtoLorentzVector FourMomentumDiff() const;
+  AliFemtoLorentzVector FourMomentumSum() const;
+  double QInv() const;
+  double KT()   const;
+  double MInv() const;
+  // pair rapidity
+  double Rap() const;
+  double EmissionAngle() const;
+
+  // Bertsch-Pratt momentum components in Pair Frame - written by Bekele/Humanic
+  double QSidePf() const;
+  double QOutPf() const;
+  double QLongPf() const;
+   
+  // Bertsch-Pratt momentum components in Local CMS (longitudinally comoving) frame
+  // - written by Bekele/Humanic
+  double QSideCMS() const;
+  double QOutCMS() const;
+  double QLongCMS() const;
+
+  double KSide() const;
+  double KOut() const;
+  double KLong() const;
+
+  // Bertsch-Pratt momentum components in a longitudinally boosted frame
+  // the argument is the beta of the longitudinal boost (default is 0.0, meaning lab frame)
+  // - written by Bekele/Humanic
+  double QSideBf(double beta=0.0) const;
+  double QOutBf(double beta=0.0) const;
+  double QLongBf(double beta=0.0) const;
+
+  // Yano-Koonin-Podgoretskii Parametrisation 
+  // source rest frame (usually lab frame)
+  void QYKPCMS(double& qP, double& qT, double& q0) const ;
+  // longitudinal comoving frame
+  void QYKPLCMS(double& qP, double& qT, double& q0) const ;
+  // pair rest frame
+  void QYKPPF(double& qP, double& qT, double& q0) const ;
+
+
+  double Quality() const;
+
+  // the following two methods calculate the "nominal" separation of the tracks 
+  // at the inner field cage (EntranceSeparation) and when they exit the TPC,
+  // which may be at the outer field cage, or at the endcaps.
+  // "nominal" means that the tracks are assumed to start at (0,0,0).  Making this
+  // assumption is important for the Event Mixing-- it is not a mistake. - MALisa
+  double NominalTpcExitSeparation() const;
+  double NominalTpcEntranceSeparation() const;
+  //  double NominalTpcAverageSeparation() const;
+  // adapted calculation of Entrance/Exit/Average Tpc separation to V0 daughters
+/*   double TpcExitSeparationTrackV0Pos() const; */
+/*   double TpcEntranceSeparationTrackV0Pos() const; */
+/*   double TpcAverageSeparationTrackV0Pos() const;  */
+
+/*   double TpcExitSeparationTrackV0Neg() const; */
+/*   double TpcEntranceSeparationTrackV0Neg() const; */
+/*   double TpcAverageSeparationTrackV0Neg() const;  */
+
+/*   double TpcExitSeparationV0PosV0Pos() const; */
+/*   double TpcEntranceSeparationV0PosV0Pos() const; */
+/*   double TpcAverageSeparationV0PosV0Pos() const;  */
+
+/*   double TpcExitSeparationV0PosV0Neg() const; */
+/*   double TpcEntranceSeparationV0PosV0Neg() const; */
+/*   double TpcAverageSeparationV0PosV0Neg() const;  */
+/*   double TpcExitSeparationV0NegV0Pos() const; */
+/*   double TpcEntranceSeparationV0NegV0Pos() const; */
+/*   double TpcAverageSeparationV0NegV0Pos() const;  */
+  
+/*   double TpcExitSeparationV0NegV0Neg() const; */
+/*   double TpcEntranceSeparationV0NegV0Neg() const; */
+/*   double TpcAverageSeparationV0NegV0Neg() const;  */
+
+  double PInv() const;
+  double KStar() const;
+  double KStarFlipped() const;
+  double CVK() const;
+  double CVKFlipped() const;
+  double QInvFlippedXY() const;
+
+  double OpeningAngle() const;
+
+  // Fabrice Private <<<
+  double KStarSide() const;
+  double KStarOut() const;
+  double KStarLong() const;
+
+  float PionPairProbability() const;
+  float ElectronPairProbability() const;
+  float KaonPairProbability() const;
+  float ProtonPairProbability() const;
+  float KaonPionPairProbability() const;
+
+  double DcaInsideTpc() const;
+  double Quality2() const;
+
+ /* double KStarGlobal() const;
+  double CVKGlobal() const;
+  double KStarSideGlobal() const;
+  double KStarOutGlobal() const;
+  double KStarLongGlobal() const;*/
+
+  void SetMergingPar(double aMaxDuInner, double aMaxDzInner,
+                    double aMaxDuOuter, double aMaxDzOuter);
+  void SetDefaultHalfFieldMergingPar();
+  void SetDefaultFullFieldMergingPar();
+  double GetFracOfMergedRow() const;
+  double GetClosestRowAtDCA() const;
+  double GetWeightedAvSep() const;
+  // >>>
+/*   double GetFracOfMergedRowTrkV0Pos() const; */
+/*   double GetClosestRowAtDCATrkV0Pos() const; */
+
+/*   double GetFracOfMergedRowTrkV0Neg() const; */
+/*   double GetClosestRowAtDCATrkV0Neg() const; */
+
+/*   double GetFracOfMergedRowV0PosV0Neg() const; */
+/*   double GetFracOfMergedRowV0NegV0Pos() const; */
+/*   double GetFracOfMergedRowV0PosV0Pos() const; */
+/*   double GetFracOfMergedRowV0NegV0Neg() const; */
+
+//Setting and getting emission angle wrt EP
+  double       GetPairAngleEP() const;
+  void         SetPairAngleEP(double x) {fPairAngleEP = x;}
+
+private:
+  AliFemtoParticle* fTrack1; // Link to the first track in the pair
+  AliFemtoParticle* fTrack2; // Link to the second track in the pair
+
+  double fPairAngleEP; //Pair emission angle wrt EP
+
+  mutable short fNonIdParNotCalculated; // Set to 1 when NonId variables (kstar) have been already calculated for this pair
+  mutable double fDKSide; // momemntum of first particle in PRF - k* side component
+  mutable double fDKOut;  // momemntum of first particle in PRF - k* out component
+  mutable double fDKLong; // momemntum of first particle in PRF - k* long component
+  mutable double fCVK;    // cos between velocity and relative momentum k*
+  mutable double fKStarCalc; // momemntum of first particle in PRF - k* 
+  void CalcNonIdPar() const;
+
+  mutable short fNonIdParNotCalculatedGlobal; // If global k* was calculated
+ /* mutable double fDKSideGlobal;
+  mutable double fDKOutGlobal;
+  mutable double fDKLongGlobal;
+  mutable double kStarCalcGlobal;
+  mutable double fCVKGlobal;*/
+  //void calcNonIdParGlobal() const;
+
+  mutable short fMergingParNotCalculated; // If merging parameters were calculated
+  mutable double fWeightedAvSep;          // Weighted average separation
+  mutable double fFracOfMergedRow;        // Fraction of merged rows
+  mutable double fClosestRowAtDCA;        // Row at wchich DCA occurs
+
+  mutable short fMergingParNotCalculatedTrkV0Pos; // merging parameters for track - V0 pos      
+  mutable double fFracOfMergedRowTrkV0Pos;        // fraction of merged rows for track - V0 pos 
+  mutable double fClosestRowAtDCATrkV0Pos;        // Row at which DCA occurs for track - V0 pos 
+
+  mutable short fMergingParNotCalculatedTrkV0Neg; // merging parameters for track - V0 neg      
+  mutable double fFracOfMergedRowTrkV0Neg;       // fraction of merged rows for track - V0 neg 
+  mutable double fClosestRowAtDCATrkV0Neg;       // Row at which DCA occurs for track - V0 neg 
+
+  mutable short fMergingParNotCalculatedV0PosV0Neg; // merging parameters for V0 pos - V0 neg   
+  mutable double fFracOfMergedRowV0PosV0Neg;       // fraction of merged rows for V0 pos - V0 neg 
+  mutable double fClosestRowAtDCAV0PosV0Neg;       // Row at which DCA occurs for V0 pos - V0 neg 
+
+  mutable short fMergingParNotCalculatedV0NegV0Pos; // merging parameters for V0 neg - V0 pos   
+  mutable double fFracOfMergedRowV0NegV0Pos;       // fraction of merged rows for V0 neg - V0 pos 
+  mutable double fClosestRowAtDCAV0NegV0Pos;       // Row at which DCA occurs for V0 neg - V0 pos 
+
+  mutable short fMergingParNotCalculatedV0PosV0Pos; // merging parameters for V0 pos - V0 pos   
+  mutable double fFracOfMergedRowV0PosV0Pos;       // fraction of merged rows for V0 pos - V0 pos 
+  mutable double fClosestRowAtDCAV0PosV0Pos;       // Row at which DCA occurs for V0 pos - V0 pos 
+
+  mutable short fMergingParNotCalculatedV0NegV0Neg; // merging parameters for V0 neg - V0 neg   
+  mutable double fFracOfMergedRowV0NegV0Neg;       // fraction of merged rows for V0 neg - V0 neg 
+  mutable double fClosestRowAtDCAV0NegV0Neg;       // Row at which DCA occurs for V0 neg - V0 neg 
+
+  static double fgMaxDuInner; // Minimum cluster separation in x in inner TPC padrow
+  static double fgMaxDzInner; // Minimum cluster separation in z in inner TPC padrow
+  static double fgMaxDuOuter; // Minimum cluster separation in x in outer TPC padrow
+  static double fgMaxDzOuter; // Minimum cluster separation in z in outer TPC padrow
+  void CalcMergingPar() const;
+
+  void CalcMergingParFctn(short* tmpMergingParNotCalculatedFctn,
+                         float* tmpZ1,float* tmpU1,
+                         float* tmpZ2,float* tmpU2,
+                         int *tmpSect1,int *tmpSect2,
+                         double* tmpFracOfMergedRow,
+                         double* tmpClosestRowAtDCA
+                         ) const;
+
+  void ResetParCalculated();
+};
+
+inline void AliFemtoPair::ResetParCalculated(){
+  fNonIdParNotCalculated=1;
+  fNonIdParNotCalculatedGlobal=1;
+  fMergingParNotCalculated=1;
+  fMergingParNotCalculatedTrkV0Pos=1;
+  fMergingParNotCalculatedTrkV0Neg=1;
+  fMergingParNotCalculatedV0PosV0Pos=1;
+  fMergingParNotCalculatedV0NegV0Pos=1;
+  fMergingParNotCalculatedV0PosV0Neg=1;
+  fMergingParNotCalculatedV0NegV0Neg=1;
+}
+
+inline void AliFemtoPair::SetTrack1(const AliFemtoParticle* trkPtr){
+  fTrack1=(AliFemtoParticle*)trkPtr;
+  ResetParCalculated();
+}
+inline void AliFemtoPair::SetTrack2(const AliFemtoParticle* trkPtr){
+  fTrack2=(AliFemtoParticle*)trkPtr;
+  ResetParCalculated();
+}
+
+inline AliFemtoParticle* AliFemtoPair::Track1() const {return fTrack1;}
+inline AliFemtoParticle* AliFemtoPair::Track2() const {return fTrack2;}
+
+inline double AliFemtoPair::KSide() const{
+  if(fNonIdParNotCalculated) CalcNonIdPar();
+  return fDKSide;
+}
+inline double AliFemtoPair::KOut() const{
+  if(fNonIdParNotCalculated) CalcNonIdPar();
+  return fDKOut;
+}
+inline double AliFemtoPair::KLong() const{
+  if(fNonIdParNotCalculated) CalcNonIdPar();
+  return fDKLong;
+}
+inline double AliFemtoPair::KStar() const{
+  if(fNonIdParNotCalculated) CalcNonIdPar();
+  return fKStarCalc;
+}
+inline double AliFemtoPair::QInv() const {
+  AliFemtoLorentzVector tDiff = (fTrack1->FourMomentum()-fTrack2->FourMomentum());
+  return ( -1.* tDiff.m());
+}
+
+// Fabrice private <<<
+inline double AliFemtoPair::KStarSide() const{
+  if(fNonIdParNotCalculated) CalcNonIdPar();
+  return fDKSide;//mKStarSide;
+}
+inline double AliFemtoPair::KStarOut() const{
+  if(fNonIdParNotCalculated) CalcNonIdPar();
+  return fDKOut;//mKStarOut;
+}
+inline double AliFemtoPair::KStarLong() const{
+  if(fNonIdParNotCalculated) CalcNonIdPar();
+  return fDKLong;//mKStarLong;
+}
+inline double AliFemtoPair::CVK() const{
+  if(fNonIdParNotCalculated) CalcNonIdPar();
+  return fCVK;
+}
+
+inline float AliFemtoPair::PionPairProbability() const{
+  return (fTrack1->Track()->PidProbPion()) * 
+         (fTrack2->Track()->PidProbPion());
+}
+inline float AliFemtoPair::ElectronPairProbability() const{
+  return (fTrack1->Track()->PidProbElectron()) * 
+         (fTrack2->Track()->PidProbElectron());
+}
+inline float AliFemtoPair::KaonPairProbability() const{
+  return (fTrack1->Track()->PidProbKaon()) * 
+         (fTrack2->Track()->PidProbKaon());
+}
+inline float AliFemtoPair::ProtonPairProbability() const{
+  return (fTrack1->Track()->PidProbProton()) * 
+         (fTrack2->Track()->PidProbProton());
+}
+inline float AliFemtoPair::KaonPionPairProbability() const{
+  return (fTrack1->Track()->PidProbKaon()) * 
+         (fTrack2->Track()->PidProbPion());
+}
+
+inline double AliFemtoPair::GetFracOfMergedRow() const{
+  if(fMergingParNotCalculated) CalcMergingPar();
+  return fFracOfMergedRow;
+}
+inline double AliFemtoPair::GetClosestRowAtDCA() const { 
+  if(fMergingParNotCalculated) CalcMergingPar();
+  return fClosestRowAtDCA;
+}
+inline double AliFemtoPair::GetWeightedAvSep() const {
+  if(fMergingParNotCalculated) CalcMergingPar();
+  return fWeightedAvSep;
+}
+
+
+/* inline double AliFemtoPair::GetFracOfMergedRowTrkV0Pos() const{ */
+/*   if(fMergingParNotCalculatedTrkV0Pos) */
+/*     CalcMergingParFctn(&fMergingParNotCalculatedTrkV0Pos, */
+/*                    &(fTrack1->fZ[0]),&(fTrack1->fU[0]), */
+/*                    &(fTrack2->fZ[0]),&(fTrack2->fU[0]), */
+/*                    &(fTrack1->fSect[0]),&(fTrack2->fSect[0]), */
+/*                    &(fFracOfMergedRowTrkV0Pos),&(fClosestRowAtDCATrkV0Pos) */
+/*                    ); */
+/*   return fFracOfMergedRowTrkV0Pos; */
+/* } */
+/* inline double AliFemtoPair::GetClosestRowAtDCATrkV0Pos() const{ */
+/*   if(fMergingParNotCalculatedTrkV0Pos) */
+/*     CalcMergingParFctn(&fMergingParNotCalculatedTrkV0Pos, */
+/*                    &(fTrack1->fZ[0]),&(fTrack1->fU[0]), */
+/*                    &(fTrack2->fZ[0]),&(fTrack2->fU[0]), */
+/*                    &(fTrack1->fSect[0]),&(fTrack2->fSect[0]), */
+/*                    &fFracOfMergedRowTrkV0Pos,&fClosestRowAtDCATrkV0Pos */
+/*                    ); */
+/*   return fClosestRowAtDCATrkV0Pos; */
+/* } */
+/* inline double AliFemtoPair::GetFracOfMergedRowTrkV0Neg() const{ */
+/*   if(fMergingParNotCalculatedTrkV0Neg) */
+/*     CalcMergingParFctn(&fMergingParNotCalculatedTrkV0Neg, */
+/*                    &(fTrack1->fZ[0]),&(fTrack1->fU[0]), */
+/*                    &(fTrack2->fV0NegZ[0]),&(fTrack2->fV0NegU[0]), */
+/*                    &(fTrack1->fSect[0]),&(fTrack2->fV0NegSect[0]), */
+/*                    &(fFracOfMergedRowTrkV0Neg),&(fClosestRowAtDCATrkV0Neg) */
+/*                    ); */
+/*   return fFracOfMergedRowTrkV0Neg; */
+/* } */
+/* inline double AliFemtoPair::GetClosestRowAtDCATrkV0Neg() const{ */
+/*   if(fMergingParNotCalculatedTrkV0Neg) */
+/*     CalcMergingParFctn(&fMergingParNotCalculatedTrkV0Neg, */
+/*                    &(fTrack1->fZ[0]),&(fTrack1->fU[0]), */
+/*                    &(fTrack2->fV0NegZ[0]),&(fTrack2->fV0NegU[0]), */
+/*                    &(fTrack1->fSect[0]),&(fTrack2->fV0NegSect[0]), */
+/*                    &fFracOfMergedRowTrkV0Neg,&fClosestRowAtDCATrkV0Neg */
+/*                    ); */
+/*   return fClosestRowAtDCATrkV0Neg; */
+/* } */
+/* inline double AliFemtoPair::GetFracOfMergedRowV0PosV0Neg() const{ */
+/*   if(fMergingParNotCalculatedV0PosV0Neg) */
+/*     CalcMergingParFctn(&fMergingParNotCalculatedV0PosV0Neg, */
+/*                    &(fTrack1->fZ[0]),&(fTrack1->fU[0]), */
+/*                    &(fTrack2->fV0NegZ[0]),&(fTrack2->fV0NegU[0]), */
+/*                    &(fTrack1->fSect[0]),&(fTrack2->fV0NegSect[0]), */
+/*                    &(fFracOfMergedRowV0PosV0Neg), */
+/*                    &(fClosestRowAtDCAV0PosV0Neg) */
+/*                    ); */
+/*   return fFracOfMergedRowV0PosV0Neg; */
+/* } */
+/* inline double AliFemtoPair::GetFracOfMergedRowV0NegV0Pos() const{ */
+/*   if(fMergingParNotCalculatedV0NegV0Pos) */
+/*     CalcMergingParFctn(&fMergingParNotCalculatedV0NegV0Pos, */
+/*                    &(fTrack1->fV0NegZ[0]),&(fTrack1->fV0NegU[0]), */
+/*                    &(fTrack2->fZ[0]),&(fTrack2->fU[0]), */
+/*                    &(fTrack1->fV0NegSect[0]), */
+/*                    &(fTrack2->fSect[0]), */
+/*                    &(fFracOfMergedRowV0NegV0Pos), */
+/*                    &(fClosestRowAtDCAV0NegV0Pos) */
+/*                    ); */
+/*   return fFracOfMergedRowV0NegV0Pos; */
+/* } */
+/* inline double AliFemtoPair::GetFracOfMergedRowV0PosV0Pos() const{ */
+/*   if(fMergingParNotCalculatedV0PosV0Pos) */
+/*     CalcMergingParFctn(&fMergingParNotCalculatedV0PosV0Pos, */
+/*                    &(fTrack1->fZ[0]),&(fTrack1->fU[0]), */
+/*                    &(fTrack2->fZ[0]),&(fTrack2->fU[0]), */
+/*                    &(fTrack1->fSect[0]), */
+/*                    &(fTrack2->fSect[0]), */
+/*                    &(fFracOfMergedRowV0PosV0Pos), */
+/*                    &(fClosestRowAtDCAV0PosV0Pos) */
+/*                    ); */
+/*   return fFracOfMergedRowV0PosV0Pos; */
+/* } */
+/* inline double AliFemtoPair::GetFracOfMergedRowV0NegV0Neg() const{ */
+/*   if(fMergingParNotCalculatedV0NegV0Neg) */
+/*     CalcMergingParFctn(&fMergingParNotCalculatedV0NegV0Neg, */
+/*                    &(fTrack1->fV0NegZ[0]),&(fTrack1->fV0NegU[0]), */
+/*                    &(fTrack2->fV0NegZ[0]),&(fTrack2->fV0NegU[0]), */
+/*                    &(fTrack1->fV0NegSect[0]), */
+/*                    &(fTrack2->fV0NegSect[0]), */
+/*                    &(fFracOfMergedRowV0NegV0Neg), */
+/*                    &(fClosestRowAtDCAV0NegV0Neg) */
+/*                    ); */
+/*   return fFracOfMergedRowV0NegV0Neg; */
+/* } */
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoPairCut.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoPairCut.h
new file mode 100644 (file)
index 0000000..26ce99b
--- /dev/null
@@ -0,0 +1,61 @@
+////////////////////////////////////////////////////////////////////////////////
+/// AliFemtoPairCut - the pure virtual base class for the pair cut           ///
+/// All pair cuts must inherit from this one                                 ///
+////////////////////////////////////////////////////////////////////////////////
+
+#ifndef AliFemtoPairCut_hh
+#define AliFemtoPairCut_hh
+
+#include <string>
+
+class AliFemtoAnalysis;
+
+#include "AliFemtoString.h"
+#include "AliFemtoEvent.h"
+#include "AliFemtoPair.h"
+#include "AliFemtoCutMonitorHandler.h"
+#include <TList.h>
+#include <TObjString.h>
+
+class AliFemtoPairCut : public AliFemtoCutMonitorHandler {
+
+  friend class AliFemtoAnalysis;
+
+public:
+
+  AliFemtoPairCut();   // default constructor. - Users should write their own
+  AliFemtoPairCut(const AliFemtoPairCut& c); // copy constructor
+  virtual ~AliFemtoPairCut(){/* no-op */};  // destructor
+  AliFemtoPairCut& operator=(const AliFemtoPairCut &aCut);
+
+  virtual bool Pass(const AliFemtoPair* pair) =0;  // true if passes, false if not
+
+  virtual AliFemtoString Report() =0;    // user-written method to return string describing cuts
+  virtual TList *ListSettings() =0;
+  virtual void EventBegin(const AliFemtoEvent* aEvent);
+  virtual void EventEnd(const AliFemtoEvent* aEvent);
+  virtual AliFemtoPairCut* Clone() { return 0;}
+
+  // the following allows "back-pointing" from the CorrFctn to the "parent" Analysis
+  AliFemtoAnalysis* HbtAnalysis(){return fyAnalysis;};
+  void SetAnalysis(AliFemtoAnalysis* aAnalysis);    // Set Back pointer to Analysis
+
+protected:
+  AliFemtoAnalysis* fyAnalysis; // Link to the base analysis class
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoPairCut, 0)
+#endif
+};
+
+
+inline AliFemtoPairCut::AliFemtoPairCut(const AliFemtoPairCut& /* c */) :  AliFemtoCutMonitorHandler(), fyAnalysis(0) {  }
+inline void AliFemtoPairCut::SetAnalysis(AliFemtoAnalysis* analysis) { fyAnalysis = analysis; }
+inline AliFemtoPairCut::AliFemtoPairCut(): AliFemtoCutMonitorHandler(), fyAnalysis(0) {}   // default constructor. - Users should write their own
+inline AliFemtoPairCut& AliFemtoPairCut::operator=(const AliFemtoPairCut &aCut) { if (this == &aCut) return *this; fyAnalysis = aCut.fyAnalysis; return *this; }
+
+inline void AliFemtoPairCut::EventBegin(const AliFemtoEvent* /* aEvent */ ) 
+{ /* no-op */ }
+inline void AliFemtoPairCut::EventEnd(const AliFemtoEvent* /* aEvent */ ) 
+{ /* no-op */ }
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoParticle.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoParticle.cxx
new file mode 100644 (file)
index 0000000..a162848
--- /dev/null
@@ -0,0 +1,772 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFemtoParticle: main class halding all the necessary information    //
+// about particle that is required during femtoscopic analysis           //
+// This includes all the information about the quality of the track,     //
+// its identification as well as track chracteristics with connection    //
+// to the detector parts, e.g. entrance and exit points.                 //
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+#include "AliFemtoKink.h"
+#include "AliFemtoParticle.h"
+#include "AliFemtoXi.h"
+
+double AliFemtoParticle::fgPrimPimPar0= 9.05632e-01;
+double AliFemtoParticle::fgPrimPimPar1= -2.26737e-01;
+double AliFemtoParticle::fgPrimPimPar2= -1.03922e-01;
+double AliFemtoParticle::fgPrimPipPar0= 9.09616e-01;
+double AliFemtoParticle::fgPrimPipPar1= -9.00511e-02;
+double AliFemtoParticle::fgPrimPipPar2= -6.02940e-02;
+double AliFemtoParticle::fgPrimPmPar0= 0.;
+double AliFemtoParticle::fgPrimPmPar1= 0.;
+double AliFemtoParticle::fgPrimPmPar2= 0.;
+double AliFemtoParticle::fgPrimPpPar0= 0.;
+double AliFemtoParticle::fgPrimPpPar1= 0.;
+double AliFemtoParticle::fgPrimPpPar2= 0.;
+
+int TpcLocalTransform(AliFmThreeVectorD& xgl, 
+                     int& iSector, 
+                     int& iPadrow, 
+                     float& xlocal,
+                     double& ttPhi);
+
+
+//_____________________
+AliFemtoParticle::AliFemtoParticle() : 
+//   fTpcV0NegPosSample(0),
+//   fV0NegZ(0),
+//   fV0NegU(0),
+//   fV0NegSect(0),
+  fTrack(0), fV0(0), fKink(0), fXi(0), 
+  fFourMomentum(0),
+  fHelix(),
+//   fNominalTpcExitPoint(0),
+//   fNominalTpcEntrancePoint(0),
+  fHiddenInfo(0),
+  fPrimaryVertex(0),
+  fSecondaryVertex(0),
+  fHelixV0Pos(),
+  fTpcV0PosEntrancePoint(0),
+  fTpcV0PosExitPoint(0),
+  fHelixV0Neg(),
+  fTpcV0NegEntrancePoint(0),
+  fTpcV0NegExitPoint(0)
+{
+  // Default constructor
+  /* no-op for default */
+  for (int ip=0; ip<6; ip++) fPurity[ip] = 0.0;
+  //  cout << "Created particle " << this << endl;
+}
+//_____________________
+AliFemtoParticle::AliFemtoParticle(const AliFemtoParticle& aParticle):
+//   fTpcV0NegPosSample(0),
+//   fV0NegZ(0),
+//   fV0NegU(0),
+//   fV0NegSect(0),
+  fTrack(0), fV0(0), fKink(0), fXi(0),
+  fFourMomentum(0),
+  fHelix(),
+//   fNominalTpcExitPoint(0),
+//   fNominalTpcEntrancePoint(0),
+  fHiddenInfo(0), 
+  fPrimaryVertex(0),
+  fSecondaryVertex(0),
+  fHelixV0Pos(),
+  fTpcV0PosEntrancePoint(0),
+  fTpcV0PosExitPoint(0),
+  fHelixV0Neg(),
+  fTpcV0NegEntrancePoint(0),
+  fTpcV0NegExitPoint(0)
+{
+  // Copy constructor
+  if (aParticle.fTrack)
+    fTrack = new AliFemtoTrack(*aParticle.fTrack);
+  if (aParticle.fV0)
+    fV0    = new AliFemtoV0(*aParticle.fV0);
+  if (aParticle.fKink)
+    fKink  = new AliFemtoKink(*aParticle.fKink);
+  if (aParticle.fXi)
+    fXi    = new AliFemtoXi(*aParticle.fXi);
+  fFourMomentum = aParticle.fFourMomentum;
+  fHelix = aParticle.fHelix;
+  for (int ip=0; ip<6; ip++) fPurity[ip] = 0.0;
+
+//   for (int iter=0; iter<11; iter++)
+//     fNominalPosSample[iter] = aParticle.fNominalPosSample[iter];
+
+//   if (aParticle.fTpcV0NegPosSample) {
+//     fTpcV0NegPosSample = (AliFemtoThreeVector *) malloc(sizeof(AliFemtoThreeVector) * 11);
+//     for (int iter=0; iter<11; iter++)
+//       fTpcV0NegPosSample[iter] = aParticle.fTpcV0NegPosSample[iter];
+//   }
+
+//   if (aParticle.fV0NegZ) {
+//     fV0NegZ = (float *) malloc(sizeof(float) * 45);
+//     for (int iter=0; iter<11; iter++)
+//       fV0NegZ[iter] = aParticle.fV0NegZ[iter];
+//   }
+//   if (aParticle.fV0NegU) {
+//     fV0NegU = (float *) malloc(sizeof(float) * 45);
+//     for (int iter=0; iter<11; iter++)
+//       fV0NegU[iter] = aParticle.fV0NegU[iter];
+//   }
+//   if (aParticle.fV0NegSect) {
+//     fV0NegSect = (int *) malloc(sizeof(int) * 45);
+//     for (int iter=0; iter<11; iter++)
+//       fV0NegSect[iter] = aParticle.fV0NegSect[iter];
+//   }
+
+  fPrimaryVertex = aParticle.fPrimaryVertex;
+  fSecondaryVertex = aParticle.fSecondaryVertex;
+  CalculatePurity();
+  if(aParticle.fHiddenInfo){
+    fHiddenInfo= aParticle.HiddenInfo()->Clone();
+  }
+  
+//   fNominalTpcEntrancePoint = aParticle.fNominalTpcEntrancePoint;
+//   fNominalTpcExitPoint     = aParticle.fNominalTpcExitPoint;
+  
+  for (int iter=0; iter<6; iter++)
+    fPurity[iter] = aParticle.fPurity[iter];
+  
+  fHelixV0Pos = aParticle.fHelixV0Pos;
+  fTpcV0PosEntrancePoint = aParticle.fTpcV0PosEntrancePoint;
+  fTpcV0PosExitPoint     = aParticle.fTpcV0PosExitPoint;
+  fHelixV0Neg = aParticle.fHelixV0Neg;
+  fTpcV0NegEntrancePoint = aParticle.fTpcV0NegEntrancePoint;
+  fTpcV0NegExitPoint     = aParticle.fTpcV0NegExitPoint;
+}
+//_____________________
+AliFemtoParticle::~AliFemtoParticle(){
+  //  cout << "Issuing delete for AliFemtoParticle." << endl;
+
+  if (fTrack) delete fTrack;
+  if (fV0) {
+//     delete[] fTpcV0NegPosSample;
+//     delete[] fV0NegZ;
+//     delete[] fV0NegU;
+//     delete[] fV0NegSect;
+    delete fV0;
+  }
+  if (fKink) delete fKink;
+  if (fXi) delete fXi;
+  //  cout << "Trying to delete HiddenInfo: " << fHiddenInfo << endl;
+  if (fHiddenInfo) 
+    {
+      //      cout << "Deleting HiddenInfo." << endl;
+      delete fHiddenInfo;
+    }
+  //  cout << "Deleted particle " << this << endl;
+}
+//_____________________
+AliFemtoParticle::AliFemtoParticle(const AliFemtoTrack* const hbtTrack,const double& mass) : 
+//   fTpcV0NegPosSample(0),
+//   fV0NegZ(0),
+//   fV0NegU(0),
+//   fV0NegSect(0),
+  fTrack(0), fV0(0), fKink(0), fXi(0),
+  fFourMomentum(0),
+  fHelix(),
+//   fNominalTpcExitPoint(0),
+//   fNominalTpcEntrancePoint(0),
+  fHiddenInfo(0), 
+  fPrimaryVertex(0),
+  fSecondaryVertex(0),
+  fHelixV0Pos(),
+  fTpcV0PosEntrancePoint(0),
+  fTpcV0PosExitPoint(0),
+  fHelixV0Neg(),
+  fTpcV0NegEntrancePoint(0),
+  fTpcV0NegExitPoint(0)
+{
+  // Constructor from normal track
+  
+  // I know there is a better way to do this...
+  fTrack = new AliFemtoTrack(*hbtTrack);
+  AliFemtoThreeVector temp = hbtTrack->P();
+  fFourMomentum.SetVect(temp);
+  double ener = ::sqrt(temp.Mag2()+mass*mass);
+  fFourMomentum.SetE(ener);
+//  fMap[0] = hbtTrack->TopologyMap(0);
+ // fMap[1] = hbtTrack->TopologyMap(1);
+ // fNhits = hbtTrack->NHits();
+  fHelix = hbtTrack->Helix();
+  //CalculateNominalTpcExitAndEntrancePoints();
+
+  fPrimaryVertex.SetX(0.);
+  fPrimaryVertex.SetY(0.);
+  fPrimaryVertex.SetZ(0.);
+  fSecondaryVertex.SetX(0.);
+  fSecondaryVertex.SetY(0.);
+  fSecondaryVertex.SetZ(0.);
+  /* TO JA ODZNACZYLEM NIE WIEM DLACZEGO
+  CalculateTpcExitAndEntrancePoints(&fHelix,&fPrimaryVertex,
+                                   &fSecondaryVertex,
+                                   &fNominalTpcEntrancePoint,
+                                   &fNominalTpcExitPoint,
+                                   &mNominalPosSample[0],
+                                   &fZ[0],
+                                   &fU[0],
+                                   &fSect[0]);
+  */
+  CalculatePurity();
+  // ***
+  fHiddenInfo= 0;
+  if(hbtTrack->ValidHiddenInfo()){
+    fHiddenInfo= hbtTrack->GetHiddenInfo()->Clone();
+  }
+  // ***
+  //  cout << "Created particle " << this << endl;
+
+}
+//_____________________
+AliFemtoParticle::AliFemtoParticle(const AliFemtoV0* const hbtV0,const double& mass) : 
+//   fTpcV0NegPosSample(0),
+//   fV0NegZ(0),
+//   fV0NegU(0),
+//   fV0NegSect(0),
+  fTrack(0), fV0(0), fKink(0),  fXi(0),
+  fFourMomentum(0),
+  fHelix(),
+//   fNominalTpcExitPoint(0),
+//   fNominalTpcEntrancePoint(0),
+  fHiddenInfo(0),
+  fPrimaryVertex(0),
+  fSecondaryVertex(0),
+  fHelixV0Pos(),
+  fTpcV0PosEntrancePoint(0),
+  fTpcV0PosExitPoint(0),
+  fHelixV0Neg(),
+  fTpcV0NegEntrancePoint(0),
+  fTpcV0NegExitPoint(0)
+{
+  // Constructor from V0
+  fV0 = new AliFemtoV0(*hbtV0);
+ //fMap[0]= 0;
+  //fMap[1]= 0;
+  // I know there is a better way to do this...
+  AliFemtoThreeVector temp = hbtV0->MomV0();
+  fFourMomentum.SetVect(temp);
+  double ener = ::sqrt(temp.Mag2()+mass*mass);
+  fFourMomentum.SetE(ener);
+  // Calculating TpcEntrancePoint for Positive V0 daugther
+  fPrimaryVertex = hbtV0->PrimaryVertex();
+  fSecondaryVertex = hbtV0->DecayVertexV0();
+  fHelixV0Pos = hbtV0->HelixPos();
+
+//   fTpcV0NegPosSample = new AliFemtoThreeVector[45];//for V0Neg
+//   fV0NegZ = new float[45];//for V0Neg
+//   fV0NegU = new float[45];//for V0Neg
+//   fV0NegSect = new int[45];//for V0Neg
+//   CalculateTpcExitAndEntrancePoints(&fHelixV0Pos,&fPrimaryVertex,
+//                                 &fSecondaryVertex,
+//                                 &fTpcV0PosEntrancePoint,
+//                                 &fTpcV0PosExitPoint,
+//                                 &fNominalPosSample[0],
+//                                 &fZ[0],
+//                                 &fU[0],&fSect[0]);
+  fHelixV0Neg = hbtV0->HelixNeg();
+
+//   CalculateTpcExitAndEntrancePoints(&fHelixV0Neg,
+//                                 &fPrimaryVertex,
+//                                 &fSecondaryVertex,
+//                                 &fTpcV0NegEntrancePoint,
+//                                 &fTpcV0NegExitPoint,
+//                                 &fTpcV0NegPosSample[0],
+//                                 &fV0NegZ[0],
+//                                 &fV0NegU[0],&fV0NegSect[0]);
+
+  // ***
+  fHiddenInfo= 0;
+  if(hbtV0->ValidHiddenInfo()){
+    fHiddenInfo= hbtV0->GetHiddenInfo()->Clone();
+  }
+  for (int ip=0; ip<6; ip++) fPurity[ip] = 0.0;
+  // ***
+}
+//_____________________
+AliFemtoParticle::AliFemtoParticle(const AliFemtoKink* const hbtKink,const double& mass) : 
+//   fTpcV0NegPosSample(0),
+//   fV0NegZ(0),
+//   fV0NegU(0),
+//   fV0NegSect(0),
+  fTrack(0), fV0(0), fKink(0), fXi(0),
+  fFourMomentum(0),
+  fHelix(),
+//   fNominalTpcExitPoint(0),
+//   fNominalTpcEntrancePoint(0),
+  fHiddenInfo(0),
+  fPrimaryVertex(0),
+  fSecondaryVertex(0),
+  fHelixV0Pos(),
+  fTpcV0PosEntrancePoint(0),
+  fTpcV0PosExitPoint(0),
+  fHelixV0Neg(),
+  fTpcV0NegEntrancePoint(0),
+  fTpcV0NegExitPoint(0)
+{
+  // Constructor from Kink
+  fKink = new AliFemtoKink(*hbtKink);
+ // fMap[0]= 0;
+  //fMap[1]= 0;
+  // I know there is a better way to do this...
+  AliFemtoThreeVector temp = hbtKink->Parent().P();
+  fFourMomentum.SetVect(temp);
+  double ener = ::sqrt(temp.Mag2()+mass*mass);
+  fFourMomentum.SetE(ener);
+  for (int ip=0; ip<6; ip++) fPurity[ip] = 0.0;
+}
+
+//_____________________
+AliFemtoParticle::AliFemtoParticle(const AliFemtoXi* const hbtXi, const double& mass) :
+//   fTpcV0NegPosSample(0),
+//   fV0NegZ(0),
+//   fV0NegU(0),
+//   fV0NegSect(0),
+  fTrack(0), fV0(0), fKink(0), fXi(0),
+  fFourMomentum(0),
+  fHelix(),
+//   fNominalTpcExitPoint(0),
+//   fNominalTpcEntrancePoint(0),
+  fHiddenInfo(0), 
+  fPrimaryVertex(0),
+  fSecondaryVertex(0),
+  fHelixV0Pos(),
+  fTpcV0PosEntrancePoint(0),
+  fTpcV0PosExitPoint(0),
+  fHelixV0Neg(),
+  fTpcV0NegEntrancePoint(0),
+  fTpcV0NegExitPoint(0)
+{
+  // Constructor from Xi
+  fXi = new AliFemtoXi(*hbtXi);
+ // fMap[0]= 0;
+  //fMap[1]= 0;
+  AliFemtoThreeVector temp;// = hbtXi->mMofXi;
+  fFourMomentum.SetVect(temp);
+  double ener = ::sqrt(temp.Mag2()+mass*mass);
+  fFourMomentum.SetE(ener);
+  fHiddenInfo = 0;
+  for (int ip=0; ip<6; ip++) fPurity[ip] = 0.0;
+
+}
+//_____________________
+AliFemtoParticle& AliFemtoParticle::operator=(const AliFemtoParticle& aParticle)
+{
+  // assignment operator
+  if (this != &aParticle) {
+
+    if (fTrack) delete fTrack;
+    if (aParticle.fTrack) {
+      fTrack = new AliFemtoTrack(*aParticle.fTrack);
+      CalculatePurity();
+    }
+    if (fV0) delete fV0;
+    if (aParticle.fV0)
+      fV0    = new AliFemtoV0(*aParticle.fV0);
+    if (fKink) delete fKink;
+    if (aParticle.fKink)
+      fKink  = new AliFemtoKink(*aParticle.fKink);
+    if (fXi) delete fXi;
+    if (aParticle.fXi)
+      fXi    = new AliFemtoXi(*aParticle.fXi);
+    fFourMomentum = aParticle.fFourMomentum;
+    fHelix = aParticle.fHelix;
+    
+    //   for (int iter=0; iter<11; iter++)
+    //     fNominalPosSample[iter] = aParticle.fNominalPosSample[iter];
+
+    //   if (fTpcV0NegPosSample) delete fTpcV0NegPosSample;
+    //   if (aParticle.fTpcV0NegPosSample) {
+    //     fTpcV0NegPosSample = (AliFemtoThreeVector *) malloc(sizeof(AliFemtoThreeVector) * 11);
+    //     for (int iter=0; iter<11; iter++)
+    //       fTpcV0NegPosSample[iter] = aParticle.fTpcV0NegPosSample[iter];
+    //   }
+    
+    //   if (fV0NegZ) delete fV0NegZ;
+    //   if (aParticle.fV0NegZ) {
+    //     fV0NegZ = (float *) malloc(sizeof(float) * 45);
+    //     for (int iter=0; iter<11; iter++)
+    //       fV0NegZ[iter] = aParticle.fV0NegZ[iter];
+    //   }
+    //   if (fV0NegU) delete fV0NegU;
+    //   if (aParticle.fV0NegU) {
+    //     fV0NegU = (float *) malloc(sizeof(float) * 45);
+    //     for (int iter=0; iter<11; iter++)
+    //       fV0NegU[iter] = aParticle.fV0NegU[iter];
+    //   }
+    //   if (fV0NegSect) delete fV0NegSect;
+    //   if (aParticle.fV0NegSect) {
+    //     fV0NegSect = (int *) malloc(sizeof(int) * 45);
+    //     for (int iter=0; iter<11; iter++)
+    //       fV0NegSect[iter] = aParticle.fV0NegSect[iter];
+    //   }
+    
+    fPrimaryVertex = aParticle.fPrimaryVertex;
+    fSecondaryVertex = aParticle.fSecondaryVertex;
+//     if (fHiddenInfo) delete fHiddenInfo;
+//     if(aParticle.fHiddenInfo){
+//       fHiddenInfo= aParticle.fHiddenInfo->Clone();
+//     }
+    
+    //   fNominalTpcEntrancePoint = aParticle.fNominalTpcEntrancePoint;
+    //   fNominalTpcExitPoint     = aParticle.fNominalTpcExitPoint;
+    
+    if (fHiddenInfo) delete fHiddenInfo;
+    if (aParticle.fHiddenInfo) 
+      fHiddenInfo = aParticle.HiddenInfo()->Clone();
+    
+    for (int iter=0; iter<6; iter++)
+      fPurity[iter] = aParticle.fPurity[iter];
+    
+    fHelixV0Pos = aParticle.fHelixV0Pos;
+    fTpcV0PosEntrancePoint = aParticle.fTpcV0PosEntrancePoint;
+    fTpcV0PosExitPoint     = aParticle.fTpcV0PosExitPoint;
+    fHelixV0Neg = aParticle.fHelixV0Neg;
+    fTpcV0NegEntrancePoint = aParticle.fTpcV0NegEntrancePoint;
+    fTpcV0NegExitPoint     = aParticle.fTpcV0NegExitPoint;
+    
+  }
+
+  return *this;
+}
+// //_____________________
+// const AliFemtoThreeVector& AliFemtoParticle::NominalTpcExitPoint() const{
+//   // in future, may want to calculate this "on demand" only, sot this routine may get more sophisticated
+//   // for now, we calculate Exit and Entrance points upon instantiation
+//   return fNominalTpcExitPoint;
+// }
+// //_____________________
+// const AliFemtoThreeVector& AliFemtoParticle::NominalTpcEntrancePoint() const{
+//   // in future, may want to calculate this "on demand" only, sot this routine may get more sophisticated
+//   // for now, we calculate Exit and Entrance points upon instantiation
+//   return fNominalTpcEntrancePoint;
+// }
+//_____________________
+void AliFemtoParticle::CalculatePurity(){
+  // Calculate additional parameterized purity
+
+  double tPt = fFourMomentum.Perp();
+  // pi -
+  fPurity[0] = fgPrimPimPar0*(1.-exp((tPt-fgPrimPimPar1)/fgPrimPimPar2));
+  fPurity[0] *= fTrack->PidProbPion();
+  // pi+
+  fPurity[1] = fgPrimPipPar0*(1.-exp((tPt-fgPrimPipPar1)/fgPrimPipPar2));
+  fPurity[1] *= fTrack->PidProbPion();
+  // K-
+  fPurity[2] = fTrack->PidProbKaon();
+  // K+
+  fPurity[3] = fTrack->PidProbKaon();
+  // pbar
+  fPurity[4] = fTrack->PidProbProton();
+  // p
+  fPurity[5] = fTrack->PidProbProton();
+}
+
+double AliFemtoParticle::GetPionPurity()
+{
+  // Get full pion purity
+  if (fTrack->Charge()>0)
+    return fPurity[1];
+  else
+    return fPurity[0];
+}
+double AliFemtoParticle::GetKaonPurity()
+{
+  // Get full kaon purity
+  if (fTrack->Charge()>0)
+    return fPurity[3];
+  else
+    return fPurity[2];
+}
+double AliFemtoParticle::GetProtonPurity()
+{
+  // Get full proton purity
+  if (fTrack->Charge()>0)
+    return fPurity[5];
+  else
+    return fPurity[4];
+}
+
+// void AliFemtoParticle::CalculateTpcExitAndEntrancePoints(AliFmPhysicalHelixD* tHelix,
+//                                                    AliFemtoThreeVector*  PrimVert,
+//                                                    AliFemtoThreeVector*  SecVert,
+//                                                    AliFemtoThreeVector* tmpTpcEntrancePoint,
+//                                                    AliFemtoThreeVector* tmpTpcExitPoint,
+//                                                    AliFemtoThreeVector* tmpPosSample,
+//                                                    float* tmpZ,
+//                                                    float* tmpU,
+//                                                    int* tmpSect){
+//   // this calculates the exit point of a secondary track, 
+//   // either through the endcap or through the Outer Field Cage
+//   // We assume the track to start at tHelix.origin-PrimaryVertex
+//   // it also calculates the entrance point of the secondary track, 
+//   // which is the point at which it crosses the
+//   // inner field cage
+//   //  static AliFemtoThreeVector ZeroVec(0.,0.,0.);
+//   AliFemtoThreeVector tZeroVec(0.,0.,0.);
+// //   tZeroVec.SetX(tHelix->origin().x()-PrimVert->x());
+// //   tZeroVec.SetY(tHelix->origin().y()-PrimVert->y());
+// //   tZeroVec.SetZ(tHelix->origin().z()-PrimVert->z());
+//   tZeroVec.SetX(SecVert->x()-PrimVert->x());
+//   tZeroVec.SetY(SecVert->y()-PrimVert->y());
+//   tZeroVec.SetZ(SecVert->z()-PrimVert->z());
+//   double dip, curv, phase;
+//   int h;
+//   curv = tHelix->Curvature();
+//   dip  = tHelix->DipAngle();
+//   phase= tHelix->Phase();
+//   h    = tHelix->H();
+  
+//   AliFmHelixD hel(curv,dip,phase,tZeroVec,h);
+
+//   pairD candidates;
+//   double sideLength;  // this is how much length to go to leave through sides of TPC
+//   double endLength;  // this is how much length to go to leave through endcap of TPC
+//   // figure out how far to go to leave through side...
+//   candidates = hel.PathLength(200.0);  // bugfix MAL jul00 - 200cm NOT 2cm
+//   sideLength = (candidates.first > 0) ? candidates.first : candidates.second;
+
+//   static AliFemtoThreeVector tWestEnd(0.,0.,200.);  // bugfix MAL jul00 - 200cm NOT 2cm
+//   static AliFemtoThreeVector tEastEnd(0.,0.,-200.); // bugfix MAL jul00 - 200cm NOT 2cm
+//   static AliFemtoThreeVector tEndCapNormal(0.,0.,1.0);
+
+//   endLength = hel.PathLength(tWestEnd,tEndCapNormal);
+//   if (endLength < 0.0) endLength = hel.PathLength(tEastEnd,tEndCapNormal);
+
+//   if (endLength < 0.0) cout << 
+//                      "AliFemtoParticle::CalculateTpcExitAndEntrancePoints(): "
+//                             << "Hey -- I cannot find an exit point out endcaps" << endl;
+//   // OK, firstExitLength will be the shortest way out of the detector...
+//   double firstExitLength = (endLength < sideLength) ? endLength : sideLength;
+//   // now then, let's return the POSITION at which particle leaves TPC...
+//   *tmpTpcExitPoint = hel.At(firstExitLength);
+//   // Finally, calculate the position at which the track crosses the inner field cage
+//   candidates = hel.PathLength(50.0);  // bugfix MAL jul00 - 200cm NOT 2cm
+
+//   sideLength = (candidates.first > 0) ? candidates.first : candidates.second;
+//   //  cout << "sideLength 2 ="<<sideLength << endl;
+//   *tmpTpcEntrancePoint = hel.At(sideLength);
+//   // This is the secure way !  
+//   if (IsNaN(tmpTpcEntrancePoint->x()) || 
+//       IsNaN(tmpTpcEntrancePoint->y()) || 
+//       IsNaN(tmpTpcEntrancePoint->z()) ){ 
+//     cout << "tmpTpcEntrancePoint NAN"<< endl; 
+//     cout << "tmpNominalTpcEntrancePoint = " <<tmpTpcEntrancePoint<< endl;
+//     tmpTpcEntrancePoint->SetX(-9999.);
+//     tmpTpcEntrancePoint->SetY(-9999.);
+//     tmpTpcEntrancePoint->SetZ(-9999.);
+//   } 
+    
+//   if (IsNaN(tmpTpcExitPoint->x()) || 
+//       IsNaN(tmpTpcExitPoint->y()) || 
+//       IsNaN(tmpTpcExitPoint->z()) ) {
+// //     cout << "tmpTpcExitPoint NAN Set at (-9999,-9999,-9999)"<< endl; 
+// //     cout << "tmpTpcExitPoint X= " <<tmpTpcExitPoint->x()<< endl;
+// //     cout << "tmpTpcExitPoint Y= " <<tmpTpcExitPoint->y()<< endl;
+// //     cout << "tmpTpcExitPoint Z= " <<tmpTpcExitPoint->z()<< endl;
+//     tmpTpcExitPoint->SetX(-9999.);
+//     tmpTpcExitPoint->SetY(-9999.);
+//     tmpTpcExitPoint->SetZ(-9999.);
+//   }
+
+
+// //   if (IsNaN(tmpTpcExitPoint->x())) *tmpTpcExitPoint = AliFemtoThreeVector(-9999.,-9999.,-9999); 
+// //   if (IsNaN(tmpTpcEntrancetPoint->x())) *tmpTpcEntrancePoint = AliFemtoThreeVector(-9999.,-9999.,-9999); 
+//   //  cout << "tmpTpcEntrancePoint"<<*tmpTpcEntrancePoint << endl;
+
+//   // 03Oct00 - mal.  OK, let's try something a little more 
+//   // along the lines of NA49 and E895 strategy.
+//   // calculate the "nominal" position at N radii (say N=11) 
+//   // within the TPC, and for a pair cut
+//   // use the average separation of these N
+//   int irad = 0;
+//   candidates = hel.PathLength(50.0);
+//   sideLength = (candidates.first > 0) ? candidates.first : candidates.second;
+//   while (irad<11 && !IsNaN(sideLength)){ 
+//     float radius = 50.0 + irad*15.0;
+//     candidates = hel.PathLength(radius);
+//     sideLength = (candidates.first > 0) ? candidates.first : candidates.second;
+//     tmpPosSample[irad] = hel.At(sideLength);
+//     if(IsNaN(tmpPosSample[irad].x()) ||
+//        IsNaN(tmpPosSample[irad].y()) ||
+//        IsNaN(tmpPosSample[irad].z()) 
+//        ){
+//       cout << "tmpPosSample for radius=" << radius << " NAN"<< endl; 
+//       cout << "tmpPosSample=(" <<tmpPosSample[irad]<<")"<< endl;
+//       tmpPosSample[irad] =  AliFemtoThreeVector(-9999.,-9999.,-9999);
+//     }
+//     irad++;
+//     if (irad<11){
+//       float radius = 50.0 + irad*15.0;
+//       candidates = hel.PathLength(radius);
+//       sideLength = (candidates.first > 0) ? candidates.first : candidates.second;
+//     }
+//    }
+//    for (int i = irad; i<11; i++)
+//      {
+//        tmpPosSample[i] =  AliFemtoThreeVector(-9999.,-9999.,-9999);   
+//      }
+
+//   static float tRowRadius[45] = {60,64.8,69.6,74.4,79.2,84,88.8,93.6,98.8, 
+//                              104,109.2,114.4,119.6,127.195,129.195,131.195,
+//                              133.195,135.195,137.195,139.195,141.195,
+//                              143.195,145.195,147.195,149.195,151.195,
+//                              153.195,155.195,157.195,159.195,161.195,
+//                              163.195,165.195,167.195,169.195,171.195,
+//                              173.195,175.195,177.195,179.195,181.195,
+//                              183.195,185.195,187.195,189.195};
+//   int tRow,tSect,tOutOfBound;
+//   double tLength,tPhi;
+//   float tU;
+//   AliFemtoThreeVector tPoint;
+//   AliFmThreeVectorD tn(0,0,0);
+//   AliFmThreeVectorD tr(0,0,0);
+//   int ti =0;
+//   // test to enter the loop
+//   candidates =  hel.PathLength(tRowRadius[ti]);
+//   tLength = (candidates.first > 0) ? candidates.first : candidates.second;
+//   if (IsNaN(tLength)){
+//     cout <<"tLength Init tmp NAN" << endl;
+//     cout <<"padrow number= "<<ti << "not reached" << endl;
+//     cout << "*** DO NOT ENTER THE LOOP***" << endl;
+//     tmpSect[ti]=-1;//sector
+//   }
+//   // end test
+//   while(ti<45 && !IsNaN(tLength)){
+//     candidates =  hel.PathLength(tRowRadius[ti]);
+//     tLength = (candidates.first > 0) ? candidates.first : candidates.second;
+//     if (IsNaN(tLength)){
+//       cout <<"tLength loop 1st NAN" << endl;
+//       cout <<"padrow number=  " << ti << " not reached" << endl;
+//       cout << "*** THIS IS AN ERROR SHOULDN'T  LOOP ***" << endl;
+//       tmpSect[ti]=-1;//sector
+//     }
+//     tPoint = hel.At(tLength);
+//     // Find which sector it is on
+//     TpcLocalTransform(tPoint,tmpSect[ti],tRow,tU,tPhi);
+//     if (IsNaN(tmpSect[ti])){
+//       cout <<"***ERROR tmpSect"<< endl; 
+//     }
+//     if (IsNaN(tRow)){
+//       cout <<"***ERROR tRow"<< endl;
+//     }
+//     if (IsNaN(tU)){
+//       cout <<"***ERROR tU"<< endl;
+//     }
+//     if (IsNaN(tPhi)){
+//       cout <<"***ERROR tPhi"<< endl;
+//     }  
+//     // calculate crossing plane
+//     tn.SetX(cos(tPhi));
+//     tn.SetY(sin(tPhi));       
+//     tr.SetX(tRowRadius[ti]*cos(tPhi));
+//     tr.SetY(tRowRadius[ti]*sin(tPhi));
+//     // find crossing point
+//     tLength = hel.PathLength(tr,tn); 
+//     if (IsNaN(tLength)){
+//       cout <<"tLength loop 2nd  NAN" << endl;
+//       cout <<"padrow number=  " << ti << " not reached" << endl;
+//       tmpSect[ti]=-2;//sector
+//     }
+//     tPoint = hel.At(tLength);
+//     tmpZ[ti] = tPoint.z();
+//     tOutOfBound = TpcLocalTransform(tPoint,tSect,tRow,tmpU[ti],tPhi);
+//     if (IsNaN(tSect)){
+//       cout <<"***ERROR tSect 2"<< endl; 
+//     }
+//     if (IsNaN(tRow)){
+//       cout <<"***ERROR tRow 2"<< endl;
+//     }
+//     if (IsNaN(tmpU[ti])){
+//       cout <<"***ERROR tmpU[ti] 2"<< endl;
+//     }
+//     if (IsNaN(tPhi)){
+//       cout <<"***ERROR tPhi 2 "<< endl;
+//     }  
+//     if(tOutOfBound || (tmpSect[ti] == tSect && tRow!=(ti+1))){
+//       tmpSect[ti]=-2;
+//       //      cout << "missed once"<< endl;
+//     }
+//     else{
+//       if(tmpSect[ti] != tSect){
+//     // Try again on the other sector
+//     tn.SetX(cos(tPhi));
+//     tn.SetY(sin(tPhi));       
+//     tr.SetX(tRowRadius[ti]*cos(tPhi));
+//     tr.SetY(tRowRadius[ti]*sin(tPhi));
+//     // find crossing point
+//     tLength = hel.PathLength(tr,tn);
+//     tPoint = hel.At(tLength);
+//     if (IsNaN(tLength)){
+//       cout <<"tLength loop 3rd NAN" << endl;
+//       cout <<"padrow number=  "<< ti << " not reached" << endl;
+//       tmpSect[ti]=-1;//sector
+//     }
+//     tmpZ[ti] = tPoint.z();
+//     tmpSect[ti] = tSect;
+//     tOutOfBound = TpcLocalTransform(tPoint,tSect,tRow,tmpU[ti],tPhi);
+//     if (IsNaN(tSect)){
+//       cout <<"***ERROR tSect 3"<< endl; 
+//     }
+//     if (IsNaN(tRow)){
+//       cout <<"***ERROR tRow 3"<< endl;
+//     }
+//     if (IsNaN(tmpU[ti])){
+//       cout <<"***ERROR tmpU[ti] 3"<< endl;
+//     }
+//     if (IsNaN(tPhi)){
+//       cout <<"***ERROR tPhi 3 "<< endl;
+//     }  
+//     if(tOutOfBound || tSect!= tmpSect[ti] || tRow!=(ti+1)){
+//       tmpSect[ti]=-1;
+//     }
+//       }
+//     }
+//     if (IsNaN(tmpSect[ti])){
+//       cout << "*******************ERROR***************************" << endl;
+//       cout <<"AliFemtoParticle--Fctn tmpSect=" << tmpSect[ti] << endl;
+//       cout << "*******************ERROR***************************" << endl;
+//     }
+//     if (IsNaN(tmpU[ti])){
+//       cout << "*******************ERROR***************************" << endl;
+//       cout <<"AliFemtoParticle--Fctn tmpU=" << tmpU[ti] << endl;
+//       cout << "*******************ERROR***************************" << endl;
+//     }
+//     if (IsNaN(tmpZ[ti])){
+//       cout << "*******************ERROR***************************" << endl;
+//       cout <<"AliFemtoParticle--Fctn tmpZ=" << tmpZ[ti] << endl;
+//       cout << "*******************ERROR***************************" << endl;
+//     }
+//     // If padrow ti not reached all other beyond are not reached
+//     // in this case Set sector to -1
+//     if (tmpSect[ti]==-1){
+//       for (int tj=ti; tj<45;tj++){
+//     tmpSect[tj] = -1;
+//     ti=45;
+//       }
+//     }
+//     ti++;
+//     if (ti<45){
+//       candidates =  hel.PathLength(tRowRadius[ti]);
+//       tLength = (candidates.first > 0) ? candidates.first : candidates.second;}
+//   }
+// }
+//_____________________
+const AliFemtoThreeVector& AliFemtoParticle::TpcV0PosExitPoint() const{
+  return fTpcV0PosExitPoint;
+}
+//_____________________
+const AliFemtoThreeVector& AliFemtoParticle::TpcV0PosEntrancePoint() const{
+  return fTpcV0PosEntrancePoint;
+}
+//______________________
+const AliFemtoThreeVector& AliFemtoParticle::TpcV0NegExitPoint() const{
+  return fTpcV0NegExitPoint;
+}
+//_____________________
+const AliFemtoThreeVector& AliFemtoParticle::TpcV0NegEntrancePoint() const{
+  return fTpcV0NegEntrancePoint;
+}
+//______________________
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoParticle.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoParticle.h
new file mode 100644 (file)
index 0000000..009aa88
--- /dev/null
@@ -0,0 +1,161 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFemtoParticle: main class halding all the necessary information    //
+// about a particle that is required during femtoscopic analysis         //
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+
+#ifndef ALIFEMTOPARTICLE_H
+#define ALIFEMTOPARTICLE_H
+
+//#include "math.h"
+#include "AliFemtoTypes.h"
+#include "AliFemtoTrack.h"
+#include "AliFemtoV0.h"
+#include "AliFemtoKink.h"
+#include "AliFemtoXi.h"
+#include "AliFmPhysicalHelixD.h"
+// ***
+class AliFemtoHiddenInfo;
+// ***
+class AliFemtoParticle{
+public:
+  AliFemtoParticle();
+  AliFemtoParticle(const AliFemtoParticle& aParticle);
+  AliFemtoParticle(const AliFemtoTrack* const hbtTrack, const double& mass);
+  AliFemtoParticle(const AliFemtoV0* const hbtV0, const double& mass);
+  AliFemtoParticle(const AliFemtoKink* const hbtKink, const double& mass);
+  AliFemtoParticle(const AliFemtoXi* const hbtXi, const double& mass);
+  ~AliFemtoParticle();
+
+  AliFemtoParticle& operator=(const AliFemtoParticle& aParticle);
+
+  const AliFemtoLorentzVector& FourMomentum() const;
+
+  AliFmPhysicalHelixD& Helix();
+
+  const AliFemtoThreeVector DecayVertexPosition() const;
+  unsigned long TopologyMap(const int word) const;
+  int NumberOfHits() const;
+
+  unsigned long TrackId() const;         // only for particles from tracks 
+  unsigned short   NegTrackId() const;   // only for particles from v0 
+  unsigned short   PosTrackId() const;   // only for particles from v0 
+
+  AliFemtoTrack* Track() const;
+  AliFemtoV0* V0() const;
+  AliFemtoKink* Kink() const;
+
+/*   const AliFemtoThreeVector& NominalTpcExitPoint() const;     // position track exits TPC assuming start at (0,0,0) */
+/*   const AliFemtoThreeVector& NominalTpcEntrancePoint() const; // position track crosses IFC assuming start at (0,0,0) */
+  const AliFemtoThreeVector& TpcV0PosExitPoint() const;  
+  const AliFemtoThreeVector& TpcV0PosEntrancePoint() const;
+  const AliFemtoThreeVector& TpcV0NegExitPoint() const;  
+  const AliFemtoThreeVector& TpcV0NegEntrancePoint() const;
+
+  // the following method is for explicit internal calculation to fill datamembers.
+  // It is invoked automatically if AliFemtoParticle constructed from AliFemtoTrack
+  // void CalculateNominalTpcExitAndEntrancePoints(); 
+  // NOTE - this requires the fHelix, so be sure this is filled
+
+
+/*   AliFemtoThreeVector fNominalPosSample[11];  // I make this public for convenience and speed of AliFemtoPair() */
+/*   float fZ[45];  // Z position of cluster on padrow */
+/*   float fU[45];  // U position of cluster on padrow */
+/*   int fSect[45]; // Sector number of cluster on padrow */
+
+  void ResetFourMomentum(const AliFemtoLorentzVector& fourMomentum);
+
+  const AliFemtoHiddenInfo*  HiddenInfo() const;
+  // Fab private
+  AliFemtoHiddenInfo*  GetHiddenInfo() const;
+  void SetHiddenInfo(AliFemtoHiddenInfo* aHiddenInfo);
+  void CalculatePurity();
+  double GetPionPurity();
+  double GetKaonPurity();
+  double GetProtonPurity();
+/*   void CalculateTpcExitAndEntrancePoints( AliFmPhysicalHelixD* tHelix, */
+/*                                       AliFemtoThreeVector* PrimVert, */
+/*                                       AliFemtoThreeVector* SecVert, */
+/*                                       AliFemtoThreeVector* tmpTpcEntrancePoint, */
+/*                                       AliFemtoThreeVector* tmpTpcExitPoint, */
+/*                                       AliFemtoThreeVector* tmpPosSample, */
+/*                                       float* tmpZ,float* tmpU,int* tmpSect); */
+
+  // For V0 Neg Daugthers TpcEntrance/ExitPoints
+/*   AliFemtoThreeVector* fTpcV0NegPosSample; // Sample of TPC V0 neg */
+/*   float* fV0NegZ;                          // Array of Neg Z cluster positions */
+/*   float* fV0NegU;                          // Array of Neg U cluster positions */
+/*   int* fV0NegSect;                         // Array of Neg cluster sectors */
+private:
+  AliFemtoTrack* fTrack;  // copy of the track the particle was formed of, else Null
+  AliFemtoV0* fV0;        // copy of the v0 the particle was formed of, else Null
+  AliFemtoKink* fKink;    // copy of the v0 the particle was formed of, else Null
+  AliFemtoXi* fXi;        // copy of the Xi the particle was formed of, else Null  
+
+  AliFemtoLorentzVector fFourMomentum; // Particle momentum
+  AliFmPhysicalHelixD fHelix;          // Particle trajectory helix
+  //unsigned long  fMap[2]; 
+  //int fNhits;
+/*   AliFemtoThreeVector fNominalTpcExitPoint; // Point where particle exits TPC */
+/*   AliFemtoThreeVector fNominalTpcEntrancePoint; // Point where particle enters TPC */
+  AliFemtoHiddenInfo* fHiddenInfo;  // Fab private
+
+  double fPurity[6];  // Purity variables
+
+  static double fgPrimPimPar0; // purity parameterization parameter
+  static double fgPrimPimPar1; // purity parameterization parameter
+  static double fgPrimPimPar2; // purity parameterization parameter
+  static double fgPrimPipPar0; // purity parameterization parameter 
+  static double fgPrimPipPar1; // purity parameterization parameter
+  static double fgPrimPipPar2; // purity parameterization parameter
+  static double fgPrimPmPar0;  // purity parameterization parameter
+  static double fgPrimPmPar1;  // purity parameterization parameter
+  static double fgPrimPmPar2;  // purity parameterization parameter
+  static double fgPrimPpPar0;  // purity parameterization parameter
+  static double fgPrimPpPar1;  // purity parameterization parameter
+  static double fgPrimPpPar2;  // purity parameterization parameter
+
+   // For V0 Daugthers TpcEntrance/ExitPoints
+  AliFemtoThreeVector fPrimaryVertex;   // primary vertex of V0
+  AliFemtoThreeVector fSecondaryVertex; // secondary vertex of V0
+
+  AliFmPhysicalHelixD fHelixV0Pos;            // helix for positive V0 daughter                   
+  AliFemtoThreeVector fTpcV0PosEntrancePoint; // positive V0 daughter entrance point to TPC
+  AliFemtoThreeVector fTpcV0PosExitPoint;     // positive V0 daughter exit point from TPC  
+
+  AliFmPhysicalHelixD fHelixV0Neg;            // helix for negative V0 daughter                   
+  AliFemtoThreeVector fTpcV0NegEntrancePoint; // negative V0 daughter entrance point to TPC
+  AliFemtoThreeVector fTpcV0NegExitPoint;     // negative V0 daughter exit point from TPC  
+};
+
+inline AliFemtoTrack* AliFemtoParticle::Track() const { return fTrack; }
+inline unsigned long  AliFemtoParticle::TrackId() const { return fTrack->TrackId(); }
+inline const AliFemtoLorentzVector& AliFemtoParticle::FourMomentum() const {return fFourMomentum;}
+inline AliFmPhysicalHelixD& AliFemtoParticle::Helix() {return fHelix;}
+//inline unsigned long AliFemtoParticle::TopologyMap(const int word) const {return fMap[word];}
+//inline int AliFemtoParticle::NumberOfHits() const {return fNhits;}
+//by marek chojnacki to could compile 
+
+inline unsigned long AliFemtoParticle::TopologyMap(const int /* word */) const {return 1;}
+inline int AliFemtoParticle::NumberOfHits() const {return 1;}
+
+inline AliFemtoV0* AliFemtoParticle::V0() const { return fV0; }
+inline unsigned short AliFemtoParticle::NegTrackId() const { return fV0->IdNeg(); }
+inline unsigned short AliFemtoParticle::PosTrackId() const { return fV0->IdPos(); }
+inline const AliFemtoThreeVector AliFemtoParticle::DecayVertexPosition() const {return fV0->DecayVertexV0(); }
+// ***
+inline AliFemtoHiddenInfo* AliFemtoParticle::GetHiddenInfo() const
+{return fHiddenInfo;}
+inline const AliFemtoHiddenInfo* AliFemtoParticle::HiddenInfo() const
+{return fHiddenInfo;}
+inline void AliFemtoParticle::SetHiddenInfo(AliFemtoHiddenInfo* aHiddenInfo)
+{ fHiddenInfo = aHiddenInfo->Clone();}
+// ***
+
+inline void AliFemtoParticle::ResetFourMomentum(const AliFemtoLorentzVector& vec){fFourMomentum = vec;}
+
+inline AliFemtoKink* AliFemtoParticle::Kink() const { return fKink; }
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoParticleCollection.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoParticleCollection.h
new file mode 100644 (file)
index 0000000..fe101c7
--- /dev/null
@@ -0,0 +1,46 @@
+/***************************************************************************
+ *
+ * $Id$
+ *
+ * Author: Mike Lisa, Ohio State, lisa@mps.ohio-state.edu
+ ***************************************************************************
+ *
+ * Description: part of STAR HBT Framework: AliFemtoMaker package
+ *   The ParticleCollection is the main component of the picoEvent
+ *   It points to the particle objects in the picoEvent.           
+ *
+ ***************************************************************************
+ *
+ * $Log$
+ * Revision 1.1.1.1  2007/04/25 15:38:41  panos
+ * Importing the HBT code dir
+ *
+ * Revision 1.1.1.1  2007/03/07 10:14:49  mchojnacki
+ * First version on CVS
+ *
+ * Revision 1.2  2000/02/01 00:33:32  laue
+ * namespaces changed to run on the new Solaris Compiler CC5
+ * since we can use member templates in franks1Histo.h we are doing it
+ *
+ * Revision 1.1.1.1  1999/06/29 16:02:57  lisa
+ * Installation of AliFemtoMaker
+ *
+ **************************************************************************/
+#ifndef AliFemtoParticleCollection_hh
+#define AliFemtoParticleCollection_hh
+#include "AliFemtoParticle.h"
+#include <list>
+
+#if !defined(ST_NO_NAMESPACES)
+using std::list;
+#endif
+
+#ifdef ST_NO_TEMPLATE_DEF_ARGS
+typedef list<AliFemtoParticle*, allocator<AliFemtoParticle*> >            AliFemtoParticleCollection;
+typedef list<AliFemtoParticle*, allocator<AliFemtoParticle*> >::iterator  AliFemtoParticleIterator;
+#else
+typedef list<AliFemtoParticle*>            AliFemtoParticleCollection;
+typedef list<AliFemtoParticle*>::iterator  AliFemtoParticleIterator;
+#endif
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoParticleCut.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoParticleCut.h
new file mode 100644 (file)
index 0000000..8a36120
--- /dev/null
@@ -0,0 +1,69 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoParticleCut - the pure virtual base class for the particle cut     //
+// All particle cuts must inherit from this one                               //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+
+#ifndef ALIFEMTOPARTICLECUT_H
+#define ALIFEMTOPARTICLECUT_H
+
+#include "AliFemtoTypes.h"
+#include "AliFemtoCutMonitorHandler.h"
+#include <TObjString.h>
+#include <TList.h>
+
+class AliFemtoAnalysis;
+
+class AliFemtoParticleCut : public AliFemtoCutMonitorHandler {
+
+  friend class AliFemtoAnalysis;
+
+public:
+  AliFemtoParticleCut();   // default constructor. - Users should write their own
+  AliFemtoParticleCut(const AliFemtoParticleCut&); // copy constructor
+  virtual ~AliFemtoParticleCut(){/* no-op */};  // destructor
+  AliFemtoParticleCut& operator=(const AliFemtoParticleCut& aCut);
+
+  virtual AliFemtoString Report() =0;    // user-written method to return string describing cuts
+  virtual TList* ListSettings();      // user-written list of settings which is stored in the result file
+
+  double Mass(){return fMass;};       // mass of the particle being selected
+  virtual void SetMass(const double& mass) {fMass = mass;};
+
+  virtual AliFemtoParticleCut* Clone() { return 0;}
+
+  virtual AliFemtoParticleType Type()=0;
+
+  // the following allows "back-pointing" from the CorrFctn to the "parent" Analysis
+  AliFemtoAnalysis* HbtAnalysis(){return fyAnalysis;};
+  void SetAnalysis(AliFemtoAnalysis*);
+
+protected:
+  AliFemtoAnalysis* fyAnalysis; // Link to the base analysis class
+  double fMass;
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoParticleCut, 0)
+#endif
+};
+
+inline AliFemtoParticleCut::AliFemtoParticleCut(): AliFemtoCutMonitorHandler(), fyAnalysis(0), fMass(0){}   // default constructor. - Users should write their own
+inline AliFemtoParticleCut::AliFemtoParticleCut(const AliFemtoParticleCut& c): AliFemtoCutMonitorHandler(), fyAnalysis(0), fMass(0) { 
+  fMass = c.fMass; fyAnalysis = 0; 
+#ifdef STHBTDEBUG
+  cout << " AliFemtoParticleCut::AliFemtoParticleCut(const AliFemtoParticleCut& c) - fMass: " << fMass << endl;
+#endif
+}
+inline void AliFemtoParticleCut::SetAnalysis(AliFemtoAnalysis* analysis) { fyAnalysis = analysis; }
+inline AliFemtoParticleCut& AliFemtoParticleCut::operator=(const AliFemtoParticleCut& aCut) { if (this == &aCut) return *this; fyAnalysis = aCut.fyAnalysis; fMass=aCut.fMass; return *this; }
+  inline TList *AliFemtoParticleCut::ListSettings() { 
+    TList *tListSetttings = new TList(); 
+    char buf[100];
+    snprintf(buf, 100, "AliFemtoParticleCut.mass=%f", fMass);
+    TObjString *str = new TObjString(buf);
+    tListSetttings->Add(str);
+    return tListSetttings;
+  }
+  
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoPicoEvent.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoPicoEvent.cxx
new file mode 100644 (file)
index 0000000..06bcbf3
--- /dev/null
@@ -0,0 +1,198 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoPicoEvent - internal AliFemto representation of the event.         //
+// Created for the sake of minimizing the used size. Multiple instances are   //
+// stored in memory when several mixing bins are used.                        //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+/***************************************************************************
+ *
+ * $Id$
+ *
+ * Author: Mike Lisa, Ohio State, lisa@mps.ohio-state.edu
+ ***************************************************************************
+ *
+ * Description: part of STAR HBT Framework: AliFemtoMaker package
+ *  PicoEvents are last-step ultra-compressed "events" just containing
+ *  bare information about the particles of interest.  They have already
+ *  gone through Event and Track cuts, so only Pair cuts are left.
+ *  PicoEvents are *internal* to the code, and are stored in the
+ *  Event-mixing buffers.
+ *           
+ *
+ ***************************************************************************
+ *
+ * $Log$
+ * Revision 1.1.2.1  2007/10/12 14:28:37  akisiel
+ * New wave of cleanup and rule conformance
+ *
+ * Revision 1.1  2007/05/16 10:22:11  akisiel
+ * Making the directory structure of AliFemto flat. All files go into one common directory
+ *
+ * Revision 1.2  2007/05/03 09:42:29  akisiel
+ * Fixing Effective C++ warnings
+ *
+ * Revision 1.1.1.1  2007/04/25 15:38:41  panos
+ * Importing the HBT code dir
+ *
+ * Revision 1.1.1.1  2007/03/07 10:14:49  mchojnacki
+ * First version on CVS
+ *
+ * Revision 1.4  2000/07/16 21:38:23  laue
+ * AliFemtoCoulomb.cxx AliFemtoSectoredAnalysis.cxx : updated for standalone version
+ * AliFemtoV0.cc AliFemtoV0.h : some cast to prevent compiling warnings
+ * AliFemtoParticle.cc AliFemtoParticle.h : pointers mTrack,mV0 initialized to 0
+ * AliFemtoIOBinary.cc : some printouts in #ifdef STHBTDEBUG
+ * AliFemtoEvent.cc : B-Field set to 0.25Tesla, we have to think about a better
+ *                 solution
+ *
+ * Revision 1.3  2000/06/01 20:40:13  laue
+ * AliFemtoIO.cc: updated for new V0s
+ * AliFemtoPicoEvent.cc: collections especially cleared
+ * franks1DHistoD.h, include changed from  <stdio> to <cstdio>
+ * franks1DHistoD.cc, cout statement deleted
+ *
+ * Revision 1.2  2000/03/17 17:23:05  laue
+ * Roberts new three particle correlations implemented.
+ *
+ * Revision 1.1.1.1  1999/06/29 16:02:57  lisa
+ * Installation of AliFemtoMaker
+ *
+ **************************************************************************/
+
+#include "AliFemtoPicoEvent.h"
+#include "AliFemtoParticleCollection.h"
+
+//________________
+AliFemtoPicoEvent::AliFemtoPicoEvent() :
+  fFirstParticleCollection(0),
+  fSecondParticleCollection(0),
+  fThirdParticleCollection(0)
+{
+  // Default constructor
+  fFirstParticleCollection = new AliFemtoParticleCollection;
+  fSecondParticleCollection = new AliFemtoParticleCollection;
+  fThirdParticleCollection = new AliFemtoParticleCollection;
+}
+//_________________
+AliFemtoPicoEvent::AliFemtoPicoEvent(const AliFemtoPicoEvent& aPicoEvent) :
+  fFirstParticleCollection(0),
+  fSecondParticleCollection(0),
+  fThirdParticleCollection(0)
+{
+  // Copy constructor
+  AliFemtoParticleIterator iter;
+
+  fFirstParticleCollection = new AliFemtoParticleCollection;
+  if (aPicoEvent.fFirstParticleCollection) {
+    for (iter=aPicoEvent.fFirstParticleCollection->begin();iter!=aPicoEvent.fFirstParticleCollection->end();iter++){
+      fFirstParticleCollection->push_back(*iter);
+    }
+  }
+  fSecondParticleCollection = new AliFemtoParticleCollection;
+  if (aPicoEvent.fSecondParticleCollection) {
+    for (iter=aPicoEvent.fSecondParticleCollection->begin();iter!=aPicoEvent.fSecondParticleCollection->end();iter++){
+      fSecondParticleCollection->push_back(*iter);
+    }
+  }
+  fThirdParticleCollection = new AliFemtoParticleCollection;
+  if (aPicoEvent.fThirdParticleCollection) {
+    for (iter=aPicoEvent.fThirdParticleCollection->begin();iter!=aPicoEvent.fThirdParticleCollection->end();iter++){
+      fThirdParticleCollection->push_back(*iter);
+    }
+  }
+}
+//_________________
+AliFemtoPicoEvent::~AliFemtoPicoEvent(){
+  // Destructor
+  AliFemtoParticleIterator iter;
+  
+  if (fFirstParticleCollection){
+    for (iter=fFirstParticleCollection->begin();iter!=fFirstParticleCollection->end();iter++){
+      delete *iter;
+    }
+    fFirstParticleCollection->clear();
+    delete fFirstParticleCollection;
+    fFirstParticleCollection = 0;
+  }
+  
+  if (fSecondParticleCollection){
+    for (iter=fSecondParticleCollection->begin();iter!=fSecondParticleCollection->end();iter++){
+      delete *iter;
+    }
+    fSecondParticleCollection->clear();
+    delete fSecondParticleCollection;
+    fSecondParticleCollection = 0;
+  }
+
+  if (fThirdParticleCollection){
+    if (fThirdParticleCollection->size() != 0 ) {
+      for (iter=fThirdParticleCollection->begin();iter!=fThirdParticleCollection->end();iter++){
+       delete *iter;
+      }
+    }
+    fThirdParticleCollection->clear();
+    delete fThirdParticleCollection;
+    fThirdParticleCollection = 0;
+  }
+}
+//_________________
+AliFemtoPicoEvent& AliFemtoPicoEvent::operator=(const AliFemtoPicoEvent& aPicoEvent) 
+{
+  // Assignment operator
+  if (this == &aPicoEvent) 
+    return *this;
+
+  AliFemtoParticleIterator iter;
+   
+  if (fFirstParticleCollection){
+      for (iter=fFirstParticleCollection->begin();iter!=fFirstParticleCollection->end();iter++){
+       delete *iter;
+      }
+      fFirstParticleCollection->clear();
+      delete fFirstParticleCollection;
+      fFirstParticleCollection = 0;
+  }
+
+  if (fSecondParticleCollection){
+    for (iter=fSecondParticleCollection->begin();iter!=fSecondParticleCollection->end();iter++){
+      delete *iter;
+    }
+    fSecondParticleCollection->clear();
+    delete fSecondParticleCollection;
+    fSecondParticleCollection = 0;
+  }
+
+  if (fThirdParticleCollection){
+    if (fThirdParticleCollection->size() != 0 ) {
+      for (iter=fThirdParticleCollection->begin();iter!=fThirdParticleCollection->end();iter++){
+       delete *iter;
+      }
+    }
+    fThirdParticleCollection->clear();
+    delete fThirdParticleCollection;
+    fThirdParticleCollection = 0;
+  }
+
+  fFirstParticleCollection = new AliFemtoParticleCollection;
+  if (aPicoEvent.fFirstParticleCollection) {
+    for (iter=aPicoEvent.fFirstParticleCollection->begin();iter!=aPicoEvent.fFirstParticleCollection->end();iter++){
+      fFirstParticleCollection->push_back(*iter);
+    }
+  }
+  fSecondParticleCollection = new AliFemtoParticleCollection;
+  if (aPicoEvent.fSecondParticleCollection) {
+    for (iter=aPicoEvent.fSecondParticleCollection->begin();iter!=aPicoEvent.fSecondParticleCollection->end();iter++){
+      fSecondParticleCollection->push_back(*iter);
+    }
+  }
+  fThirdParticleCollection = new AliFemtoParticleCollection;
+  if (aPicoEvent.fThirdParticleCollection) {
+    for (iter=aPicoEvent.fThirdParticleCollection->begin();iter!=aPicoEvent.fThirdParticleCollection->end();iter++){
+      fThirdParticleCollection->push_back(*iter);
+    }
+  }
+
+  return *this;
+}
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoPicoEvent.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoPicoEvent.h
new file mode 100644 (file)
index 0000000..bcea239
--- /dev/null
@@ -0,0 +1,71 @@
+/***************************************************************************
+ *
+ * $Id$
+ *
+ * Author: Mike Lisa, Ohio State, lisa@mps.ohio-state.edu
+ ***************************************************************************
+ *
+ * Description: part of STAR HBT Framework: AliFemtoMaker package
+ *  PicoEvents are last-step ultra-compressed "events" just containing
+ *  bare information about the particles of interest.  They have already
+ *  gone through Event and Track cuts, so only Pair cuts are left.
+ *  PicoEvents are *internal* to the code, and are stored in the
+ *  Event-mixing buffers.
+ *           
+ *
+ ***************************************************************************
+ *
+ * $Log$
+ * Revision 1.1.2.1  2007/10/12 14:28:37  akisiel
+ * New wave of cleanup and rule conformance
+ *
+ * Revision 1.1  2007/05/16 10:22:11  akisiel
+ * Making the directory structure of AliFemto flat. All files go into one common directory
+ *
+ * Revision 1.2  2007/05/03 09:42:29  akisiel
+ * Fixing Effective C++ warnings
+ *
+ * Revision 1.1.1.1  2007/04/25 15:38:41  panos
+ * Importing the HBT code dir
+ *
+ * Revision 1.1.1.1  2007/03/07 10:14:49  mchojnacki
+ * First version on CVS
+ *
+ * Revision 1.2  2000/03/17 17:23:05  laue
+ * Roberts new three particle correlations implemented.
+ *
+ * Revision 1.1.1.1  1999/06/29 16:02:57  lisa
+ * Installation of AliFemtoMaker
+ *
+ **************************************************************************/
+
+#ifndef ALIFEMTOPICOEVENT_H
+#define ALIFEMTOPICOEVENT_H
+
+#include "AliFemtoParticleCollection.h"
+
+class AliFemtoPicoEvent{
+public:
+  AliFemtoPicoEvent();
+  AliFemtoPicoEvent(const AliFemtoPicoEvent& aPicoEvent);
+  ~AliFemtoPicoEvent();
+
+  AliFemtoPicoEvent& operator=(const AliFemtoPicoEvent& aPicoEvent);
+
+  /* may want to have other stuff in here, like where is primary vertex */
+
+  AliFemtoParticleCollection* FirstParticleCollection();
+  AliFemtoParticleCollection* SecondParticleCollection();
+  AliFemtoParticleCollection* ThirdParticleCollection();
+
+private:
+  AliFemtoParticleCollection* fFirstParticleCollection;  // Collection of particles of type 1
+  AliFemtoParticleCollection* fSecondParticleCollection; // Collection of particles of type 2
+  AliFemtoParticleCollection* fThirdParticleCollection;  // Collection of particles of type 3
+};
+
+inline AliFemtoParticleCollection* AliFemtoPicoEvent::FirstParticleCollection(){return fFirstParticleCollection;}
+inline AliFemtoParticleCollection* AliFemtoPicoEvent::SecondParticleCollection(){return fSecondParticleCollection;}
+inline AliFemtoParticleCollection* AliFemtoPicoEvent::ThirdParticleCollection(){return fThirdParticleCollection;}
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoPicoEventCollection.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoPicoEventCollection.h
new file mode 100644 (file)
index 0000000..3e035ed
--- /dev/null
@@ -0,0 +1,47 @@
+/***************************************************************************
+ *
+ * $Id$
+ *
+ * Author: Mike Lisa, Ohio State, lisa@mps.ohio-state.edu
+ ***************************************************************************
+ *
+ * Description: part of STAR HBT Framework: AliFemtoMaker package
+ *   A Collection of PicoEvents is what makes up the EventMixingBuffer
+ *   of each Analysis
+ *
+ ***************************************************************************
+ *
+ * $Log$
+ * Revision 1.1.1.1  2007/04/25 15:38:41  panos
+ * Importing the HBT code dir
+ *
+ * Revision 1.1.1.1  2007/03/07 10:14:49  mchojnacki
+ * First version on CVS
+ *
+ * Revision 1.2  2000/02/01 00:33:32  laue
+ * namespaces changed to run on the new Solaris Compiler CC5
+ * since we can use member templates in franks1Histo.h we are doing it
+ *
+ * Revision 1.1.1.1  1999/06/29 16:02:57  lisa
+ * Installation of AliFemtoMaker
+ *
+ **************************************************************************/
+
+#ifndef AliFemtoPicoEventCollection_hh
+#define AliFemtoPicoEventCollection_hh
+#include "AliFemtoPicoEvent.h"
+#include <list>
+
+#if !defined(ST_NO_NAMESPACES)
+using std::list;
+#endif
+
+#ifdef ST_NO_TEMPLATE_DEF_ARGS
+typedef list<AliFemtoPicoEvent*, allocator<AliFemtoPicoEvent*> >            AliFemtoPicoEventCollection;
+typedef list<AliFemtoPicoEvent*, allocator<AliFemtoPicoEvent*> >::iterator  AliFemtoPicoEventIterator;
+#else
+typedef list<AliFemtoPicoEvent*>            AliFemtoPicoEventCollection;
+typedef list<AliFemtoPicoEvent*>::iterator  AliFemtoPicoEventIterator;
+#endif
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoPicoEventCollectionVector.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoPicoEventCollectionVector.h
new file mode 100644 (file)
index 0000000..f7244f0
--- /dev/null
@@ -0,0 +1,44 @@
+/***************************************************************************
+ *
+ * $Id$
+ *
+ * Author: Mike Lisa, Ohio State, lisa@mps.ohio-state.edu
+ ***************************************************************************
+ *
+ * Description: part of STAR HBT Framework: AliFemtoMaker package
+ *
+ ***************************************************************************
+ *
+ * $Log$
+ * Revision 1.1.1.1  2007/04/25 15:38:41  panos
+ * Importing the HBT code dir
+ *
+ * Revision 1.1.1.1  2007/03/07 10:14:49  mchojnacki
+ * First version on CVS
+ *
+ * Revision 1.1  2000/07/16 21:44:11  laue
+ * Collection and analysis for vertex dependent event mixing
+ *
+ *
+ **************************************************************************/
+
+#ifndef AliFemtoPicoEventCollectionVector_hh
+#define AliFemtoPicoEventCollectionVector_hh
+#include "AliFemtoPicoEventCollection.h"
+#include <vector>
+#include <list>
+
+#if !defined(ST_NO_NAMESPACES)
+using std::vector;
+using std::list;
+#endif
+
+#ifdef ST_NO_TEMPLATE_DEF_ARGS
+typedef vector<AliFemtoPicoEventCollection*, allocator<AliFemtoPicoEventCollection*> >            AliFemtoPicoEventCollectionVector;  //!
+typedef vector<AliFemtoPicoEventCollection*, allocator<AliFemtoPicoEventCollection*> >::iterator  AliFemtoPicoEventCollectionIterator;//!
+#else
+typedef vector<AliFemtoPicoEventCollection*>            AliFemtoPicoEventCollectionVector;//!
+typedef vector<AliFemtoPicoEventCollection*>::iterator  AliFemtoPicoEventCollectionIterator;//!
+#endif
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoPicoEventCollectionVectorHideAway.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoPicoEventCollectionVectorHideAway.cxx
new file mode 100644 (file)
index 0000000..31f67e9
--- /dev/null
@@ -0,0 +1,128 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFemtoPicoEventCollectionVectorHideAway: a helper class for         //
+// managing many mixing buffers with up to three variables used for      //
+// binning.                                                              //
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+#include "AliFemtoPicoEventCollectionVectorHideAway.h"
+
+// -----------------------------------
+AliFemtoPicoEventCollectionVectorHideAway::AliFemtoPicoEventCollectionVectorHideAway(int bx, double lx, double ux,
+                                                                                    int by, double ly, double uy,
+                                                                                    int bz, double lz, double uz):
+  fBinsTot(0),
+  fBinsx(bx), fBinsy(by), fBinsz(bz),
+  fMinx(lx),  fMiny(ly),  fMinz(lz),
+  fMaxx(ux),  fMaxy(uy),  fMaxz(uz),
+  fStepx(0),  fStepy(0),  fStepz(0),
+  fCollection(0),
+  fCollectionVector(0)
+{
+  // basic constructor
+  fBinsTot = fBinsx * fBinsy * fBinsz;
+  fStepx=0;  fStepx = (fMaxx-fMinx)/fBinsx;
+  fStepy=0;  fStepy = (fMaxy-fMiny)/fBinsy;
+  fStepz=0;  fStepz = (fMaxz-fMinz)/fBinsz;
+  
+  
+  //fCollectionVector = new AliFemtoPicoEventCollectionVector();
+  fCollection = 0;
+  for ( int i=0; i<fBinsTot; i++) {
+    fCollection = new AliFemtoPicoEventCollection();
+    fCollectionVector.push_back(fCollection);
+  }
+}
+// -----------------------------------
+AliFemtoPicoEventCollection* AliFemtoPicoEventCollectionVectorHideAway::PicoEventCollection(int ix, int iy, int iz) { 
+  // return mixing event collection from a given bin
+  if ( ix<0 || ix >= fBinsx) return 0;
+  if ( iy<0 || iy >= fBinsy) return 0;
+  if ( iz<0 || iz >= fBinsz) return 0;
+  int bin = ix + iy*fBinsx + iz*fBinsy*fBinsx; 
+//   cout << " AliFemtoPicoEventCollectionVectorHideAway::PicoEventCollection(...) - bin(ix,iy,iz): ";
+//   cout << bin << "(" << ix <<"," << iy << "," << iz <<")" << endl;
+  return fCollectionVector[bin]; 
+}
+// -----------------------------------
+AliFemtoPicoEventCollection* AliFemtoPicoEventCollectionVectorHideAway::PicoEventCollection(double x, double y, double z) {
+  // return mixing event collection for given values on x, y, z axes
+  int ix,iy,iz;
+  ix=0;iy=0;iz=0;
+
+  ix = (int)floor( (x-fMinx)/fStepx );
+  iy = (int)floor( (y-fMiny)/fStepy );
+  iz = (int)floor( (z-fMinz)/fStepz );
+
+  return PicoEventCollection( ix,iy,iz );
+}
+//___________________________________
+AliFemtoPicoEventCollectionVectorHideAway::AliFemtoPicoEventCollectionVectorHideAway(const AliFemtoPicoEventCollectionVectorHideAway& aColl):
+  fBinsTot(0),
+  fBinsx(0), fBinsy(0), fBinsz(0),
+  fMinx(0),  fMiny(0),  fMinz(0),
+  fMaxx(0),  fMaxy(0),  fMaxz(0),
+  fStepx(0),  fStepy(0),  fStepz(0),
+  fCollection(0),
+  fCollectionVector(0)
+{
+  // copy constructor
+  fBinsTot = aColl.fBinsTot;
+  fBinsx = aColl.fBinsx;
+  fBinsy = aColl.fBinsy;
+  fBinsz = aColl.fBinsz;
+  fMinx  = aColl.fMinx;
+  fMiny  = aColl.fMiny;
+  fMinz  = aColl.fMinz;
+  fMaxx  = aColl.fMaxx;
+  fMaxy  = aColl.fMaxy;
+  fMaxz  = aColl.fMaxz;
+  fStepx = aColl.fStepx;
+  fStepy = aColl.fStepy;
+  fStepz = aColl.fStepz;
+  fCollection = aColl.fCollection;
+
+  fCollectionVector.clear();
+  for (int iter=0; aColl.fCollectionVector.size();iter++){
+    fCollectionVector.push_back(aColl.fCollectionVector[iter]);
+  }
+}
+//___________________________________
+AliFemtoPicoEventCollectionVectorHideAway::~AliFemtoPicoEventCollectionVectorHideAway()
+{
+  // destructor
+  fCollectionVector.clear();
+}
+//___________________________________
+AliFemtoPicoEventCollectionVectorHideAway& AliFemtoPicoEventCollectionVectorHideAway::operator=(const AliFemtoPicoEventCollectionVectorHideAway& aColl)
+{
+  // assignment operator
+  if (this == &aColl)
+    return *this;
+
+  fBinsTot = aColl.fBinsTot;
+  fBinsx = aColl.fBinsx;
+  fBinsy = aColl.fBinsy;
+  fBinsz = aColl.fBinsz;
+  fMinx  = aColl.fMinx;
+  fMiny  = aColl.fMiny;
+  fMinz  = aColl.fMinz;
+  fMaxx  = aColl.fMaxx;
+  fMaxy  = aColl.fMaxy;
+  fMaxz  = aColl.fMaxz;
+  fStepx = aColl.fStepx;
+  fStepy = aColl.fStepy;
+  fStepz = aColl.fStepz;
+  fCollection = aColl.fCollection;
+
+  fCollectionVector.clear();
+
+  for (int iter=0; aColl.fCollectionVector.size();iter++){
+    fCollectionVector.push_back(aColl.fCollectionVector[iter]);
+  }
+
+  return *this;
+}
+unsigned int AliFemtoPicoEventCollectionVectorHideAway::GetBinXNumber(double x) { return (int)floor( (x-fMinx)/fStepx ); }
+unsigned int AliFemtoPicoEventCollectionVectorHideAway::GetBinYNumber(double y) { return (int)floor( (y-fMiny)/fStepy ); }
+unsigned int AliFemtoPicoEventCollectionVectorHideAway::GetBinZNumber(double z) { return (int)floor( (z-fMinz)/fStepz ); }
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoPicoEventCollectionVectorHideAway.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoPicoEventCollectionVectorHideAway.h
new file mode 100644 (file)
index 0000000..c4518d2
--- /dev/null
@@ -0,0 +1,48 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFemtoPicoEventCollectionVectorHideAway: a helper class for         //
+// managing many mixing buffers with up to three variables used for      //
+// binning.                                                              //
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+
+#ifndef ALIFEMTOPICOEVENTCOLLECTIONVECTORHIDEAWAY_H
+#define ALIFEMTOPICOEVENTCOLLECTIONVECTORHIDEAWAY_H
+#include "AliFemtoPicoEvent.h"
+#include "AliFemtoPicoEventCollection.h"
+#include "AliFemtoPicoEventCollectionVector.h"
+#include <vector>
+#include <list>
+#include <float.h>
+#include <limits.h>
+
+#if !defined(ST_NO_NAMESPACES)
+using std::vector;
+using std::list;
+#endif
+
+class AliFemtoPicoEventCollectionVectorHideAway {
+public:
+  AliFemtoPicoEventCollectionVectorHideAway(int bx=1, double lx=-FLT_MAX, double ux=FLT_MAX,
+                                           int by=1, double ly=-FLT_MAX, double uy=FLT_MAX,
+                                           int bz=1, double lz=-FLT_MAX, double uz=FLT_MAX);
+  AliFemtoPicoEventCollectionVectorHideAway(const AliFemtoPicoEventCollectionVectorHideAway& aColl);
+  ~AliFemtoPicoEventCollectionVectorHideAway();
+  AliFemtoPicoEventCollectionVectorHideAway& operator=(const AliFemtoPicoEventCollectionVectorHideAway& aColl);
+
+  AliFemtoPicoEventCollection* PicoEventCollection(int bx, int by, int bz);
+  AliFemtoPicoEventCollection* PicoEventCollection(double x, double y=0, double z=0);
+  unsigned int GetBinXNumber(double x);
+  unsigned int GetBinYNumber(double y);
+  unsigned int GetBinZNumber(double z);
+private:
+  int fBinsTot;                                        // Total number of bins 
+  int fBinsx,fBinsy,fBinsz;                            // Number of bins on x, y, z axis
+  double fMinx,fMiny,fMinz;                            // Minima on x, y, z axis
+  double fMaxx,fMaxy,fMaxz;                            // Maxima on x, y, z axis
+  double fStepx,fStepy,fStepz;                         // Steps on x, y, z axis
+  AliFemtoPicoEventCollection* fCollection;            // Pico event collection
+  AliFemtoPicoEventCollectionVector fCollectionVector; // Collection vector
+};
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoQinvCorrFctn.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoQinvCorrFctn.cxx
new file mode 100644 (file)
index 0000000..af14d2a
--- /dev/null
@@ -0,0 +1,165 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFemtoQinvCorrFctn:                                                 //
+// a simple Q-invariant correlation function                             // 
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+
+#include "AliFemtoQinvCorrFctn.h"
+//#include "AliFemtoHisto.h"
+#include <cstdio>
+
+#ifdef __ROOT__ 
+ClassImp(AliFemtoQinvCorrFctn)
+#endif
+
+//____________________________
+AliFemtoQinvCorrFctn::AliFemtoQinvCorrFctn(char* title, const int& nbins, const float& QinvLo, const float& QinvHi):
+  fNumerator(0),
+  fDenominator(0),
+  fRatio(0),
+  fkTMonitor(0)
+{
+  // set up numerator
+  //  title = "Num Qinv (MeV/c)";
+  char tTitNum[101] = "Num";
+  strncat(tTitNum,title, 100);
+  fNumerator = new TH1D(tTitNum,title,nbins,QinvLo,QinvHi);
+  // set up denominator
+  //title = "Den Qinv (MeV/c)";
+  char tTitDen[101] = "Den";
+  strncat(tTitDen,title, 100);
+  fDenominator = new TH1D(tTitDen,title,nbins,QinvLo,QinvHi);
+  // set up ratio
+  //title = "Ratio Qinv (MeV/c)";
+  char tTitRat[101] = "Rat";
+  strncat(tTitRat,title, 100);
+  fRatio = new TH1D(tTitRat,title,nbins,QinvLo,QinvHi);
+  char tTitkT[101] = "kTDep";
+  strncat(tTitkT,title, 100);
+  fkTMonitor = new TH1D(tTitkT,title,200,0.0,2.0);
+  // this next bit is unfortunately needed so that we can have many histos of same "title"
+  // it is neccessary if we typedef TH1D to TH1d (which we do)
+  //fNumerator->SetDirectory(0);
+  //fDenominator->SetDirectory(0);
+  //fRatio->SetDirectory(0);
+
+  // to enable error bar calculation...
+  fNumerator->Sumw2();
+  fDenominator->Sumw2();
+  fRatio->Sumw2();
+  fkTMonitor->Sumw2();
+}
+
+//____________________________
+AliFemtoQinvCorrFctn::AliFemtoQinvCorrFctn(const AliFemtoQinvCorrFctn& aCorrFctn) :
+  AliFemtoCorrFctn(),
+  fNumerator(0),
+  fDenominator(0),
+  fRatio(0),
+  fkTMonitor(0)
+{
+  // copy constructor
+  fNumerator = new TH1D(*aCorrFctn.fNumerator);
+  fDenominator = new TH1D(*aCorrFctn.fDenominator);
+  fRatio = new TH1D(*aCorrFctn.fRatio);
+  fkTMonitor = new TH1D(*aCorrFctn.fkTMonitor);
+}
+//____________________________
+AliFemtoQinvCorrFctn::~AliFemtoQinvCorrFctn(){
+  // destructor
+  delete fNumerator;
+  delete fDenominator;
+  delete fRatio;
+  delete fkTMonitor;
+}
+//_________________________
+AliFemtoQinvCorrFctn& AliFemtoQinvCorrFctn::operator=(const AliFemtoQinvCorrFctn& aCorrFctn)
+{
+  // assignment operator
+  if (this == &aCorrFctn)
+    return *this;
+
+  if (fNumerator) delete fNumerator;
+  fNumerator = new TH1D(*aCorrFctn.fNumerator);
+  if (fDenominator) delete fDenominator;
+  fDenominator = new TH1D(*aCorrFctn.fDenominator);
+  if (fRatio) delete fRatio;
+  fRatio = new TH1D(*aCorrFctn.fRatio);
+  if (fkTMonitor) delete fkTMonitor;
+  fkTMonitor = new TH1D(*aCorrFctn.fkTMonitor);
+
+  return *this;
+}
+
+//_________________________
+void AliFemtoQinvCorrFctn::Finish(){
+  // here is where we should normalize, fit, etc...
+  // we should NOT Draw() the histos (as I had done it below),
+  // since we want to insulate ourselves from root at this level
+  // of the code.  Do it instead at root command line with browser.
+  //  fNumerator->Draw();
+  //fDenominator->Draw();
+  //fRatio->Draw();
+  fRatio->Divide(fNumerator,fDenominator,1.0,1.0);
+
+}
+
+//____________________________
+AliFemtoString AliFemtoQinvCorrFctn::Report(){
+  // construct report
+  string stemp = "Qinv Correlation Function Report:\n";
+  char ctemp[100];
+  snprintf(ctemp , 100, "Number of entries in numerator:\t%E\n",fNumerator->GetEntries());
+  stemp += ctemp;
+  snprintf(ctemp , 100, "Number of entries in denominator:\t%E\n",fDenominator->GetEntries());
+  stemp += ctemp;
+  snprintf(ctemp , 100, "Number of entries in ratio:\t%E\n",fRatio->GetEntries());
+  stemp += ctemp;
+  //  stemp += mCoulombWeight->Report();
+  AliFemtoString returnThis = stemp;
+  return returnThis;
+}
+//____________________________
+void AliFemtoQinvCorrFctn::AddRealPair(AliFemtoPair* pair){
+  // add true pair
+  if (fPairCut)
+    if (!fPairCut->Pass(pair)) return;
+  
+  double tQinv = fabs(pair->QInv());   // note - qInv() will be negative for identical pairs...
+  fNumerator->Fill(tQinv);
+  fkTMonitor->Fill(pair->KT());
+  //  cout << "AliFemtoQinvCorrFctn::AddRealPair : " << pair->qInv() << " " << tQinv <<
+  //" " << pair->track1().FourMomentum() << " " << pair->track2().FourMomentum() << endl;
+}
+//____________________________
+void AliFemtoQinvCorrFctn::AddMixedPair(AliFemtoPair* pair){
+  // add mixed (background) pair
+  if (fPairCut)
+    if (!fPairCut->Pass(pair)) return;
+  
+  double weight = 1.0;
+  double tQinv = fabs(pair->QInv());   // note - qInv() will be negative for identical pairs...
+  fDenominator->Fill(tQinv,weight);
+}
+//____________________________
+void AliFemtoQinvCorrFctn::Write(){
+  // Write out neccessary objects
+  fNumerator->Write(); 
+  fDenominator->Write();  
+  fkTMonitor->Write();
+}
+//______________________________
+TList* AliFemtoQinvCorrFctn::GetOutputList()
+{
+  // Prepare the list of objects to be written to the output
+  TList *tOutputList = new TList();
+
+  tOutputList->Add(fNumerator); 
+  tOutputList->Add(fDenominator);  
+  tOutputList->Add(fkTMonitor);
+
+  return tOutputList;
+}
+
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoQinvCorrFctn.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoQinvCorrFctn.h
new file mode 100644 (file)
index 0000000..f0bc3f2
--- /dev/null
@@ -0,0 +1,90 @@
+/***************************************************************************
+ *
+ * $Id$
+ *
+ * Author: Mike Lisa, Ohio State, lisa@mps.ohio-state.edu
+ ***************************************************************************
+ *
+ * Description: part of STAR HBT Framework: AliFemtoMaker package
+ *   a simple Q-invariant correlation function           
+ *
+ ***************************************************************************
+ *
+ * $Log$
+ * Revision 1.1  2007/05/16 10:22:11  akisiel
+ * Making the directory structure of AliFemto flat. All files go into one common directory
+ *
+ * Revision 1.2  2007/05/03 09:40:42  akisiel
+ * Fixing Effective C++ warnings
+ *
+ * Revision 1.1.1.1  2007/04/25 15:38:41  panos
+ * Importing the HBT code dir
+ *
+ * Revision 1.1.1.1  2007/03/07 10:14:49  mchojnacki
+ * First version on CVS
+ *
+ * Revision 1.3  2000/01/25 17:34:45  laue
+ * I. In order to run the stand alone version of the AliFemtoMaker the following
+ * changes have been done:
+ * a) all ClassDefs and ClassImps have been put into #ifdef __ROOT__ statements
+ * b) unnecessary includes of StMaker.h have been removed
+ * c) the subdirectory AliFemtoMaker/doc/Make has been created including everything
+ * needed for the stand alone version
+ *
+ * II. To reduce the amount of compiler warning
+ * a) some variables have been type casted
+ * b) some destructors have been declared as virtual
+ *
+ * Revision 1.2  1999/07/06 22:33:20  lisa
+ * Adjusted all to work in pro and new - dev itself is broken
+ *
+ * Revision 1.1.1.1  1999/06/29 16:02:57  lisa
+ * Installation of AliFemtoMaker
+ *
+ **************************************************************************/
+
+#ifndef ALIFEMTOQINVCORRFCTN_H
+#define ALIFEMTOQINVCORRFCTN_H
+
+#include "TH1D.h"
+#include "AliFemtoCorrFctn.h"
+
+class AliFemtoQinvCorrFctn : public AliFemtoCorrFctn {
+public:
+  AliFemtoQinvCorrFctn(char* title, const int& nbins, const float& QinvLo, const float& QinvHi);
+  AliFemtoQinvCorrFctn(const AliFemtoQinvCorrFctn& aCorrFctn);
+  virtual ~AliFemtoQinvCorrFctn();
+
+  AliFemtoQinvCorrFctn& operator=(const AliFemtoQinvCorrFctn& aCorrFctn);
+
+  virtual AliFemtoString Report();
+  virtual void AddRealPair(AliFemtoPair* aPair);
+  virtual void AddMixedPair(AliFemtoPair* aPair);
+
+  virtual void Finish();
+
+  TH1D* Numerator();
+  TH1D* Denominator();
+  TH1D* Ratio();
+
+  virtual TList* GetOutputList();
+  void Write();
+
+private:
+  TH1D* fNumerator;          // numerator - real pairs
+  TH1D* fDenominator;        // denominator - mixed pairs
+  TH1D* fRatio;              // ratio - correlation function
+  TH1D* fkTMonitor;          // Monitor the kT of pairs in the function
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoQinvCorrFctn, 1)
+#endif
+};
+
+inline  TH1D* AliFemtoQinvCorrFctn::Numerator(){return fNumerator;}
+inline  TH1D* AliFemtoQinvCorrFctn::Denominator(){return fDenominator;}
+inline  TH1D* AliFemtoQinvCorrFctn::Ratio(){return fRatio;}
+
+
+#endif
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoSimpleAnalysis.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoSimpleAnalysis.cxx
new file mode 100644 (file)
index 0000000..af3ffe6
--- /dev/null
@@ -0,0 +1,617 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFemtoSimpleAnalysis - the most basic analysis there is. All other        //
+// inherit from this one. Provides basic functionality for the analysis. //
+// To properly set up the analysis the following steps should be taken:  //
+//                                                                       //
+// - create particle cuts and add them via SetFirstParticleCut and       //
+//   SetSecondParticleCut. If one analyzes identical particle            //
+//   correlations, the first particle cut must be also the second        //
+//   particle cut.                                                       //
+//                                                                       //
+// - create pair cuts and add them via SetPairCut                        //
+//                                                                       //
+// - create one or many correlation functions and add them via           //
+//   AddCorrFctn method.                                                 //
+//                                                                       //
+// - specify how many events are to be strored in the mixing buffer for  //
+//   background construction                                             //
+//                                                                       //
+// Then, when the analysis is run, for each event, the EventBegin is     //
+// called before any processing is done, then the ProcessEvent is called //
+// which takes care of creating real and mixed pairs and sending them    //
+// to all the registered correlation functions. At the end of each event,//
+// after all pairs are processed, EventEnd is called. After the whole    //
+// analysis finishes (there is no more events to process) Finish() is    //
+// called.                                                               //
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+#include "AliFemtoSimpleAnalysis.h"
+#include "AliFemtoTrackCut.h"
+#include "AliFemtoV0Cut.h"
+#include "AliFemtoKinkCut.h"
+#include <string>
+#include <iostream>
+
+// blah blah
+
+#ifdef __ROOT__ 
+ClassImp(AliFemtoSimpleAnalysis)
+#endif
+
+AliFemtoEventCut*    copyTheCut(AliFemtoEventCut*);
+AliFemtoParticleCut* copyTheCut(AliFemtoParticleCut*);
+AliFemtoPairCut*     copyTheCut(AliFemtoPairCut*);
+AliFemtoCorrFctn*    copyTheCorrFctn(AliFemtoCorrFctn*);
+
+// this little function used to apply ParticleCuts (TrackCuts or V0Cuts) and fill ParticleCollections of picoEvent
+//  it is called from AliFemtoSimpleAnalysis::ProcessEvent()
+void FillHbtParticleCollection(AliFemtoParticleCut*         partCut,
+                              AliFemtoEvent*               hbtEvent,
+                              AliFemtoParticleCollection*  partCollection)
+{
+  // Fill particle collections from the event
+  // by the particles that pass all the cuts
+  switch (partCut->Type()) {
+  case hbtTrack:       // cut is cutting on Tracks
+    {
+      AliFemtoTrackCut* pCut = (AliFemtoTrackCut*) partCut;
+      AliFemtoTrack* pParticle;
+      AliFemtoTrackIterator pIter;
+      AliFemtoTrackIterator startLoop = hbtEvent->TrackCollection()->begin();
+      AliFemtoTrackIterator endLoop   = hbtEvent->TrackCollection()->end();
+      for (pIter=startLoop;pIter!=endLoop;pIter++){
+       pParticle = *pIter;
+       bool tmpPassParticle = pCut->Pass(pParticle);
+       pCut->FillCutMonitor(pParticle, tmpPassParticle);
+       if (tmpPassParticle){   
+         AliFemtoParticle* particle = new AliFemtoParticle(pParticle,pCut->Mass());
+         partCollection->push_back(particle);
+       }
+      }
+      break;
+    }
+  case hbtV0:          // cut is cutting on V0s
+    {
+      AliFemtoV0Cut* pCut = (AliFemtoV0Cut*) partCut;
+      AliFemtoV0* pParticle;
+      AliFemtoV0Iterator pIter;
+      AliFemtoV0Iterator startLoop = hbtEvent->V0Collection()->begin();
+      AliFemtoV0Iterator endLoop   = hbtEvent->V0Collection()->end();
+      // this following "for" loop is identical to the one above, but because of scoping, I can's see how to avoid repitition...
+      for (pIter=startLoop;pIter!=endLoop;pIter++){
+       pParticle = *pIter; 
+       bool tmpPassV0 = pCut->Pass(pParticle);
+       pCut->FillCutMonitor(pParticle,tmpPassV0);
+       if (tmpPassV0){
+         AliFemtoParticle* particle = new AliFemtoParticle(pParticle,partCut->Mass());
+         partCollection->push_back(particle);
+       }
+      }
+      pCut->FillCutMonitor(hbtEvent,partCollection);// Gael 19/06/02
+      break;
+    }
+  case hbtKink:          // cut is cutting on Kinks  -- mal 25May2001
+    {
+      AliFemtoKinkCut* pCut = (AliFemtoKinkCut*) partCut;
+      AliFemtoKink* pParticle;
+      AliFemtoKinkIterator pIter;
+      AliFemtoKinkIterator startLoop = hbtEvent->KinkCollection()->begin();
+      AliFemtoKinkIterator endLoop   = hbtEvent->KinkCollection()->end();
+      // this following "for" loop is identical to the one above, but because of scoping, I can's see how to avoid repitition...
+      for (pIter=startLoop;pIter!=endLoop;pIter++){
+       pParticle = *pIter; 
+       bool tmpPass = pCut->Pass(pParticle);
+       pCut->FillCutMonitor(pParticle,tmpPass);
+       if (tmpPass){
+         AliFemtoParticle* particle = new AliFemtoParticle(pParticle,partCut->Mass());
+         partCollection->push_back(particle);
+       }
+      }
+      break;
+    }
+  default:
+    cout << "FillHbtParticleCollection function (in AliFemtoSimpleAnalysis.cxx) - undefined Particle Cut type!!! \n";
+  }
+}
+//____________________________
+AliFemtoSimpleAnalysis::AliFemtoSimpleAnalysis() :
+  fPicoEventCollectionVectorHideAway(0), 
+  fPairCut(0),            
+  fCorrFctnCollection(0), 
+  fEventCut(0),           
+  fFirstParticleCut(0),   
+  fSecondParticleCut(0),  
+  fMixingBuffer(0),       
+  fPicoEvent(0),          
+  fNumEventsToMix(0),                     
+  fNeventsProcessed(0),                   
+  fMinSizePartCollection(0)
+{
+  // Default constructor
+  //  mControlSwitch     = 0;
+  fCorrFctnCollection = new AliFemtoCorrFctnCollection;
+  fMixingBuffer = new AliFemtoPicoEventCollection;
+}
+//____________________________
+
+AliFemtoSimpleAnalysis::AliFemtoSimpleAnalysis(const AliFemtoSimpleAnalysis& a) : 
+  AliFemtoAnalysis(),
+  fPicoEventCollectionVectorHideAway(0), 
+  fPairCut(0),            
+  fCorrFctnCollection(0), 
+  fEventCut(0),           
+  fFirstParticleCut(0),   
+  fSecondParticleCut(0),  
+  fMixingBuffer(0),       
+  fPicoEvent(0),          
+  fNumEventsToMix(0),                     
+  fNeventsProcessed(0),                   
+  fMinSizePartCollection(0)
+{
+  // Copy constructor
+  //AliFemtoSimpleAnalysis();
+  fCorrFctnCollection = new AliFemtoCorrFctnCollection;
+  fMixingBuffer = new AliFemtoPicoEventCollection;
+
+  // find the right event cut
+  fEventCut = a.fEventCut->Clone();
+  // find the right first particle cut
+  fFirstParticleCut = a.fFirstParticleCut->Clone();
+  // find the right second particle cut
+  if (a.fFirstParticleCut==a.fSecondParticleCut) 
+    SetSecondParticleCut(fFirstParticleCut); // identical particle hbt
+  else
+  fSecondParticleCut = a.fSecondParticleCut->Clone();
+
+  fPairCut = a.fPairCut->Clone();
+  
+  if ( fEventCut ) {
+      SetEventCut(fEventCut); // this will set the myAnalysis pointer inside the cut
+      cout << " AliFemtoSimpleAnalysis::AliFemtoSimpleAnalysis(const AliFemtoSimpleAnalysis& a) - event cut set " << endl;
+  }
+  if ( fFirstParticleCut ) {
+      SetFirstParticleCut(fFirstParticleCut); // this will set the myAnalysis pointer inside the cut
+      cout << " AliFemtoSimpleAnalysis::AliFemtoSimpleAnalysis(const AliFemtoSimpleAnalysis& a) - first particle cut set " << endl;
+  }
+  if ( fSecondParticleCut ) {
+      SetSecondParticleCut(fSecondParticleCut); // this will set the myAnalysis pointer inside the cut
+      cout << " AliFemtoSimpleAnalysis::AliFemtoSimpleAnalysis(const AliFemtoSimpleAnalysis& a) - second particle cut set " << endl;
+  }  if ( fPairCut ) {
+      SetPairCut(fPairCut); // this will set the myAnalysis pointer inside the cut
+      cout << " AliFemtoSimpleAnalysis::AliFemtoSimpleAnalysis(const AliFemtoSimpleAnalysis& a) - pair cut set " << endl;
+  }
+
+  AliFemtoCorrFctnIterator iter;
+  for (iter=a.fCorrFctnCollection->begin(); iter!=a.fCorrFctnCollection->end();iter++){
+    cout << " AliFemtoSimpleAnalysis::AliFemtoSimpleAnalysis(const AliFemtoSimpleAnalysis& a) - looking for correlation functions " << endl;
+    AliFemtoCorrFctn* fctn = (*iter)->Clone();
+    if (fctn) AddCorrFctn(fctn);
+    else cout << " AliFemtoSimpleAnalysis::AliFemtoSimpleAnalysis(const AliFemtoSimpleAnalysis& a) - correlation function not found " << endl;
+  }
+
+  fNumEventsToMix = a.fNumEventsToMix;
+
+  fMinSizePartCollection = a.fMinSizePartCollection;  // minimum # particles in ParticleCollection
+
+  cout << " AliFemtoSimpleAnalysis::AliFemtoSimpleAnalysis(const AliFemtoSimpleAnalysis& a) - analysis copied " << endl;
+
+}
+//____________________________
+AliFemtoSimpleAnalysis::~AliFemtoSimpleAnalysis(){
+  // destructor
+  cout << " AliFemtoSimpleAnalysis::~AliFemtoSimpleAnalysis()" << endl;
+  if (fEventCut) delete fEventCut; fEventCut=0;
+  if (fFirstParticleCut == fSecondParticleCut) fSecondParticleCut=0;
+  if (fFirstParticleCut)  delete fFirstParticleCut; fFirstParticleCut=0;
+  if (fSecondParticleCut) delete fSecondParticleCut; fSecondParticleCut=0;
+  if (fPairCut) delete fPairCut; fPairCut=0;
+  // now delete every CorrFunction in the Collection, and then the Collection itself
+  AliFemtoCorrFctnIterator iter;
+  for (iter=fCorrFctnCollection->begin(); iter!=fCorrFctnCollection->end();iter++){
+    delete *iter;
+  }
+  delete fCorrFctnCollection;
+  // now delete every PicoEvent in the EventMixingBuffer and then the Buffer itself
+  if (fMixingBuffer) {
+    AliFemtoPicoEventIterator piter;
+    for (piter=fMixingBuffer->begin();piter!=fMixingBuffer->end();piter++){
+      delete *piter;
+    }
+    delete fMixingBuffer;
+  }
+}
+//______________________
+AliFemtoSimpleAnalysis& AliFemtoSimpleAnalysis::operator=(const AliFemtoSimpleAnalysis& aAna) 
+{
+  // Assignment operator
+  if (this == &aAna)
+    return *this;
+
+  if (fCorrFctnCollection) delete fCorrFctnCollection;
+  fCorrFctnCollection = new AliFemtoCorrFctnCollection;
+  if (fMixingBuffer) delete fMixingBuffer;
+  fMixingBuffer = new AliFemtoPicoEventCollection;
+
+  // find the right event cut
+  if (fEventCut) delete fEventCut;
+  fEventCut = aAna.fEventCut->Clone();
+  // find the right first particle cut
+  if (fFirstParticleCut) delete fFirstParticleCut;
+  fFirstParticleCut = aAna.fFirstParticleCut->Clone();
+  // find the right second particle cut
+  if (fSecondParticleCut) delete fSecondParticleCut;
+  if (aAna.fFirstParticleCut==aAna.fSecondParticleCut) 
+    SetSecondParticleCut(fFirstParticleCut); // identical particle hbt
+  else
+    fSecondParticleCut = aAna.fSecondParticleCut->Clone();
+
+  if (fPairCut) delete fPairCut;
+  fPairCut = aAna.fPairCut->Clone();
+  
+  if ( fEventCut ) {
+    SetEventCut(fEventCut); // this will set the myAnalysis pointer inside the cut
+  }
+  if ( fFirstParticleCut ) {
+    SetFirstParticleCut(fFirstParticleCut); // this will set the myAnalysis pointer inside the cut
+  }
+  if ( fSecondParticleCut ) {
+    SetSecondParticleCut(fSecondParticleCut); // this will set the myAnalysis pointer inside the cut
+  }  
+  if ( fPairCut ) {
+    SetPairCut(fPairCut); // this will set the myAnalysis pointer inside the cut
+  }
+
+  AliFemtoCorrFctnIterator iter;
+  for (iter=aAna.fCorrFctnCollection->begin(); iter!=aAna.fCorrFctnCollection->end();iter++){
+    AliFemtoCorrFctn* fctn = (*iter)->Clone();
+    if (fctn) AddCorrFctn(fctn);
+  }
+
+  fNumEventsToMix = aAna.fNumEventsToMix;
+
+  fMinSizePartCollection = aAna.fMinSizePartCollection;  // minimum # particles in ParticleCollection
+
+  return *this;
+}
+//______________________
+AliFemtoCorrFctn* AliFemtoSimpleAnalysis::CorrFctn(int n){  
+  // return pointer to n-th correlation function
+  if ( n<0 || n > (int)fCorrFctnCollection->size() )
+    return NULL;
+  AliFemtoCorrFctnIterator iter=fCorrFctnCollection->begin();
+  for (int i=0; i<n ;i++){
+    iter++;
+  }
+  return *iter;
+}
+//____________________________
+AliFemtoString AliFemtoSimpleAnalysis::Report()
+{
+  // Create a simple report from the analysis execution
+  cout << "AliFemtoSimpleAnalysis - constructing Report..."<<endl;
+  string temp = "-----------\nHbt Analysis Report:\n";
+  temp += "\nEvent Cuts:\n";
+  temp += fEventCut->Report();
+  temp += "\nParticle Cuts - First Particle:\n";
+  temp += fFirstParticleCut->Report();
+  temp += "\nParticle Cuts - Second Particle:\n";
+  temp += fSecondParticleCut->Report();
+  temp += "\nPair Cuts:\n";
+  temp += fPairCut->Report();
+  temp += "\nCorrelation Functions:\n";
+  AliFemtoCorrFctnIterator iter;
+  if ( fCorrFctnCollection->size()==0 ) {
+    cout << "AliFemtoSimpleAnalysis-Warning : no correlations functions in this analysis " << endl;
+  }
+  for (iter=fCorrFctnCollection->begin(); iter!=fCorrFctnCollection->end();iter++){
+    temp += (*iter)->Report();
+    temp += "\n";
+  }
+  temp += "-------------\n";
+  AliFemtoString returnThis=temp;
+  return returnThis;
+}
+//_________________________
+void AliFemtoSimpleAnalysis::ProcessEvent(const AliFemtoEvent* hbtEvent) {
+  // Add event to processed events
+  fPicoEvent=0; // we will get a new pico event, if not prevent corr. fctn to access old pico event
+  AddEventProcessed();
+  // startup for EbyE 
+  EventBegin(hbtEvent);  
+  // event cut and event cut monitor
+  bool tmpPassEvent = fEventCut->Pass(hbtEvent);
+  if (!tmpPassEvent) 
+    fEventCut->FillCutMonitor(hbtEvent, tmpPassEvent);
+  if (tmpPassEvent) {
+//     cout << "AliFemtoSimpleAnalysis::ProcessEvent() - Event has passed cut - build picoEvent from " <<
+//       hbtEvent->TrackCollection()->size() << " tracks in TrackCollection" << endl;
+//    cout << "Event has passed cut with " << hbtEvent->TrackCollection()->size() << " tracks" << endl;
+    // OK, analysis likes the event-- build a pico event from it, using tracks the analysis likes...
+    fPicoEvent = new AliFemtoPicoEvent; // this is what we will make pairs from and put in Mixing Buffer
+    // no memory leak. we will delete picoevents when they come out of the mixing buffer
+    FillHbtParticleCollection(fFirstParticleCut,(AliFemtoEvent*)hbtEvent,fPicoEvent->FirstParticleCollection());
+    if ( !(AnalyzeIdenticalParticles()) )
+      FillHbtParticleCollection(fSecondParticleCut,(AliFemtoEvent*)hbtEvent,fPicoEvent->SecondParticleCollection());
+//     cout <<"AliFemtoSimpleAnalysis::ProcessEvent - #particles in First, Second Collections: " <<
+//       fPicoEvent->FirstParticleCollection()->size() << " " <<
+//       fPicoEvent->SecondParticleCollection()->size() << endl;
+    
+    cout << "#particles in Collection 1, 2: " <<
+      fPicoEvent->FirstParticleCollection()->size() << " " <<
+      fPicoEvent->SecondParticleCollection()->size() << endl;
+    
+    // mal - implement a switch which allows only using events with ParticleCollections containing a minimum
+    // number of entries (jun2002)
+    if ((fPicoEvent->FirstParticleCollection()->size() >= fMinSizePartCollection )
+       && ( AnalyzeIdenticalParticles() || (fPicoEvent->SecondParticleCollection()->size() >= fMinSizePartCollection ))) {
+      fEventCut->FillCutMonitor(hbtEvent, tmpPassEvent);
+      
+
+//------------------------------------------------------------------------------
+//   Temporary comment:
+//      This whole section rewritten so that all pairs are built using the
+//      same code... easier to read and manage, and MakePairs() can be called by
+//      derived classes.  Also, the requirement of a full mixing buffer before
+//      mixing is removed.
+//                          Dan Magestro, 11/2002
+
+      //------ Make real pairs. If identical, make pairs for one collection ------//
+
+      if (AnalyzeIdenticalParticles()) {
+        MakePairs("real", fPicoEvent->FirstParticleCollection() );
+      }
+      else {
+        MakePairs("real", fPicoEvent->FirstParticleCollection(),
+                          fPicoEvent->SecondParticleCollection() );
+      }
+      cout << "AliFemtoSimpleAnalysis::ProcessEvent() - reals done ";
+
+      //---- Make pairs for mixed events, looping over events in mixingBuffer ----//
+
+      AliFemtoPicoEvent* storedEvent;
+      AliFemtoPicoEventIterator fPicoEventIter;
+      for (fPicoEventIter=MixingBuffer()->begin();fPicoEventIter!=MixingBuffer()->end();fPicoEventIter++){
+        storedEvent = *fPicoEventIter;
+        if (AnalyzeIdenticalParticles()) {
+          MakePairs("mixed",fPicoEvent->FirstParticleCollection(),
+                            storedEvent->FirstParticleCollection() );
+        }
+        else {
+          MakePairs("mixed",fPicoEvent->FirstParticleCollection(),
+                            storedEvent->SecondParticleCollection() );
+
+          MakePairs("mixed",storedEvent->FirstParticleCollection(),
+                            fPicoEvent->SecondParticleCollection() );
+        }
+      }
+      cout << " - mixed done   " << endl;
+
+      //--------- If mixing buffer is full, delete oldest event ---------//
+
+      if ( MixingBufferFull() ) {
+        delete MixingBuffer()->back();
+        MixingBuffer()->pop_back();
+      }
+
+      //-------- Add current event (fPicoEvent) to mixing buffer --------//
+
+      MixingBuffer()->push_front(fPicoEvent);
+
+
+// Temporary comment: End of rewritten section... Dan Magestro, 11/2002
+//------------------------------------------------------------------------------
+
+
+    }  // if ParticleCollections are big enough (mal jun2002)
+    else{
+      fEventCut->FillCutMonitor(hbtEvent, !tmpPassEvent);
+      delete fPicoEvent;
+    }
+  }   // if currentEvent is accepted by currentAnalysis
+  EventEnd(hbtEvent);  // cleanup for EbyE 
+  //cout << "AliFemtoSimpleAnalysis::ProcessEvent() - return to caller ... " << endl;
+}
+//_________________________
+void AliFemtoSimpleAnalysis::MakePairs(const char* typeIn, AliFemtoParticleCollection *partCollection1,
+                                      AliFemtoParticleCollection *partCollection2){
+// Build pairs, check pair cuts, and call CFs' AddRealPair() or
+// AddMixedPair() methods. If no second particle collection is
+// specfied, make pairs within first particle collection.
+
+  string type = typeIn;
+
+  //  int swpart = ((long int) partCollection1) % 2;
+  int swpart = fNeventsProcessed % 2;
+
+  AliFemtoPair* tPair = new AliFemtoPair;
+
+  AliFemtoCorrFctnIterator tCorrFctnIter;
+
+  AliFemtoParticleIterator tPartIter1, tPartIter2;
+
+  AliFemtoParticleIterator tStartOuterLoop = partCollection1->begin();  // always
+  AliFemtoParticleIterator tEndOuterLoop   = partCollection1->end();    // will be one less if identical
+  AliFemtoParticleIterator tStartInnerLoop;
+  AliFemtoParticleIterator tEndInnerLoop;
+  if (partCollection2) {                        // Two collections:
+    tStartInnerLoop = partCollection2->begin();  //   Full inner & outer loops
+    tEndInnerLoop   = partCollection2->end();    //
+  }
+  else {                                        // One collection:
+    tEndOuterLoop--;                             //   Outer loop goes to next-to-last particle
+    tEndInnerLoop = partCollection1->end() ;     //   Inner loop goes to last particle
+  }
+  for (tPartIter1=tStartOuterLoop;tPartIter1!=tEndOuterLoop;tPartIter1++) {
+    if (!partCollection2){
+      tStartInnerLoop = tPartIter1;
+      tStartInnerLoop++;
+    }
+    tPair->SetTrack1(*tPartIter1);
+    for (tPartIter2 = tStartInnerLoop; tPartIter2!=tEndInnerLoop;tPartIter2++) {
+      tPair->SetTrack2(*tPartIter2);
+
+      // The following lines have to be uncommented if you want pairCutMonitors
+      // they are not in for speed reasons
+      // bool tmpPassPair = fPairCut->Pass(tPair);
+      // fPairCut->FillCutMonitor(tPair, tmpPassPair);
+      // if ( tmpPassPair )
+
+      //---- If pair passes cut, loop over CF's and add pair to real/mixed ----//
+
+      if (!partCollection2) {
+       if (swpart) {
+         tPair->SetTrack1(*tPartIter2);
+         tPair->SetTrack2(*tPartIter1);
+         swpart = 0;
+       }
+       else {
+         tPair->SetTrack1(*tPartIter1);
+         tPair->SetTrack2(*tPartIter2);
+         swpart = 1;
+       }
+      }
+
+      if (fPairCut->Pass(tPair)){
+        for (tCorrFctnIter=fCorrFctnCollection->begin();
+             tCorrFctnIter!=fCorrFctnCollection->end();tCorrFctnIter++){
+          AliFemtoCorrFctn* tCorrFctn = *tCorrFctnIter;
+          if(type == "real")
+            tCorrFctn->AddRealPair(tPair);
+         else if(type == "mixed")
+            tCorrFctn->AddMixedPair(tPair);
+          else
+            cout << "Problem with pair type, type = " << type.c_str() << endl;
+        }
+      }
+
+    }    // loop over second particle
+
+  }      // loop over first particle
+
+  delete tPair;
+
+}
+//_________________________
+void AliFemtoSimpleAnalysis::EventBegin(const AliFemtoEvent* ev){
+  // Perform initialization operations at the beginning of the event processing
+  //cout << " AliFemtoSimpleAnalysis::EventBegin(const AliFemtoEvent* ev) " << endl;
+  fFirstParticleCut->EventBegin(ev);
+  fSecondParticleCut->EventBegin(ev);
+  fPairCut->EventBegin(ev);
+  for (AliFemtoCorrFctnIterator iter=fCorrFctnCollection->begin(); iter!=fCorrFctnCollection->end();iter++){
+    (*iter)->EventBegin(ev);
+  }
+}
+//_________________________
+void AliFemtoSimpleAnalysis::EventEnd(const AliFemtoEvent* ev){
+  // Fiinsh operations at the end of event processing
+  fFirstParticleCut->EventEnd(ev);
+  fSecondParticleCut->EventEnd(ev);
+  fPairCut->EventEnd(ev);
+  for (AliFemtoCorrFctnIterator iter=fCorrFctnCollection->begin(); iter!=fCorrFctnCollection->end();iter++){
+    (*iter)->EventEnd(ev);
+  }
+}
+//_________________________
+void AliFemtoSimpleAnalysis::Finish(){
+  // Perform finishing operations after all events are processed
+  AliFemtoCorrFctnIterator iter;
+  for (iter=fCorrFctnCollection->begin(); iter!=fCorrFctnCollection->end();iter++){
+    (*iter)->Finish();
+  }
+}
+//_________________________
+void AliFemtoSimpleAnalysis::AddEventProcessed() {
+  // Increase count of processed events
+  fNeventsProcessed++;
+}
+//_________________________
+TList* AliFemtoSimpleAnalysis::ListSettings()
+{
+  // Collect settings list
+  TList *tListSettings = new TList();
+
+  TList *p1Cut = fFirstParticleCut->ListSettings();
+
+  TListIter nextp1(p1Cut);
+  while (TObject *obj = nextp1.Next()) {
+    TString cuts(obj->GetName());
+    cuts.Prepend("AliFemtoSimpleAnalysis.");
+    tListSettings->Add(new TObjString(cuts.Data()));
+  }
+
+  if (fSecondParticleCut != fFirstParticleCut) {
+    TList *p2Cut = fSecondParticleCut->ListSettings();
+    
+    TIter nextp2(p2Cut);
+    while (TObject *obj = nextp2()) {
+      TString cuts(obj->GetName());
+      cuts.Prepend("AliFemtoSimpleAnalysis.");
+      tListSettings->Add(new TObjString(cuts.Data()));
+    }
+  }
+
+  TList *pairCut = fPairCut->ListSettings();
+
+  TIter nextpair(pairCut);
+  while (TObject *obj = nextpair()) {
+    TString cuts(obj->GetName());
+    cuts.Prepend("AliFemtoSimpleAnalysis.");
+    tListSettings->Add(new TObjString(cuts.Data()));
+  }
+
+  return tListSettings;
+  
+}
+
+//_________________________
+TList* AliFemtoSimpleAnalysis::GetOutputList()
+{
+  // Collect the list of output objects
+  // to be written 
+  TList *tOutputList = new TList();
+
+  TList *p1Cut = fFirstParticleCut->GetOutputList();
+
+  TListIter nextp1(p1Cut);
+  while (TObject *obj = nextp1.Next()) {
+    tOutputList->Add(obj);
+  }
+
+  if (fSecondParticleCut != fFirstParticleCut) {
+    TList *p2Cut = fSecondParticleCut->GetOutputList();
+    
+    TIter nextp2(p2Cut);
+    while (TObject *obj = nextp2()) {
+      tOutputList->Add(obj);
+    }
+  }
+
+  TList *pairCut = fPairCut->GetOutputList();
+
+  TIter nextpair(pairCut);
+  while (TObject *obj = nextpair()) {
+    tOutputList->Add(obj);
+  }
+
+  TList *eventCut = fEventCut->GetOutputList();
+
+  TIter nextevent(eventCut);
+  while (TObject *obj = nextevent()) {
+    tOutputList->Add(obj);
+  }
+
+  AliFemtoCorrFctnIterator iter;
+  for (iter=fCorrFctnCollection->begin(); iter!=fCorrFctnCollection->end();iter++){
+    TList *tListCf = (*iter)->GetOutputList();
+    
+    TIter nextListCf(tListCf);
+    while (TObject *obj = nextListCf()) {
+      tOutputList->Add(obj);
+    }
+  }
+
+  return tOutputList;
+  
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoSimpleAnalysis.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoSimpleAnalysis.h
new file mode 100644 (file)
index 0000000..83677b6
--- /dev/null
@@ -0,0 +1,130 @@
+/**************************************************************************
+ AliFemtoSimpleAnalysis - the most basic analysis there is.
+ Most others (e.g. AliFemtoVertexAnalysis) wrap this one.
+**************************************************************************/
+
+#ifndef ALIFEMTO_SIMPLE_ANALYSIS_H
+#define ALIFEMTO_SIMPLE_ANALYSIS_H
+//#ifndef StMaker_H
+//#include "StMaker.h"
+//#endif
+
+#include "AliFemtoAnalysis.h"        // base analysis class
+#include "AliFemtoPairCut.h"     
+#include "AliFemtoEventCut.h"
+#include "AliFemtoParticleCut.h"
+#include "AliFemtoCorrFctn.h"
+#include "AliFemtoCorrFctnCollection.h"
+#include "AliFemtoPicoEventCollection.h"
+#include "AliFemtoParticleCollection.h"
+#include "AliFemtoPicoEvent.h"
+
+class AliFemtoPicoEventCollectionVectorHideAway;
+
+class AliFemtoSimpleAnalysis : public AliFemtoAnalysis {
+
+  // friend class AliFemtoLikeSignAnalysis;
+
+ public:
+  AliFemtoSimpleAnalysis();
+  AliFemtoSimpleAnalysis(const AliFemtoSimpleAnalysis& OriginalAnalysis);  // copy constructor
+  virtual ~AliFemtoSimpleAnalysis();
+
+  AliFemtoSimpleAnalysis& operator=(const AliFemtoSimpleAnalysis& aAna);
+
+  // Gets and Sets
+
+  virtual AliFemtoPairCut*       PairCut();
+  virtual AliFemtoEventCut*      EventCut();
+  virtual AliFemtoParticleCut*   FirstParticleCut();
+  virtual AliFemtoParticleCut*   SecondParticleCut();
+
+  AliFemtoCorrFctnCollection* CorrFctnCollection();
+  virtual AliFemtoCorrFctn* CorrFctn(int n);     // Access to CFs within the collection
+  void AddCorrFctn(AliFemtoCorrFctn* AnotherCorrFctn);
+
+  void SetPairCut(AliFemtoPairCut* ThePairCut);
+  void SetEventCut(AliFemtoEventCut* TheEventCut);
+  void SetFirstParticleCut(AliFemtoParticleCut* TheFirstParticleCut);
+  void SetSecondParticleCut(AliFemtoParticleCut* TheSecondParticleCut);
+
+  void SetMinSizePartCollection(unsigned int minSize);
+
+  unsigned int NumEventsToMix() const;
+  void SetNumEventsToMix(const unsigned int& NumberOfEventsToMix);
+  AliFemtoPicoEvent* CurrentPicoEvent();
+  AliFemtoPicoEventCollection* MixingBuffer();
+  bool MixingBufferFull();
+
+  bool AnalyzeIdenticalParticles() const;
+  virtual AliFemtoString Report();       //! returns reports of all cuts applied and correlation functions being done
+  virtual TList* ListSettings();         // return list of cut settings for the analysis
+  virtual TList* GetOutputList();        // Return a TList of objects to be written as output
+  
+  virtual void EventBegin(const AliFemtoEvent* TheEventToBegin); // startup for EbyE
+  virtual void ProcessEvent(const AliFemtoEvent* EventToProcess);
+  virtual void EventEnd(const AliFemtoEvent* TheEventToWrapUp);   // cleanup for EbyE
+  int GetNeventsProcessed() const;
+
+  virtual void Finish();
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoSimpleAnalysis, 0)
+#endif 
+
+
+ protected:
+
+  void AddEventProcessed();
+  void MakePairs(const char* type, 
+                AliFemtoParticleCollection* ParticlesPassingCut1,
+                AliFemtoParticleCollection* ParticlesPssingCut2=0);
+
+  AliFemtoPicoEventCollectionVectorHideAway* fPicoEventCollectionVectorHideAway; //! Mixing Buffer used for Analyses which wrap this one 
+
+  AliFemtoPairCut*             fPairCut;             //  cut applied to pairs 
+  AliFemtoCorrFctnCollection*  fCorrFctnCollection;  //  correlation functions of this analysis 
+  AliFemtoEventCut*            fEventCut;            //  cut to select events 
+  AliFemtoParticleCut*         fFirstParticleCut;    //  select particles of type #1 
+  AliFemtoParticleCut*         fSecondParticleCut;   //  select particles of type #2 
+  AliFemtoPicoEventCollection* fMixingBuffer;        //  mixing buffer used in this simplest analysis 
+  AliFemtoPicoEvent*           fPicoEvent;           //! The current event, in the small (pico) form 
+  unsigned int fNumEventsToMix;                      //  How many "previous" events get mixed with this one, to make background 
+  unsigned int fNeventsProcessed;                    //  How many events processed so far 
+
+  unsigned int fMinSizePartCollection;               //  Don't use event if it has fewer than this many particles passing ParticleCuts default 0
+
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoSimpleAnalysis, 0)
+#endif
+
+    };
+
+// Get's
+inline AliFemtoPairCut*              AliFemtoSimpleAnalysis::PairCut() {return fPairCut;}
+inline AliFemtoEventCut*             AliFemtoSimpleAnalysis::EventCut() {return fEventCut;}
+inline AliFemtoParticleCut*          AliFemtoSimpleAnalysis::FirstParticleCut() {return fFirstParticleCut;}
+inline AliFemtoParticleCut*          AliFemtoSimpleAnalysis::SecondParticleCut() {return fSecondParticleCut;}
+inline AliFemtoCorrFctnCollection*   AliFemtoSimpleAnalysis::CorrFctnCollection() {return fCorrFctnCollection;}
+inline unsigned int                  AliFemtoSimpleAnalysis::NumEventsToMix() const {return fNumEventsToMix;}
+inline AliFemtoPicoEvent*            AliFemtoSimpleAnalysis::CurrentPicoEvent() {return fPicoEvent;}
+
+inline AliFemtoPicoEventCollection*  AliFemtoSimpleAnalysis::MixingBuffer() {return fMixingBuffer;}
+
+inline bool AliFemtoSimpleAnalysis::AnalyzeIdenticalParticles() const { return (fFirstParticleCut==fSecondParticleCut); }
+
+// Set's
+inline void AliFemtoSimpleAnalysis::SetPairCut(AliFemtoPairCut* x) { fPairCut = x; x->SetAnalysis((AliFemtoAnalysis*)this);}
+inline void AliFemtoSimpleAnalysis::AddCorrFctn(AliFemtoCorrFctn* cf) {fCorrFctnCollection->push_back(cf); cf->SetAnalysis((AliFemtoAnalysis*)this);}
+inline void AliFemtoSimpleAnalysis::SetEventCut(AliFemtoEventCut* x) {fEventCut = x; x->SetAnalysis((AliFemtoAnalysis*)this);}
+inline void AliFemtoSimpleAnalysis::SetFirstParticleCut(AliFemtoParticleCut* x) {fFirstParticleCut = x; x->SetAnalysis((AliFemtoAnalysis*)this);}
+inline void AliFemtoSimpleAnalysis::SetSecondParticleCut(AliFemtoParticleCut* x) {fSecondParticleCut = x; x->SetAnalysis((AliFemtoAnalysis*)this);}
+
+inline void AliFemtoSimpleAnalysis::SetNumEventsToMix(const unsigned int& nmix){ fNumEventsToMix = nmix;}
+inline bool AliFemtoSimpleAnalysis::MixingBufferFull(){return (fMixingBuffer->size() >= fNumEventsToMix);}
+inline int AliFemtoSimpleAnalysis::GetNeventsProcessed() const {return fNeventsProcessed;}
+
+inline void AliFemtoSimpleAnalysis::SetMinSizePartCollection(unsigned int minSize){fMinSizePartCollection = minSize;}
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoString.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoString.h
new file mode 100644 (file)
index 0000000..a91e862
--- /dev/null
@@ -0,0 +1,26 @@
+#ifndef AliFemtoString_hh
+#define AliFemtoString_hh
+
+#ifndef __CINT__
+
+#ifndef AliFemtoString_noCint
+#define AliFemtoString_noCint
+#include <string>
+
+#if !defined(ST_NO_NAMESPACES)
+using std::string;
+#endif
+
+typedef string AliFemtoString; //!
+#endif
+
+#else
+
+#ifndef AliFemtoString_yesCint
+#define AliFemtoString_yesCint
+class AliFemtoString; //!
+#endif
+
+#endif
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoThreeVector.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoThreeVector.h
new file mode 100644 (file)
index 0000000..e533c1b
--- /dev/null
@@ -0,0 +1,863 @@
+/***************************************************************************
+ *
+ * $Id$
+ *
+ * Author: Brian Lasiuk, Thomas Ullrich, April 1998
+ ***************************************************************************
+ *
+ * Description:  
+ *
+ * Remarks:   Since not all compilers support member templates
+ *            we have to specialize the templated member on these
+ *            platforms. If member templates are not supported the
+ *            ST_NO_MEMBER_TEMPLATES flag has to be set. tu.
+ *
+ ***************************************************************************
+ *
+ * $Log$
+ * Revision 1.1.1.1  2007/04/25 15:38:41  panos
+ * Importing the HBT code dir
+ *
+ * Revision 1.1.1.1  2007/03/07 10:14:49  mchojnacki
+ * First version on CVS
+ *
+ * Revision 1.15  2005/09/22 20:09:20  fisyak
+ * Make AliFmLorentzVector persistent
+ *
+ * Revision 1.14  2005/07/19 22:27:11  perev
+ * Cleanup
+ *
+ * Revision 1.13  2005/07/06 18:49:57  fisyak
+ * Replace AliFmHelixD, AliFmLorentzVectorD,AliFmLorentzVectorF,AliFmMatrixD,AliFmMatrixF,AliFmPhysicalHelixD,AliFmThreeVectorD,AliFmThreeVectorF by templated version
+ *
+ * Revision 1.12  2005/03/28 06:03:41  perev
+ * Defence FPE added
+ *
+ * Revision 1.11  2004/12/02 20:07:32  fine
+ * define the valid method for both flavor of AliFmThreeVector
+ *
+ * Revision 1.10  2003/10/30 20:06:46  perev
+ * Check of quality added
+ *
+ * Revision 1.9  2003/09/02 17:59:35  perev
+ * gcc 3.2 updates + WarnOff
+ *
+ * Revision 1.8  2002/06/21 17:47:37  genevb
+ * Added pseudoProduct
+ *
+ * Revision 1.7  2000/01/04 19:56:05  ullrich
+ * Added cpp macro for CINT.
+ *
+ * Revision 1.6  1999/12/21 15:14:31  ullrich
+ * Modified to cope with new compiler version on Sun (CC5.0).
+ *
+ * Revision 1.5  1999/10/15 15:46:54  ullrich
+ * Changed output format in operator<<
+ *
+ * Revision 1.4  1999/06/04 18:00:05  ullrich
+ * Added new constructor which takes C-style array as argument.
+ * New operators operator() and operator[] which can be used
+ * as lvalues.
+ *
+ * Revision 1.3  1999/02/17 11:42:19  ullrich
+ * Removed specialization for 'long double'.
+ *
+ * Revision 1.2  1999/02/14 23:11:48  fisyak
+ * Fixes for Rootcint
+ *
+ * Revision 1.1  1999/01/30 03:59:05  fisyak
+ * Root Version of AliFmarClassLibrary
+ *
+ * Revision 1.1  1999/01/23 00:28:04  ullrich
+ * Initial Revision
+ *
+ **************************************************************************/
+/*//
+//// General class for a three-vector
+///*/
+#ifndef ST_THREE_VECTOR_HH
+#define ST_THREE_VECTOR_HH
+#ifdef __ROOT__
+#include "Rtypes.h"
+#endif
+#ifndef __CINT__
+#include <iostream>
+#include <fstream>
+#include <math.h>
+#ifdef GNU_GCC
+#    include <stddef.h>
+#endif
+#if defined (__SUNPRO_CC) && __SUNPRO_CC < 0x500
+#    include <stdcomp.h>
+#endif
+#ifndef ST_NO_EXCEPTIONS
+#    include <stdexcept>
+#    if !defined(ST_NO_NAMESPACES)
+using std::out_of_range;
+#    endif
+#endif
+#endif // __CINT__
+
+#ifdef WIN32
+#include "gcc2vs.h"
+#endif
+
+class TRootIOCtor;//nic nie rozumiem
+using namespace std;
+
+
+template<class T> class AliFmThreeVector {
+public:    
+    AliFmThreeVector(T = 0, T = 0, T = 0);
+  //                     ROOT_VERSION(5,03,01)
+#if ROOT_VERSION_CODE >= 328449
+   AliFmThreeVector(TRootIOCtor*) : mX1(0), mX2(0), mX3(0) {}
+#endif
+    virtual ~AliFmThreeVector();
+
+#ifndef ST_NO_MEMBER_TEMPLATES
+    template<class X> AliFmThreeVector(const AliFmThreeVector<X>&);
+    template<class X> AliFmThreeVector(const X*);  
+    template<class X> AliFmThreeVector<T>& operator=(const AliFmThreeVector<X>&);
+    // AliFmThreeVector(const AliFmThreeVector<T>&);                use default
+    // AliFmThreeVector<T>& operator=(const AliFmThreeVector<T>&);  use default
+#else    
+    AliFmThreeVector(const AliFmThreeVector<float>&);
+    AliFmThreeVector(const AliFmThreeVector<double>&);
+    
+    AliFmThreeVector(const float*); 
+    AliFmThreeVector(const double*);
+    
+    AliFmThreeVector<T>& operator=(const AliFmThreeVector<float>&);
+    AliFmThreeVector<T>& operator=(const AliFmThreeVector<double>&);
+#endif
+    
+    void SetX(T);
+    void SetY(T);
+    void SetZ(T);
+
+    void SetPhi(T);
+    void SetTheta(T);
+    void SetMag(T);
+    void SetMagnitude(T);
+    
+    T   x()                        const;
+    T   y()                        const;
+    T   z()                        const;
+    T   Theta()                    const;
+    T   CosTheta()                 const;
+    T   Phi()                      const;
+    T   Perp()                     const;
+    T   Perp2()                    const;
+    T   Magnitude()                const;
+    T   Mag()                      const;
+    T   Mag2()                     const;
+    T   PseudoRapidity()           const;
+    T   operator() (size_t)        const;
+    T   operator[] (size_t)        const;
+
+    T&  operator() (size_t);
+    T&  operator[] (size_t);
+    
+    T   MassHypothesis(T mass)     const;
+    
+    AliFmThreeVector<T>  Unit()       const;
+    AliFmThreeVector<T>  Orthogonal() const;
+
+    void  RotateX(T);
+    void  RotateY(T);
+    void  RotateZ(T);
+    
+    AliFmThreeVector<T>  operator- ();
+    AliFmThreeVector<T>  operator+ ();
+    AliFmThreeVector<T>& operator*= (double);
+    AliFmThreeVector<T>& operator/= (double);
+    AliFmThreeVector<T>  PseudoProduct(double,double,double) const;
+#ifndef ST_NO_MEMBER_TEMPLATES
+    template<class X> T                Angle(const AliFmThreeVector<X>&) const;
+    template<class X> AliFmThreeVector<T> Cross(const AliFmThreeVector<X>&) const;
+    template<class X> T                Dot  (const AliFmThreeVector<X>&) const;
+    template<class X> AliFmThreeVector<T> PseudoProduct(const AliFmThreeVector<X>&) const;
+    
+    template<class X> bool operator == (const AliFmThreeVector<X>& v) const;
+    template<class X> bool operator != (const AliFmThreeVector<X>& v) const;
+
+    template<class X> AliFmThreeVector<T>& operator+= (const AliFmThreeVector<X>&);
+    template<class X> AliFmThreeVector<T>& operator-= (const AliFmThreeVector<X>&);
+#else    
+    T                Angle(const AliFmThreeVector<float>&) const;
+    AliFmThreeVector<T> Cross(const AliFmThreeVector<float>&) const;
+    T                Dot  (const AliFmThreeVector<float>&) const;
+    AliFmThreeVector<T> PseudoProduct(const AliFmThreeVector<float>&) const;
+    
+    T                Angle(const AliFmThreeVector<double>&) const;
+    T                Dot  (const AliFmThreeVector<double>&) const;
+    AliFmThreeVector<T> Cross(const AliFmThreeVector<double>&) const;
+    AliFmThreeVector<T> PseudoProduct(const AliFmThreeVector<double>&) const;
+
+    bool operator == (const AliFmThreeVector<float>& v) const;
+    bool operator != (const AliFmThreeVector<float>& v) const;
+    AliFmThreeVector<T>& operator+= (const AliFmThreeVector<float>&);
+    AliFmThreeVector<T>& operator-= (const AliFmThreeVector<float>&);
+    
+    bool operator == (const AliFmThreeVector<double>& v) const;
+    bool operator != (const AliFmThreeVector<double>& v) const;
+    AliFmThreeVector<T>& operator+= (const AliFmThreeVector<double>&);
+    AliFmThreeVector<T>& operator-= (const AliFmThreeVector<double>&);
+#endif
+  int             valid(double world = 1.e+5) const;
+    int               bad(double world = 1.e+5) const;
+protected:
+    T    mX1, mX2, mX3;  // Three vector components
+#ifdef __ROOT__
+  ClassDef(AliFmThreeVector,3)
+#endif /* __ROOT__ */
+};
+
+#ifndef __CINT__
+//
+//        Implementation of member functions
+//
+template<class T>
+inline AliFmThreeVector<T>::AliFmThreeVector(T x, T y, T z)
+    : mX1(x), mX2(y), mX3(z) {/* nop */}
+template<class T>
+inline AliFmThreeVector<T>::~AliFmThreeVector() {/* nop */}
+
+template<class T>
+inline void AliFmThreeVector<T>::SetX(T x) {mX1 = x;}
+
+template<class T>
+inline void AliFmThreeVector<T>::SetY(T y) {mX2 = y;}
+
+template<class T>
+inline void AliFmThreeVector<T>::SetZ(T z) {mX3 = z;}
+
+template<class T>
+void AliFmThreeVector<T>::SetPhi(T angle)
+{
+    double  r = Magnitude();
+    double th = Theta();
+    
+    mX1 = r*sin(th)*cos(angle);
+    mX2 = r*sin(th)*sin(angle);
+}
+
+template <class T>
+void AliFmThreeVector<T>::SetTheta(T angle)
+{
+    double r  = Magnitude();
+    double ph = Phi();
+
+    mX1 = r*sin(angle)*cos(ph);
+    mX2 = r*sin(angle)*sin(ph);
+    mX3 = r*cos(angle);
+}
+
+template <class T>
+void AliFmThreeVector<T>::SetMagnitude(T r)
+{
+    double th = Theta();
+    double ph = Phi();
+    
+    mX1 = r*sin(th)*cos(ph);
+    mX2 = r*sin(th)*sin(ph);
+    mX3 = r*cos(th);
+}
+
+template <class T>
+void AliFmThreeVector<T>::SetMag(T mag)
+{
+    SetMagnitude(mag);
+}
+
+template<class T>
+inline T AliFmThreeVector<T>::x() const {return mX1;}
+
+template<class T>
+inline T AliFmThreeVector<T>::y() const {return mX2;}
+
+template<class T>
+inline T AliFmThreeVector<T>::z() const {return mX3;}
+
+template<class T>
+inline T AliFmThreeVector<T>::Theta() const
+{
+  return acos(CosTheta());
+}
+
+template<class T>
+inline T AliFmThreeVector<T>::CosTheta() const
+{
+  return mX3/(Mag()+1e-20);
+}
+
+template<class T>
+inline T AliFmThreeVector<T>::Phi() const
+{
+    return atan2(mX2,mX1);
+}
+
+template<class T>
+inline T AliFmThreeVector<T>::PseudoRapidity() const
+{
+    //
+    // change code to more optimal:
+    // double m = Mag();
+    // return 0.5*::log( (m+z())/(m-z()) );
+    double tmp = tan(Theta()/2.); if (tmp <=0.) return 1e20;
+    return -::log(tmp);
+}
+
+template<class T>
+inline AliFmThreeVector<T> AliFmThreeVector<T>::Unit() const
+{
+    double tmp = Mag(); if (tmp<=0.) tmp = 1e-20;
+    return *this/tmp;
+}
+
+template <class T>
+T AliFmThreeVector<T>::MassHypothesis(T mass) const
+{
+    return ::sqrt((*this)*(*this) + mass*mass);
+}
+
+template <class T>
+AliFmThreeVector<T> AliFmThreeVector<T>::Orthogonal() const
+{
+    // Direct copy from CLHEP--it is probably better to
+    // use your own dot/cross product code...
+    double x = (mX1 < 0.0) ? -mX1 : mX1;
+    double y = (mX2 < 0.0) ? -mX2 : mX2;
+    double z = (mX3 < 0.0) ? -mX3 : mX3;
+    
+    if(x<y)
+       return x < z ? AliFmThreeVector<T>(0,mX3,-mX2) :  AliFmThreeVector<T>(mX2,-mX1,0);
+    else
+       return  mX2 < mX3 ? AliFmThreeVector<T>(-mX3,0,mX1) :  AliFmThreeVector<T>(mX2,-mX1,0);
+}
+
+template <class T>
+void AliFmThreeVector<T>::RotateX(T angle)
+{
+    // may in the future make use of the AliFmRotation class!
+    double yPrime = cos(angle)*mX2 - sin(angle)*mX3;
+    double zPrime = sin(angle)*mX2 + cos(angle)*mX3;
+
+    mX2 = yPrime;
+    mX3 = zPrime;
+}
+
+template <class T>
+void AliFmThreeVector<T>::RotateY(T angle)
+{
+    // may in the future make use of the AliFmRotation class!
+    double zPrime = cos(angle)*mX3 - sin(angle)*mX1;
+    double xPrime = sin(angle)*mX3 + cos(angle)*mX1;
+
+    mX1 = xPrime;
+    mX3 = zPrime;
+}
+
+template <class T>
+void AliFmThreeVector<T>::RotateZ(T angle)
+{
+    // may in the future make use of the AliFmRotation class!
+    double xPrime = cos(angle)*mX1 - sin(angle)*mX2;
+    double yPrime = sin(angle)*mX1 + cos(angle)*mX2;
+
+    mX1 = xPrime;
+    mX2 = yPrime;
+}
+
+template<class T>
+inline T AliFmThreeVector<T>::Perp() const
+{
+    return ::sqrt(mX1*mX1+mX2*mX2);
+}
+
+template<class T>
+inline T AliFmThreeVector<T>::Perp2() const
+{
+    return mX1*mX1+mX2*mX2;
+}
+
+template<class T>
+inline T AliFmThreeVector<T>::Magnitude() const
+{
+    return Mag();
+}
+
+template<class T>
+inline T AliFmThreeVector<T>::Mag() const
+{
+    return ::sqrt(mX1*mX1+mX2*mX2+mX3*mX3);
+}
+
+template<class T>
+inline T AliFmThreeVector<T>::Mag2() const
+{
+    return mX1*mX1+mX2*mX2+mX3*mX3;
+}
+
+template<class T>
+inline T AliFmThreeVector<T>::operator() (size_t i) const
+{
+    if (0 <=i && i <= 2)  return (&mX1)[i];
+#ifndef ST_NO_EXCEPTIONS
+    throw out_of_range("AliFmThreeVector<T>::operator(): bad index");
+#else
+    cerr << "AliFmThreeVector<T>::operator(): bad index" << endl;
+#endif
+    return 0;
+}
+
+template<class T>
+inline T& AliFmThreeVector<T>::operator() (size_t i) 
+{
+    if (0 <=i && i <= 2)  return (&mX1)[i];
+#ifndef ST_NO_EXCEPTIONS
+    throw out_of_range("AliFmThreeVector<T>::operator(): bad index");
+#else
+    cerr << "AliFmThreeVector<T>::operator(): bad index" << endl;
+#endif
+    return mX1;
+}
+
+template<class T>
+inline T AliFmThreeVector<T>::operator[] (size_t i) const
+{
+    if (0 <=i && i <= 2)  return (&mX1)[i];
+#ifndef ST_NO_EXCEPTIONS
+      throw out_of_range("AliFmThreeVector<T>::operator[]: bad index"); 
+#else
+      cerr << "AliFmThreeVector<T>::operator[]: bad index" << endl;
+#endif
+      return 0;
+}
+
+template<class T>
+inline T &AliFmThreeVector<T>::operator[] (size_t i) 
+{
+    if (0 <=i && i <= 2)  return (&mX1)[i];
+#ifndef ST_NO_EXCEPTIONS
+      throw out_of_range("AliFmThreeVector<T>::operator[]: bad index"); 
+#else
+      cerr << "AliFmThreeVector<T>::operator[]: bad index" << endl;
+#endif
+      return mX1;
+}
+
+template<class T>
+inline AliFmThreeVector<T>& AliFmThreeVector<T>::operator*= (double c)
+{
+    mX1 *= c; mX2 *= c; mX3 *= c;
+    return *this;
+}
+
+template<class T>
+inline AliFmThreeVector<T>& AliFmThreeVector<T>::operator/= (double c)
+{
+    mX1 /= c; mX2 /= c; mX3 /= c;
+    return *this;
+}
+
+template<class T>
+inline AliFmThreeVector<T>
+AliFmThreeVector<T>::PseudoProduct(double x,double y,double z) const
+{
+    return AliFmThreeVector<T>(mX1*x,mX2*y,mX3*z);
+}
+
+template<class T>
+AliFmThreeVector<T> AliFmThreeVector<T>::operator- ()
+{
+    return AliFmThreeVector<T>(-mX1, -mX2, -mX3);
+}
+
+template<class T>
+AliFmThreeVector<T> AliFmThreeVector<T>::operator+ ()
+{
+    return *this;
+}
+
+#ifndef ST_NO_MEMBER_TEMPLATES
+#ifndef WIN32
+
+template<class T>
+template<class X>
+inline AliFmThreeVector<T>::AliFmThreeVector(const AliFmThreeVector<X>& v)
+    : mX1(v.x()), mX2(v.y()), mX3(v.z()) {/* nop */}
+
+template<class T>
+template<class X>
+inline AliFmThreeVector<T>::AliFmThreeVector(const X *a)
+{
+    mX1 = a[0];
+    mX2 = a[1];
+    mX3 = a[2];
+}
+
+template<class T>
+template<class X>
+inline AliFmThreeVector<T>&
+AliFmThreeVector<T>::operator=(const AliFmThreeVector<X>& v)
+{
+  if(this != &v) {
+    mX1 = v.x();  mX2 = v.y();  mX3 = v.z();
+  }
+  return *this;
+}
+
+template<class T>
+template<class X>
+inline bool AliFmThreeVector<T>::operator== (const AliFmThreeVector<X>& v) const
+{
+    return mX1 == v.x() && mX2 == v.y() && mX3 == v.z();
+}
+
+template<class T>
+template<class X>
+inline bool AliFmThreeVector<T>::operator!= (const AliFmThreeVector<X>& v) const
+{
+    return !(*this == v);
+}
+
+template<class T>
+template<class X>
+inline AliFmThreeVector<T>&
+AliFmThreeVector<T>::operator+= (const AliFmThreeVector<X>& v)
+{
+    mX1 += v.x(); mX2 += v.y(); mX3 += v.z();
+    return *this;
+}
+
+template<class T>
+template<class X>
+inline AliFmThreeVector<T>&
+AliFmThreeVector<T>::operator-= (const AliFmThreeVector<X>& v)
+{
+    mX1 -= v.x(); mX2 -= v.y(); mX3 -= v.z();
+    return *this;
+}
+
+template<class T>
+template<class X>
+inline T AliFmThreeVector<T>::Dot(const AliFmThreeVector<X>& v) const
+{
+    return mX1*v.x() + mX2*v.y() + mX3*v.z();
+}
+
+template<class T>
+template<class X>
+inline AliFmThreeVector<T>
+AliFmThreeVector<T>::Cross(const AliFmThreeVector<X>& v) const
+{
+    return AliFmThreeVector<T>(mX2*v.z() - mX3*v.y(),
+                           mX3*v.x() - mX1*v.z(),
+                           mX1*v.y() - mX2*v.x());
+}
+
+template<class T>
+template<class X>
+inline T AliFmThreeVector<T>::Angle(const AliFmThreeVector<X>& vec) const
+{
+    double norm = this->Mag2()*vec.Mag2(); 
+    
+    return norm > 0 ? acos(this->Dot(vec)/(::sqrt(norm))) : 0;
+}
+
+template<class T>
+template<class X>
+inline AliFmThreeVector<T>
+AliFmThreeVector<T>::PseudoProduct(const AliFmThreeVector<X>& v) const
+{
+    return this->PseudoProduct(v.x(),v.y(),v.z());
+}
+
+#endif
+#else
+
+template<class T>
+inline AliFmThreeVector<T>::AliFmThreeVector(const AliFmThreeVector<float>& v)
+    : mX1(v.x()), mX2(v.y()), mX3(v.z()) {/* nop */}
+
+template<class T>
+inline AliFmThreeVector<T>::AliFmThreeVector(const AliFmThreeVector<double>& v)
+    : mX1(v.x()), mX2(v.y()), mX3(v.z()) {/* nop */}
+
+template<class T>
+inline AliFmThreeVector<T>::AliFmThreeVector(const float *a)
+{
+    mX1 = a[0];
+    mX2 = a[1];
+    mX3 = a[2];
+}
+
+template<class T>
+inline AliFmThreeVector<T>::AliFmThreeVector(const double *a)
+{
+    mX1 = a[0];
+    mX2 = a[1];
+    mX3 = a[2];
+}
+
+template<class T>
+inline AliFmThreeVector<T>&
+AliFmThreeVector<T>::operator=(const AliFmThreeVector<float>& v)
+{
+    mX1 = v.x();  mX2 = v.y();  mX3 = v.z();
+    return *this;
+}
+
+template<class T>
+inline AliFmThreeVector<T>&
+AliFmThreeVector<T>::operator=(const AliFmThreeVector<double>& v)
+{
+    mX1 = v.x();  mX2 = v.y();  mX3 = v.z();
+    return *this;
+}
+
+template<class T>
+inline bool
+AliFmThreeVector<T>::operator== (const AliFmThreeVector<float>& v) const
+{
+    return mX1 == v.x() && mX2 == v.y() && mX3 == v.z();
+}
+
+template<class T>
+inline bool
+AliFmThreeVector<T>::operator== (const AliFmThreeVector<double>& v) const
+{
+    return mX1 == v.x() && mX2 == v.y() && mX3 == v.z();
+}
+
+template<class T>
+inline bool
+AliFmThreeVector<T>::operator!= (const AliFmThreeVector<float>& v) const
+{
+    return !(*this == v);
+}
+
+template<class T>
+inline bool
+AliFmThreeVector<T>::operator!= (const AliFmThreeVector<double>& v) const
+{
+    return !(*this == v);
+}
+
+template<class T>
+inline AliFmThreeVector<T>&
+AliFmThreeVector<T>::operator+= (const AliFmThreeVector<float>& v)
+{
+    mX1 += v.x(); mX2 += v.y(); mX3 += v.z();
+    return *this;
+}
+
+template<class T>
+inline AliFmThreeVector<T>&
+AliFmThreeVector<T>::operator+= (const AliFmThreeVector<double>& v)
+{
+    mX1 += v.x(); mX2 += v.y(); mX3 += v.z();
+    return *this;
+}
+
+template<class T>
+inline AliFmThreeVector<T>&
+AliFmThreeVector<T>::operator-= (const AliFmThreeVector<float>& v)
+{
+    mX1 -= v.x(); mX2 -= v.y(); mX3 -= v.z();
+    return *this;
+}
+
+template<class T>
+inline AliFmThreeVector<T>&
+AliFmThreeVector<T>::operator-= (const AliFmThreeVector<double>& v)
+{
+    mX1 -= v.x(); mX2 -= v.y(); mX3 -= v.z();
+    return *this;
+}
+
+template<class T>
+inline T AliFmThreeVector<T>::Dot(const AliFmThreeVector<float>& v) const
+{
+    return mX1*v.x() + mX2*v.y() + mX3*v.z();
+}
+
+template<class T>
+inline T AliFmThreeVector<T>::Dot(const AliFmThreeVector<double>& v) const
+{
+    return mX1*v.x() + mX2*v.y() + mX3*v.z();
+}
+
+template<class T>
+inline AliFmThreeVector<T>
+AliFmThreeVector<T>::Cross(const AliFmThreeVector<float>& v) const
+{
+    return AliFmThreeVector<T>(mX2*v.z() - mX3*v.y(),
+                           mX3*v.x() - mX1*v.z(),
+                           mX1*v.y() - mX2*v.x());
+}
+
+template<class T>
+inline AliFmThreeVector<T>
+AliFmThreeVector<T>::Cross(const AliFmThreeVector<double>& v) const
+{
+    return AliFmThreeVector<T>(mX2*v.z() - mX3*v.y(),
+                           mX3*v.x() - mX1*v.z(),
+                           mX1*v.y() - mX2*v.x());
+}
+
+template<class T>
+inline T AliFmThreeVector<T>::Angle(const AliFmThreeVector<float>& v) const
+{
+    double tmp = Mag()*v.Mag(); if (tmp <=0) tmp = 1e-20;
+    return acos(this->Dot(v)/tmp);
+}
+
+template<class T>
+inline T AliFmThreeVector<T>::Angle(const AliFmThreeVector<double>& v) const
+{
+    double tmp = Mag()*v.Mag(); if (tmp <=0) tmp = 1e-20;
+    return acos(this->Dot(v)/tmp);
+}
+
+template<class T>
+inline AliFmThreeVector<T>
+AliFmThreeVector<T>::PseudoProduct(const AliFmThreeVector<float>& v) const
+{
+    return this->PseudoProduct(v.x(),v.y(),v.z());
+}
+
+template<class T>
+inline AliFmThreeVector<T>
+AliFmThreeVector<T>::PseudoProduct(const AliFmThreeVector<double>& v) const
+{
+    return this->PseudoProduct(v.x(),v.y(),v.z());
+}
+#endif  // ST_NO_MEMBER_TEMPLATES
+template<class T>
+inline int
+AliFmThreeVector<T>::valid(double world) const  {return !bad(world);}
+
+template<class T>
+inline int
+AliFmThreeVector<T>::bad(double world) const
+{
+  for (int i=0;i<3;i++) {
+         if (!finite((&mX1)[i])      ) return 10+i;            
+         if ( fabs  ((&mX1)[i])>world) return 20+i;            
+  }            
+  return 0;            
+}
+#endif /*! __CINT__ */
+#ifdef __CINT__
+template<> float abs(const AliFmThreeVector<float>& v);
+template<> double abs(const AliFmThreeVector<double>& v);
+template<> AliFmThreeVector<double> cross_product(const AliFmThreeVector<double>& v1, const AliFmThreeVector<double>& v2);
+template<> AliFmThreeVector<float>  cross_product(const AliFmThreeVector<float>&  v1, const AliFmThreeVector<float>& v2);
+template<> AliFmThreeVector<double> cross_product(const AliFmThreeVector<float>&  v1, const AliFmThreeVector<double>& v2);
+template<> AliFmThreeVector<double> cross_product(const AliFmThreeVector<double>& v1, const AliFmThreeVector<float>& v2);
+template<> AliFmThreeVector<double> operator+ (const AliFmThreeVector<double>& v1, const AliFmThreeVector<double>& v2);
+template<> AliFmThreeVector<float>  operator+ (const AliFmThreeVector<float>&  v1, const AliFmThreeVector<float>& v2);
+template<> AliFmThreeVector<double> operator+ (const AliFmThreeVector<double>& v1, const AliFmThreeVector<float>& v2);
+template<> AliFmThreeVector<double> operator+ (const AliFmThreeVector<float>&  v1, const AliFmThreeVector<double>& v2);
+template<> AliFmThreeVector<double> operator- (const AliFmThreeVector<double>& v1, const AliFmThreeVector<double>& v2);
+template<> AliFmThreeVector<float>  operator- (const AliFmThreeVector<float>&  v1, const AliFmThreeVector<float>& v2);
+template<> AliFmThreeVector<double> operator- (const AliFmThreeVector<double>& v1, const AliFmThreeVector<float>& v2);
+template<> AliFmThreeVector<double> operator- (const AliFmThreeVector<float>&  v1, const AliFmThreeVector<double>& v2);
+template<> AliFmThreeVector<double> operator* (const AliFmThreeVector<double>& v1, const AliFmThreeVector<double>& v2);
+template<> AliFmThreeVector<float>  operator* (const AliFmThreeVector<float>&  v1, const AliFmThreeVector<float>& v2);
+template<> AliFmThreeVector<double> operator* (const AliFmThreeVector<double>& v1, const AliFmThreeVector<float>& v2);
+template<> AliFmThreeVector<double> operator* (const AliFmThreeVector<float>&  v1, const AliFmThreeVector<double>& v2);
+template<> AliFmThreeVector<double> operator* (const double                 v1, const AliFmThreeVector<float>& v2);
+template<> AliFmThreeVector<double> operator* (const AliFmThreeVector<float>&  v1, const double v2);
+template<> AliFmThreeVector<double> operator* (const double                 v1, const AliFmThreeVector<double>& v2);
+template<> AliFmThreeVector<double> operator* (const AliFmThreeVector<double>& v1, const double v2);
+template<> AliFmThreeVector<double> operator/ (const AliFmThreeVector<double>& v1, const AliFmThreeVector<double>& v2);
+template<> AliFmThreeVector<float>  operator/ (const AliFmThreeVector<float>&  v1, const AliFmThreeVector<float>& v2);
+template<> AliFmThreeVector<double> operator/ (const AliFmThreeVector<double>& v1, const AliFmThreeVector<float>& v2);
+template<> AliFmThreeVector<double> operator/ (const AliFmThreeVector<float>&  v1, const AliFmThreeVector<double>& v2);
+template<> AliFmThreeVector<double> operator/ (const                double  v1, const AliFmThreeVector<double>& v2);
+template<> AliFmThreeVector<float>  operator/ (const                double  v1, const AliFmThreeVector<float>& v2);
+template<> AliFmThreeVector<double> operator/ (const AliFmThreeVector<double>& v1, const double v2);
+template<> AliFmThreeVector<double> operator/ (const AliFmThreeVector<float>&  v1, const double v2);
+template<> istream&  operator>>(istream& is,const AliFmThreeVector<double>& v);
+template<> istream&  operator>>(istream& is,const AliFmThreeVector<float>& v);
+template<> ostream&  operator<<(ostream& os,const AliFmThreeVector<double>& v);
+template<> ostream&  operator<<(ostream& os,const AliFmThreeVector<float>& v);
+#else
+//
+//        Non-member functions
+//
+template<class T>
+inline T abs(const AliFmThreeVector<T>& v) {return v.Mag();}
+
+template<class T, class X>
+inline AliFmThreeVector<T>
+cross_product(const AliFmThreeVector<T>& v1, const AliFmThreeVector<X>& v2)
+{
+    return v1.Cross(v2);
+}
+
+
+//
+//        Non-member operators
+//
+template<class T, class X>
+inline AliFmThreeVector<T>
+operator+ (const AliFmThreeVector<T>& v1, const AliFmThreeVector<X>& v2)
+{
+    return AliFmThreeVector<T>(v1) += v2;
+}
+
+template<class T, class X>
+inline AliFmThreeVector<T>
+operator- (const AliFmThreeVector<T>& v1, const AliFmThreeVector<X>& v2)
+{
+    return AliFmThreeVector<T>(v1) -= v2;
+}
+
+template<class T, class X>
+inline T operator* (const AliFmThreeVector<T>& v1, const AliFmThreeVector<X>& v2)
+{
+    return AliFmThreeVector<T>(v1).Dot(v2);
+}
+
+template<class T>
+inline AliFmThreeVector<T> operator* (const AliFmThreeVector<T>& v, double c)
+{
+    return AliFmThreeVector<T>(v) *= c;
+}
+
+template<class T>
+inline AliFmThreeVector<T> operator* (double c, const AliFmThreeVector<T>& v)
+{
+    return AliFmThreeVector<T>(v) *= c;
+}
+
+template<class T, class X>
+inline AliFmThreeVector<T> operator/ (const AliFmThreeVector<T>& v, X c)
+{
+    return AliFmThreeVector<T>(v) /= c;
+}
+
+template<class T>
+ostream&  operator<<(ostream& os, const AliFmThreeVector<T>& v)
+{
+    return os << v.x() << '\t' << v.y() << '\t' << v.z();
+}
+
+template<class T>
+istream&  operator>>(istream& is, AliFmThreeVector<T>& v)
+{
+    T  x, y, z;
+    is >> x >> y >> z;
+    v.SetX(x);
+    v.SetY(y);
+    v.SetZ(z);
+    return is;
+}
+#endif /* ! __CINT__ */
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoThreeVectorD.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoThreeVectorD.h
new file mode 100644 (file)
index 0000000..b230a23
--- /dev/null
@@ -0,0 +1,20 @@
+/***************************************************************************
+ *
+ * $Id$
+ * $Log$
+ * Revision 1.1.1.1  2007/04/25 15:38:41  panos
+ * Importing the HBT code dir
+ *
+ * Revision 1.1.1.1  2007/03/07 10:14:49  mchojnacki
+ * First version on CVS
+ *
+ * Revision 1.11  2005/07/06 18:49:57  fisyak
+ * Replace AliFemtoHelixD, AliFemtoLorentzVectorD,AliFemtoLorentzVectorF,AliFemtoMatrixD,AliFemtoMatrixF,AliFemtoPhysicalHelixD,AliFemtoThreeVectorD,AliFemtoThreeVectorF by templated version
+ *
+
+****************************************************************************/
+#ifndef ALIFM_THREE_VECTOR_D_HH
+#define ALIFM_THREE_VECTOR_D_HH
+#include "AliFmThreeVector.h"
+typedef AliFmThreeVector<double> AliFmThreeVectorD;
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoTrack.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoTrack.cxx
new file mode 100644 (file)
index 0000000..013f280
--- /dev/null
@@ -0,0 +1,398 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFemtoTrack: main class holding all the necessary information       //
+// about a track (before the identification) that is required during     //
+// femtoscopic analysis. This class is filled with information from the  //
+// input stream by the reader. A particle has a link back to the Track   //
+// it was created from, so we do not copy the information.               //
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+
+#include "AliFemtoTrack.h" 
+#ifndef __NO_STAR_DEPENDENCE_ALLOWED__
+#ifdef __ROOT__
+#include "StEvent/StEnumerations.h"
+#include "AliFemtoAihongPid.h"
+#include "StEventUtilities/StuProbabilityPidAlgorithm.h"
+#endif
+#endif
+
+#include "SystemOfUnits.h"   // has "tesla" in it
+//#include "AliFemtoParticleTypes.h"
+//#include "AliFemtoTTreeEvent.h" 
+//#include "AliFemtoTTreeTrack.h" 
+
+AliFemtoTrack::AliFemtoTrack():
+  fCharge(0),
+  fPidProbElectron(0),
+  fPidProbPion(0),
+  fPidProbKaon(0),
+  fPidProbProton(0),
+  fPidProbMuon(0),
+  fTrackId(0),
+  fTofPionTime(-100000.0),
+  fTofKaonTime(-100000.0),
+  fTofProtonTime(-100000.0),
+  fP(0,0,0),
+  fPt(0),
+  fHelix(),
+  fFlags(0),
+  fLabel(0),
+  fImpactD(0),
+  fImpactZ(0),
+  fCdd(0),
+  fCdz(0),
+  fCzz(0),
+  fITSchi2(0),       
+  fITSncls(0),        
+  fTPCchi2(0),       
+  fTPCncls(0),       
+  fTPCnclsF(0),      
+  fTPCsignal(0),
+  fTPCsignalN(0),    
+  fTPCsignalS(0),
+  fVTOF(0),
+  fNSigmaTPCPi(0),
+  fNSigmaTPCK(0),
+  fNSigmaTPCP(0),
+  fNSigmaTOFPi(0),
+  fNSigmaTOFK(0),
+  fNSigmaTOFP(0),
+  fSigmaToVertex(0),
+  fClusters(159),
+  fShared(159),
+  fNominalTpcEntrancePoint(0,0,0),
+  fNominalTpcExitPoint(0,0,0),
+  fHiddenInfo(0)
+{
+  // Default constructor
+  fHiddenInfo = NULL;
+  fKinkIndexes[0] = 0;
+  fKinkIndexes[1] = 0;
+  fKinkIndexes[2] = 0;
+  //  cout << "Created track " << this << endl;
+}
+
+
+AliFemtoTrack::AliFemtoTrack(const AliFemtoTrack& t) :
+  fCharge(0),
+  fPidProbElectron(0),
+  fPidProbPion(0),
+  fPidProbKaon(0),
+  fPidProbProton(0),
+  fPidProbMuon(0),
+  fTrackId(0),
+  fTofPionTime(-100000.0),
+  fTofKaonTime(-100000.0),
+  fTofProtonTime(-100000.0),
+  fP(0,0,0),
+  fPt(0),
+  fHelix(),
+  fFlags(0),
+  fLabel(0),
+  fImpactD(0),
+  fImpactZ(0),
+  fCdd(0),
+  fCdz(0),
+  fCzz(0),
+  fITSchi2(0),       
+  fITSncls(0),        
+  fTPCchi2(0),       
+  fTPCncls(0),       
+  fTPCnclsF(0),      
+  fTPCsignal(0),
+  fTPCsignalN(0),    
+  fTPCsignalS(0),
+  fVTOF(0),
+  fNSigmaTPCPi(0),
+  fNSigmaTPCK(0),
+  fNSigmaTPCP(0),
+  fNSigmaTOFPi(0),
+  fNSigmaTOFK(0),
+  fNSigmaTOFP(0),
+  fSigmaToVertex(0),
+  fClusters(159),
+  fShared(159),
+  fNominalTpcEntrancePoint(0,0,0),
+  fNominalTpcExitPoint(0,0,0),
+  fHiddenInfo(0)
+ { 
+   // copy constructor
+  fCharge = t.fCharge;
+  fPidProbElectron = t.fPidProbElectron;
+  fPidProbPion = t.fPidProbPion;
+  fPidProbKaon = t.fPidProbKaon;
+  fPidProbProton = t.fPidProbProton;
+  fPidProbMuon=t.fPidProbMuon;
+  fTofPionTime=t.fTofPionTime;
+  fTofKaonTime=t.fTofKaonTime;
+  fTofProtonTime=t.fTofProtonTime;
+  fP = t.fP;
+  fPt = t.fPt;
+  fHelix = t.fHelix;
+  fTrackId = t.fTrackId;
+  fFlags=t.fFlags;
+  fLabel=t.fLabel;
+  fImpactD=t.fImpactD;
+  fImpactZ=t.fImpactZ;
+  fCdd=t.fCdd;
+  fCdz=t.fCdz;
+  fCzz=t.fCzz;
+  fITSchi2=t.fITSchi2;       
+  fITSncls=t.fITSncls;        
+  fTPCchi2=t.fTPCchi2;       
+  fTPCncls=t.fTPCncls;       
+  fTPCnclsF=t.fTPCnclsF;      
+  fTPCsignal=t.fTPCsignal;
+  fTPCsignalN=t.fTPCsignalN;    
+  fTPCsignalS=t.fTPCsignalS;  
+  fVTOF=t.fVTOF;
+  fNSigmaTPCPi=t.fNSigmaTPCPi;
+  fNSigmaTPCK=t.fNSigmaTPCK;
+  fNSigmaTPCP=t.fNSigmaTPCP;
+  fNSigmaTOFPi=t.fNSigmaTOFPi;
+  fNSigmaTOFK=t.fNSigmaTOFK;
+  fNSigmaTOFP=t.fNSigmaTOFP;
+  fSigmaToVertex=t.fSigmaToVertex;
+  fClusters=t.fClusters;
+  fShared=t.fShared;
+  fNominalTpcEntrancePoint=t.fNominalTpcEntrancePoint;
+  fNominalTpcExitPoint=t.fNominalTpcExitPoint;
+  if (t.ValidHiddenInfo())
+    fHiddenInfo = t.GetHiddenInfo()->Clone();
+  else 
+    fHiddenInfo = NULL;
+  fKinkIndexes[0] = t.fKinkIndexes[0];
+  fKinkIndexes[1] = t.fKinkIndexes[1];
+  fKinkIndexes[2] = t.fKinkIndexes[2];
+  //  cout << "Created track " << this << endl;
+}
+
+AliFemtoTrack& AliFemtoTrack::operator=(const AliFemtoTrack& aTrack)
+{
+  // assignment operator
+  if (this == &aTrack)
+    return *this;
+  fCharge = aTrack.fCharge;
+  fPidProbElectron = aTrack.fPidProbElectron;
+  fPidProbPion = aTrack.fPidProbPion;
+  fPidProbKaon = aTrack.fPidProbKaon;
+  fPidProbProton = aTrack.fPidProbProton;
+  fPidProbMuon=aTrack.fPidProbMuon;
+  fTofPionTime=aTrack.fTofPionTime;
+  fTofKaonTime=aTrack.fTofKaonTime;
+  fTofProtonTime=aTrack.fTofProtonTime;
+  fP = aTrack.fP;
+  fPt = aTrack.fPt;
+  fHelix = aTrack.fHelix;
+  fTrackId = aTrack.fTrackId;
+  fFlags=aTrack.fFlags;
+  fLabel=aTrack.fLabel;
+  fImpactD=aTrack.fImpactD;
+  fImpactZ=aTrack.fImpactZ;
+  fCdd=aTrack.fCdd;
+  fCdz=aTrack.fCdz;
+  fCzz=aTrack.fCzz;
+  fITSchi2=aTrack.fITSchi2;       
+  fITSncls=aTrack.fITSncls;        
+  fTPCchi2=aTrack.fTPCchi2;       
+  fTPCncls=aTrack.fTPCncls;       
+  fTPCnclsF=aTrack.fTPCnclsF;
+  fTPCsignal=aTrack.fTPCsignal;
+  fTPCsignalN=aTrack.fTPCsignalN;    
+  fTPCsignalS=aTrack.fTPCsignalS;  
+  fVTOF=aTrack.fVTOF;    
+  fNSigmaTPCPi=aTrack.fNSigmaTPCPi;    
+  fNSigmaTPCK=aTrack.fNSigmaTPCK;    
+  fNSigmaTPCP=aTrack.fNSigmaTPCP;    
+  fNSigmaTOFPi=aTrack.fNSigmaTOFPi;    
+  fNSigmaTOFK=aTrack.fNSigmaTOFK;    
+  fNSigmaTOFP=aTrack.fNSigmaTOFP;    
+  fClusters=aTrack.fClusters;
+  fShared=aTrack.fShared;
+  fNominalTpcEntrancePoint=aTrack.fNominalTpcEntrancePoint;
+  fNominalTpcExitPoint=aTrack.fNominalTpcExitPoint;
+  fKinkIndexes[0] = aTrack.fKinkIndexes[0];
+  fKinkIndexes[1] = aTrack.fKinkIndexes[1];
+  fKinkIndexes[2] = aTrack.fKinkIndexes[2];
+  if (ValidHiddenInfo())
+    delete fHiddenInfo;
+  if (aTrack.ValidHiddenInfo())
+    fHiddenInfo = aTrack.GetHiddenInfo()->Clone();
+  else 
+    fHiddenInfo = NULL;
+
+  return *this;
+}
+
+void AliFemtoTrack::SetCharge(const short& ch){fCharge=ch;}
+
+void AliFemtoTrack::SetPidProbElectron(const float& x){fPidProbElectron = x;}
+void AliFemtoTrack::SetPidProbPion(const float& x){fPidProbPion = x;}
+void AliFemtoTrack::SetPidProbKaon(const float& x){fPidProbKaon = x;}
+void AliFemtoTrack::SetPidProbProton(const float& x){fPidProbProton = x;}
+void AliFemtoTrack::SetPidProbMuon(const float& x){fPidProbMuon = x;}
+void AliFemtoTrack::SetTofExpectedTimes(const float& tpi, const float& tkn, const float& tpr){fTofPionTime = tpi; fTofKaonTime = tkn; fTofProtonTime = tpr; }
+void AliFemtoTrack::SetP(const AliFemtoThreeVector& p){fP = p;}
+void AliFemtoTrack::SetPt(const float& pt){fPt = pt;} 
+void AliFemtoTrack::SetHelix(const AliFmPhysicalHelixD& h){fHelix = h;}
+void AliFemtoTrack::SetTrackId(const short & id) { fTrackId=id;}
+void AliFemtoTrack::SetFlags(const long int &flags) {fFlags=flags;}
+void AliFemtoTrack::SetLabel(const int &label) {fLabel=label;}
+void AliFemtoTrack::SetImpactD(const float& aImpactD){fImpactD=aImpactD;}
+void AliFemtoTrack::SetImpactZ(const float& aImpactZ){fImpactZ=aImpactZ;}
+void AliFemtoTrack::SetCdd(const float& aCdd){fCdd=aCdd;}
+void AliFemtoTrack::SetCdz(const float& aCdz){fCdz=aCdz;}
+void AliFemtoTrack::SetCzz(const float& aCzz){fCzz=aCzz;}
+void AliFemtoTrack::SetITSchi2(const float& aITSchi2){fITSchi2=aITSchi2;}    
+void AliFemtoTrack::SetITSncls(const int& aITSncls){fITSncls=aITSncls;}     
+void AliFemtoTrack::SetTPCchi2(const float& aTPCchi2){fTPCchi2=aTPCchi2;}       
+void AliFemtoTrack::SetTPCncls(const int& aTPCncls){fTPCncls=aTPCncls;}       
+void AliFemtoTrack::SetTPCnclsF(const short& aTPCnclsF){fTPCnclsF=aTPCnclsF;}      
+void AliFemtoTrack::SetTPCsignal(const float& aTPCsig){fTPCsignal=aTPCsig;}
+void AliFemtoTrack::SetTPCsignalN(const short& aTPCsignalN){fTPCsignalN=aTPCsignalN;}    
+void AliFemtoTrack::SetTPCsignalS(const float& aTPCsignalS){fTPCsignalS=aTPCsignalS;} 
+void AliFemtoTrack::SetVTOF(const float& aVTOF){fVTOF=aVTOF;}
+void AliFemtoTrack::SetNSigmaTPCPi(const float& aNSigmaTPCPi){fNSigmaTPCPi=aNSigmaTPCPi;}
+void AliFemtoTrack::SetNSigmaTPCK(const float& aNSigmaTPCK){fNSigmaTPCK=aNSigmaTPCK;}
+void AliFemtoTrack::SetNSigmaTPCP(const float& aNSigmaTPCP){fNSigmaTPCP=aNSigmaTPCP;}
+void AliFemtoTrack::SetNSigmaTOFPi(const float& aNSigmaTOFPi){fNSigmaTOFPi=aNSigmaTOFPi;}
+void AliFemtoTrack::SetNSigmaTOFK(const float& aNSigmaTOFK){fNSigmaTOFK=aNSigmaTOFK;}
+void AliFemtoTrack::SetNSigmaTOFP(const float& aNSigmaTOFP){fNSigmaTOFP=aNSigmaTOFP;}
+void AliFemtoTrack::SetSigmaToVertex(const float& aSigma){fSigmaToVertex=aSigma;} 
+
+
+short AliFemtoTrack::Charge() const {return fCharge;}  
+AliFemtoThreeVector AliFemtoTrack::P() const {return fP;}
+float AliFemtoTrack::Pt() const {return fPt;}              
+const AliFmPhysicalHelixD& AliFemtoTrack::Helix() const {return fHelix;}
+short AliFemtoTrack::TrackId() const { return fTrackId; }
+long int AliFemtoTrack::Flags() const {return fFlags;}
+int AliFemtoTrack::Label()const {return fLabel;}
+float AliFemtoTrack::ImpactD()const{return fImpactD;}
+float AliFemtoTrack::ImpactZ()const{return fImpactZ;}
+float AliFemtoTrack::Cdd() const{return fCdd;}
+float AliFemtoTrack::Cdz() const{return fCdz;}
+float AliFemtoTrack::Czz() const{return fCzz;} 
+float AliFemtoTrack::ITSchi2() const{return fITSchi2;}    
+int   AliFemtoTrack::ITSncls() const{return fITSncls;}     
+float AliFemtoTrack::TPCchi2() const{return fTPCchi2;}       
+int   AliFemtoTrack::TPCncls() const{return fTPCncls;}       
+short AliFemtoTrack::TPCnclsF() const{return fTPCnclsF;}      
+float AliFemtoTrack::TPCsignal() const{return fTPCsignal;}
+short AliFemtoTrack::TPCsignalN() const{return fTPCsignalN;}    
+float AliFemtoTrack::TPCsignalS() const{return fTPCsignalS;} 
+float AliFemtoTrack::VTOF() const{return fVTOF;}
+float AliFemtoTrack::NSigmaTPCPi() const{return fNSigmaTPCPi;}
+float AliFemtoTrack::NSigmaTPCK() const{return fNSigmaTPCK;}
+float AliFemtoTrack::NSigmaTPCP() const{return fNSigmaTPCP;}
+float AliFemtoTrack::NSigmaTOFPi() const{return fNSigmaTOFPi;}
+float AliFemtoTrack::NSigmaTOFK() const{return fNSigmaTOFK;}
+float AliFemtoTrack::NSigmaTOFP() const{return fNSigmaTOFP;}
+float AliFemtoTrack::SigmaToVertex() const{return fSigmaToVertex;} 
+float AliFemtoTrack::TOFpionTime() const{return fTofPionTime;}
+float AliFemtoTrack::TOFkaonTime() const{return fTofKaonTime;}
+float AliFemtoTrack::TOFprotonTime() const{return fTofProtonTime;}
+
+
+void AliFemtoTrack::SetHiddenInfo(AliFemtoHiddenInfo* aHiddenInfo) {fHiddenInfo=aHiddenInfo;}
+bool AliFemtoTrack::ValidHiddenInfo() const { if (fHiddenInfo) return true; else return false; }
+AliFemtoHiddenInfo* AliFemtoTrack::GetHiddenInfo() const {return fHiddenInfo;}
+  
+AliFemtoTrack::~AliFemtoTrack()
+{
+  // destructor
+  if (fHiddenInfo)
+    delete fHiddenInfo;
+  //  cout << "Deleted track " << this << endl;
+}
+
+const TBits& AliFemtoTrack::TPCclusters() const {return fClusters;}
+const TBits& AliFemtoTrack::TPCsharing()  const {return fShared;}
+
+void AliFemtoTrack::SetTPCcluster(const short& aNBit, const Bool_t& aValue)
+{
+  fClusters.SetBitNumber(aNBit, aValue);
+}
+
+void AliFemtoTrack::SetTPCshared(const short& aNBit, const Bool_t& aValue)
+{
+  fShared.SetBitNumber(aNBit, aValue);
+}
+
+void AliFemtoTrack::SetTPCClusterMap(const TBits& aBits)
+{
+  fClusters = aBits;
+}
+void AliFemtoTrack::SetTPCSharedMap(const TBits& aBits)
+{
+  fShared = aBits;
+}
+
+void AliFemtoTrack::SetKinkIndexes(int points[3])
+{
+  // Transfer the Kink indices
+  fKinkIndexes[0] = points[0];
+  fKinkIndexes[1] = points[1];
+  fKinkIndexes[2] = points[2];
+}
+
+int  AliFemtoTrack::KinkIndex(int aIndex) const
+{
+  // Return Kink index
+  if ((aIndex <3) && (aIndex>=0))
+    return fKinkIndexes[aIndex];
+  else
+    return 0;
+}
+
+// void AliFemtoTrack::SetXTPC(const AliFemtoThreeVector& aXTPC)
+// {
+//   fXTPC = aXTPC;
+// }
+
+// void AliFemtoTrack::SetXTPC(double *aXTPC)
+// {
+//   fXTPC.setX(aXTPC[0]);
+//   fXTPC.setY(aXTPC[1]);
+//   fXTPC.setZ(aXTPC[2]);
+// }
+
+// AliFemtoThreeVector AliFemtoTrack::XTPC() const
+// {
+//   return fXTPC;
+// }
+
+const AliFemtoThreeVector& AliFemtoTrack::NominalTpcExitPoint() const
+{
+  return fNominalTpcExitPoint;
+}
+const AliFemtoThreeVector& AliFemtoTrack::NominalTpcEntrancePoint() const
+{
+  return fNominalTpcEntrancePoint;
+}
+
+void AliFemtoTrack::SetNominalTPCEntrancePoint(const AliFemtoThreeVector& aXTPC)
+{
+  fNominalTpcEntrancePoint = aXTPC;
+}
+void AliFemtoTrack::SetNominalTPCEntrancePoint(double *aXTPC)
+{
+  // Store the nominal TPC entrance point
+  fNominalTpcEntrancePoint.SetX(aXTPC[0]);
+  fNominalTpcEntrancePoint.SetY(aXTPC[1]);
+  fNominalTpcEntrancePoint.SetZ(aXTPC[2]);
+}
+
+void AliFemtoTrack::SetNominalTPCExitPoint(const AliFemtoThreeVector& aXTPC)
+{
+  fNominalTpcExitPoint = aXTPC;
+}
+void AliFemtoTrack::SetNominalTPCExitPoint(double *aXTPC)
+{
+  // Store the nominal TPC exit point
+  fNominalTpcExitPoint.SetX(aXTPC[0]);
+  fNominalTpcExitPoint.SetY(aXTPC[1]);
+  fNominalTpcExitPoint.SetZ(aXTPC[2]);
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoTrack.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoTrack.h
new file mode 100644 (file)
index 0000000..2f930eb
--- /dev/null
@@ -0,0 +1,229 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFemtoTrack: main class holding all the necessary information       //
+// about a track (before the identification) that is required during     //
+// femtoscopic analysis. This class is filled with information from the  //
+// input stream by the reader. A particle has a link back to the Track   //
+// it was created from, so we do not copy the information.               //
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+
+#ifndef ALIFEMTOTRACK_H
+#define ALIFEMTOTRACK_H
+
+#include "AliFemtoTypes.h"
+#include "AliFmPhysicalHelixD.h"
+#include "TBits.h"
+/* Th stuff */
+#include "AliFemtoHiddenInfo.h"
+/***/
+
+#ifndef __NO_STAR_DEPENDENCE_ALLOWED__
+class StEvent;
+class StTrack;
+class StMuDst;
+class StMuTrack;
+#endif
+
+class AliFemtoTrack{
+public:
+  AliFemtoTrack();
+  AliFemtoTrack(const AliFemtoTrack& aTrack);// copy constructor
+  AliFemtoTrack& operator=(const AliFemtoTrack& aTrack);
+#ifndef __NO_STAR_DEPENDENCE_ALLOWED__
+#ifdef __ROOT__
+ //AliFemtoTrack(const StTrack*, AliFemtoThreeVector);   // c-tor from StTrack of STAR DSTs
+  //AliFemtoTrack(const StMuDst* dst, const StMuTrack* t);
+#endif
+  //AliFemtoTrack(const StEvent*, const StTrack*);
+#endif
+
+  ~AliFemtoTrack();
+//    ~AliFemtoTrack(){/* no-op*/};
+
+  short Charge() const;
+  float PidProbElectron() const;
+  float PidProbPion() const;
+  float PidProbKaon() const;
+  float PidProbProton() const;
+  float PidProbMuon() const;
+  
+  AliFemtoThreeVector P() const;
+  float Pt() const;
+  const AliFmPhysicalHelixD& Helix() const;
+  short TrackId() const;
+  long int Flags() const;
+  int Label()const;
+  float ImpactD()const;
+  float ImpactZ()const;
+  float Cdd() const;
+  float Cdz() const;
+  float Czz() const; 
+  
+  float ITSchi2() const;    
+  int   ITSncls() const;     
+  float TPCchi2() const;       
+  int   TPCncls() const;       
+  short TPCnclsF() const;      
+  float TPCsignal() const;
+  short TPCsignalN() const;    
+  float TPCsignalS() const;   
+  //new PID
+  float NSigmaTPCPi() const;   
+  float NSigmaTPCK() const;   
+  float NSigmaTPCP() const;   
+  float VTOF() const;   
+  float NSigmaTOFPi() const;   
+  float NSigmaTOFK() const;   
+  float NSigmaTOFP() const;   
+
+
+  float TOFpionTime() const;
+  float TOFkaonTime() const;
+  float TOFprotonTime() const;
+
+  const TBits& TPCclusters() const;
+  const TBits& TPCsharing()  const;
+  
+  void SetCharge(const short& s);
+  void SetPidProbElectron(const float& x);
+  void SetPidProbPion(const float& x);
+  void SetPidProbKaon(const float& x);
+  void SetPidProbProton(const float& x);
+  void SetPidProbMuon(const float& x);
+  void SetTofExpectedTimes(const float& tpi, const float& tkn, const float& tpr);
+   
+  void SetP(const AliFemtoThreeVector& p);
+  void SetPt(const float& x);
+  void SetHelix(const AliFmPhysicalHelixD& h);
+  void SetTrackId(const short& s);
+  void SetFlags(const long int& i);
+  void SetLabel(const int& i);
+  void SetImpactD(const float& x);
+  void SetImpactZ(const float& x);
+  void SetCdd(const float& x);
+  void SetCdz(const float& x);
+  void SetCzz(const float& x);
+  
+  void SetITSchi2(const float& x);    
+  void SetITSncls(const int& i);     
+  void SetTPCchi2(const float& x);       
+  void SetTPCncls(const int& i);       
+  void SetTPCnclsF(const short& s);      
+  void SetTPCsignal(const float& s);
+  void SetTPCsignalN(const short& s);    
+  void SetTPCsignalS(const float& x);   
+
+  //new PID
+  void SetNSigmaTPCPi(const float& x);   
+  void SetNSigmaTPCK(const float& x);   
+  void SetNSigmaTPCP(const float& x);   
+  void SetVTOF(const float& x);   
+  void SetNSigmaTOFPi(const float& x);   
+  void SetNSigmaTOFK(const float& x);   
+  void SetNSigmaTOFP(const float& x);  
+
+  void SetTPCcluster(const short& aNBit, const Bool_t& aValue);
+  void SetTPCshared(const short& aNBit, const Bool_t& aValue);
+
+  void SetTPCClusterMap(const TBits& aBits);
+  void SetTPCSharedMap(const TBits& aBits);
+
+  void SetKinkIndexes(int points[3]);
+  int  KinkIndex(int aIndex) const;
+
+  /* Th stuff */
+  void SetHiddenInfo(AliFemtoHiddenInfo* aHiddenInfo);
+  bool ValidHiddenInfo() const;
+  // Fab private : (official : const AliFemtoHiddenInfo* HiddenInfo() const;
+  AliFemtoHiddenInfo* GetHiddenInfo() const;
+  /***/
+  
+  const AliFemtoThreeVector& NominalTpcExitPoint() const;
+  const AliFemtoThreeVector& NominalTpcEntrancePoint() const;
+    
+  void SetNominalTPCEntrancePoint(const AliFemtoThreeVector& aXTPC);
+  void SetNominalTPCEntrancePoint(double *aXTPC);
+
+  void SetNominalTPCExitPoint(const AliFemtoThreeVector& aXTPC);
+  void SetNominalTPCExitPoint(double *aXTPC);
+  void SetSigmaToVertex(const float& Sigma);
+  float SigmaToVertex() const;
+  //Alice stuff
+  enum {
+    kITSin=0x0001,kITSout=0x0002,kITSrefit=0x0004,kITSpid=0x0008,
+    kTPCin=0x0010,kTPCout=0x0020,kTPCrefit=0x0040,kTPCpid=0x0080,
+    kTRDin=0x0100,kTRDout=0x0200,kTRDrefit=0x0400,kTRDpid=0x0800,
+    kTOFin=0x1000,kTOFout=0x2000,kTOFrefit=0x4000,kTOFpid=0x8000,
+    kRICHpid=0x20000,
+    kTRDbackup=0x80000,
+    kTRDStop=0x20000000,
+    kESDpid=0x40000000,
+    kTIME=0x80000000
+  };
+  
+ private:
+  char fCharge;           // track charge
+  float fPidProbElectron; // electron pid
+  float fPidProbPion;     // pion pid 
+  float fPidProbKaon;     // kaon pid 
+  float fPidProbProton;   // proton pid
+  float fPidProbMuon;     // muon pid
+  unsigned int fTrackId;  // track unique id
+  float fTofPionTime;     // TOF time - pion expected time
+  float fTofKaonTime;     // TOF time - kaon expected time
+  float fTofProtonTime;   // TOF time - proton expected time
+
+  AliFemtoThreeVector fP; // track momentum
+  float fPt;              // transverse momenta
+  AliFmPhysicalHelixD fHelix; // track helix
+  //alice stuff
+  long int fFlags; //Reconsruction status flags
+  int fLabel; //Track label  
+  float fImpactD; //impact parameter in xy plane
+  float fImpactZ;//impacct parameter in z
+  float fCdd,fCdz,fCzz;//covariance matrix of the impact parameters
+  // ITS related track information
+  float fITSchi2;        // chi2 in the ITS
+  int   fITSncls;        // number of clusters assigned in the ITS
+  // TPC related track information
+  float  fTPCchi2;       // chi2 in the TPC
+  int    fTPCncls;       // number of clusters assigned in the TPC
+  short fTPCnclsF;       // number of findable clusters in the TPC
+  float fTPCsignal;      // dEdx TPC value
+  short fTPCsignalN;     // number of points used for dEdx
+  float fTPCsignalS;     // RMS of dEdx measurement
+
+  float fVTOF;     // v=length/TOF
+  float fNSigmaTPCPi;     // nsigma TPC for pion
+  float fNSigmaTPCK;     // nsigma TPC for K
+  float fNSigmaTPCP;     // nsigma TPC for P
+  float fNSigmaTOFPi;     // nsigma TPC for pion
+  float fNSigmaTOFK;     // nsigma TPC for K
+  float fNSigmaTOFP;     // nsigma TPC for P
+
+  float fSigmaToVertex;  // Distance from track to vertex in sigmas
+  TBits fClusters;       // Cluster per padrow map
+  TBits fShared;         // Sharing per padrow map
+  AliFemtoThreeVector fNominalTpcEntrancePoint; // Nominal track entrance point into TPC
+  AliFemtoThreeVector fNominalTpcExitPoint;     // Nominal track exit point from TPC
+
+  int   fKinkIndexes[3]; // Kink Index list
+  /* Th stuff */
+  // Fab private : add mutable
+  //  mutable 
+  AliFemtoHiddenInfo* fHiddenInfo; //! hidden info
+  /***/
+};
+
+//inline const float* AliFemtoTrack::NSigma() const 
+//{return &mNSigmaElectron;} // Fab private 
+inline float AliFemtoTrack::PidProbElectron() const {return fPidProbElectron;}
+inline float AliFemtoTrack::PidProbPion() const {return fPidProbPion;}
+inline float AliFemtoTrack::PidProbKaon() const {return fPidProbKaon;}
+inline float AliFemtoTrack::PidProbProton() const {return fPidProbProton;}
+inline float AliFemtoTrack::PidProbMuon() const {return fPidProbMuon;}
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoTrackCollection.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoTrackCollection.h
new file mode 100644 (file)
index 0000000..27f6d8d
--- /dev/null
@@ -0,0 +1,47 @@
+/***************************************************************************
+ *
+ * $Id$
+ *
+ * Author: Mike Lisa, Ohio State, lisa@mps.ohio-state.edu
+ ***************************************************************************
+ *
+ * Description: part of STAR HBT Framework: AliFemtoMaker package
+ *   The Collection of Tracks is the main component of the HbtEvent,
+ *   which is essentially the transient microDST
+ *
+ ***************************************************************************
+ *
+ * $Log$
+ * Revision 1.1.1.1  2007/04/25 15:38:41  panos
+ * Importing the HBT code dir
+ *
+ * Revision 1.1.1.1  2007/03/07 10:14:49  mchojnacki
+ * First version on CVS
+ *
+ * Revision 1.2  2000/02/01 00:33:32  laue
+ * namespaces changed to run on the new Solaris Compiler CC5
+ * since we can use member templates in franks1Histo.h we are doing it
+ *
+ * Revision 1.1.1.1  1999/06/29 16:02:57  lisa
+ * Installation of AliFemtoMaker
+ *
+ **************************************************************************/
+
+#ifndef AliFemtoTrackCollection_hh
+#define AliFemtoTrackCollection_hh
+#include "AliFemtoTrack.h"
+#include <list>
+
+#if !defined(ST_NO_NAMESPACES)
+using std::list;
+#endif
+
+#ifdef ST_NO_TEMPLATE_DEF_ARGS
+typedef list<AliFemtoTrack*, allocator<AliFemtoTrack*> >            AliFemtoTrackCollection;
+typedef list<AliFemtoTrack*, allocator<AliFemtoTrack*> >::iterator  AliFemtoTrackIterator;
+#else
+typedef list<AliFemtoTrack*>            AliFemtoTrackCollection;
+typedef list<AliFemtoTrack*>::iterator  AliFemtoTrackIterator;
+#endif
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoTrackCut.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoTrackCut.h
new file mode 100644 (file)
index 0000000..07a38f4
--- /dev/null
@@ -0,0 +1,37 @@
+////////////////////////////////////////////////////////////////////////////////
+/// AliFemtoTrackCut - the pure virtual base class for the track cut         ///
+/// All track cuts must inherit from this one                                ///
+////////////////////////////////////////////////////////////////////////////////
+
+#ifndef AliFemtoTrackCut_hh
+#define AliFemtoTrackCut_hh
+
+#include "AliFemtoTypes.h"
+#include "AliFemtoTrack.h"
+#include "AliFemtoParticleCut.h"
+
+class AliFemtoTrackCut : public AliFemtoParticleCut {
+
+public:
+
+  AliFemtoTrackCut(){/* no-op */};                       // default constructor. - Users should write their own
+  AliFemtoTrackCut(const AliFemtoTrackCut&);                // copy constructor
+  virtual ~AliFemtoTrackCut(){/* no-op */};              // destructor
+  AliFemtoTrackCut& operator=(const AliFemtoTrackCut&);                // copy constructor
+
+  virtual bool Pass(const AliFemtoTrack* track)=0;       // true if passes, false if not
+  virtual AliFemtoParticleType Type(){return hbtTrack;}
+  virtual AliFemtoTrackCut* Clone() { return 0;}
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoTrackCut, 0)
+#endif
+};
+
+inline AliFemtoTrackCut::AliFemtoTrackCut(const AliFemtoTrackCut& c) : AliFemtoParticleCut(c) {
+#ifdef STHBTDEBUG
+  cout << " AliFemtoTrackCut::AliFemtoTrackCut(const AliFemtoTrackCut& c) : AliFemtoParticleCut(c) " << endl;
+#endif
+}
+inline AliFemtoTrackCut& AliFemtoTrackCut::operator=(const AliFemtoTrackCut& c) { if (this != &c) { AliFemtoParticleCut::operator=(c); } return *this; } 
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoTypes.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoTypes.h
new file mode 100644 (file)
index 0000000..b4898bb
--- /dev/null
@@ -0,0 +1,45 @@
+/***************************************************************************
+ *
+ * $Id$
+ *
+ * Author: Frank Laue, BNL, laue@bnl.gov
+ ***************************************************************************
+ *
+ ***************************************************************************
+ *
+ * $Log$
+ * Revision 1.1.1.1  2007/04/25 15:38:41  panos
+ * Importing the HBT code dir
+ *
+ * Revision 1.1.1.1  2007/03/07 10:14:49  mchojnacki
+ * First version on CVS
+ *
+ * Revision 1.14  2001/06/21 19:15:48  laue
+ * Modified fiels:
+ *   CTH.h : new constructor added
+ *   AliFemtoEvent, AliFemtoKink, AliFemtoTrack : constructors from the persistent
+ *                                   (TTree) classes added
+ *   AliFemtoLikeSignAnalysis : minor changes, for debugging
+ *   AliFemtoTypes: split into different files
+ * Added files: for the new TTree muDst's
+ *   StExceptions.cxx StExceptions.h AliFemtoEnumeration.h
+ *   AliFemtoHelix.h AliFemtoHisto.h AliFemtoString.h AliFemtoTFile.h
+ *   AliFemtoTTreeEvent.cxx AliFemtoTTreeEvent.h AliFemtoTTreeKink.cxx
+ *   AliFemtoTTreeKink.h AliFemtoTTreeTrack.cxx AliFemtoTTreeTrack.h
+ *   AliFemtoTTreeV0.cxx AliFemtoTTreeV0.h AliFemtoVector.h
+ *
+ *
+ ***************************************************************************/
+
+// 
+// I split this up into different files, so that I do not have to 
+// load/recompile everything all over again.
+//
+
+//#include "AliFemtoHisto.h"
+#include "AliFemtoString.h"
+#include "AliFemtoVector.h"
+#include "AliFemtoHelix.h"
+#include "AliFemtoEnumeration.h"
+
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoV0.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoV0.cxx
new file mode 100644 (file)
index 0000000..e9d2834
--- /dev/null
@@ -0,0 +1,290 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFemtoV0: special type of particle desling with the specifics       //
+// of the V0 type of particle                                            //
+// It stores the information both about the V0 itself and about it's     //
+// daughters, so that the caut betwen the daughter characteristics is    //
+// possible.
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+#include "AliFemtoV0.h"
+#include "phys_constants.h"
+
+// -----------------------------------------------------------------------
+AliFemtoV0::AliFemtoV0():
+  fDecayLengthV0(0), fDecayVertexV0(0), fPrimaryVertex(0),
+  fDcaV0Daughters(0), fDcaV0ToPrimVertex(0),
+  fDcaPosToPrimVertex(0), fDcaNegToPrimVertex(0),
+  fMomPos(0), fMomNeg(0),
+  fTpcHitsPos(0), fTpcHitsNeg(0),
+  fChi2V0(0),  fClV0(0),  fChi2Pos(0),  fClPos(0),  fChi2Neg(0),  fClNeg(0),
+  fDedxPos(0),  fErrDedxPos(0),  fLenDedxPos(0),
+  fDedxNeg(0),  fErrDedxNeg(0),  fLenDedxNeg(0),
+  fNufDedxPos(0), fNufDedxNeg(0),
+  fHelixPos(), fHelixNeg(), 
+  fMomV0(0),
+  fAlphaV0(0),  fPtArmV0(0),
+  fELambda(0),  fEK0Short(0),  
+  fEPosProton(0),  fEPosPion(0),
+  fENegProton(0),  fENegPion(0),
+  fMassLambda(0),  fMassAntiLambda(0),
+  fMassK0Short(0),  fRapLambda(0),
+  fRapK0Short(0),  fCTauLambda(0),
+  fCTauK0Short(0),  fPtV0(0),  fPtotV0(0),
+  fPtPos(0),  fPtotPos(0),
+  fPtNeg(0),  fPtotNeg(0),
+  fKeyNeg(0),   fKeyPos(0),
+  fHiddenInfo(0)  /***/
+{ 
+  // Default empty constructor
+  fTrackTopologyMapPos[0] = 0;
+  fTrackTopologyMapPos[1] = 0;
+  fTrackTopologyMapNeg[0] = 0;
+  fTrackTopologyMapNeg[1] = 0;
+
+}
+// -----------------------------------------------------------------------
+AliFemtoV0::AliFemtoV0(const AliFemtoV0& v) :
+  fDecayLengthV0(0), fDecayVertexV0(0), fPrimaryVertex(0),
+  fDcaV0Daughters(0), fDcaV0ToPrimVertex(0),
+  fDcaPosToPrimVertex(0), fDcaNegToPrimVertex(0),
+  fMomPos(0), fMomNeg(0),
+  fTpcHitsPos(0), fTpcHitsNeg(0),
+  fChi2V0(0),  fClV0(0),  fChi2Pos(0),  fClPos(0),  fChi2Neg(0),  fClNeg(0),
+  fDedxPos(0),  fErrDedxPos(0),  fLenDedxPos(0),
+  fDedxNeg(0),  fErrDedxNeg(0),  fLenDedxNeg(0),
+  fNufDedxPos(0), fNufDedxNeg(0),
+  fHelixPos(), fHelixNeg(), 
+  fMomV0(0),
+  fAlphaV0(0),  fPtArmV0(0),
+  fELambda(0),  fEK0Short(0),  
+  fEPosProton(0),  fEPosPion(0),
+  fENegProton(0),  fENegPion(0),
+  fMassLambda(0),  fMassAntiLambda(0),
+  fMassK0Short(0),  fRapLambda(0),
+  fRapK0Short(0),  fCTauLambda(0),
+  fCTauK0Short(0),  fPtV0(0),  fPtotV0(0),
+  fPtPos(0),  fPtotPos(0),
+  fPtNeg(0),  fPtotNeg(0),
+  fKeyNeg(0),   fKeyPos(0),
+  fHiddenInfo(0)  /***/
+{ 
+  // copy constructor
+  fDecayLengthV0 = v.fDecayLengthV0;
+  fDecayVertexV0 = v.fDecayVertexV0;
+  fDcaV0Daughters = v.fDcaV0Daughters;
+  fDcaV0ToPrimVertex = v.fDcaV0ToPrimVertex;
+  fDcaPosToPrimVertex = v.fDcaPosToPrimVertex;
+  fDcaNegToPrimVertex = v.fDcaNegToPrimVertex;
+  fMomPos = v.fMomPos;
+  fMomNeg = v.fMomNeg;
+
+  fTrackTopologyMapPos[0] = v.fTrackTopologyMapPos[0];
+  fTrackTopologyMapPos[1] = v.fTrackTopologyMapPos[1];
+  fTrackTopologyMapNeg[0] = v.fTrackTopologyMapNeg[0];
+  fTrackTopologyMapNeg[1] = v.fTrackTopologyMapNeg[1];
+   
+  fKeyPos = v.fKeyPos;
+  fKeyNeg = v.fKeyNeg;
+     
+  fTpcHitsPos = v.fTpcHitsPos;
+  fTpcHitsNeg = v.fTpcHitsNeg;
+
+  fChi2V0 = v.fChi2V0;
+  fClV0 = v.fClV0;
+  fChi2Pos = v.fChi2Pos;
+  fClPos = v.fClPos;
+  fChi2Neg = v.fChi2Neg;
+  fClNeg = v.fClNeg;
+  fDedxPos = v.fDedxPos;
+  fErrDedxPos = v.fErrDedxPos;//Gael 04Fev2002
+  fLenDedxPos = v.fLenDedxPos;//Gael 04Fev2002
+  fDedxNeg = v.fDedxNeg;
+  fErrDedxNeg = v.fErrDedxNeg;//Gael 04Fev2002
+  fLenDedxNeg = v.fLenDedxNeg;//Gael 04Fev2002
+
+  fNufDedxPos = v.fNufDedxPos;
+  fNufDedxNeg = v.fNufDedxNeg;
+
+  fHelixPos = v.fHelixPos;// Gael 12 Sept
+  fHelixNeg = v.fHelixNeg;// Gael 12 Sept
+  fHiddenInfo = v.fHiddenInfo? v.fHiddenInfo->Clone() : 0;// GR 11 DEC 02
+  UpdateV0();
+}
+AliFemtoV0& AliFemtoV0::operator=(const AliFemtoV0& aV0)
+{
+  // assignment operator
+  if (this == &aV0)
+    return *this;
+  fDecayLengthV0 = aV0.fDecayLengthV0;
+  fDecayVertexV0 = aV0.fDecayVertexV0;
+  fDcaV0Daughters = aV0.fDcaV0Daughters;
+  fDcaV0ToPrimVertex = aV0.fDcaV0ToPrimVertex;
+  fDcaPosToPrimVertex = aV0.fDcaPosToPrimVertex;
+  fDcaNegToPrimVertex = aV0.fDcaNegToPrimVertex;
+  fMomPos = aV0.fMomPos;
+  fMomNeg = aV0.fMomNeg;
+
+  fTrackTopologyMapPos[0] = aV0.fTrackTopologyMapPos[0];
+  fTrackTopologyMapPos[1] = aV0.fTrackTopologyMapPos[1];
+  fTrackTopologyMapNeg[0] = aV0.fTrackTopologyMapNeg[0];
+  fTrackTopologyMapNeg[1] = aV0.fTrackTopologyMapNeg[1];
+   
+  fKeyPos = aV0.fKeyPos;
+  fKeyNeg = aV0.fKeyNeg;
+     
+  fTpcHitsPos = aV0.fTpcHitsPos;
+  fTpcHitsNeg = aV0.fTpcHitsNeg;
+
+  fChi2V0 = aV0.fChi2V0;
+  fClV0 = aV0.fClV0;
+  fChi2Pos = aV0.fChi2Pos;
+  fClPos = aV0.fClPos;
+  fChi2Neg = aV0.fChi2Neg;
+  fClNeg = aV0.fClNeg;
+  fDedxPos = aV0.fDedxPos;
+  fErrDedxPos = aV0.fErrDedxPos;//Gael 04Fev2002
+  fLenDedxPos = aV0.fLenDedxPos;//Gael 04Fev2002
+  fDedxNeg = aV0.fDedxNeg;
+  fErrDedxNeg = aV0.fErrDedxNeg;//Gael 04Fev2002
+  fLenDedxNeg = aV0.fLenDedxNeg;//Gael 04Fev2002
+
+  fNufDedxPos = aV0.fNufDedxPos;
+  fNufDedxNeg = aV0.fNufDedxNeg;
+
+  fHelixPos = aV0.fHelixPos;// Gael 12 Sept
+  fHelixNeg = aV0.fHelixNeg;// Gael 12 Sept
+  if (fHiddenInfo) delete fHiddenInfo;
+  fHiddenInfo = aV0.fHiddenInfo? aV0.fHiddenInfo->Clone() : 0;// GR 11 DEC 02
+  UpdateV0();
+  
+  return *this;
+}
+
+// -----------------------------------------------------------------------
+void AliFemtoV0::UpdateV0(){
+  //Calc. derived memebers of the v0 class
+  float tMomNegAlongV0, tMomPosAlongV0;
+
+   fMomV0  = fMomPos + fMomNeg;
+   fPtV0   = fMomV0.Perp();
+   fPtotV0 = fMomV0.Mag();
+   fPtPos  = fMomPos.Perp();
+   fPtotPos= fMomPos.Mag();
+   fPtNeg  = fMomNeg.Perp();
+   fPtotNeg= fMomNeg.Mag();
+   fELambda= ::sqrt(fPtotV0*fPtotV0+kMLAMBDA*kMLAMBDA);
+   fEK0Short= ::sqrt(fPtotV0*fPtotV0+kMKAON0SHORT*kMKAON0SHORT);
+   fEPosProton = ::sqrt(fPtotPos*fPtotPos+kMPROTON*kMPROTON);
+   fENegProton = ::sqrt(fPtotNeg*fPtotNeg+kMPROTON*kMPROTON);
+   fEPosPion = ::sqrt(fPtotPos*fPtotPos+kMPIONPLUS*kMPIONPLUS);
+   fENegPion = ::sqrt(fPtotNeg*fPtotNeg+kMPIONMINUS*kMPIONMINUS);
+  
+   tMomNegAlongV0 =  fMomNeg*fMomV0 / ::sqrt(::pow(fPtotV0,2));
+   tMomPosAlongV0 =  fMomPos*fMomV0 / ::sqrt(::pow(fPtotV0,2));
+
+   fAlphaV0 = (tMomPosAlongV0-tMomNegAlongV0)/(tMomPosAlongV0+tMomNegAlongV0);
+   fPtArmV0 =  ::sqrt(fPtotPos*fPtotPos - tMomPosAlongV0*tMomPosAlongV0);
+   fMassLambda = ::sqrt(::pow(fEPosProton+fENegPion,2)-::pow(fPtotV0,2));
+   fMassAntiLambda = ::sqrt(::pow(fENegProton+fEPosPion,2)-::pow(fPtotV0,2));
+   fMassK0Short = ::sqrt(::pow(fENegPion+fEPosPion,2)-::pow(fPtotV0,2));
+
+   fRapLambda = 0.5*::log( (fELambda+fMomV0.z()) / (fELambda-fMomV0.z()) );
+   fCTauLambda = kMLAMBDA*(fDecayLengthV0) / ::sqrt( ::pow((double)fMomV0.Mag(),2.) );
+   
+   fRapK0Short = 0.5*::log( (fEK0Short+fMomV0.z()) / (fEK0Short-fMomV0.z()) );
+   fCTauK0Short = kMKAON0SHORT*(fDecayLengthV0) / ::sqrt( ::pow((double)fMomV0.Mag(),2.) );
+
+}
+// -----------------------------------------------------------------------
+#ifndef __NO_STAR_DEPENDENCE_ALLOWED__
+#ifdef __ROOT__
+#include "StStrangeMuDstMaker/StV0MuDst.h"
+AliFemtoV0::AliFemtoV0( StV0MuDst& v){ // from strangess micro dst structure
+  fDecayLengthV0 = v.decayLengthV0();
+  fDecayVertexV0 = AliFemtoThreeVector( v.decayVertexV0X(), v.decayVertexV0Y(), v.decayVertexV0Z() );
+  fDcaV0Daughters = v.dcaV0Daughters();
+  fDcaV0ToPrimVertex = v.dcaV0ToPrimVertex();
+  fDcaPosToPrimVertex = v.dcaPosToPrimVertex();
+  fDcaNegToPrimVertex = v.dcaNegToPrimVertex();
+  fMomPos = AliFemtoThreeVector( v.momPosX(), v.momPosY(), v.momPosZ() );
+  fMomNeg = AliFemtoThreeVector( v.momNegX(), v.momNegY(), v.momNegZ() ); 
+#ifdef STHBTDEBUG
+  cout << " hist pos ";
+  cout << v.topologyMapPos().numberOfHits(kTpcId); 
+  cout << " hist neg ";
+  cout << v.topologyMapNeg().numberOfHits(kTpcId) << endl;
+#endif
+  fTpcHitsPos = ( v.topologyMapPos().numberOfHits(kTpcId) );
+  fTpcHitsNeg = ( v.topologyMapNeg().numberOfHits(kTpcId) );
+  fTrackTopologyMapPos[0] = ( v.topologyMapPos().data(0) );
+  fTrackTopologyMapPos[1] = ( v.topologyMapPos().data(1) );
+  fTrackTopologyMapNeg[0] = ( v.topologyMapNeg().data(0) );
+  fTrackTopologyMapNeg[1] = ( v.topologyMapNeg().data(1) );
+  fKeyPos = v.keyPos();
+  fKeyNeg = v.keyNeg();
+  fChi2V0 = v.chi2V0();
+  fClV0 = v.clV0();
+  fChi2Pos = v.chi2Pos();
+  fClPos = v.clPos();
+  fChi2Neg = v.chi2Neg();
+  fClNeg = v.clNeg();
+  fDedxPos = v.dedxPos();
+  fErrDedxPos = v.errDedxPos();//Gael 04Fev2002
+  fLenDedxPos = v.lenDedxPos();//Gael 04Fev2002
+  fDedxNeg = v.dedxNeg();
+  fErrDedxNeg = v.errDedxNeg();//Gael 04Fev2002
+  fLenDedxNeg = v.lenDedxNeg();//Gael 04Fev2002
+  fNufDedxPos = v.nufDedxPos();
+  fNufDedxNeg = v.nufDedxNeg();
+  fHiddenInfo =  0;//GR 11 DEC 02
+
+#ifdef STHBTDEBUG
+  cout << " keyPos " << v.keyPos() << endl;
+  cout << " keyNeg " << v.keyNeg() << endl;
+#endif
+  fMomV0 = AliFemtoThreeVector( v.momV0X(), v.momV0Y(), v.momV0Z() );
+#ifdef STHBTDEBUG
+  cout << " alpha  ";
+  cout << v.alphaV0();
+  cout << " ptArm  ";
+  cout << v.ptArmV0() << endl;
+#endif
+  fAlphaV0 = v.alphaV0();
+  fPtArmV0 = v.ptArmV0();
+  fELambda = v.eLambda();
+  fEK0Short = v.eK0Short();
+  fEPosProton = v.ePosProton();
+  fEPosPion = v.ePosPion();
+  fENegPion = v.eNegPion();
+  fENegProton = v.eNegProton();
+  fMassLambda = v.massLambda();
+  fMassAntiLambda = v.massAntiLambda();
+  fMassK0Short = v.massK0Short();
+  fRapLambda = v.rapLambda();
+  fRapK0Short = v.rapK0Short();
+  fCTauLambda = v.cTauLambda();
+  fCTauK0Short = v.cTauK0Short();
+  fPtV0 = v.ptV0();
+  fPtotV0 = v.ptotV0();
+  fPtPos = v.ptPos();
+  fPtotPos = v.ptotPos();
+  fDedxPos = v.dedxPos();
+  fPtNeg = v.ptNeg();
+  fPtotNeg = v.ptotNeg();
+  fDedxNeg = v.dedxNeg();
+}
+#endif // __ROOT__
+#endif  //  __NO_STAR_DEPENDENCE_ALLOWED__
+
+
+
+void AliFemtoV0::SetHelixPos(const AliFmPhysicalHelixD& h){fHelixPos = h;}// Gael 12 Sept 02
+const AliFmPhysicalHelixD& AliFemtoV0::HelixPos() const {return fHelixPos;}// Gael 12 Sept 02
+void AliFemtoV0::SetHelixNeg(const AliFmPhysicalHelixD& h){fHelixNeg = h;}// Gael 12 Sept 02
+const AliFmPhysicalHelixD& AliFemtoV0::HelixNeg() const {return fHelixNeg;}// Gael 12 Sept 02
+
+void AliFemtoV0::SetHiddenInfo(AliFemtoHiddenInfo* aHiddenInfo) {fHiddenInfo=aHiddenInfo;}
+bool AliFemtoV0::ValidHiddenInfo() const { if (fHiddenInfo) return true; else return false; }
+AliFemtoHiddenInfo* AliFemtoV0::GetHiddenInfo() const {return fHiddenInfo;}
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoV0.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoV0.h
new file mode 100644 (file)
index 0000000..3323032
--- /dev/null
@@ -0,0 +1,397 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFemtoV0: special type of particle desling with the specifics       //
+// of the V0 type of particle
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+#ifndef ALIFEMTOV0_H
+#define ALIFEMTOV0_H
+
+#include "AliFemtoTypes.h" //same as in AliFemtoTrack.h
+#include "AliFmPhysicalHelixD.h" // Gael 12 Sept 02
+#ifdef __ROOT__
+#ifndef __NO_STAR_DEPENDENCE_ALLOWED__
+#include "StStrangeMuDstMaker/StV0MuDst.h"
+#endif
+#endif
+/* Th stuff */
+#include "AliFemtoHiddenInfo.h"
+/***/
+
+class AliFemtoV0 {
+public:
+  AliFemtoV0();
+  AliFemtoV0(const AliFemtoV0& v); // copy constructor
+#ifdef __ROOT__
+#ifndef __NO_STAR_DEPENDENCE_ALLOWED__
+  AliFemtoV0( StV0MuDst&); // from strangeness V0 micro dst structure
+#endif
+#endif
+  virtual ~AliFemtoV0(){if(fHiddenInfo) delete fHiddenInfo;}
+  AliFemtoV0& operator=(const AliFemtoV0& aV0);
+
+
+  float DecayLengthV0() const;       // 3-d decay distance                                              
+  AliFemtoThreeVector DecayVertexV0() const; // Coordinates of decay vertex                             
+  AliFemtoThreeVector PrimaryVertex() const; // Coordinates of primary vertex                           
+  float DecayVertexV0X() const; // Coordinates of decay vertex                                          
+  float DecayVertexV0Y() const; // Coordinates of decay vertex                                          
+  float DecayVertexV0Z() const; // Coordinates of decay vertex                                          
+  float DcaV0Daughters() const;      // DCA of v0 daughters at Decay vertex                             
+  float DcaV0ToPrimVertex() const;   // DCA of v0 to primary vertex                                     
+  float DcaPosToPrimVertex() const;  // DCA of pos v0 daughter to pri vertex                            
+  float DcaNegToPrimVertex() const;  // DCA of neg v0 daughter to pri vertex                            
+  AliFemtoThreeVector MomPos() const;   // Momentum components of pos. daughter                                 
+  float MomPosX() const;   // Momentum components of pos. daughter                                      
+  float MomPosY() const;   // Momentum components of pos. daughter                                      
+  float MomPosZ() const;   // Momentum components of pos. daughter                                      
+  AliFemtoThreeVector MomNeg() const;   // Momentum components of neg. daughter                                 
+  float MomNegX() const;   // Momentum components of neg. daughter                                      
+  float MomNegY() const;   // Momentum components of neg. daughter                                      
+  float MomNegZ() const;   // Momentum components of neg. daughter                                      
+                                                                                                        
+  int   TpcHitsPos() const;          // Number of TPC hits on pos. daughter                             
+  int   TpcHitsNeg() const;          // Number of TPC hits on neg. daughter                             
+  unsigned long TrackTopologyMapPos(unsigned int word) const;                                           
+  unsigned long TrackTopologyMapNeg(unsigned int word) const;                                           
+                                                                                                        
+  AliFemtoThreeVector MomV0() const ;    // Momentum components of V0                                   
+  float MomV0X() const ;    // Momentum components of V0                                                
+  float MomV0Y() const ;    // Momentum components of V0                                                
+  float MomV0Z() const ;    // Momentum components of V0                                                
+  float AlphaV0() const ;             // Armenteros-Podolanski variable                                         
+  float PtArmV0() const ;            // Armenteros-Podolanski variable                                  
+  float ELambda() const ;             // Energy assuming lambda hypothesis                              
+  float EK0Short() const ;            // Energy assuming k-short hypothesis                             
+  float EPosProton() const ;          // Energy of pos. daughter assuming proton                        
+  float EPosPion() const ;            // Energy of pos. daughter assuming pion                          
+  float ENegProton() const ;          // Energy of neg. daughter assuming antiproton                    
+  float ENegPion() const ;            // Energy of neg. daughter assuming pion                          
+  float MassLambda() const ;          // Mass assuming lambda hypothesis                                
+  float MassAntiLambda() const ;      // Mass assuming antilambda hypothesis                            
+  float MassK0Short() const ;         // Mass assuming k-short hypothesis                               
+  float RapLambda() const ;           // Rapidity assuming (anti) constlambda                           
+  float RapK0Short() const ;          // Rapidity assuming k-short                                      
+  float CTauLambda() const ;          // Lifetime (ctau) const assuming (anti) constlambda              
+  float CTauK0Short() const ;         // Lifetime (ctau) const assuming k-short                                 
+  float PtV0() const ;                // Transverse momentum                                            
+  float PtotV0() const ;              // Total momentum                                                         
+  float PtPos() const ;               // Transverse momentum of pos. daughter                           
+  float PtotPos() const ;             // Total momentum of pos. daughter                                
+  float DedxPos() const;              // dedx of Positive track                                                 
+  float NumdedxPos() const;                                                                             
+// number of hits in dE/dX track of pos. daughter--Gael04Fev 2002                                       
+  float ErrdedxPos() const;                                                                             
+// error on dedx of Positive track--Gael04Fev 2002                                                      
+  float LendedxPos() const;                                                                             
+// Length of dE/dX track of pos. daughter--Gael04Fev 2002                                               
+  float PseudoRapPos() const;                                                                           
+// Length of dE/dX track of neg. daughter--Gael04Fev 2002                                               
+                                                                                                        
+  float PtNeg() const ;               // Transverse momentum of neg. daughter                           
+  float PtotNeg() const ;             // Total momentum of neg. daughter                                
+  float DedxNeg() const;              // dedx of Negative track                                                 
+  float NumdedxNeg() const;                                                                             
+// number of hits in dE/dX track of neg. daughter--Gael04Fev 2002                                       
+  float ErrdedxNeg() const;                                                                             
+// error on dedx of Negative track--Gael04Fev 2002                                                      
+  float LendedxNeg() const;                                                                             
+// Length of dE/dX track of neg. daughter--Gael04Fev 2002                                               
+  float PseudoRapNeg() const;                                                                           
+// Length of dE/dX track of neg. daughter--Gael04Fev 2002                                               
+                                                                                                        
+  unsigned short   IdNeg() const;               // Id of negative track                                         
+  unsigned short   IdPos() const;               // Id of positive track                                         
+  unsigned short   KeyNeg() const;               // Id of negative track                                
+  unsigned short   KeyPos() const;               // Id of positive track                                
+                                                                                                        
+  const AliFmPhysicalHelixD& HelixPos() const; // Gael 12 Sept 02                                       
+  const AliFmPhysicalHelixD& HelixNeg() const; // Gael 12 Sept 02                                        
+
+  void UpdateV0(); // Fills derived info
+  void SetdecayLengthV0(const float x);  
+  void SetdecayVertexV0(const AliFemtoThreeVector v);  
+  void SetdecayVertexV0X(const float x);
+  void SetdecayVertexV0Y(const float x);
+  void SetdecayVertexV0Z(const float x);
+  void SetdcaV0Daughters(const float x); 
+  void SetdcaV0ToPrimVertex(const float x);  
+  void SetdcaPosToPrimVertex(const float x); 
+  void SetdcaNegToPrimVertex(const float x); 
+  void SetmomPos(const AliFemtoThreeVector v);  
+  void SetmomPosX(const float x);  
+  void SetmomPosY(const float x);  
+  void SetmomPosZ(const float x);  
+  void SetmomNeg(const AliFemtoThreeVector v);  
+  void SetmomNegX(const float x);  
+  void SetmomNegY(const float x);  
+  void SetmomNegZ(const float x);  
+
+  void SettpcHitsPos(const int& i);      
+  void SettpcHitsNeg(const int& i);      
+
+  void SetTrackTopologyMapPos(unsigned int word, const unsigned long& m);
+  void SetTrackTopologyMapNeg(unsigned int word, const unsigned long& m);      
+
+  void SetmomV0( AliFemtoThreeVector v);
+  void SetmomV0X( float x);
+  void SetmomV0Y( float x);
+  void SetmomV0Z( float x);
+  void SetalphaV0( float x);       
+  void SetptArmV0( float x);       
+  void SeteLambda( float x);     
+  void SeteK0Short( float x);    
+  void SetePosProton( float x);  
+  void SetePosPion( float x);    
+  void SeteNegProton( float x);  
+  void SeteNegPion( float x);    
+  void SetmassLambda( float x);  
+  void SetmassAntiLambda( float x);
+  void SetmassK0Short( float x);  
+  void SetrapLambda( float x);    
+  void SetrapK0Short( float x);   
+  void SetcTauLambda( float x);   
+  void SetcTauK0Short( float x);  
+  void SetptV0( float x);         
+  void SetptotV0( float x);       
+  void SetptPos( float x);        
+  void SetptotPos( float x);      
+  void SetptNeg( float x);        
+  void SetptotNeg( float x);
+  void SetidNeg(const unsigned short& i);
+  void SetidPos(const unsigned short& i);
+  void SetdedxNeg(float x);
+  void SeterrdedxNeg(float x);//Gael 04Fev2002
+  void SetlendedxNeg(float x);//Gael 04Fev2002
+  void SetpseudoRapNeg(float x);//Gael 04Fev2002
+  void SetdedxPos(float x);
+  void SeterrdedxPos(float x);//Gael 04Fev2002
+  void SetlendedxPos(float x);//Gael 04Fev2002
+  void SetpseudoRapPos(float x);//Gael 04Fev2002
+  void SetkeyNeg(const unsigned short& i);
+  void SetkeyPos(const unsigned short& i);
+     
+  void SetHelixPos(const AliFmPhysicalHelixD& h); // Gael 12 Sept 02
+  void SetHelixNeg(const AliFmPhysicalHelixD& h); // Gael 12 Sept 02
+
+  void SetprimaryVertex(const AliFemtoThreeVector v);//Gael 24 Sept 02
+  /* Th stuff */
+  void SetHiddenInfo(AliFemtoHiddenInfo* aHiddenInfo);
+  bool ValidHiddenInfo() const;
+  // Fab private : (official : const AliFemtoHiddenInfo* HiddenInfo() const;
+  AliFemtoHiddenInfo* GetHiddenInfo() const;
+  /***/
+
+protected:
+  float fDecayLengthV0;                     // 3-d decay distance                                               \\ V0 decay length                                                                  
+  AliFemtoThreeVector fDecayVertexV0;      // Coordinates of decay vertex                               
+  AliFemtoThreeVector fPrimaryVertex;      // Coordinates of primary vertex                             
+  float fDcaV0Daughters;                   // DCA of v0 daughters at Decay vertex                               
+  float fDcaV0ToPrimVertex;                // DCA of v0 to primary vertex                                       
+  float fDcaPosToPrimVertex;               // DCA of pos v0 daughter to pri vertex                              
+  float fDcaNegToPrimVertex;               // DCA of neg v0 daughter to pri vertex                              
+  AliFemtoThreeVector fMomPos;             // Momentum components of pos. daughter                              
+  AliFemtoThreeVector fMomNeg;             // Momentum components of neg. daughter                              
+
+  unsigned long  fTrackTopologyMapPos[2];   // Topology map for positive daughter
+  unsigned long  fTrackTopologyMapNeg[2];   // Topology map for negative daughter
+                                                   
+  int   fTpcHitsPos;                       // Number of TPC hits for positive daughter
+  int   fTpcHitsNeg;                       // Number of TPC hits for negative daughter
+                                           
+  float fChi2V0;                           // Fit quality for V0
+  float fClV0;                             // Confidence level for V0
+  float fChi2Pos;                          // Fit quality for positive daughter
+  float fClPos;                                    // Confidence level for positive daughter
+  float fChi2Neg;                          // Fit quality for negative daughter
+  float fClNeg;                                    // Confidence level for negative daughter
+                                           
+  float fDedxPos;                          // dEdx positive daughter       
+  float fErrDedxPos;                       // dEdx error positive daughter 
+  float fLenDedxPos;                       // dEdx length positive daughter
+                                           
+  float fDedxNeg;                          // dEdx negative daughter       
+  float fErrDedxNeg;                       // dEdx error negative daughter 
+  float fLenDedxNeg;                       // dEdx length negative daughter
+                                           
+  unsigned short fNufDedxPos;              // Number of dEdx points positive
+  unsigned short fNufDedxNeg;              // Number of dEdx points negative
+                                           
+  AliFmPhysicalHelixD fHelixPos;            // Helix for positive
+  AliFmPhysicalHelixD fHelixNeg;            // Helix for negative
+                                           
+  AliFemtoThreeVector fMomV0;              // Momentum of the V0
+  float fAlphaV0;                          // Armenteros-Podolanski variable                                    
+  float fPtArmV0;                          // Armenteros-Podolanski variable                                    
+  float fELambda;                          // Energy assuming lambda hypothesis                                 
+  float fEK0Short;                         // Energy assuming k-short hypothesis                                
+  float fEPosProton;                       // Energy of pos. daughter assuming proton                   
+  float fEPosPion;                         // Energy of pos. daughter assuming pion                             
+  float fENegProton;                       // Energy of neg. daughter assuming antiproton
+  float fENegPion;                         // Energy of neg. daughter assuming pion
+  float fMassLambda;                       // Mass assuming lambda hypothesis                           
+  float fMassAntiLambda;                   // Mass assuming antilambda hypothesis
+  float fMassK0Short;                      // Mass assuming k-short hypothesis                          
+  float fRapLambda;                        // Rapidity assuming (anti) constlambda                              
+  float fRapK0Short;                       // Rapidity assuming k-short                                         
+  float fCTauLambda;                       // Lifetime (ctau) assuming (anti)lambda             
+  float fCTauK0Short;                      // Lifetime (ctau) assuming k-short                          
+  float fPtV0;                             // Total momentum                                                    
+  float fPtotV0;                           // Transverse momentum                                               
+  float fPtPos;                                    // Transverse momentum of pos. daughter                              
+  float fPtotPos;                          // Total momentum of pos. daughter                           
+  float fPtNeg;                                    // Transverse momentum of neg. daughter                              
+  float fPtotNeg;                          // Total momentum of neg. daughter                           
+                                           
+  unsigned short   fKeyNeg;                // Unique key negative
+  unsigned short   fKeyPos;                // Unique key positive
+  /* Th stuff */                           
+  // Fab private : add mutable             
+  mutable AliFemtoHiddenInfo* fHiddenInfo; //! Hidden info
+  /***/                                            
+                                           
+                                                                                                                                
+};                                         
+                                           
+inline float AliFemtoV0::DecayLengthV0() const { return fDecayLengthV0; }
+inline AliFemtoThreeVector AliFemtoV0::DecayVertexV0() const { return fDecayVertexV0; } 
+inline AliFemtoThreeVector AliFemtoV0::PrimaryVertex() const { return fPrimaryVertex; }
+inline float AliFemtoV0::DecayVertexV0X() const { return fDecayVertexV0.x(); } 
+inline float AliFemtoV0::DecayVertexV0Y() const { return fDecayVertexV0.y(); } 
+inline float AliFemtoV0::DecayVertexV0Z() const { return fDecayVertexV0.z(); } 
+inline float AliFemtoV0::DcaV0Daughters() const { return fDcaV0Daughters; }
+inline float AliFemtoV0::DcaV0ToPrimVertex() const { return fDcaV0ToPrimVertex; }
+inline float AliFemtoV0::DcaPosToPrimVertex() const { return fDcaPosToPrimVertex; }
+inline float AliFemtoV0::DcaNegToPrimVertex() const { return fDcaNegToPrimVertex; }
+inline AliFemtoThreeVector AliFemtoV0::MomPos() const { return fMomPos; }
+inline float AliFemtoV0::MomPosX() const { return fMomPos.x(); }
+inline float AliFemtoV0::MomPosY() const { return fMomPos.y(); }
+inline float AliFemtoV0::MomPosZ() const { return fMomPos.z(); }
+inline AliFemtoThreeVector AliFemtoV0::MomNeg() const { return fMomNeg; }
+inline float AliFemtoV0::MomNegX() const { return fMomNeg.x(); }
+inline float AliFemtoV0::MomNegY() const { return fMomNeg.y(); }
+inline float AliFemtoV0::MomNegZ() const { return fMomNeg.z(); }
+inline AliFemtoThreeVector AliFemtoV0::MomV0() const { return fMomV0; }
+inline float AliFemtoV0::MomV0X() const { return fMomV0.x(); }
+inline float AliFemtoV0::MomV0Y() const { return fMomV0.y(); }
+inline float AliFemtoV0::MomV0Z() const { return fMomV0.z(); }
+inline float AliFemtoV0::AlphaV0() const { return fAlphaV0; }
+inline float AliFemtoV0::PtArmV0() const {return fPtArmV0;}
+inline float AliFemtoV0::ELambda() const {return fELambda;}
+inline float AliFemtoV0::EK0Short() const {return fEK0Short;}
+inline float AliFemtoV0::EPosProton() const {return fEPosProton;}
+inline float AliFemtoV0::EPosPion() const {return fEPosPion;}
+inline float AliFemtoV0::ENegProton() const {return fENegProton;}
+inline float AliFemtoV0::ENegPion() const {return fENegPion;}
+inline float AliFemtoV0::MassLambda() const {return fMassLambda;}
+inline float AliFemtoV0::MassAntiLambda() const {return fMassAntiLambda;}
+inline float AliFemtoV0::MassK0Short() const {return fMassK0Short;}
+inline float AliFemtoV0::RapLambda() const {return fRapLambda;}
+inline float AliFemtoV0::RapK0Short() const {return fRapK0Short;}
+inline float AliFemtoV0::CTauLambda() const {return fCTauLambda;}
+inline float AliFemtoV0::CTauK0Short() const {return fCTauK0Short;}
+inline float AliFemtoV0::PtV0() const {return fPtV0;}
+inline float AliFemtoV0::PtotV0() const {return fPtotV0;}
+inline float AliFemtoV0::PtPos() const {return fPtPos;}
+inline float AliFemtoV0::PtotPos() const {return fPtotPos;}
+inline float AliFemtoV0::PtNeg() const {return fPtNeg;}
+inline float AliFemtoV0::PtotNeg() const {return fPtotNeg;}
+inline int   AliFemtoV0::TpcHitsPos() const { return fTpcHitsPos; }
+inline int   AliFemtoV0::TpcHitsNeg() const { return fTpcHitsNeg; }
+inline float AliFemtoV0::DedxNeg() const {return fDedxNeg;}
+inline float AliFemtoV0::NumdedxNeg() const {return fNufDedxNeg;} //Gael 04Fev2002
+inline float AliFemtoV0::ErrdedxNeg() const {return fErrDedxNeg;} //Gael 04Fev2002
+inline float AliFemtoV0::LendedxNeg() const {return fLenDedxNeg;} //Gael 04Fev2002
+inline float AliFemtoV0::PseudoRapNeg() const {return fMomNeg.PseudoRapidity();} //Gael 04Fev2002
+inline float AliFemtoV0::DedxPos() const {return fDedxPos;}
+inline float AliFemtoV0::NumdedxPos() const {return fNufDedxPos;} //Gael 04Fev2002
+inline float AliFemtoV0::ErrdedxPos() const {return fErrDedxPos;} //Gael 04Fev2002
+inline float AliFemtoV0::LendedxPos() const {return fLenDedxPos;} //Gael 04Fev2002
+inline float AliFemtoV0::PseudoRapPos() const {return fMomPos.PseudoRapidity();} //Gael 04Fev2002
+
+
+inline unsigned long   AliFemtoV0::TrackTopologyMapPos(unsigned int word) const { return fTrackTopologyMapPos[word]; }
+inline unsigned long   AliFemtoV0::TrackTopologyMapNeg(unsigned int word) const { return fTrackTopologyMapNeg[word]; }
+inline unsigned short   AliFemtoV0::IdNeg() const { return fKeyNeg; } 
+inline unsigned short   AliFemtoV0::KeyNeg() const { return fKeyNeg; }
+inline unsigned short   AliFemtoV0::IdPos() const { return fKeyPos; } 
+inline unsigned short   AliFemtoV0::KeyPos() const { return fKeyPos; }
+
+inline void AliFemtoV0::SetdecayLengthV0(const float x){ fDecayLengthV0= x;}   
+inline void AliFemtoV0::SetdecayVertexV0X(const float x){ fDecayVertexV0.SetX(x);}
+inline void AliFemtoV0::SetdecayVertexV0Y(const float x){ fDecayVertexV0.SetY(x);}
+inline void AliFemtoV0::SetdecayVertexV0Z(const float x){ fDecayVertexV0.SetZ(x);}
+inline void AliFemtoV0::SetdecayVertexV0(const AliFemtoThreeVector v){ fDecayVertexV0 = v; }
+inline void AliFemtoV0::SetdcaV0Daughters(const float x){fDcaV0Daughters= x;} 
+inline void AliFemtoV0::SetdcaV0ToPrimVertex(const float x){fDcaV0ToPrimVertex= x;}   
+inline void AliFemtoV0::SetdcaPosToPrimVertex(const float x){fDcaPosToPrimVertex = x;} 
+inline void AliFemtoV0::SetdcaNegToPrimVertex(const float x){fDcaNegToPrimVertex = x;} 
+inline void AliFemtoV0::SetmomPos(const AliFemtoThreeVector v){fMomPos = v; }
+inline void AliFemtoV0::SetmomPosX(const float x){fMomPos.SetX(x);}
+inline void AliFemtoV0::SetmomPosY(const float x){fMomPos.SetY(x);}
+inline void AliFemtoV0::SetmomPosZ(const float x){fMomPos.SetZ(x);}
+inline void AliFemtoV0::SetmomNeg(const AliFemtoThreeVector v){fMomNeg = v; }
+inline void AliFemtoV0::SetmomNegX(const float x){fMomNeg.SetX(x);}
+inline void AliFemtoV0::SetmomNegY(const float x){fMomNeg.SetY(x);}
+inline void AliFemtoV0::SetmomNegZ(const float x){fMomNeg.SetZ(x);}
+inline void AliFemtoV0::SetTrackTopologyMapPos(unsigned int word, const unsigned long& m){fTrackTopologyMapPos[word]=m;} 
+inline void AliFemtoV0::SetTrackTopologyMapNeg(unsigned int word, const unsigned long& m){fTrackTopologyMapNeg[word]=m;} 
+inline void AliFemtoV0::SetmomV0(AliFemtoThreeVector v){fMomV0= v; }
+inline void AliFemtoV0::SetmomV0X(const float x){fMomV0.SetX(x);}
+inline void AliFemtoV0::SetmomV0Y(const float x){fMomV0.SetY(x);}
+inline void AliFemtoV0::SetmomV0Z(const float x){fMomV0.SetZ(x);}
+
+inline void AliFemtoV0::SetalphaV0( float x){fAlphaV0= x;}
+inline void AliFemtoV0::SetptArmV0( float x){fPtArmV0 = x;}
+inline void AliFemtoV0::SeteLambda( float x){fELambda= x;}       
+inline void AliFemtoV0::SeteK0Short( float x){fEK0Short= x;}
+inline void AliFemtoV0::SetePosProton( float x){fEPosProton= x;}      
+inline void AliFemtoV0::SetePosPion( float x){fEPosPion= x;}      
+inline void AliFemtoV0::SeteNegProton( float x){fENegProton= x;} 
+inline void AliFemtoV0::SeteNegPion( float x){fENegPion= x;}       
+inline void AliFemtoV0::SetmassLambda( float x){fMassLambda = x;} 
+inline void AliFemtoV0::SetmassAntiLambda( float x){fMassAntiLambda= x;} 
+inline void AliFemtoV0::SetmassK0Short( float x){fMassK0Short= x;}  
+inline void AliFemtoV0::SetrapLambda( float x){fRapLambda= x;}
+inline void AliFemtoV0::SetrapK0Short( float x){fRapK0Short = x;}   
+inline void AliFemtoV0::SetcTauLambda( float x){fCTauLambda = x;}   
+inline void AliFemtoV0::SetcTauK0Short( float x){fCTauK0Short = x;}   
+inline void AliFemtoV0::SetptV0( float x){fPtV0 = x;}          
+inline void AliFemtoV0::SetptotV0( float x){fPtotV0 = x;}
+inline void AliFemtoV0::SetptPos( float x){fPtPos = x;}
+inline void AliFemtoV0::SetptotPos( float x){fPtotPos = x;}    
+inline void AliFemtoV0::SetptNeg( float x){ fPtNeg= x;}    
+inline void AliFemtoV0::SetptotNeg( float x){ fPtotNeg= x;}
+inline void AliFemtoV0::SetidNeg(const unsigned short& s){ fKeyNeg= s;}
+inline void AliFemtoV0::SetidPos(const unsigned short& s){ fKeyPos= s;}
+inline void AliFemtoV0::SetkeyNeg(const unsigned short& s){ fKeyNeg= s;}
+inline void AliFemtoV0::SetkeyPos(const unsigned short& s){ fKeyPos= s;}
+inline void AliFemtoV0::SettpcHitsPos(const int& i){fTpcHitsPos=i;} 
+inline void AliFemtoV0::SettpcHitsNeg(const int& i){fTpcHitsNeg=i;}
+inline void AliFemtoV0::SetdedxNeg(float x){fDedxNeg=x;}
+inline void AliFemtoV0::SeterrdedxNeg(float x){fErrDedxNeg=x;}//Gael 04Fev2002
+inline void AliFemtoV0::SetlendedxNeg(float x){fLenDedxNeg=x;}//Gael 04Fev2002
+inline void AliFemtoV0::SetdedxPos(float x){fDedxPos=x;}
+inline void AliFemtoV0::SeterrdedxPos(float x){fErrDedxPos=x;}//Gael 04Fev2002
+inline void AliFemtoV0::SetlendedxPos(float x){fLenDedxPos=x;}//Gael 04Fev2002
+inline void AliFemtoV0::SetprimaryVertex(const AliFemtoThreeVector v) { fPrimaryVertex = v; }//Gael 24 Sept 02
+#endif
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoV0Collection.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoV0Collection.h
new file mode 100644 (file)
index 0000000..951d33d
--- /dev/null
@@ -0,0 +1,33 @@
+/***************************************************************************
+ *
+ * $Id$
+ *
+ * Author: Tom Humanic, Ohio State, humanic@mps.ohio-state.edu
+ ***************************************************************************
+ *
+ * Description: part of STAR HBT Framework: AliFemtoMaker package
+ *   The Collection of v0s is the main component of the HbtEvent,
+ *   which is essentially the transient microDST
+ *
+ ***************************************************************************/
+
+
+#ifndef AliFemtoV0Collection_hh
+#define AliFemtoV0Collection_hh
+#include "AliFemtoV0.h"
+#include <list>
+
+#if !defined(ST_NO_NAMESPACES)
+using std::list;
+#endif
+
+#ifdef ST_NO_TEMPLATE_DEF_ARGS
+typedef list<AliFemtoV0*, allocator<AliFemtoV0*> >            AliFemtoV0Collection;
+typedef list<AliFemtoV0*, allocator<AliFemtoV0*> >::iterator  AliFemtoV0Iterator;
+#else
+typedef list<AliFemtoV0*>            AliFemtoV0Collection;
+typedef list<AliFemtoV0*>::iterator  AliFemtoV0Iterator;
+#endif
+
+#endif
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoV0Cut.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoV0Cut.h
new file mode 100644 (file)
index 0000000..491fb9e
--- /dev/null
@@ -0,0 +1,35 @@
+////////////////////////////////////////////////////////////////////////////////
+/// AliFemtoV0Cut - the pure virtual base class for the V0 cut           ///
+/// All V0 cuts must inherit from this one                                 ///
+////////////////////////////////////////////////////////////////////////////////
+
+#ifndef AliFemtoV0Cut_hh
+#define AliFemtoV0Cut_hh
+
+#include "AliFemtoTypes.h"
+#include "AliFemtoV0.h"
+#include "AliFemtoParticleCut.h"
+
+class AliFemtoV0Cut : public AliFemtoParticleCut {
+
+public:
+
+  AliFemtoV0Cut(){/* no-op */};                             // default constructor. - Users should write their own
+  AliFemtoV0Cut(const AliFemtoV0Cut& aCut);                 // copy constructor
+  virtual ~AliFemtoV0Cut(){/* no-op */};                    // destructor
+  AliFemtoV0Cut& operator=(const AliFemtoV0Cut& aCut);                 // copy constructor
+
+  virtual bool Pass(const AliFemtoV0* aV0)=0;               // true if passes, false if not
+
+  virtual AliFemtoParticleType Type(){return hbtV0;}
+  virtual AliFemtoV0Cut* Clone() { return 0;}
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoV0Cut, 0)
+#endif
+};
+
+inline AliFemtoV0Cut::AliFemtoV0Cut(const AliFemtoV0Cut& c) : AliFemtoParticleCut(c) { /* no-op */ } 
+inline AliFemtoV0Cut& AliFemtoV0Cut::operator=(const AliFemtoV0Cut& c) { if (this != &c) { AliFemtoParticleCut::operator=(c); } return *this; } 
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoVector.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoVector.h
new file mode 100644 (file)
index 0000000..dccbfdf
--- /dev/null
@@ -0,0 +1,39 @@
+/***************************************************************************
+ *
+ * $Id$
+ *
+ * Author: Frank Laue, BNL, laue@bnl.gov
+ ***************************************************************************
+ *
+ ***************************************************************************
+ *
+ * $Log$
+ * Revision 1.1.1.1  2007/04/25 15:38:41  panos
+ * Importing the HBT code dir
+ *
+ * Revision 1.1.1.1  2007/03/07 10:14:49  mchojnacki
+ * First version on CVS
+ *
+ * Revision 1.1  2001/06/21 19:15:48  laue
+ * Modified fiels:
+ *   CTH.h : new constructor added
+ *   AliFemtoEvent, AliFemtoKink, AliFemtoTrack : constructors from the persistent
+ *                                   (TTree) classes added
+ *   AliFemtoLikeSignAnalysis : minor changes, for debugging
+ *   AliFemtoTypes: split into different files
+ * Added files: for the new TTree muDst's
+ *   StExceptions.cxx StExceptions.h AliFemtoEnumeration.h
+ *   AliFemtoHelix.h AliFemtoHisto.h AliFemtoString.h AliFemtoTFile.h
+ *   AliFemtoTTreeEvent.cxx AliFemtoTTreeEvent.h AliFemtoTTreeKink.cxx
+ *   AliFemtoTTreeKink.h AliFemtoTTreeTrack.cxx AliFemtoTTreeTrack.h
+ *   AliFemtoTTreeV0.cxx AliFemtoTTreeV0.h AliFemtoVector.h
+ *
+ *
+ ***************************************************************************/
+#ifndef AliFemtoVector_hh
+#define AliFemtoVector_hh
+#include "AliFmThreeVectorD.h"
+typedef AliFmThreeVectorD AliFemtoThreeVector;//!
+#include "AliFmLorentzVectorD.h"
+typedef AliFmLorentzVectorD AliFemtoLorentzVector;//!
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoVertexAnalysis.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoVertexAnalysis.cxx
new file mode 100644 (file)
index 0000000..393719b
--- /dev/null
@@ -0,0 +1,264 @@
+////////////////////////////////////////////////////////////////////////////
+//                                                                        //
+// AliFemtoVertexAnalysis - Femtoscopic analysis which mixes events       //
+// with respect to the z position of the primary vertex                   //
+//                                                                        //
+////////////////////////////////////////////////////////////////////////////
+/***************************************************************************
+ *
+ * $Id$
+ *
+ * Author: Frank Laue, Ohio State, laue@mps.ohio-state.edu
+ ***************************************************************************
+ *
+ * Description: part of STAR HBT Framework: AliFemtoMaker package
+ *      This is the Class for Analysis objects.  Each of the simultaneous
+ *      Analyses running should have one of these instantiated.  They link
+ *      into the Manager in an Analysis Collection.
+ *
+ ***************************************************************************
+ *
+ * $Log$
+ * Revision 1.2.2.2  2007/10/12 14:28:37  akisiel
+ * New wave of cleanup and rule conformance
+ *
+ * Revision 1.2.2.1  2007/10/05 09:38:17  akisiel
+ * Fix stray colons
+ *
+ * Revision 1.2  2007/07/09 16:17:11  mlisa
+ * several files changed to change name of AliFemtoAnalysis to AliFemtoSimpleAnalysis and AliFemtoBaseAnalysis to AliFemtoAnalysis.  Also removed some hard-coded cuts of Marek
+ *
+ * Revision 1.1  2007/05/16 10:22:12  akisiel
+ * Making the directory structure of AliFemto flat. All files go into one common directory
+ *
+ * Revision 1.2  2007/05/03 09:39:37  akisiel
+ * Fixing Effective C++ warnings
+ *
+ * Revision 1.1.1.1  2007/04/25 15:38:41  panos
+ * Importing the HBT code dir
+ *
+ * Revision 1.1.1.1  2007/03/07 10:14:49  mchojnacki
+ * First version on CVS
+ *
+ * Revision 1.5  2001/05/25 23:24:00  lisa
+ * Added in AliFemtoKink stuff
+ *
+ * Revision 1.4  2000/08/31 22:31:32  laue
+ * AliFemtoSimpleAnalysis: output changed (a little bit less)
+ * AliFemtoEvent: new version, members for reference mult added
+ * AliFemtoIOBinary: new IO for new AliFemtoEvent version
+ * AliFemtoTypes: TTree typedef to AliFemtoTTree added
+ * AliFemtoVertexAnalysis: overflow and underflow added
+ *
+ * Revision 1.1  2000/07/16 21:44:11  laue
+ * Collection and analysis for vertex dependent event mixing
+ *
+ *
+ **************************************************************************/
+
+#include "AliFemtoVertexAnalysis.h"
+#include "AliFemtoParticleCollection.h"
+#include "AliFemtoTrackCut.h"
+#include "AliFemtoV0Cut.h"
+#include "AliFemtoKinkCut.h"
+#include "AliFemtoPicoEventCollectionVector.h"
+#include "AliFemtoPicoEventCollectionVectorHideAway.h"
+
+
+#ifdef __ROOT__ 
+ClassImp(AliFemtoVertexAnalysis)
+#endif
+
+extern void FillHbtParticleCollection(AliFemtoParticleCut*         partCut,
+                                    AliFemtoEvent*               hbtEvent,
+                                    AliFemtoParticleCollection*  partCollection);
+
+
+//____________________________
+AliFemtoVertexAnalysis::AliFemtoVertexAnalysis(unsigned int bins, double min, double max):
+  fVertexBins(0),
+  fOverFlow(0),  
+  fUnderFlow(0)
+{
+  //  mControlSwitch     = 0;
+  fEventCut          = 0;
+  fFirstParticleCut  = 0;
+  fSecondParticleCut = 0;
+  fPairCut           = 0;
+  fCorrFctnCollection= 0;
+  fCorrFctnCollection = new AliFemtoCorrFctnCollection;
+  fVertexBins = bins;
+  fVertexZ[0] = min;
+  fVertexZ[1] = max;
+  fUnderFlow = 0; 
+  fOverFlow = 0; 
+  if (fMixingBuffer) delete fMixingBuffer;
+  fPicoEventCollectionVectorHideAway = new AliFemtoPicoEventCollectionVectorHideAway(fVertexBins,fVertexZ[0],fVertexZ[1]);
+}
+//____________________________
+
+AliFemtoVertexAnalysis::AliFemtoVertexAnalysis(const AliFemtoVertexAnalysis& a) : 
+  AliFemtoSimpleAnalysis(),
+  fVertexBins(0),
+  fOverFlow(0),  
+  fUnderFlow(0)
+{
+  //AliFemtoVertexAnalysis();
+  fEventCut          = 0;
+  fFirstParticleCut  = 0;
+  fSecondParticleCut = 0;
+  fPairCut           = 0;
+  fCorrFctnCollection= 0;
+  fCorrFctnCollection = new AliFemtoCorrFctnCollection;
+  fVertexBins = a.fVertexBins; 
+  fVertexZ[0] = a.fVertexZ[0]; 
+  fVertexZ[1] = a.fVertexZ[1];
+  fUnderFlow = 0; 
+  fOverFlow = 0; 
+  if (fMixingBuffer) delete fMixingBuffer;
+  fPicoEventCollectionVectorHideAway = new AliFemtoPicoEventCollectionVectorHideAway(fVertexBins,fVertexZ[0],fVertexZ[1]);
+
+  // find the right event cut
+  fEventCut = a.fEventCut->Clone();
+  // find the right first particle cut
+  fFirstParticleCut = a.fFirstParticleCut->Clone();
+  // find the right second particle cut
+  if (a.fFirstParticleCut==a.fSecondParticleCut) 
+    SetSecondParticleCut(fFirstParticleCut); // identical particle hbt
+  else
+  fSecondParticleCut = a.fSecondParticleCut->Clone();
+
+  fPairCut = a.fPairCut->Clone();
+  
+  if ( fEventCut ) {
+      SetEventCut(fEventCut); // this will set the myAnalysis pointer inside the cut
+      cout << " AliFemtoVertexAnalysis::AliFemtoVertexAnalysis(const AliFemtoVertexAnalysis& a) - event cut set " << endl;
+  }
+  if ( fFirstParticleCut ) {
+      SetFirstParticleCut(fFirstParticleCut); // this will set the myAnalysis pointer inside the cut
+      cout << " AliFemtoVertexAnalysis::AliFemtoVertexAnalysis(const AliFemtoVertexAnalysis& a) - first particle cut set " << endl;
+  }
+  if ( fSecondParticleCut ) {
+      SetSecondParticleCut(fSecondParticleCut); // this will set the myAnalysis pointer inside the cut
+      cout << " AliFemtoVertexAnalysis::AliFemtoVertexAnalysis(const AliFemtoVertexAnalysis& a) - second particle cut set " << endl;
+  }  if ( fPairCut ) {
+      SetPairCut(fPairCut); // this will set the myAnalysis pointer inside the cut
+      cout << " AliFemtoVertexAnalysis::AliFemtoVertexAnalysis(const AliFemtoVertexAnalysis& a) - pair cut set " << endl;
+  }
+
+  AliFemtoCorrFctnIterator iter;
+  for (iter=a.fCorrFctnCollection->begin(); iter!=a.fCorrFctnCollection->end();iter++){
+    cout << " AliFemtoVertexAnalysis::AliFemtoVertexAnalysis(const AliFemtoVertexAnalysis& a) - looking for correlation functions " << endl;
+    AliFemtoCorrFctn* fctn = (*iter)->Clone();
+    if (fctn) AddCorrFctn(fctn);
+    else cout << " AliFemtoVertexAnalysis::AliFemtoVertexAnalysis(const AliFemtoVertexAnalysis& a) - correlation function not found " << endl;
+  }
+
+  fNumEventsToMix = a.fNumEventsToMix;
+
+  cout << " AliFemtoVertexAnalysis::AliFemtoVertexAnalysis(const AliFemtoVertexAnalysis& a) - analysis copied " << endl;
+
+}
+
+AliFemtoVertexAnalysis& AliFemtoVertexAnalysis::operator=(const AliFemtoVertexAnalysis& OriginalAnalysis)
+{
+  if (this != &OriginalAnalysis) {
+    //AliFemtoVertexAnalysis();
+    fEventCut          = 0;
+    fFirstParticleCut  = 0;
+    fSecondParticleCut = 0;
+    fPairCut           = 0;
+    fCorrFctnCollection= 0;
+    fCorrFctnCollection = new AliFemtoCorrFctnCollection;
+    fVertexBins = OriginalAnalysis.fVertexBins; 
+    fVertexZ[0] = OriginalAnalysis.fVertexZ[0]; 
+    fVertexZ[1] = OriginalAnalysis.fVertexZ[1];
+    fUnderFlow = 0; 
+    fOverFlow = 0; 
+    if (fMixingBuffer) delete fMixingBuffer;
+    fPicoEventCollectionVectorHideAway = new AliFemtoPicoEventCollectionVectorHideAway(fVertexBins,fVertexZ[0],fVertexZ[1]);
+    
+    // find the right event cut
+    fEventCut = OriginalAnalysis.fEventCut->Clone();
+    // find the right first particle cut
+    fFirstParticleCut = OriginalAnalysis.fFirstParticleCut->Clone();
+    // find the right second particle cut
+    if (OriginalAnalysis.fFirstParticleCut==OriginalAnalysis.fSecondParticleCut) 
+      SetSecondParticleCut(fFirstParticleCut); // identical particle hbt
+    else
+      fSecondParticleCut = OriginalAnalysis.fSecondParticleCut->Clone();
+    
+    fPairCut = OriginalAnalysis.fPairCut->Clone();
+    
+    if ( fEventCut ) {
+      SetEventCut(fEventCut); // this will set the myAnalysis pointer inside the cut
+      cout << " AliFemtoVertexAnalysis::AliFemtoVertexAnalysis(const AliFemtoVertexAnalysis& a) - event cut set " << endl;
+    }
+    if ( fFirstParticleCut ) {
+      SetFirstParticleCut(fFirstParticleCut); // this will set the myAnalysis pointer inside the cut
+      cout << " AliFemtoVertexAnalysis::AliFemtoVertexAnalysis(const AliFemtoVertexAnalysis& a) - first particle cut set " << endl;
+    }
+    if ( fSecondParticleCut ) {
+      SetSecondParticleCut(fSecondParticleCut); // this will set the myAnalysis pointer inside the cut
+      cout << " AliFemtoVertexAnalysis::AliFemtoVertexAnalysis(const AliFemtoVertexAnalysis& a) - second particle cut set " << endl;
+    }  if ( fPairCut ) {
+      SetPairCut(fPairCut); // this will set the myAnalysis pointer inside the cut
+      cout << " AliFemtoVertexAnalysis::AliFemtoVertexAnalysis(const AliFemtoVertexAnalysis& a) - pair cut set " << endl;
+    }
+    
+    AliFemtoCorrFctnIterator iter;
+    for (iter=OriginalAnalysis.fCorrFctnCollection->begin(); iter!=OriginalAnalysis.fCorrFctnCollection->end();iter++){
+      cout << " AliFemtoVertexAnalysis::AliFemtoVertexAnalysis(const AliFemtoVertexAnalysis& a) - looking for correlation functions " << endl;
+      AliFemtoCorrFctn* fctn = (*iter)->Clone();
+      if (fctn) AddCorrFctn(fctn);
+      else cout << " AliFemtoVertexAnalysis::AliFemtoVertexAnalysis(const AliFemtoVertexAnalysis& a) - correlation function not found " << endl;
+    }
+    
+    fNumEventsToMix = OriginalAnalysis.fNumEventsToMix;
+    
+    cout << " AliFemtoVertexAnalysis::AliFemtoVertexAnalysis(const AliFemtoVertexAnalysis& a) - analysis copied " << endl;
+  }
+
+  return *this;
+}
+
+//____________________________
+AliFemtoVertexAnalysis::~AliFemtoVertexAnalysis(){
+  // now delete every PicoEvent in the EventMixingBuffer and then the Buffer itself
+  delete fPicoEventCollectionVectorHideAway;
+}
+
+//____________________________
+AliFemtoString AliFemtoVertexAnalysis::Report()
+{
+  // prepare report fromt the execution
+  cout << "AliFemtoVertexAnalysis - constructing Report..."<<endl;
+  char ctemp[200];
+  AliFemtoString temp = "-----------\nHbt AliFemtoVertexAnalysis Report:\n";
+  snprintf(ctemp , 200, "Events are mixed in %d bins in the range %E cm to %E cm.\n",fVertexBins,fVertexZ[0],fVertexZ[1]);
+  temp += ctemp;
+  snprintf(ctemp , 200, "Events underflowing: %d\n",fUnderFlow);
+  temp += ctemp;
+  snprintf(ctemp , 200, "Events overflowing: %d\n",fOverFlow);
+  temp += ctemp;
+  snprintf(ctemp , 200, "Now adding AliFemtoSimpleAnalysis(base) Report\n");
+  temp += ctemp;
+  temp += AliFemtoSimpleAnalysis::Report();
+  AliFemtoString returnThis=temp;
+  return returnThis;
+}
+//_________________________
+void AliFemtoVertexAnalysis::ProcessEvent(const AliFemtoEvent* hbtEvent) {
+  // Put the event though the analysis
+  cout << " AliFemtoVertexAnalysis::ProcessEvent(const AliFemtoEvent* hbtEvent) " << endl;
+  // get right mixing buffer
+  double vertexZ = hbtEvent->PrimVertPos().z();
+  fMixingBuffer = fPicoEventCollectionVectorHideAway->PicoEventCollection(vertexZ); 
+  if (!fMixingBuffer) {
+    if ( vertexZ < fVertexZ[0] ) fUnderFlow++;
+    if ( vertexZ > fVertexZ[1] ) fOverFlow++;
+    return;
+  }
+  // call ProcessEvent() from AliFemtoSimpleAnalysis-base
+  AliFemtoSimpleAnalysis::ProcessEvent(hbtEvent);
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoVertexAnalysis.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoVertexAnalysis.h
new file mode 100644 (file)
index 0000000..27e1b14
--- /dev/null
@@ -0,0 +1,43 @@
+////////////////////////////////////////////////////////////////////////////
+//                                                                        //
+// AliFemtoVertexAnalysis - Femtoscopic analysis which mixes events       //
+// with respect to the z position of the primary vertex                   //
+//                                                                        //
+////////////////////////////////////////////////////////////////////////////
+
+/***************************************************************************
+ * Collection and analysis for vertex dependent event mixing
+ * Frank Laue, Ohio State, 2000
+ *
+ **************************************************************************/
+
+#ifndef ALIFEMTOVERTEXANALYSIS_H
+#define ALIFEMTOVERTEXANALYSIS_H
+
+#include "AliFemtoSimpleAnalysis.h"        // base analysis class
+
+class AliFemtoVertexAnalysis : public AliFemtoSimpleAnalysis {
+
+public:
+
+  AliFemtoVertexAnalysis(unsigned int bins=10, double min=-100., double max=+100.);
+  AliFemtoVertexAnalysis(const AliFemtoVertexAnalysis& OriginalAnalysis);  // copy constructor
+  AliFemtoVertexAnalysis& operator=(const AliFemtoVertexAnalysis& OriginalAnalysis);  
+  virtual void ProcessEvent(const AliFemtoEvent* ProcessThisEvent);
+  virtual ~AliFemtoVertexAnalysis();
+  virtual AliFemtoString Report();       //! returns reports of all cuts applied and correlation functions being done
+  virtual unsigned int Overflow() { return fOverFlow;}
+  virtual unsigned int Underflow() { return fUnderFlow;}
+protected:
+  double fVertexZ[2];            /* min/max z-vertex position allowed to be processed */
+  unsigned int fVertexBins;      /* number of mixing bins in z-vertex in EventMixing Buffer */
+  unsigned int fOverFlow;        /* number of events encountered which had too large z-vertex */
+  unsigned int fUnderFlow;       /* number of events encountered which had too small z-vertex */
+  
+#ifdef __ROOT__
+  ClassDef(AliFemtoVertexAnalysis, 0)
+#endif
+    
+};
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoVertexMultAnalysis.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoVertexMultAnalysis.cxx
new file mode 100644 (file)
index 0000000..c9d5ce3
--- /dev/null
@@ -0,0 +1,294 @@
+/***************************************************************************
+ *
+ * $Id$
+ *
+ * Author: Frank Laue, Ohio State, laue@mps.ohio-state.edu
+ ***************************************************************************
+ *
+ * Description: part of STAR HBT Framework: AliFemtoMaker package
+ *      This is the Class for Analysis objects.  Each of the simultaneous
+ *      Analyses running should have one of these instantiated.  They link
+ *      into the Manager in an Analysis Collection.
+ *
+ ***************************************************************************
+ *
+ * $Log$
+ * Revision 1.2.2.2  2007/10/12 14:28:37  akisiel
+ * New wave of cleanup and rule conformance
+ *
+ * Revision 1.2.2.1  2007/10/05 09:38:17  akisiel
+ * Fix stray colons
+ *
+ * Revision 1.2  2007/07/09 16:17:11  mlisa
+ * several files changed to change name of AliFemtoAnalysis to AliFemtoSimpleAnalysis and AliFemtoBaseAnalysis to AliFemtoAnalysis.  Also removed some hard-coded cuts of Marek
+ *
+ * Revision 1.1  2007/05/16 10:22:12  akisiel
+ * Making the directory structure of AliFemto flat. All files go into one common directory
+ *
+ * Revision 1.2  2007/05/03 09:39:37  akisiel
+ * Fixing Effective C++ warnings
+ *
+ * Revision 1.1.1.1  2007/04/25 15:38:41  panos
+ * Importing the HBT code dir
+ *
+ * Revision 1.1.1.1  2007/03/07 10:14:49  mchojnacki
+ * First version on CVS
+ *
+ * Revision 1.2  2005/06/28 23:12:24  chajecki
+ * UncorrectedNumberOfNegativePrimaries() -> UncorrectedNumberOfPrimaries()
+ *
+ * For data taken in Y2 and later the centrality definition bases
+ * on UncorrectedNumberOfPrimaries() while for Y1(AuAu@130)
+ * it based on UncorrectedNumberOfNegativePrimaries().
+ * But in many places of HBT code the number of negative primaries
+ * was used as a multiplicity for all productions.
+ * This has been fixed.
+ *
+ * Revision 1.1  2001/11/11 18:34:14  laue
+ * AliFemtoPicoEventCollectionVectorHideAway: updated for 3d grid
+ * AliFemtoVertexMultAnalysis: new
+ *
+ *
+ **************************************************************************/
+////////////////////////////////////////////////////////////////////////////
+//                                                                        //
+// AliFemtoVertexMultAnalysis - Femtoscopic analysis which mixes event    //
+// with respect to the z position of the primary vertex and event total   //
+// multiplicity                                                           //
+// You need to provide the number of z-vertex and multiplicity bins       //
+// as well as ranges for the variables                                    //
+//                                                                        //
+////////////////////////////////////////////////////////////////////////////
+
+#include "AliFemtoVertexMultAnalysis.h"
+#include "AliFemtoParticleCollection.h"
+#include "AliFemtoTrackCut.h"
+#include "AliFemtoV0Cut.h"
+#include "AliFemtoKinkCut.h"
+#include "AliFemtoPicoEventCollectionVector.h"
+#include "AliFemtoPicoEventCollectionVectorHideAway.h"
+
+
+#ifdef __ROOT__ 
+ClassImp(AliFemtoVertexMultAnalysis)
+#endif
+
+extern void FillHbtParticleCollection(AliFemtoParticleCut*         partCut,
+                                     AliFemtoEvent*               hbtEvent,
+                                     AliFemtoParticleCollection*  partCollection);
+
+
+//____________________________
+AliFemtoVertexMultAnalysis::AliFemtoVertexMultAnalysis(unsigned int binsVertex, double minVertex, double maxVertex,
+                                                      unsigned int binsMult, double minMult, double maxMult) 
+  : 
+  fVertexZBins(binsVertex), 
+  fOverFlowVertexZ(0), 
+  fUnderFlowVertexZ(0),
+  fMultBins(binsMult) ,
+  fOverFlowMult(0),    
+  fUnderFlowMult(0)    
+{
+  //  mControlSwitch     = 0;
+  fEventCut          = 0;
+  fFirstParticleCut  = 0;
+  fSecondParticleCut = 0;
+  fPairCut           = 0;
+  fCorrFctnCollection= 0;
+  fCorrFctnCollection = new AliFemtoCorrFctnCollection;
+  fVertexZ[0] = minVertex;
+  fVertexZ[1] = maxVertex;
+  fUnderFlowVertexZ = 0; 
+  fOverFlowVertexZ = 0; 
+  fMult[0] = minMult;
+  fMult[1] = maxMult;
+  fUnderFlowMult = 0; 
+  fOverFlowMult = 0; 
+  if (fMixingBuffer) delete fMixingBuffer;
+  fPicoEventCollectionVectorHideAway = new AliFemtoPicoEventCollectionVectorHideAway(fVertexZBins,fVertexZ[0],fVertexZ[1],
+                                                                                 fMultBins,fMult[0],fMult[1]);
+}
+//____________________________
+
+AliFemtoVertexMultAnalysis::AliFemtoVertexMultAnalysis(const AliFemtoVertexMultAnalysis& a) : 
+  AliFemtoSimpleAnalysis(),
+  fVertexZBins(a.fVertexZBins), 
+  fOverFlowVertexZ(0), 
+  fUnderFlowVertexZ(0),
+  fMultBins(a.fMultBins) ,
+  fOverFlowMult(0),    
+  fUnderFlowMult(0)    
+{
+  //AliFemtoVertexMultAnalysis();
+  fEventCut          = 0;
+  fFirstParticleCut  = 0;
+  fSecondParticleCut = 0;
+  fPairCut           = 0;
+  fCorrFctnCollection= 0;
+  fCorrFctnCollection = new AliFemtoCorrFctnCollection;
+  fVertexZ[0] = a.fVertexZ[0]; 
+  fVertexZ[1] = a.fVertexZ[1];
+  fUnderFlowVertexZ = 0; 
+  fOverFlowVertexZ = 0; 
+  fMult[0] = a.fMult[0]; 
+  fMult[1] = a.fMult[1];
+  fUnderFlowMult = 0; 
+  fOverFlowMult = 0; 
+  if (fMixingBuffer) delete fMixingBuffer;
+  fPicoEventCollectionVectorHideAway = new AliFemtoPicoEventCollectionVectorHideAway(fVertexZBins,fVertexZ[0],fVertexZ[1],
+                                                                                 fMultBins,fMult[0],fMult[1]);
+
+  // find the right event cut
+  fEventCut = a.fEventCut->Clone();
+  // find the right first particle cut
+  fFirstParticleCut = a.fFirstParticleCut->Clone();
+  // find the right second particle cut
+  if (a.fFirstParticleCut==a.fSecondParticleCut) 
+    SetSecondParticleCut(fFirstParticleCut); // identical particle hbt
+  else
+  fSecondParticleCut = a.fSecondParticleCut->Clone();
+
+  fPairCut = a.fPairCut->Clone();
+  
+  if ( fEventCut ) {
+      SetEventCut(fEventCut); // this will set the myAnalysis pointer inside the cut
+      cout << " AliFemtoVertexMultAnalysis::AliFemtoVertexMultAnalysis(const AliFemtoVertexMultAnalysis& a) - event cut set " << endl;
+  }
+  if ( fFirstParticleCut ) {
+      SetFirstParticleCut(fFirstParticleCut); // this will set the myAnalysis pointer inside the cut
+      cout << " AliFemtoVertexMultAnalysis::AliFemtoVertexMultAnalysis(const AliFemtoVertexMultAnalysis& a) - first particle cut set " << endl;
+  }
+  if ( fSecondParticleCut ) {
+      SetSecondParticleCut(fSecondParticleCut); // this will set the myAnalysis pointer inside the cut
+      cout << " AliFemtoVertexMultAnalysis::AliFemtoVertexMultAnalysis(const AliFemtoVertexMultAnalysis& a) - second particle cut set " << endl;
+  }  if ( fPairCut ) {
+      SetPairCut(fPairCut); // this will set the myAnalysis pointer inside the cut
+      cout << " AliFemtoVertexMultAnalysis::AliFemtoVertexMultAnalysis(const AliFemtoVertexMultAnalysis& a) - pair cut set " << endl;
+  }
+
+  AliFemtoCorrFctnIterator iter;
+  for (iter=a.fCorrFctnCollection->begin(); iter!=a.fCorrFctnCollection->end();iter++){
+    cout << " AliFemtoVertexMultAnalysis::AliFemtoVertexMultAnalysis(const AliFemtoVertexMultAnalysis& a) - looking for correlation functions " << endl;
+    AliFemtoCorrFctn* fctn = (*iter)->Clone();
+    if (fctn) AddCorrFctn(fctn);
+    else cout << " AliFemtoVertexMultAnalysis::AliFemtoVertexMultAnalysis(const AliFemtoVertexMultAnalysis& a) - correlation function not found " << endl;
+  }
+
+  fNumEventsToMix = a.fNumEventsToMix;
+
+  cout << " AliFemtoVertexMultAnalysis::AliFemtoVertexMultAnalysis(const AliFemtoVertexMultAnalysis& a) - analysis copied " << endl;
+
+}
+AliFemtoVertexMultAnalysis& AliFemtoVertexMultAnalysis::operator=(const AliFemtoVertexMultAnalysis& TheOriginalAnalysis)
+{
+  if (this != &TheOriginalAnalysis) {
+    AliFemtoVertexMultAnalysis::operator=(TheOriginalAnalysis);
+    fVertexZBins = TheOriginalAnalysis.fVertexZBins; 
+    fMultBins = TheOriginalAnalysis.fMultBins;
+
+    fEventCut          = 0;
+    fFirstParticleCut  = 0;
+    fSecondParticleCut = 0;
+    fPairCut           = 0;
+    if (fCorrFctnCollection) delete fCorrFctnCollection;
+    fCorrFctnCollection = new AliFemtoCorrFctnCollection;
+    fVertexZ[0] = TheOriginalAnalysis.fVertexZ[0]; 
+    fVertexZ[1] = TheOriginalAnalysis.fVertexZ[1];
+    fUnderFlowVertexZ = 0; 
+    fOverFlowVertexZ = 0; 
+    fMult[0] = TheOriginalAnalysis.fMult[0]; 
+    fMult[1] = TheOriginalAnalysis.fMult[1];
+    fUnderFlowMult = 0; 
+    fOverFlowMult = 0; 
+    if (fMixingBuffer) delete fMixingBuffer;
+    if (fPicoEventCollectionVectorHideAway) delete fPicoEventCollectionVectorHideAway;
+    fPicoEventCollectionVectorHideAway = new AliFemtoPicoEventCollectionVectorHideAway(fVertexZBins,fVertexZ[0],fVertexZ[1],
+                                                                                      fMultBins,fMult[0],fMult[1]);
+
+    // find the right event cut
+    fEventCut = TheOriginalAnalysis.fEventCut->Clone();
+    // find the right first particle cut
+    fFirstParticleCut = TheOriginalAnalysis.fFirstParticleCut->Clone();
+    // find the right second particle cut
+    if (TheOriginalAnalysis.fFirstParticleCut==TheOriginalAnalysis.fSecondParticleCut) 
+      SetSecondParticleCut(fFirstParticleCut); // identical particle hbt
+    else
+      fSecondParticleCut = TheOriginalAnalysis.fSecondParticleCut->Clone();
+
+    fPairCut = TheOriginalAnalysis.fPairCut->Clone();
+  
+    if ( fEventCut ) {
+      SetEventCut(fEventCut); // this will set the myAnalysis pointer inside the cut
+    }
+    if ( fFirstParticleCut ) {
+      SetFirstParticleCut(fFirstParticleCut); // this will set the myAnalysis pointer inside the cut
+    }
+    if ( fSecondParticleCut ) {
+      SetSecondParticleCut(fSecondParticleCut); // this will set the myAnalysis pointer inside the cut
+    }  if ( fPairCut ) {
+      SetPairCut(fPairCut); // this will set the myAnalysis pointer inside the cut
+      
+    }
+
+    AliFemtoCorrFctnIterator iter;
+    for (iter=TheOriginalAnalysis.fCorrFctnCollection->begin(); iter!=TheOriginalAnalysis.fCorrFctnCollection->end();iter++){
+      AliFemtoCorrFctn* fctn = (*iter)->Clone();
+      if (fctn) AddCorrFctn(fctn);
+    }
+    
+    fNumEventsToMix = TheOriginalAnalysis.fNumEventsToMix;
+  }
+
+  return *this;
+}
+//____________________________
+AliFemtoVertexMultAnalysis::~AliFemtoVertexMultAnalysis(){
+  // now delete every PicoEvent in the EventMixingBuffer and then the Buffer itself
+  delete fPicoEventCollectionVectorHideAway;
+}
+
+//____________________________
+AliFemtoString AliFemtoVertexMultAnalysis::Report()
+{
+  // Prepare a report of the execution
+  cout << "AliFemtoVertexMultAnalysis - constructing Report..."<<endl;
+  char ctemp[200];
+  AliFemtoString temp = "-----------\nHbt AliFemtoVertexMultAnalysis Report:\n";
+  snprintf(ctemp , 200, "Events are mixed in %d VertexZ bins in the range %E cm to %E cm.\n",fVertexZBins,fVertexZ[0],fVertexZ[1]);
+  temp += ctemp;
+  snprintf(ctemp , 200, "Events underflowing: %d\n",fUnderFlowVertexZ);
+  temp += ctemp;
+  snprintf(ctemp , 200, "Events overflowing: %d\n",fOverFlowVertexZ);
+  temp += ctemp;
+  snprintf(ctemp , 200, "Events are mixed in %d Mult bins in the range %E cm to %E cm.\n",fMultBins,fMult[0],fMult[1]);
+  temp += ctemp;
+  snprintf(ctemp , 200, "Events underflowing: %d\n",fUnderFlowMult);
+  temp += ctemp;
+  snprintf(ctemp , 200, "Events overflowing: %d\n",fOverFlowMult);
+  temp += ctemp;
+  snprintf(ctemp , 200, "Now adding AliFemtoSimpleAnalysis(base) Report\n");
+  temp += ctemp;
+  temp += AliFemtoSimpleAnalysis::Report();
+  AliFemtoString returnThis=temp;
+  return returnThis;
+}
+//_________________________
+void AliFemtoVertexMultAnalysis::ProcessEvent(const AliFemtoEvent* hbtEvent) {
+  // Perform event processing
+  // in bins of z vertex and multiplicity
+
+  // cout << " AliFemtoVertexMultAnalysis::ProcessEvent(const AliFemtoEvent* hbtEvent) " << endl;
+  // get right mixing buffer
+  double vertexZ = hbtEvent->PrimVertPos().z();
+  double mult = hbtEvent->UncorrectedNumberOfPrimaries();
+  fMixingBuffer = fPicoEventCollectionVectorHideAway->PicoEventCollection(vertexZ,mult); 
+  if (!fMixingBuffer) {
+    if ( vertexZ < fVertexZ[0] ) fUnderFlowVertexZ++;
+    if ( vertexZ > fVertexZ[1] ) fOverFlowVertexZ++;
+    if ( mult < fMult[0] ) fUnderFlowMult++;
+    if ( mult > fMult[1] ) fOverFlowMult++;
+    return;
+  }
+  // call ProcessEvent() from AliFemtoSimpleAnalysis-base
+  AliFemtoSimpleAnalysis::ProcessEvent(hbtEvent);
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoVertexMultAnalysis.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoVertexMultAnalysis.h
new file mode 100644 (file)
index 0000000..342bc52
--- /dev/null
@@ -0,0 +1,44 @@
+////////////////////////////////////////////////////////////////////////////
+//                                                                        //
+// AliFemtoVertexMultAnalysis - Femtoscopic analysis which mixes event    //
+// with respect to the z position of the primary vertex and event total   //
+// multiplicity                                                           //
+//                                                                        //
+////////////////////////////////////////////////////////////////////////////
+
+#ifndef ALIFEMTOVERTEXMULTANALYSIS_H
+#define ALIFEMTOVERTEXMULTANALYSIS_H
+
+#include "AliFemtoSimpleAnalysis.h"        // base analysis class
+
+class AliFemtoVertexMultAnalysis : public AliFemtoSimpleAnalysis {
+
+public:
+
+  AliFemtoVertexMultAnalysis(unsigned int binsVertex=10, double minVertex=-100., double maxVertex=+100., unsigned int binsMult=10, double minMult=-1.e9, double maxMult=+1.e9);
+  AliFemtoVertexMultAnalysis(const AliFemtoVertexMultAnalysis& TheOriginalAnalysis);  // copy constructor
+  AliFemtoVertexMultAnalysis& operator=(const AliFemtoVertexMultAnalysis& TheOriginalAnalysis);    
+  virtual void ProcessEvent(const AliFemtoEvent* ProcessThisEvent);
+  virtual ~AliFemtoVertexMultAnalysis();
+  virtual AliFemtoString Report();       //! returns reports of all cuts applied and correlation functions being done
+  virtual unsigned int OverflowVertexZ() const { return fOverFlowVertexZ;}
+  virtual unsigned int UnderflowVertexZ() const { return fUnderFlowVertexZ;}
+  virtual unsigned int OverflowMult() const { return fOverFlowMult;}
+  virtual unsigned int UnderflowMult() const { return fUnderFlowMult;}
+protected:
+  double fVertexZ[2];                 /* min/max z-vertex position allowed to be processed */
+  unsigned int fVertexZBins;          /* number of VERTEX mixing bins in z-vertex in EventMixing Buffer */
+  unsigned int fOverFlowVertexZ;      /* number of events encountered which had too large z-vertex */
+  unsigned int fUnderFlowVertexZ;     /* number of events encountered which had too small z-vertex */
+  double fMult[2];                    /* min/max multiplicity allowed for event to be processed */
+  unsigned int fMultBins;             /* number of MULTIPLICITY mixing bins in z-vertex in EventMixing Buffer */
+  unsigned int fOverFlowMult;         /* number of events encountered which had too large multiplicity */
+  unsigned int fUnderFlowMult;        /* number of events encountered which had too small multiplicity */
+  
+#ifdef __ROOT__
+  ClassDef(AliFemtoVertexMultAnalysis, 0)
+#endif
+    
+};
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoXi.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoXi.cxx
new file mode 100644 (file)
index 0000000..f8cdc6f
--- /dev/null
@@ -0,0 +1,100 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFemtoXi: special type of particle desling with the specifics       //
+// of the Xi type of particle                                            //
+// It stores the information both about the Xi itself and about it's     //
+// daughters, as well as the bachelor particle from first decay vertex   //
+// so that the caut betwen the daughter characteristics and the bachelor //
+// is possible.                                                          //
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+#include "AliFemtoXi.h"
+#include "phys_constants.h"
+
+// -----------------------------------------------------------------------
+AliFemtoXi::AliFemtoXi():
+  fCharge(0), fDecayLengthXi(0),
+  fDecayVertexXi(0),
+  fDcaXiDaughters(0), fDcaXiToPrimVertex(0), fDcaBachelorToPrimVertex(0),
+  fMomBachelor(0), fKeyBachelor(0),
+  fTpcHitsBac(0), fChi2Xi(0), fClXi(0), fChi2Bachelor(0), fClBachelor(0),
+  fDedxBachelor(0), fNufDedxBachelor(0), fMomXi(0),
+  fAlphaXi(0), fPtArmXi(0),
+  fEXi(0), fEOmega(0), fEBacPion(0), fEBacKaon(0),
+  fMassXi(0), fMassOmega(0), fRapXi(0), fRapOmega(0),
+  fCTauXi(0), fCTauOmega(0),
+  fPtXi(0), fPtotXi(0), fPtBac(0), fPtotBac(0),
+  fKeyBac(0)
+{
+  fTopologyMapBachelor[0] = 0;
+  fTopologyMapBachelor[1] = 0;
+}
+// -----------------------------------------------------------------------
+void AliFemtoXi::UpdateXi(){
+  //Calc. derived members of the xi class
+  float tMomV0AlongXi, tMomBacAlongXi;
+
+   fMomXi  = MomV0() + MomBac(); 
+   fPtXi   = fMomXi.Perp();
+   fPtotXi = fMomXi.Mag();
+   fPtBac  = MomBac().Perp();
+   fPtotBac= MomBac().Mag();
+   fEXi= ::sqrt(fPtotXi*fPtotXi+kMXIMINUS*kMXIMINUS);
+   fEOmega= ::sqrt(fPtotXi*fPtotXi+kMOMEGAMINUS*kMOMEGAMINUS);
+   fEBacPion = ::sqrt(PtotBac()*PtotBac()+kMPIONMINUS*kMPIONMINUS);
+   fEBacKaon = ::sqrt(PtotBac()*PtotBac()+kMKAONMINUS*kMKAONMINUS);
+
+   tMomV0AlongXi  =  MomV0()*fMomXi / ::sqrt(::pow(fPtotXi,2));
+   tMomBacAlongXi =  MomBac()*fMomXi / ::sqrt(::pow(fPtotXi,2));
+
+   fAlphaXi = (tMomBacAlongXi-tMomV0AlongXi)/(tMomBacAlongXi+tMomV0AlongXi);
+   fPtArmXi =  ::sqrt(PtotBac()*PtotBac() - tMomBacAlongXi*tMomBacAlongXi);
+   fMassXi = ::sqrt(::pow(EBacPion()+ELambda(),2)-::pow(fPtotXi,2));
+   fMassOmega = ::sqrt(::pow(EBacKaon()+ELambda(),2)-::pow(fPtotXi,2));
+
+   fRapXi = 0.5*::log( (EXi()+fMomXi.z()) / (EXi()-fMomXi.z()) );
+   fCTauXi = kMXIMINUS*(fDecayLengthXi) / ::sqrt( ::pow((double)fMomXi.Mag(),2.) );
+   
+   fRapOmega = 0.5*::log( (EOmega()+fMomXi.z()) / (EOmega()-fMomXi.z()) );// eO,
+   fCTauOmega = kMOMEGAMINUS*(fDecayLengthXi) / ::sqrt( ::pow((double)fMomXi.Mag(),2.) );
+}
+// -----------------------------------------------------------------------
+#ifdef __ROOT__
+#ifndef __NO_STAR_DEPENDENCE_ALLOWED__
+#include "StStrangeMuDstMaker/StXiMuDst.h"
+AliFemtoXi::AliFemtoXi( StXiMuDst& xiFromMuDst)  : AliFemtoV0(xiFromMuDst) { // from strangess micro dst structure
+  UpdateV0(); // the v0 stuff
+
+
+  fCharge = xiFromMuDst.charge();
+  fDecayLengthXi = xiFromMuDst.decayLengthXi(); // 12/07/2001 Gael
+  fDecayVertexXi.setX(xiFromMuDst.decayVertexXiX());
+  fDecayVertexXi.setY(xiFromMuDst.decayVertexXiY());
+  fDecayVertexXi.setZ(xiFromMuDst.decayVertexXiZ());
+  fDcaXiDaughters = xiFromMuDst.dcaXiDaughters();
+  fDcaBachelorToPrimVertex = xiFromMuDst.dcaBachelorToPrimVertex();
+  fDcaXiToPrimVertex = xiFromMuDst.dcaXiToPrimVertex();
+  fMomBachelor.setX(xiFromMuDst.momBachelorX());
+  fMomBachelor.setY(xiFromMuDst.momBachelorY());
+  fMomBachelor.setZ(xiFromMuDst.momBachelorZ());
+  
+  fKeyBachelor = xiFromMuDst.keyBachelor();
+  fTopologyMapBachelor[0] = xiFromMuDst.topologyMapBachelor().data(1);
+  fTopologyMapBachelor[1] = xiFromMuDst.topologyMapBachelor().data(2);
+  fTpcHitsBac = xiFromMuDst.topologyMapBachelor().numberOfHits(kTpcId); // 12/07/2001 Gael
+
+  fChi2Xi = xiFromMuDst.chi2Xi();//nulle
+  fClXi = xiFromMuDst.clXi();//nulle
+  fChi2Bachelor = xiFromMuDst.chi2Bachelor();
+  fClBachelor = xiFromMuDst.clBachelor();
+  
+  fDedxBachelor = xiFromMuDst.dedxBachelor();
+  fNufDedxBachelor = xiFromMuDst.nufDedxBachelor();
+
+  UpdateXi(); // the xi stuff
+  
+}
+
+#endif // __NO_STAR_DEPENDENCE_ALLOWED__
+#endif // __ROOT__
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoXi.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoXi.h
new file mode 100644 (file)
index 0000000..ac00616
--- /dev/null
@@ -0,0 +1,280 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFemtoXi: special type of particle desling with the specifics       //
+// of the Xi type of particle                                            //
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+#ifndef ALIFEMTOXI_H
+#define ALIFEMTOXI_H
+
+#include "AliFemtoVector.h" //same as in AliFemtoTrack.h
+#include "AliFemtoV0.h"
+
+#ifdef __ROOT__
+#ifndef __NO_STAR_DEPENDENCE_ALLOWED__
+#include "StStrangeMuDstMaker/StXiMuDst.h"
+#endif
+#endif
+
+class AliFemtoXi : public AliFemtoV0 {
+public:
+  AliFemtoXi();
+#ifdef __ROOT__
+#ifndef __NO_STAR_DEPENDENCE_ALLOWED__
+  AliFemtoXi(StXiMuDst&); // from strangeness Xi micro dst structure
+#endif
+#endif
+  virtual ~AliFemtoXi(){/* no-op */}
+
+  void UpdateXi();
+  float DecayLengthXi() const;            // 3-d decay distance
+  AliFemtoThreeVector DecayVertexXi() const; // Coordinates of decay vertex
+  float DecayVertexXiX() const;           // Coordinates of decay vertex
+  float DecayVertexXiY() const;           // Coordinates of decay vertex
+  float DecayVertexXiZ() const;           // Coordinates of decay vertex
+  float DcaXiDaughters() const;           // DCA of xi daughters at decay vertex
+  float DcaXiToPrimVertex() const;        // DCA of xi to primary vertex
+  float DcaBacToPrimVertex() const;       // DCA of bachelor  xi daughter to pri vertex
+  AliFemtoThreeVector MomBac() const;        // Momentum components of bac. daughter
+  float MomBacX() const;                  // Momentum components of bac. daughter
+  float MomBacY() const;                  // Momentum components of bac. daughter
+  float MomBacZ() const;                  // Momentum components of bac. daughter
+
+  int   TpcHitsBac() const;               // Number of TPC hits on bac. daughter
+  unsigned long TrackTopologyMapBac(unsigned int i) const;
+
+  AliFemtoThreeVector MomXi() const ;        // Momentum components of Xi
+  float MomXiX() const ;                  // Momentum components of Xi
+  float MomXiY() const ;                  // Momentum components of Xi
+  float MomXiZ() const ;                  // Momentum components of Xi
+  float AlphaXi() const ;                 // Armenteros-Podolanski variable
+  float PtArmXi() const ;                 // Armenteros-Podolanski variable
+  float EXi() const ;                     // Energy assuming xi hypothesis                  
+  float EOmega() const ;                  // Energy assuming omega hypothesis               
+  float EBacKaon() const ;                // Energy of bac. daughter assuming kaon          
+  float EBacPion() const ;                // Energy of bac. daughter assuming pion          
+  float MassXi() const ;                  // Mass assuming Xi hypothesis                    
+  float MassOmega() const ;               // Mass assuming Omega hypothesis                 
+  float RapXi() const ;                   // Rapidity assuming (anti) xi                    
+  float RapOmega() const ;                // Rapidity assuming (anti) omega                 
+  float CTauXi() const ;                  // Lifetime (ctau) const assuming (anti) xi       
+  float CTauOmega() const ;               // Lifetime (ctau) const assuming (anti) omega     
+  float PtXi() const ;                    // Transverse momentum                            
+  float PtotXi() const ;                  // Total momentum                                 
+  float PtBac() const ;                   // Transverse momentum of bac. daughter           
+  float PtotBac() const ;                 // Total momentum of bac. daughter                
+  float DedxBac() const;                  // dedx of Bac track                              
+  unsigned short   IdBac() const;         // Id of bac. track                               
+  unsigned short   KeyBac() const;        // Id of bac. track                                
+
+  void SetdecayLengthXi(const float x);  
+  void SetdecayVertexXi(const AliFemtoThreeVector v);  
+  void SetdecayVertexXiX(const float x);
+  void SetdecayVertexXiY(const float x);
+  void SetdecayVertexXiZ(const float x);
+  void SetdcaXiDaughters(const float x); 
+  void SetdcaXiToPrimVertex(const float x);  
+  void SetdcaBacToPrimVertex(const float x); 
+  void SetmomBac(const AliFemtoThreeVector v);  
+  void SetmomBacX(const float x);  
+  void SetmomBacY(const float x);  
+  void SetmomBacZ(const float x);  
+
+  void SettpcHitsBac(const int& word);      
+
+  void SetTrackTopologyMapBac(unsigned int word, const unsigned long& m);
+
+  void SetmomXi( AliFemtoThreeVector v);
+  void SetmomXiX( float x);
+  void SetmomXiY( float x);
+  void SetmomXiZ( float x);
+  void SetalphaXi( float x);       
+  void SetptArmXi( float x);       
+  void SeteXi( float x);     
+  void SeteOmega( float x);    
+  void SeteBacPion( float x);  
+  void SeteBacKaon( float x);    
+  void SetmassXi( float x);  
+  void SetmassOmega( float x);
+  void SetrapXi( float x);    
+  void SetrapOmega( float x);   
+  void SetcTauXi( float x);   
+  void SetcTauOmega( float x);  
+  void SetptXi( float x);         
+  void SetptotXi( float x);       
+  void SetptBac( float x);        
+  void SetptotBac( float x);      
+  void SetidBac(const unsigned short& s);
+  void SetdedxBac(float x);
+  void SetkeyBac(const unsigned short& s);
+
+
+protected: 
+  int   fCharge;                           // Charge                
+  float fDecayLengthXi;                    // Decay Length of th Xi
+  AliFemtoThreeVector fDecayVertexXi;      // Xi decay vertex location
+  float fDcaXiDaughters;                   // Dca of Xi daughters
+  float fDcaXiToPrimVertex;                // Dca of Xi to primary vertex
+  float fDcaBachelorToPrimVertex;          // Dca of bachelor to primary vertex
+  AliFemtoThreeVector fMomBachelor;        // Momentum of the bachelor
+
+  unsigned int   fTopologyMapBachelor[2];  // TPC topology map for the bachelor
+  unsigned short fKeyBachelor;             // Unique key for the bachelor
+
+  int   fTpcHitsBac;                       // Number of TPC hits for bachelor
+
+  float fChi2Xi;                           // Fit quality for Xi
+  float fClXi;                            // Confidence level for Xi
+  float fChi2Bachelor;                    // Fit quality for bachelor
+  float fClBachelor;                      // Confidence level for bachelor
+
+  float fDedxBachelor;                     // dEdx for bachelor
+  unsigned short fNufDedxBachelor;         // dEdx for bachelor
+
+  // the following variables are not in the persistent version and can be calculated via UpdateXi();
+  AliFemtoThreeVector fMomXi; // Momentum of the Xi
+  float fAlphaXi;             // Armenteros-Podolanski variable
+  float fPtArmXi;            // Armenteros-Podolanski variable
+
+  float fEXi;                 // Energy assuming xi hypothesis              
+  float fEOmega;             // Energy assuming omega hypothesis                    
+  float fEBacPion;           // Energy of bac. daughter assuming kaon       
+  float fEBacKaon;           // Energy of bac. daughter assuming pion       
+  float fMassXi;             // Mass assuming Xi hypothesis                 
+  float fMassOmega;          // Mass assuming Omega hypothesis              
+  float fRapXi;                      // Rapidity assuming (anti) xi                 
+  float fRapOmega;           // Rapidity assuming (anti) omega              
+  float fCTauXi;             // Lifetime (ctau) const assuming (anti) xi            
+  float fCTauOmega;          // Lifetime (ctau) const assuming (anti) omega     
+  float fPtXi;               // Transverse momentum                         
+  float fPtotXi;             // Total momentum                              
+  float fPtBac;                      // Transverse momentum of bac. daughter        
+  float fPtotBac;            // Total momentum of bac. daughter                     
+
+  unsigned short   fKeyBac;   // Key of bac. track                                  
+};
+
+inline float AliFemtoXi::DecayLengthXi() const { return fDecayLengthXi; }
+inline AliFemtoThreeVector AliFemtoXi::DecayVertexXi() const { return fDecayVertexXi; } 
+inline float AliFemtoXi::DecayVertexXiX() const { return fDecayVertexXi.x(); } 
+inline float AliFemtoXi::DecayVertexXiY() const { return fDecayVertexXi.y(); } 
+inline float AliFemtoXi::DecayVertexXiZ() const { return fDecayVertexXi.z(); } 
+inline float AliFemtoXi::DcaXiDaughters() const { return fDcaXiDaughters; }
+inline float AliFemtoXi::DcaXiToPrimVertex() const { return fDcaXiToPrimVertex; }
+inline float AliFemtoXi::DcaBacToPrimVertex() const { return fDcaBachelorToPrimVertex; }
+inline AliFemtoThreeVector AliFemtoXi::MomBac() const { return fMomBachelor; }
+inline float AliFemtoXi::MomBacX() const { return fMomBachelor.x(); }
+inline float AliFemtoXi::MomBacY() const { return fMomBachelor.y(); }
+inline float AliFemtoXi::MomBacZ() const { return fMomBachelor.z(); }
+inline AliFemtoThreeVector AliFemtoXi::MomXi() const { return fMomXi; }
+inline float AliFemtoXi::MomXiX() const { return fMomXi.x(); }
+inline float AliFemtoXi::MomXiY() const { return fMomXi.y(); }
+inline float AliFemtoXi::MomXiZ() const { return fMomXi.z(); }
+inline float AliFemtoXi::AlphaXi() const { return fAlphaXi; }
+inline float AliFemtoXi::PtArmXi() const {return fPtArmXi;}
+inline float AliFemtoXi::EXi() const {return fEXi;}
+inline float AliFemtoXi::EOmega() const {return fEOmega;}
+inline float AliFemtoXi::EBacPion() const {return fEBacPion;}
+inline float AliFemtoXi::EBacKaon() const {return fEBacKaon;}
+inline float AliFemtoXi::MassXi() const {return fMassXi;}
+inline float AliFemtoXi::MassOmega() const {return fMassOmega;}
+inline float AliFemtoXi::RapXi() const {return fRapXi;}
+inline float AliFemtoXi::RapOmega() const {return fRapOmega;}
+inline float AliFemtoXi::CTauXi() const {return fCTauXi;}
+inline float AliFemtoXi::CTauOmega() const {return fCTauOmega;}
+inline float AliFemtoXi::PtXi() const {return fPtXi;}
+inline float AliFemtoXi::PtotXi() const {return fPtotXi;}
+inline float AliFemtoXi::PtBac() const {return fPtBac;}
+inline float AliFemtoXi::PtotBac() const {return fPtotBac;}
+inline int   AliFemtoXi::TpcHitsBac() const
+             { return fTpcHitsBac; }
+inline float AliFemtoXi::DedxBac() const {return fDedxBachelor;}
+
+inline unsigned long    AliFemtoXi::TrackTopologyMapBac(unsigned int word) const { return fTopologyMapBachelor[word]; }
+inline unsigned short   AliFemtoXi::IdBac() const { return fKeyBac; }
+inline unsigned short   AliFemtoXi::KeyBac() const { return fKeyBac; }
+
+inline void AliFemtoXi::SetdecayLengthXi(const float x){ fDecayLengthXi= x;}   
+inline void AliFemtoXi::SetdecayVertexXiX(const float x){ fDecayVertexXi.SetX(x);}
+inline void AliFemtoXi::SetdecayVertexXiY(const float x){ fDecayVertexXi.SetY(x);}
+inline void AliFemtoXi::SetdecayVertexXiZ(const float x){ fDecayVertexXi.SetZ(x);}
+inline void AliFemtoXi::SetdecayVertexXi(const AliFemtoThreeVector v){ fDecayVertexXi = v; }
+inline void AliFemtoXi::SetdcaXiDaughters(const float x){fDcaXiDaughters= x;} 
+inline void AliFemtoXi::SetdcaXiToPrimVertex(const float x){fDcaXiToPrimVertex= x;}   
+inline void AliFemtoXi::SetdcaBacToPrimVertex(const float x){ fDcaBachelorToPrimVertex = x;} 
+inline void AliFemtoXi::SetmomBac(const AliFemtoThreeVector v){fMomBachelor = v; }
+inline void AliFemtoXi::SetmomBacX(const float x){fMomBachelor.SetX(x);}
+inline void AliFemtoXi::SetmomBacY(const float x){fMomBachelor.SetY(x);}
+inline void AliFemtoXi::SetmomBacZ(const float x){fMomBachelor.SetZ(x);}
+inline void AliFemtoXi::SetTrackTopologyMapBac(unsigned int word, const unsigned long& m){fTopologyMapBachelor[word]=m;} 
+inline void AliFemtoXi::SetmomXi(AliFemtoThreeVector v){fMomXi= v; }
+inline void AliFemtoXi::SetmomXiX(const float x){fMomXi.SetX(x);}
+inline void AliFemtoXi::SetmomXiY(const float x){fMomXi.SetY(x);}
+inline void AliFemtoXi::SetmomXiZ(const float x){fMomXi.SetZ(x);}
+
+inline void AliFemtoXi::SetalphaXi( float x){fAlphaXi= x;}
+inline void AliFemtoXi::SetptArmXi( float x){fPtArmXi = x;}
+inline void AliFemtoXi::SeteXi( float x){fEXi= x;}       
+inline void AliFemtoXi::SeteOmega( float x){fEOmega= x;}
+inline void AliFemtoXi::SeteBacPion( float x){fEBacPion= x;}
+inline void AliFemtoXi::SeteBacKaon( float x){fEBacKaon= x;}
+inline void AliFemtoXi::SetmassXi( float x){fMassXi = x;} 
+inline void AliFemtoXi::SetmassOmega( float x){fMassOmega= x;}  
+inline void AliFemtoXi::SetrapXi( float x){fRapXi= x;}
+inline void AliFemtoXi::SetrapOmega( float x){fRapOmega = x;}   
+inline void AliFemtoXi::SetcTauXi( float x){fCTauXi = x;}   
+inline void AliFemtoXi::SetcTauOmega( float x){fCTauOmega = x;}   
+inline void AliFemtoXi::SetptXi( float x){fPtXi = x;}          
+inline void AliFemtoXi::SetptotXi( float x){fPtotXi = x;}
+inline void AliFemtoXi::SetptBac( float x){fPtBac = x;}
+inline void AliFemtoXi::SetptotBac( float x){fPtotBac = x;}    
+inline void AliFemtoXi::SetidBac(const unsigned short& s){ fKeyBac= s;}
+inline void AliFemtoXi::SetkeyBac(const unsigned short& s){ fKeyBac= s;}
+inline void AliFemtoXi::SettpcHitsBac(const int& i){fTpcHitsBac=i;} 
+inline void AliFemtoXi::SetdedxBac(float x){fDedxBachelor=x;}
+
+#endif
+
+
+/***********************************************************************
+ *
+ * $Log$
+ * Revision 1.1.2.1  2007/10/05 09:38:17  akisiel
+ * Fix stray colons
+ *
+ * Revision 1.1  2007/05/16 10:22:12  akisiel
+ * Making the directory structure of AliFemto flat. All files go into one common directory
+ *
+ * Revision 1.2  2007/05/03 09:42:29  akisiel
+ * Fixing Effective C++ warnings
+ *
+ * Revision 1.1.1.1  2007/04/25 15:38:41  panos
+ * Importing the HBT code dir
+ *
+ * Revision 1.1.1.1  2007/03/07 10:14:49  mchojnacki
+ * First version on CVS
+ *
+ * Revision 1.3  2003/09/02 17:58:33  perev
+ * gcc 3.2 updates + WarnOff
+ *
+ * Revision 1.2  2001/12/05 15:10:33  laue
+ * Boris' updates (mainly access functions)
+ *
+ *
+ ***********************************************************************/
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoXiCollection.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoXiCollection.h
new file mode 100644 (file)
index 0000000..8446dae
--- /dev/null
@@ -0,0 +1,33 @@
+/***************************************************************************
+ *
+ * $Id$
+ *
+ * Author: Frank Laue, BNL
+ ***************************************************************************
+ *
+ * Description: part of STAR HBT Framework: AliFemtoMaker package
+ *   The Collection of v0s is the main component of the HbtEvent,
+ *   which is essentially the transient microDST
+ *
+ ***************************************************************************/
+
+
+#ifndef AliFemtoXiCollection_hh
+#define AliFemtoXiCollection_hh
+#include "AliFemtoXi.h"
+#include <list>
+
+#if !defined(ST_NO_NAMESPACES)
+using std::list;
+#endif
+
+#ifdef ST_NO_TEMPLATE_DEF_ARGS
+typedef list<AliFemtoXi*, allocator<AliFemtoXi*> >            AliFemtoXiCollection;
+typedef list<AliFemtoXi*, allocator<AliFemtoXi*> >::iterator  AliFemtoXiIterator;
+#else
+typedef list<AliFemtoXi*>            AliFemtoXiCollection;
+typedef list<AliFemtoXi*>::iterator  AliFemtoXiIterator;
+#endif
+
+#endif
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoXiCut.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFemtoXiCut.h
new file mode 100644 (file)
index 0000000..8e3bc64
--- /dev/null
@@ -0,0 +1,35 @@
+////////////////////////////////////////////////////////////////////////////////
+/// AliFemtoXiCut - the pure virtual base class for the Xi cut               ///
+/// All Xi cuts must inherit from this one                                   ///
+////////////////////////////////////////////////////////////////////////////////
+
+#ifndef AliFemtoXiCut_hh
+#define AliFemtoXiCut_hh
+
+#include "AliFemtoTypes.h"
+#include "AliFemtoXi.h"
+#include "AliFemtoParticleCut.h"
+
+class AliFemtoXiCut : public AliFemtoParticleCut {
+
+public:
+
+  AliFemtoXiCut(){/* no-op */};                          // default constructor. - Users should write their own
+  AliFemtoXiCut(const AliFemtoXiCut& aCut);              // copy constructor
+  virtual ~AliFemtoXiCut(){/* no-op */};                 // destructor
+  AliFemtoXiCut& operator=(const AliFemtoXiCut& aCut);              // copy constructor
+
+  virtual bool Pass(const AliFemtoXi* aCut)=0;               // true if passes, false if not
+
+  virtual AliFemtoParticleType Type(){return hbtXi;}
+  virtual AliFemtoXiCut* Clone() { return 0;}
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoXiCut, 0)
+#endif
+};
+
+inline AliFemtoXiCut::AliFemtoXiCut(const AliFemtoXiCut& c) : AliFemtoParticleCut(c) { /* no-op */ } 
+inline AliFemtoXiCut& AliFemtoXiCut::operator=(const AliFemtoXiCut& c) { if (this != &c) { AliFemtoParticleCut::operator=(c); } return *this; } 
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFmHelix.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFmHelix.cxx
new file mode 100644 (file)
index 0000000..5d2cf57
--- /dev/null
@@ -0,0 +1,650 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFmHelix: a helper helix class                                      //
+// Includes all the operations and specifications of the helix. Can be   //
+// used to determine path lengths, distance of closest approach etc.     //
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+#if !defined(ST_NO_NUMERIC_LIMITS)
+#    include <limits>
+#    if !defined(ST_NO_NAMESPACES)
+using std::numeric_limits;
+#    endif
+#endif
+#define FOR_HELIX
+#include <float.h>
+#include <assert.h>
+
+#include "AliFmHelix.h"
+#include "PhysicalConstants.h" 
+#include "SystemOfUnits.h"
+#ifdef __ROOT__
+ClassImpT(AliFmHelix,double);
+#endif
+
+#ifdef WIN32
+#include "gcc2vs.h"
+#endif
+
+#include <iostream>
+#include <fstream>
+using namespace std;
+
+const double AliFmHelix::fgkNoSolution = 3.e+33;
+
+AliFmHelix::AliFmHelix() :
+  fSingularity(0),
+  fOrigin(0,0,0),
+  fDipAngle(0),
+  fCurvature(0),
+  fPhase(0),
+  fH(0),
+  fCosDipAngle(0),
+  fSinDipAngle(0),
+  fCosPhase(0),
+  fSinPhase(0)
+{
+  //Default constructor
+/*noop*/ 
+}
+
+AliFmHelix::AliFmHelix(double c, double d, double phase,
+                      const AliFmThreeVector<double>& o, int h) :
+  fSingularity(0),
+  fOrigin(0,0,0),
+  fDipAngle(0),
+  fCurvature(0),
+  fPhase(0),
+  fH(0),
+  fCosDipAngle(0),
+  fSinDipAngle(0),
+  fCosPhase(0),
+  fSinPhase(0)
+{
+  // Constructor with helix parameters
+  SetParameters(c, d, phase, o, h);
+}
+
+AliFmHelix::~AliFmHelix() { 
+  // Default destructor
+/* noop */ 
+}
+
+void AliFmHelix::SetParameters(double c, double dip, double phase,
+                              const AliFmThreeVector<double>& o, int h)
+{
+       //
+       //  The order in which the parameters are set is important
+       //  since setCurvature might have to adjust the others.
+       //
+       fH = (h>=0) ? 1 : -1;    // Default is: positive particle
+       //             positive field
+       fOrigin   = o;
+       SetDipAngle(dip);
+       SetPhase(phase);
+
+       //
+       // Check for singularity and correct for negative curvature.           
+       // May change mH and mPhase. Must therefore be set last.
+       //
+       SetCurvature(c);
+
+       //
+       // For the case B=0, h is ill defined. In the following we
+       // always assume h = +1. Since phase = psi - h * pi/2
+       // we have to correct the phase in case h = -1.
+       // This assumes that the user uses the same h for phase
+       // as the one he passed to the constructor.
+       //
+       if (fSingularity && fH == -1) {
+               fH = +1;
+               SetPhase(fPhase-M_PI);
+       }
+}
+
+void AliFmHelix::SetCurvature(double val)
+{
+  // Set helix curvature
+       if (val < 0) {
+               fCurvature = -val;
+               fH = -fH;
+               SetPhase(fPhase+M_PI);
+       }
+       else
+               fCurvature = val;
+
+#ifndef ST_NO_NUMERIC_LIMITS
+       if (fabs(fCurvature) <= numeric_limits<double>::epsilon())
+#else
+       if (fabs(fCurvature) <= static_cast<double>(0))
+#endif    
+               fSingularity = true;                    // straight line
+       else
+               fSingularity = false;                   // curved
+}
+
+void AliFmHelix::SetPhase(double val)
+{
+  // Set helix phase
+       fPhase       = val;
+       fCosPhase    = cos(fPhase);
+       fSinPhase    = sin(fPhase);
+       if (fabs(fPhase) > M_PI)
+               fPhase = atan2(fSinPhase, fCosPhase);  // force range [-pi,pi]
+}
+
+void AliFmHelix::SetDipAngle(double val)
+{
+  // Set helix dip angle
+       fDipAngle    = val;
+       fCosDipAngle = cos(fDipAngle);
+       fSinDipAngle = sin(fDipAngle);
+}
+
+double AliFmHelix::XCenter() const
+{
+  // Set helix center in X
+       if (fSingularity)
+               return 0;
+       else
+               return fOrigin.x()-fCosPhase/fCurvature;
+}
+
+double AliFmHelix::YCenter() const
+{
+  // Set helix center in Y
+       if (fSingularity)
+               return 0;
+       else
+               return fOrigin.y()-fSinPhase/fCurvature;
+}
+
+double AliFmHelix::FudgePathLength(const AliFmThreeVector<double>& p) const
+{
+  // Path length
+       double s;
+       double dx = p.x()-fOrigin.x();
+       double dy = p.y()-fOrigin.y();
+
+       if (fSingularity) {
+               s = (dy*fCosPhase - dx*fSinPhase)/fCosDipAngle;
+       }
+       else {
+               s = atan2(dy*fCosPhase - dx*fSinPhase,
+                       1/fCurvature + dx*fCosPhase+dy*fSinPhase)/
+                       (fH*fCurvature*fCosDipAngle);
+       }
+       return s;
+}
+
+double AliFmHelix::Distance(const AliFmThreeVector<double>& p, bool scanPeriods) const
+{
+  // calculate distance between origin an p along the helix
+       return abs(this->At(PathLength(p,scanPeriods))-p);
+}
+
+double AliFmHelix::PathLength(const AliFmThreeVector<double>& p, bool scanPeriods) const 
+{
+       //
+       //  Returns the path length at the distance of closest 
+       //  approach between the helix and point p. 
+       //  For the case of B=0 (straight line) the path length
+       //  can be calculated analytically. For B>0 there is
+       //  unfortunately no easy solution to the problem.
+       //  Here we use the Newton method to find the root of the
+       //  referring equation. The 'fudgePathLength' serves
+       //  as a starting value.
+       //
+       double s;
+       double dx = p.x()-fOrigin.x();
+       double dy = p.y()-fOrigin.y();
+       double dz = p.z()-fOrigin.z();
+
+       if (fSingularity) {
+               s = fCosDipAngle*(fCosPhase*dy-fSinPhase*dx) +
+                       fSinDipAngle*dz;
+       }
+       else { //
+#ifndef ST_NO_NAMESPACES
+               {
+                       using namespace units;
+#endif
+                       const double ktMaxPrecisionNeeded = micrometer;
+                       const int    ktMaxIterations      = 100;
+
+                       //
+                       // The math is taken from Maple with C(expr,optimized) and
+                       // some hand-editing. It is not very nice but efficient.
+                       //
+                       double t34 = fCurvature*fCosDipAngle*fCosDipAngle;
+                       double t41 = fSinDipAngle*fSinDipAngle;
+                       double t6, t7, t11, t12, t19;
+
+                       //
+                       // Get a first guess by using the dca in 2D. Since
+                       // in some extreme cases we might be off by n periods
+                       // we add (subtract) periods in case we get any closer.
+                       // 
+                       s = FudgePathLength(p);
+
+                       if (scanPeriods) {
+                               double ds = Period();
+                               int    j, jmin = 0;
+                               double d, dmin = abs(At(s) - p);
+                               for(j=1; j<ktMaxIterations; j++) {
+                                       if ((d = abs(At(s+j*ds) - p)) < dmin) {
+                                               dmin = d;
+                                               jmin = j;
+                                       }
+                                       else
+                                               break;
+                               }
+                               for(j=-1; -j<ktMaxIterations; j--) {
+                                       if ((d = abs(At(s+j*ds) - p)) < dmin) {
+                                               dmin = d;
+                                               jmin = j;
+                                       }
+                                       else
+                                               break;
+                               }
+                               if (jmin) s += jmin*ds;
+                       }
+
+                       //
+                       // Newtons method:
+                       // Stops after ktMaxIterations iterations or if the required
+                       // precision is obtained. Whatever comes first.
+                       //
+                       double sOld = s;
+                       for (int i=0; i<ktMaxIterations; i++) {
+                               t6  = fPhase+s*fH*fCurvature*fCosDipAngle;
+                               t7  = cos(t6);
+                               t11 = dx-(1/fCurvature)*(t7-fCosPhase);
+                               t12 = sin(t6);
+                               t19 = dy-(1/fCurvature)*(t12-fSinPhase);
+                               s  -= (t11*t12*fH*fCosDipAngle-t19*t7*fH*fCosDipAngle -
+                                       (dz-s*fSinDipAngle)*fSinDipAngle)/
+                                       (t12*t12*fCosDipAngle*fCosDipAngle+t11*t7*t34 +
+                                       t7*t7*fCosDipAngle*fCosDipAngle +
+                                       t19*t12*t34+t41);
+                               if (fabs(sOld-s) < ktMaxPrecisionNeeded) break;
+                               sOld = s;
+                       }
+#ifndef ST_NO_NAMESPACES
+               }
+#endif
+       }
+       return s;
+}
+
+double AliFmHelix::Period() const
+{
+  // period
+       if (fSingularity)
+#ifndef ST_NO_NUMERIC_LIMITS
+               return numeric_limits<double>::max();
+#else
+               return DBL_MAX;
+#endif    
+       else    
+               return fabs(2*M_PI/(fH*fCurvature*fCosDipAngle)); 
+}
+
+pair<double, double> AliFmHelix::PathLength(double r) const
+{
+       //
+       // The math is taken from Maple with C(expr,optimized) and
+       // some hand-editing. It is not very nice but efficient.
+       // 'first' is the smallest of the two solutions (may be negative)
+       // 'second' is the other.
+       //
+       pair<double,double> tvalue;
+       pair<double,double> tVALUE(999999999.,999999999.);
+       if (fSingularity) {
+               double t1 = fCosDipAngle*(fOrigin.x()*fSinPhase-fOrigin.y()*fCosPhase);
+               double t12 = fOrigin.y()*fOrigin.y();
+               double t13 = fCosPhase*fCosPhase;
+               double t15 = r*r;
+               double t16 = fOrigin.x()*fOrigin.x();
+               double t20 = -fCosDipAngle*fCosDipAngle*(2.0*fOrigin.x()*fSinPhase*fOrigin.y()*fCosPhase +
+                       t12-t12*t13-t15+t13*t16);
+               if (t20<0.) return tVALUE;
+               t20 = ::sqrt(t20);
+               tvalue.first  = (t1-t20)/(fCosDipAngle*fCosDipAngle);
+               tvalue.second = (t1+t20)/(fCosDipAngle*fCosDipAngle);
+       }
+       else {
+               double t1 = fOrigin.y()*fCurvature;
+               double t2 = fSinPhase;
+               double t3 = fCurvature*fCurvature;
+               double t4 = fOrigin.y()*t2;
+               double t5 = fCosPhase;
+               double t6 = fOrigin.x()*t5;
+               double t8 = fOrigin.x()*fOrigin.x();
+               double t11 = fOrigin.y()*fOrigin.y();
+               double t14 = r*r;
+               double t15 = t14*fCurvature;
+               double t17 = t8*t8;
+               double t19 = t11*t11;
+               double t21 = t11*t3;
+               double t23 = t5*t5;
+               double t32 = t14*t14;
+               double t35 = t14*t3;
+               double t38 = 8.0*t4*t6 - 4.0*t1*t2*t8 - 4.0*t11*fCurvature*t6 +
+                       4.0*t15*t6 + t17*t3 + t19*t3 + 2.0*t21*t8 + 4.0*t8*t23 -
+                       4.0*t8*fOrigin.x()*fCurvature*t5 - 4.0*t11*t23 -
+                       4.0*t11*fOrigin.y()*fCurvature*t2 + 4.0*t11 - 4.0*t14 +
+                       t32*t3 + 4.0*t15*t4 - 2.0*t35*t11 - 2.0*t35*t8;
+               double t40 = (-t3*t38);
+               if (t40<0.) return tVALUE;
+               t40 = ::sqrt(t40);
+
+               double t43 = fOrigin.x()*fCurvature;
+               double t45 = 2.0*t5 - t35 + t21 + 2.0 - 2.0*t1*t2 -2.0*t43 - 2.0*t43*t5 + t8*t3;
+               double t46 = fH*fCosDipAngle*fCurvature;
+
+               tvalue.first = (-fPhase + 2.0*atan((-2.0*t1 + 2.0*t2 + t40)/t45))/t46;
+               tvalue.second = -(fPhase + 2.0*atan((2.0*t1 - 2.0*t2 + t40)/t45))/t46;
+
+               //
+               //   Solution can be off by +/- one Period, select smallest
+               //
+               double p = Period();
+               //      malisa deletes "isnan" check 22apr2006  if (!isnan(value.first)) {
+               if (fabs(tvalue.first-p) < fabs(tvalue.first)) tvalue.first = tvalue.first-p;
+               else if (fabs(tvalue.first+p) < fabs(tvalue.first)) tvalue.first = tvalue.first+p;
+               //      malisa  }
+               //      malisa deletes "isnan" check 22apr2006          if (!isnan(tvalue.second)) {
+               if (fabs(tvalue.second-p) < fabs(tvalue.second)) tvalue.second = tvalue.second-p;
+               else if (fabs(tvalue.second+p) < fabs(tvalue.second)) tvalue.second = tvalue.second+p;
+               //      malisa }
+       }
+       if (tvalue.first > tvalue.second)
+               swap(tvalue.first,tvalue.second);
+       return(tvalue);
+}
+
+pair<double, double> AliFmHelix::PathLength(double r, double x, double y, bool /* scanPeriods */)
+{
+  // path length
+       double x0 = fOrigin.x();
+       double y0 = fOrigin.y();
+       fOrigin.SetX(x0-x);
+       fOrigin.SetY(y0-y);
+       pair<double, double> result = this->PathLength(r);
+       fOrigin.SetX(x0);
+       fOrigin.SetY(y0);
+       return result;  
+}
+
+double AliFmHelix::PathLength(const AliFmThreeVector<double>& r,
+                                                  const AliFmThreeVector<double>& n) const
+{
+       //
+       // Vector 'r' defines the position of the center and
+       // vector 'n' the normal vector of the plane.
+       // For a straight line there is a simple analytical
+       // solution. For curvatures > 0 the root is determined
+       // by Newton method. In case no valid s can be found
+       // the max. largest value for s is returned.
+       //
+       double s;
+
+       if (fSingularity) {
+               double t = n.z()*fSinDipAngle +
+                       n.y()*fCosDipAngle*fCosPhase -
+                       n.x()*fCosDipAngle*fSinPhase;
+               if (t == 0)
+                       s = fgkNoSolution;
+               else
+                       s = ((r - fOrigin)*n)/t;
+       }
+       else {
+               const double ktMaxPrecisionNeeded = micrometer;
+               const int    ktMaxIterations      = 20;
+
+               double tA = fCurvature*((fOrigin - r)*n) -
+                       n.x()*fCosPhase - 
+                       n.y()*fSinPhase;
+               double t = fH*fCurvature*fCosDipAngle;
+               double u = n.z()*fCurvature*fSinDipAngle;
+
+               double a, f, fp;
+               double sOld = s = 0;  
+               double shiftOld = 0;
+               double shift;
+               //              (cos(kangMax)-1)/kangMax = 0.1
+               const double kangMax = 0.21;
+               double deltas = fabs(kangMax/(fCurvature*fCosDipAngle));
+               //              dampingFactor = exp(-0.5);
+               double dampingFactor = 0.60653;
+               int i;
+
+               for (i=0; i<ktMaxIterations; i++) {
+                       a  = t*s+fPhase;
+                       double sina = sin(a);
+                       double cosa = cos(a);
+                       f  = tA +
+                               n.x()*cosa +
+                               n.y()*sina +
+                               u*s;
+                       fp = -n.x()*sina*t +
+                               n.y()*cosa*t +
+                               u;
+                       if ( fabs(fp)*deltas <= fabs(f) ) { //too big step
+                               int sgn = 1;
+                               if (fp<0.) sgn = -sgn;
+                               if (f <0.) sgn = -sgn;
+                               shift = sgn*deltas;
+                               if (shift == -shiftOld) { // don't get stuck shifting +/-deltas
+                                       deltas *= dampingFactor; // dampen magnitude of shift
+                                       shift = sgn*deltas;
+                                       // allow iterations to run out
+                               } else {
+                                       i--; // don't count against iterations
+                               }
+                       } else {
+                               shift = f/fp;
+                       }
+                       s -= shift;
+                       shiftOld = shift;
+                       if (fabs(sOld-s) < ktMaxPrecisionNeeded) break;
+                       sOld = s;
+               }
+               if (i == ktMaxIterations) return fgkNoSolution;
+       }
+       return s;
+}
+
+pair<double, double>
+AliFmHelix::PathLengths(const AliFmHelix& h, bool scanPeriods) const
+{
+       //
+       //      Cannot handle case where one is a helix
+       //  and the other one is a straight line.
+       //
+       if (fSingularity != h.fSingularity) 
+               return pair<double, double>(fgkNoSolution, fgkNoSolution);
+
+       double s1, s2;
+
+       if (fSingularity) {
+               //
+               //  Analytic solution
+               //
+               AliFmThreeVector<double> dv = h.fOrigin - fOrigin;
+               AliFmThreeVector<double> a(-fCosDipAngle*fSinPhase,
+                       fCosDipAngle*fCosPhase,
+                       fSinDipAngle);
+               AliFmThreeVector<double> b(-h.fCosDipAngle*h.fSinPhase,
+                       h.fCosDipAngle*h.fCosPhase,
+                       h.fSinDipAngle);        
+               double ab = a*b;
+               double g  = dv*a;
+               double k  = dv*b;
+               s2 = (k-ab*g)/(ab*ab-1.);
+               s1 = g+s2*ab;
+               return pair<double, double>(s1, s2);
+       }
+       else {  
+               //
+               //  First step: get dca in the xy-plane as start value
+               //
+               double dx = h.XCenter() - XCenter();
+               double dy = h.YCenter() - YCenter();
+               double dd = ::sqrt(dx*dx + dy*dy);
+               double r1 = 1/Curvature();
+               double r2 = 1/h.Curvature();
+
+               /* malisa 22apr2006 is commenting out the "isnan" check
+                *              if ( !finite(r1) || isnan(r1) || !finite(r2) || isnan(r2) ) {
+                *               cerr << __FUNCTION__ << " *** error *** ";
+                *                      cerr << "  r1=" << r1;
+                *                      cerr << "  r2=" << r2 << endl;
+                *                      return pair<double, double>(fgkNoSolution, fgkNoSolution);
+                *              }
+                */
+
+               double cosAlpha = (r1*r1 + dd*dd - r2*r2)/(2*r1*dd);
+
+               double s;
+               double x, y;
+               if (fabs(cosAlpha) < 1) {           // two solutions
+                       double sinAlpha = sin(acos(cosAlpha));
+                       x = XCenter() + r1*(cosAlpha*dx - sinAlpha*dy)/dd;
+                       y = YCenter() + r1*(sinAlpha*dx + cosAlpha*dy)/dd;
+                       s = PathLength(x, y);
+                       x = XCenter() + r1*(cosAlpha*dx + sinAlpha*dy)/dd;
+                       y = YCenter() + r1*(cosAlpha*dy - sinAlpha*dx)/dd;
+                       double a = PathLength(x, y);
+                       if (h.Distance(At(a),scanPeriods) < h.Distance(At(s),scanPeriods)) s = a;
+               }
+               else {                              // no intersection (or exactly one)
+                       x = XCenter() + r1*dx/dd;
+                       y = YCenter() + r1*dy/dd;
+                       s = PathLength(x, y);
+               }
+
+               //
+               //   Second step: scan in decreasing intervals around seed 's'
+               // 
+               const double ktMinStepSize = 10*micrometer;
+               const double ktMinRange    = 10*centimeter;    
+               double dmin              = h.Distance(At(s),scanPeriods);
+               double range             = max(2*dmin, ktMinRange);
+
+               /* malisa comments out the "isnan" check 22apr2006
+                *              if ( !finite(range) || isnan(range)) {
+                *                      cerr << __FUNCTION__ << " *** error *** ";
+                *                      cerr << "  range=" << range << endl;
+                *                      return pair<double, double>(fgkNoSolution, fgkNoSolution);
+                *              }
+                */
+
+               double ds = range/10.;
+               double slast=-999999, d;
+               s1 = s - range/2.;
+               s2 = s + range/2.;
+
+               double tmp1;
+               double tmp2;
+
+               while (ds > ktMinStepSize) {
+                       if ( !(s1<s2) ) {
+                               cerr << __FUNCTION__ << " *** error *** s1 = ";
+                               cerr << "    s2 = " << s2;
+                               cerr << "    range = " << range;
+                               cerr << "     ds = " << ds << endl;
+                               return pair<double, double>(fgkNoSolution, fgkNoSolution);
+                       }       
+                       tmp1 = (s2-s1);
+                       tmp2 = tmp1/10.0;
+                       ds = tmp2;
+                       if ( ds<0) {
+                           cerr << __FUNCTION__ << " *** error *** ds = " << ds << endl;
+                           return pair<double, double>(fgkNoSolution, fgkNoSolution);
+                       }
+                       int iterations = 0;
+                       for (double ss=s1; ss<(s2+ds); ss+=ds) {
+                           iterations++;
+                           if ( iterations > 100 ) {
+                               cerr << __FUNCTION__ << " *** error *** iterations = " << iterations << endl;
+                               return pair<double, double>(fgkNoSolution, fgkNoSolution);
+                           }
+                           d = h.Distance(At(ss),scanPeriods);
+                           if (d < dmin) {
+                               dmin = d;
+                               s = ss;
+                           }
+                           slast = ss;
+                       }
+                       //
+                       //  In the rare cases where the minimum is at the
+                       //  the border of the current range we shift the range
+                       //  and start all over, i.e we do not decrease 'ds'.
+                       //  Else we decrease the search intervall around the
+                       //  current minimum and redo the scan in smaller steps.
+                       //
+                       if (s == s1) {
+                               d = 0.8*(s2-s1);
+                               s1 -= d;
+                               s2 -= d;
+                       }
+                       else if (s == slast) {
+                               d = 0.8*(s2-s1);
+                               s1 += d;
+                               s2 += d;
+                       }
+                       else {           
+                               s1 = s-ds;
+                               s2 = s+ds;
+                       //      ds /= 10;
+                       }
+               }
+               return pair<double, double>(s, h.PathLength(At(s),scanPeriods));
+       }
+}
+
+
+void AliFmHelix::MoveOrigin(double s)
+{
+  // Move the helix origin
+       if (fSingularity)
+               fOrigin = At(s);
+       else {
+               AliFmThreeVector<double> newOrigin = At(s);
+               double newPhase = atan2(newOrigin.y() - YCenter(),
+                       newOrigin.x() - XCenter());
+               fOrigin = newOrigin;
+               SetPhase(newPhase);             
+       }
+}
+
+int operator== (const AliFmHelix& a, const AliFmHelix& b)
+{
+       //
+       // Checks for numerical identity only !
+       //
+       return (a.Origin()    == b.Origin()    &&
+               a.DipAngle()  == b.DipAngle()  &&
+               a.Curvature() == b.Curvature() &&
+               a.Phase()     == b.Phase()     &&
+               a.H()         == b.H());
+}
+
+int operator!= (const AliFmHelix& a, const AliFmHelix& b) {return !(a == b);}
+
+ostream& operator<<(ostream& os, const AliFmHelix& h)
+{
+       return os << '('
+               << "curvature = "  << h.Curvature() << ", " 
+               << "dip angle = "  << h.DipAngle()  << ", "
+               << "phase = "      << h.Phase()     << ", "  
+               << "h = "          << h.H()         << ", "    
+               << "origin = "     << h.Origin()    << ')';
+}
+
+
+
+
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFmHelix.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFmHelix.h
new file mode 100644 (file)
index 0000000..865271e
--- /dev/null
@@ -0,0 +1,190 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFmHelix: a helper helix class                                      //
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+
+#ifndef ALIFMHELIX_H
+#define ALIFMHELIX_H
+
+#include <math.h>
+#include <utility>
+#include <algorithm>
+#include "AliFmThreeVector.h"
+#include <TMath.h>
+#if !defined(ST_NO_NAMESPACES)
+using std::pair;
+using std::swap;
+using std::max;
+#endif
+
+#ifdef WIN32
+#include "gcc2vs.h"
+#endif
+
+#ifdef __SUNPRO_CC
+#include <ieeefp.h>
+#define __FUNCTION__ "__FILE__:__LINE__"
+#endif
+
+class AliFmHelix {
+public:
+    /// curvature, dip angle, phase, origin, h
+    AliFmHelix(double c, double dip, double phase,
+              const AliFmThreeVector<double>& o, int h=-1);
+    
+    virtual ~AliFmHelix();
+    // AliFmHelix(const AliFmHelix&);                  // use default
+    // AliFmHelix& operator=(const AliFmHelix&);       // use default
+
+    double       DipAngle()   const;           
+    double       Curvature()  const;   /// 1/R in xy-plane
+    double       Phase()      const;   /// aziumth in xy-plane measured from ring center
+    double       XCenter()    const;   /// x-center of circle in xy-plane
+    double       YCenter()    const;   /// y-center of circle in xy-plane
+    int          H()          const;   /// -sign(q*B);
+    
+    const AliFmThreeVector<double>& Origin() const;    /// starting point
+
+    void SetParameters(double c, double dip, double phase, const AliFmThreeVector<double>& o, int h);
+    
+    double       X(double s)  const;
+    double       Y(double s)  const;
+    double       Z(double s)  const;
+
+    AliFmThreeVector<double>  At(double s) const;
+
+    /// returns period length of helix
+    double       Period()       const;
+    
+    /// path length at given r (cylindrical r)
+    pair<double, double> PathLength(double r)   const;
+    
+    /// path length at given r (cylindrical r, cylinder axis at x,y)
+    pair<double, double> PathLength(double r, double x, double y, bool scanPeriods = true);
+    
+    /// path length at distance of closest approach to a given point
+    double       PathLength(const AliFmThreeVector<double>& p, bool scanPeriods = true) const;
+    
+    /// path length at intersection with plane
+    double       PathLength(const AliFmThreeVector<double>& r,
+                           const AliFmThreeVector<double>& n) const;
+
+    /// path length at distance of closest approach in the xy-plane to a given point
+    double       PathLength(double x, double y) const;
+
+    /// path lengths at dca between two helices 
+    pair<double, double> PathLengths(const AliFmHelix& h, bool scanPeriods = true) const;
+    
+    /// minimal distance between point and helix
+    double       Distance(const AliFmThreeVector<double>& p, bool scanPeriods = true) const;    
+    
+    /// checks for valid parametrization
+    bool         Valid(double world = 1.e+5) const {return !Bad(world);}
+    int            Bad(double world = 1.e+5) const;
+    
+    /// move the origin along the helix to s which becomes then s=0
+    virtual void MoveOrigin(double s);
+    
+    static const double fgkNoSolution;  // coinstant indicating lack of solution
+    
+protected:
+    AliFmHelix();
+    
+    void SetCurvature(double d);       /// performs also various checks   
+    void SetPhase(double d);           
+    void SetDipAngle(double d);
+    
+    /// value of S where distance in x-y plane is minimal
+    double FudgePathLength(const AliFmThreeVector<double>& v) const;
+    
+protected:
+    bool                   fSingularity;       // true for straight line case (B=0)
+    AliFmThreeVector<double>  fOrigin;          // Helix origin
+    double                 fDipAngle;           // Helix dip angle
+    double                 fCurvature;          // curvature
+    double                 fPhase;              // phase
+    int                    fH;                 // -sign(q*B);
+
+    double                 fCosDipAngle;        // cosine of the dip angle
+    double                 fSinDipAngle;        // sine of the dip angle
+    double                 fCosPhase;           // cosine of the phase
+    double                 fSinPhase;           // sine of the phase
+#ifdef __ROOT__
+  ClassDef(AliFmHelix,1)
+#endif
+};
+
+//
+//     Non-member functions
+//
+int operator== (const AliFmHelix&, const AliFmHelix&);
+int operator!= (const AliFmHelix&, const AliFmHelix&);
+ostream& operator<<(ostream&, const AliFmHelix&);
+
+//
+//     Inline functions
+//
+inline int AliFmHelix::H() const {return fH;}
+
+inline double AliFmHelix::DipAngle() const {return fDipAngle;}
+
+inline double AliFmHelix::Curvature() const {return fCurvature;}
+
+inline double AliFmHelix::Phase() const {return fPhase;}
+
+inline double AliFmHelix::X(double s) const
+{
+    if (fSingularity)
+       return fOrigin.x() - s*fCosDipAngle*fSinPhase;
+    else
+       return fOrigin.x() + (cos(fPhase + s*fH*fCurvature*fCosDipAngle)-fCosPhase)/fCurvature;
+}
+inline double AliFmHelix::Y(double s) const
+{
+    if (fSingularity)
+       return fOrigin.y() + s*fCosDipAngle*fCosPhase;
+    else
+       return fOrigin.y() + (sin(fPhase + s*fH*fCurvature*fCosDipAngle)-fSinPhase)/fCurvature;
+}
+
+inline double AliFmHelix::Z(double s) const
+{
+    return fOrigin.z() + s*fSinDipAngle;
+}
+
+inline const AliFmThreeVector<double>& AliFmHelix::Origin() const {return fOrigin;}
+
+inline AliFmThreeVector<double> AliFmHelix::At(double s) const
+{
+    return AliFmThreeVector<double>(X(s), Y(s), Z(s));
+}
+
+inline double AliFmHelix::PathLength(double x, double y) const
+{
+    return FudgePathLength(AliFmThreeVector<double>(x, y, 0));
+}
+inline int AliFmHelix::Bad(double WorldSize) const
+{
+
+    int ierr;
+    if (!TMath::Finite(fDipAngle    ))         return   11;
+    if (!TMath::Finite(fCurvature   ))         return   12;
+
+    ierr = fOrigin.Bad(WorldSize);
+    if (ierr)                           return    3+ierr*100;
+
+    if (::fabs(fDipAngle)  >1.58)      return   21;
+    double qwe = ::fabs(::fabs(fDipAngle)-M_PI/2);
+    if (qwe < 1./WorldSize      )      return   31; 
+
+    if (::fabs(fCurvature) > WorldSize)        return   22;
+    if (fCurvature < 0          )      return   32;
+
+    if (abs(fH) != 1            )       return   24; 
+
+    return 0;
+}
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFmHelixD.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFmHelixD.h
new file mode 100644 (file)
index 0000000..d2cd52e
--- /dev/null
@@ -0,0 +1,23 @@
+/***************************************************************************
+ *
+ * $Id$
+ * $Log$
+ * Revision 1.1.1.1  2007/04/25 15:38:41  panos
+ * Importing the HBT code dir
+ *
+ * Revision 1.1.1.1  2007/03/07 10:14:49  mchojnacki
+ * First version on CVS
+ *
+ * Revision 1.8  2005/07/06 18:49:56  fisyak
+ * Replace AliFmHelixD, AliFmLorentzVectorD,AliFmLorentzVectorF,AliFmMatrixD,AliFmMatrixF,AliFmPhysicalHelixD,AliFmThreeVectorD,AliFmThreeVectorF by templated version
+ *
+
+****************************************************************************/
+#ifndef ST_HELIX_D_HH
+#define ST_HELIX_D_HH
+#include "AliFmThreeVectorD.h"
+#include "AliFmHelix.h"
+#include <utility>
+typedef AliFmHelix AliFmHelixD;
+typedef pair<double,double> pairD;
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFmLorentzVector.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFmLorentzVector.h
new file mode 100644 (file)
index 0000000..60f31eb
--- /dev/null
@@ -0,0 +1,741 @@
+/***************************************************************************
+ *
+ * $Id$
+ *
+ * Author: Brian Lasiuk, Thomas Ullrich, April 1998
+ ***************************************************************************
+ *
+ * Description:
+ *
+ * Remarks:   Since not all compilers support member templates
+ *            we have to specialize the templated member on these
+ *            platforms. If member templates are not supported the
+ *            ST_NO_MEMBER_TEMPLATES flag has to be set. tu.
+ *
+ *            In the near future when all compilers can handle member
+ *            templates this class should be cleaned up. A lot of
+ *            redundant code can be removed as soon as the compilers
+ *            are up-to-date. tu
+ *
+ ***************************************************************************
+ *
+ * $Log$
+ * Revision 1.1.1.1  2007/04/25 15:38:41  panos
+ * Importing the HBT code dir
+ *
+ * Revision 1.1.1.1  2007/03/07 10:14:49  mchojnacki
+ * First version on CVS
+ *
+ * Revision 1.11  2005/09/22 20:09:20  fisyak
+ * Make AliFmLorentzVector persistent
+ *
+ * Revision 1.10  2005/07/06 18:49:56  fisyak
+ * Replace AliFmHelixD, AliFmLorentzVectorD,AliFmLorentzVectorF,AliFmMatrixD,AliFmMatrixF,AliFmPhysicalHelixD,AliFmThreeVectorD,AliFmThreeVectorF by templated version
+ *
+ * Revision 1.9  2005/03/28 06:02:45  perev
+ * Defence FPE added
+ *
+ * Revision 1.8  2003/09/02 17:59:35  perev
+ * gcc 3.2 updates + WarnOff
+ *
+ * Revision 1.7  2003/05/01 19:24:31  ullrich
+ * Corrected problem in boost().
+ *
+ * Revision 1.6  1999/10/15 15:56:36  ullrich
+ * Changed output format in operator<<, added operator>>
+ *
+ * Revision 1.5  1999/06/04 18:01:36  ullrich
+ * New operators operator() and operator[] which can be used
+ * as lvalues.
+ *
+ * Revision 1.4  1999/04/14 23:12:07  fisyak
+ * Add __CINT__ to handle references
+ *
+ * Revision 1.3  1999/02/17 11:38:36  ullrich
+ * Removed specialization for 'long double'.
+ *
+ * Revision 1.2  1999/02/14 23:11:42  fisyak
+ * Fixes for Rootcint
+ *
+ * Revision 1.1  1999/01/30 03:59:02  fisyak
+ * Root Version of AliFmarClassLibrary
+ *
+ * Revision 1.1  1999/01/23 00:27:52  ullrich
+ * Initial Revision
+ *
+ **************************************************************************/
+/*//
+//// General class for a Lorentz four-vector
+///*/
+#ifndef ST_LORENTZ_VECTOR_HH
+#define ST_LORENTZ_VECTOR_HH
+
+#include "AliFmThreeVector.h"
+template<class T> class AliFmLorentzVector {
+public:
+    AliFmLorentzVector(T = 0, T = 0, T = 0, T = 0);
+    virtual ~AliFmLorentzVector();
+    
+#ifndef ST_NO_MEMBER_TEMPLATES
+    template<class X> AliFmLorentzVector(const AliFmThreeVector<X>&, T);
+    template<class X> AliFmLorentzVector(T, const AliFmThreeVector<X>&);   
+
+    template<class X> AliFmLorentzVector(const AliFmLorentzVector<X>&);
+    template<class X> AliFmLorentzVector<T>& operator=(const AliFmLorentzVector<X>&);
+    // AliFmLorentzVector(const AliFmLorentzVector<T>&);                use default
+    // AliFmLorentzVector<T>& operator=(const AliFmLorentzVector<T>&);  use default
+#else
+    AliFmLorentzVector(const AliFmThreeVector<float>&, T);
+    AliFmLorentzVector(T, const AliFmThreeVector<float>&);   
+    AliFmLorentzVector(const AliFmLorentzVector<float>&);
+    
+    AliFmLorentzVector(const AliFmThreeVector<double>&, T);
+    AliFmLorentzVector(T, const AliFmThreeVector<double>&);   
+    AliFmLorentzVector(const AliFmLorentzVector<double>&);
+        
+    AliFmLorentzVector<T>& operator=(const AliFmLorentzVector<float>&);
+    AliFmLorentzVector<T>& operator=(const AliFmLorentzVector<double>&);
+#endif
+    
+    T x()                     const;
+    T y()                     const;
+    T z()                     const;
+    T t()                     const;
+    T px()                    const;
+    T py()                    const;
+    T pz()                    const;
+    T e()                     const;
+    T operator()  (size_t)    const;
+    T operator[]  (size_t)    const;
+    
+    T& operator()  (size_t);
+    T& operator[]  (size_t);
+
+    const AliFmThreeVector<T>& vect() const;    
+    
+    void SetX(T);
+    void SetY(T);
+    void SetZ(T);
+    void SetPx(T);
+    void SetPy(T);
+    void SetPz(T);
+    void SetE(T);
+    void SetT(T);
+    
+#ifndef ST_NO_MEMBER_TEMPLATES
+    template <class X> void SetVect(const AliFmThreeVector<X>&);
+#else
+    void SetVect(const AliFmThreeVector<float>&);
+    void SetVect(const AliFmThreeVector<double>&);
+#endif   
+
+    T Perp()               const;
+    T Perp2()              const;
+    T PseudoRapidity()     const;
+    T Phi()                const;
+    T Theta()              const;
+    T CosTheta()           const;
+    
+    T Plus()               const;
+    T Minus()              const;
+    
+    T m()                  const; 
+    T m2()                 const; 
+    T mt()                 const;
+    T mt2()                const;
+    T Rapidity()           const;
+    
+#ifndef ST_NO_MEMBER_TEMPLATES
+    template<class X> AliFmLorentzVector<T> boost(const AliFmLorentzVector<X>&) const;
+#else
+    AliFmLorentzVector<T> boost(const AliFmLorentzVector<float>&) const;
+    AliFmLorentzVector<T> boost(const AliFmLorentzVector<double>&) const;
+#endif   
+    
+    AliFmLorentzVector<T>  operator- ();
+    AliFmLorentzVector<T>  operator+ ();
+    AliFmLorentzVector<T>& operator*= (double);
+    AliFmLorentzVector<T>& operator/= (double);
+
+#ifndef ST_NO_MEMBER_TEMPLATES
+    template<class X> bool operator == (const AliFmLorentzVector<X>&) const;
+    template<class X> bool operator != (const AliFmLorentzVector<X>&) const;
+    template<class X> AliFmLorentzVector<T>& operator+= (const AliFmLorentzVector<X>&);
+    template<class X> AliFmLorentzVector<T>& operator-= (const AliFmLorentzVector<X>&);
+#else    
+    bool operator == (const AliFmLorentzVector<float>&) const;
+    bool operator != (const AliFmLorentzVector<float>&) const;
+    bool operator == (const AliFmLorentzVector<double>&) const;
+    bool operator != (const AliFmLorentzVector<double>&) const;
+
+    AliFmLorentzVector<T>& operator+= (const AliFmLorentzVector<float>&);
+    AliFmLorentzVector<T>& operator-= (const AliFmLorentzVector<float>&);
+    AliFmLorentzVector<T>& operator+= (const AliFmLorentzVector<double>&);
+    AliFmLorentzVector<T>& operator-= (const AliFmLorentzVector<double>&);
+#endif
+
+protected:
+    AliFmThreeVector<T> fThreeVector; // The spatial three-vector
+    T               fX4;             // The fourth components
+#ifdef __ROOT__
+  ClassDef(AliFmLorentzVector,3)
+#endif
+};
+#ifndef __CINT__
+//
+//        Implementation of member functions
+//
+template<class T>
+AliFmLorentzVector<T>::AliFmLorentzVector(T ax, T ay, T az, T at)
+    : fThreeVector(ax, ay, az), fX4(at) { /* nop */ }
+
+template<class T>
+AliFmLorentzVector<T>::~AliFmLorentzVector() { /* nopt */ }    
+
+template<class T>
+const AliFmThreeVector<T>& AliFmLorentzVector<T>::vect() const 
+{
+    return fThreeVector;
+}
+
+template<class T>
+T AliFmLorentzVector<T>::m2() const
+{
+    return (fX4*fX4 - fThreeVector*fThreeVector);    
+}
+
+template<class T>
+T AliFmLorentzVector<T>::Plus() const { return (e() + pz()); }
+
+template<class T>
+T AliFmLorentzVector<T>::Minus() const { return (e() - pz()); }
+
+template<class T>
+T AliFmLorentzVector<T>::m() const
+{
+    T mass2 = m2();
+    if (mass2 < 0)
+       return -::sqrt(-mass2);
+    else
+       return ::sqrt(mass2);
+}
+
+template<class T>
+T AliFmLorentzVector<T>::mt2() const
+{
+    return this->Perp2() + m2();
+}
+
+template<class T>
+T AliFmLorentzVector<T>::mt() const
+{
+    //
+    // change to more optimal code ?
+    // return e()*e() - pz()*pz();
+    T massPerp2 = mt2();
+    if (massPerp2 < 0)
+       return -::sqrt(-massPerp2);
+    else
+       return ::sqrt(massPerp2);
+}
+
+template<class T>
+void AliFmLorentzVector<T>::SetPx(T ax) {fThreeVector.SetX(ax);}
+
+template<class T>
+void AliFmLorentzVector<T>::SetPy(T ay) {fThreeVector.SetY(ay);}
+
+template<class T>
+void AliFmLorentzVector<T>::SetPz(T az) {fThreeVector.SetZ(az);}
+
+template<class T>
+void AliFmLorentzVector<T>::SetX(T ax) {fThreeVector.SetX(ax);}
+
+template<class T>
+void AliFmLorentzVector<T>::SetY(T ay) {fThreeVector.SetY(ay);}
+
+template<class T>
+void AliFmLorentzVector<T>::SetZ(T az) {fThreeVector.SetZ(az);}
+
+template<class T>
+void AliFmLorentzVector<T>::SetT(T at) {fX4 = at;}
+
+template<class T>
+void AliFmLorentzVector<T>::SetE(T ae) {fX4 = ae;}
+
+template<class T>
+T AliFmLorentzVector<T>::x() const {return fThreeVector.x();}
+
+template<class T>
+T AliFmLorentzVector<T>::y() const {return fThreeVector.y();}
+
+template<class T>
+T AliFmLorentzVector<T>::z() const {return fThreeVector.z();}
+
+template<class T>
+T AliFmLorentzVector<T>::px() const {return fThreeVector.x();}
+
+template<class T>
+T AliFmLorentzVector<T>::py() const {return fThreeVector.y();}
+
+template<class T>
+T AliFmLorentzVector<T>::pz() const {return fThreeVector.z();}
+
+template<class T>
+T AliFmLorentzVector<T>::e() const {return fX4;}
+
+template<class T>
+T AliFmLorentzVector<T>::t() const {return fX4;}
+
+template<class T>
+T AliFmLorentzVector<T>::Perp() const {return fThreeVector.Perp();}
+
+template<class T>
+T AliFmLorentzVector<T>::Perp2() const {return fThreeVector.Perp2();}
+
+template<class T>
+T AliFmLorentzVector<T>::PseudoRapidity() const {return fThreeVector.PseudoRapidity();}
+
+template<class T>
+T AliFmLorentzVector<T>::Phi() const {return fThreeVector.Phi();}
+
+template<class T>
+T AliFmLorentzVector<T>::Theta() const {return fThreeVector.Theta();}
+
+template<class T>
+T AliFmLorentzVector<T>::CosTheta() const {return fThreeVector.CosTheta();}
+
+template<class T>
+T AliFmLorentzVector<T>::operator() (size_t i) const
+{
+    if (i < 3)
+        return fThreeVector(i);
+    else if (i == 3)
+        return fX4;
+    else {
+#ifndef ST_NO_EXCEPTIONS
+      throw out_of_range("AliFmLorentzVector<T>::operator(): bad index");  
+#else
+      cerr << "AliFmLorentzVector<T>::operator(): bad index." << endl;
+#endif
+      return 0;
+    }
+}
+
+template<class T>
+T& AliFmLorentzVector<T>::operator() (size_t i)
+{
+    if (i < 3)
+        return fThreeVector(i);
+    else if (i == 3)
+        return fX4;
+    else {
+#ifndef ST_NO_EXCEPTIONS
+      throw out_of_range("AliFmLorentzVector<T>::operator(): bad index");  
+#else
+      cerr << "AliFmLorentzVector<T>::operator(): bad index." << endl;
+      return fX4;
+#endif
+    }
+}
+
+template<class T>
+T AliFmLorentzVector<T>::operator[] (size_t i) const
+{
+    if (i < 3)
+        return fThreeVector[i];
+    else if (i == 3)
+        return fX4;
+    else {
+#ifndef ST_NO_EXCEPTIONS
+      throw out_of_range("AliFmLorentzVector<T>::operator[]: bad index"); 
+#else
+      cerr << "AliFmLorentzVector<T>::operator[]: bad index." << endl;
+      return 0;
+#endif
+    }
+}
+
+template<class T>
+T& AliFmLorentzVector<T>::operator[] (size_t i)
+{
+    if (i < 3)
+        return fThreeVector[i];
+    else if (i == 3)
+        return fX4;
+    else {
+#ifndef ST_NO_EXCEPTIONS
+      throw out_of_range("AliFmLorentzVector<T>::operator[]: bad index"); 
+#else
+      cerr << "AliFmLorentzVector<T>::operator[]: bad index." << endl;
+      return fX4;
+#endif
+    }
+}
+
+template<class T>
+T AliFmLorentzVector<T>::Rapidity() const
+{
+    return 0.5*::log((fX4+fThreeVector.z())/(fX4-fThreeVector.z())+1e-20);
+}
+
+template<class T>
+AliFmLorentzVector<T> AliFmLorentzVector<T>::operator- ()
+{
+    return AliFmLorentzVector<T>(-fX4,-fThreeVector);
+}
+
+template<class T>
+AliFmLorentzVector<T> AliFmLorentzVector<T>::operator+ ()
+{
+    return *this;
+}
+
+template<class T>
+AliFmLorentzVector<T>& AliFmLorentzVector<T>::operator*= (double c)
+{
+    fThreeVector *= c;
+    fX4 *= c;
+    return *this;
+}
+
+template<class T>
+AliFmLorentzVector<T>& AliFmLorentzVector<T>::operator/= (double c)
+{
+    fThreeVector /= c;
+    fX4 /= c;
+    return *this;
+}
+
+#ifndef ST_NO_MEMBER_TEMPLATES
+#ifndef WIN32
+
+template<class T>
+template<class X>
+AliFmLorentzVector<T>::AliFmLorentzVector(const AliFmThreeVector<X> &vec, T at)
+       : fThreeVector(vec), fX4(at) { /* nop */ }
+
+template<class T>
+template<class X>
+AliFmLorentzVector<T>::AliFmLorentzVector(T at, const AliFmThreeVector<X> &vec)
+       : fThreeVector(vec), fX4(at) { /* nop */ }
+
+template<class T>
+template<class X>
+AliFmLorentzVector<T>::AliFmLorentzVector(const AliFmLorentzVector<X> &vec)
+       : fThreeVector(vec.vect()), fX4(vec.t()) { /* nop */ }
+
+template<class T>
+template<class X>
+AliFmLorentzVector<T>
+AliFmLorentzVector<T>::boost(const AliFmLorentzVector<X>& pframe) const
+{
+    T mass               = abs(pframe);
+    AliFmThreeVector<T> eta = (-1./mass)*pframe.vect();            // gamma*beta
+    T gamma              = fabs(pframe.e())/mass;
+    AliFmThreeVector<T> pl  = ((this->vect()*eta)/(eta*eta))*eta;  // longitudinal momentum
+    return AliFmLorentzVector<T>(gamma*this->e() - this->vect()*eta,
+                              this->vect() + (gamma-1.)*pl - this->e()*eta);
+}
+
+template<class T>
+template<class X>
+void AliFmLorentzVector<T>::SetVect(const AliFmThreeVector<X>& v)
+{
+    fThreeVector = v;
+}
+
+template<class T>
+template<class X>
+AliFmLorentzVector<T>&
+AliFmLorentzVector<T>::operator=(const AliFmLorentzVector<X>& vec)
+{
+    fThreeVector = vec.vect();
+    fX4 = vec.t();
+    return *this;
+}
+
+template<class T>
+template<class X>
+bool
+AliFmLorentzVector<T>::operator== (const AliFmLorentzVector<X>& v) const
+{
+    return (fThreeVector == v.vect()) && (fX4 == v.t());
+}
+
+template<class T>
+template<class X>
+bool
+AliFmLorentzVector<T>::operator!= (const AliFmLorentzVector<X>& v) const
+{
+    return !(*this == v);
+}
+
+template<class T>
+template<class X>
+AliFmLorentzVector<T>&
+AliFmLorentzVector<T>::operator+= (const AliFmLorentzVector<X>& v)
+{
+    fThreeVector += v.vect();
+    fX4 += v.t();
+    return *this;
+}
+
+template<class T>
+template<class X>
+AliFmLorentzVector<T>&
+AliFmLorentzVector<T>::operator-= (const AliFmLorentzVector<X>& v)
+{
+    fThreeVector -= v.vect();
+    fX4 -= v.t();
+    return *this;
+}
+
+#endif 
+#else
+
+template<class T>
+AliFmLorentzVector<T>::AliFmLorentzVector(const AliFmThreeVector<float> &vec, T t)
+       : fThreeVector(vec), fX4(t) { /* nop */ }
+
+template<class T>
+AliFmLorentzVector<T>::AliFmLorentzVector(const AliFmThreeVector<double> &vec, T t)
+       : fThreeVector(vec), fX4(t) { /* nop */ }
+
+template<class T>
+AliFmLorentzVector<T>::AliFmLorentzVector(T t, const AliFmThreeVector<float> &vec)
+       : fThreeVector(vec), fX4(t) { /* nop */ }
+
+template<class T>
+AliFmLorentzVector<T>::AliFmLorentzVector(T t, const AliFmThreeVector<double> &vec)
+       : fThreeVector(vec), fX4(t) { /* nop */ }
+
+template<class T>
+AliFmLorentzVector<T>::AliFmLorentzVector(const AliFmLorentzVector<float> &vec)
+       : fThreeVector(vec.vect()), fX4(vec.t()) { /* nop */ }
+    
+template<class T>
+AliFmLorentzVector<T>::AliFmLorentzVector(const AliFmLorentzVector<double> &vec)
+       : fThreeVector(vec.vect()), fX4(vec.t()) { /* nop */ }
+    
+template<class T>
+AliFmLorentzVector<T>
+AliFmLorentzVector<T>::boost(const AliFmLorentzVector<float>& pframe) const
+{
+    T mass               = abs(pframe);
+    AliFmThreeVector<T> eta = (-1./mass)*pframe.vect();            // gamma*beta
+    T gamma              = fabs(pframe.e())/mass;
+    AliFmThreeVector<T> pl  = ((this->vect()*eta)/(eta*eta))*eta;  // longitudinal momentum
+    return AliFmLorentzVector<T>(gamma*this->e() - this->vect()*eta,
+                              this->vect() + (gamma-1.)*pl - this->e()*eta);
+}
+
+template<class T>
+AliFmLorentzVector<T>
+AliFmLorentzVector<T>::boost(const AliFmLorentzVector<double>& pframe) const
+{
+    T mass               = abs(pframe);
+    AliFmThreeVector<T> eta = (-1./mass)*pframe.vect();            // gamma*beta
+    T gamma              = fabs(pframe.e())/mass;
+    AliFmThreeVector<T> pl  = ((this->vect()*eta)/(eta*eta))*eta;  // longitudinal momentum
+    return AliFmLorentzVector<T>(gamma*this->e() - this->vect()*eta,
+                              this->vect() + (gamma-1.)*pl - this->e()*eta);
+}
+
+template<class T>
+void AliFmLorentzVector<T>::SetVect(const AliFmThreeVector<float>& v)
+{
+    fThreeVector = v;
+}
+
+template<class T>
+void AliFmLorentzVector<T>::SetVect(const AliFmThreeVector<double>& v)
+{
+    fThreeVector = v;
+}
+
+template<class T>
+AliFmLorentzVector<T>&
+AliFmLorentzVector<T>::operator=(const AliFmLorentzVector<float>& vec)
+{
+    fThreeVector = vec.vect();
+    fX4 = vec.t();
+    return *this;
+}
+
+template<class T>
+AliFmLorentzVector<T>&
+AliFmLorentzVector<T>::operator=(const AliFmLorentzVector<double>& vec)
+{
+    fThreeVector = vec.vect();
+    fX4 = vec.t();
+    return *this;
+}
+
+template<class T>
+bool
+AliFmLorentzVector<T>::operator== (const AliFmLorentzVector<float>& v) const
+{
+    return (this->vect() == v.vect()) && (fX4 == v.t());
+}
+
+template<class T>
+bool
+AliFmLorentzVector<T>::operator== (const AliFmLorentzVector<double>& v) const
+{
+    return (fThreeVector == v.vect()) && (fX4 == v.t());
+}
+
+template<class T>
+bool
+AliFmLorentzVector<T>::operator!= (const AliFmLorentzVector<float>& v) const
+{
+    return !(*this == v);
+}
+
+template<class T>
+bool
+AliFmLorentzVector<T>::operator!= (const AliFmLorentzVector<double>& v) const
+{
+    return !(*this == v);
+}
+
+template<class T>
+AliFmLorentzVector<T>&
+AliFmLorentzVector<T>::operator+= (const AliFmLorentzVector<float>& v)
+{
+    fThreeVector += v.vect();
+    fX4 += v.t();
+    return *this;
+}
+
+template<class T>
+AliFmLorentzVector<T>&
+AliFmLorentzVector<T>::operator+= (const AliFmLorentzVector<double>& v)
+{
+    fThreeVector += v.vect();
+    fX4 += v.t();
+    return *this;
+}
+
+template<class T>
+AliFmLorentzVector<T>&
+AliFmLorentzVector<T>::operator-= (const AliFmLorentzVector<float>& v)
+{
+    fThreeVector -= v.vect();
+    fX4 -= v.t();
+    return *this;
+}
+
+template<class T>
+AliFmLorentzVector<T>&
+AliFmLorentzVector<T>::operator-= (const AliFmLorentzVector<double>& v)
+{
+    fThreeVector -= v.vect();
+    fX4 -= v.t();
+    return *this;
+}
+
+#endif // ST_NO_MEMBER_TEMPLATES
+#endif /* ! __CINT__ */
+#ifdef __CINT__
+template<> AliFmLorentzVector<double> operator+ (const AliFmLorentzVector<double>& v1, const AliFmLorentzVector<double>& v2);
+template<> AliFmLorentzVector<double> operator+ (const AliFmLorentzVector<double>& v1, const AliFmLorentzVector<float>& v2);
+template<> AliFmLorentzVector<double> operator+ (const AliFmLorentzVector<float>&  v1, const AliFmLorentzVector<double>& v2);
+template<> AliFmLorentzVector<float>  operator+ (const AliFmLorentzVector<float>&  v1, const AliFmLorentzVector<float>& v2);
+template<> AliFmLorentzVector<double> operator- (const AliFmLorentzVector<double>& v1, const AliFmLorentzVector<double>& v2);
+template<> AliFmLorentzVector<double> operator- (const AliFmLorentzVector<double>& v1, const AliFmLorentzVector<float>& v2);
+template<> AliFmLorentzVector<double> operator- (const AliFmLorentzVector<float>&  v1, const AliFmLorentzVector<double>& v2);
+template<> AliFmLorentzVector<float>  operator- (const AliFmLorentzVector<float>&  v1, const AliFmLorentzVector<float>& v2);
+template<> AliFmLorentzVector<double> operator* (const AliFmLorentzVector<double>& v1, const AliFmLorentzVector<double>& v2);
+template<> AliFmLorentzVector<double> operator* (const AliFmLorentzVector<double>& v1, const AliFmLorentzVector<float>& v2);
+template<> AliFmLorentzVector<double> operator* (const AliFmLorentzVector<float>&  v1, const AliFmLorentzVector<double>& v2);
+template<> AliFmLorentzVector<float>  operator* (const AliFmLorentzVector<float>&  v1, const AliFmLorentzVector<float>& v2);
+template<> AliFmLorentzVector<double> operator* (const              double v1, const AliFmLorentzVector<double>& v2);
+template<> AliFmLorentzVector<double> operator* (const              double v1, const AliFmLorentzVector<float>&  v2);
+template<> AliFmLorentzVector<double> operator* (const AliFmLorentzVector<double>& v1, const double              v2);
+template<> AliFmLorentzVector<double> operator* (const AliFmLorentzVector<float>&  v1, const double              v2);
+template<> AliFmLorentzVector<double> operator/ (const AliFmLorentzVector<double>& v1, const AliFmLorentzVector<double>& v2);
+template<> AliFmLorentzVector<double> operator/ (const AliFmLorentzVector<double>& v1, const AliFmLorentzVector<float>& v2);
+template<> AliFmLorentzVector<double> operator/ (const AliFmLorentzVector<float>&  v1, const AliFmLorentzVector<double>& v2);
+template<> AliFmLorentzVector<float>  operator/ (const AliFmLorentzVector<float>&  v1, const AliFmLorentzVector<float>& v2);
+template<> AliFmLorentzVector<double> operator/ (const              double v1, const AliFmLorentzVector<double>& v2);
+template<> AliFmLorentzVector<double> operator/ (const              double v1, const AliFmLorentzVector<float>&  v2);
+template<> AliFmLorentzVector<double> operator/ (const AliFmLorentzVector<double>& v1, const double              v2);
+template<> AliFmLorentzVector<double> operator/ (const AliFmLorentzVector<float>&  v1, const double              v2);
+template<> istream& operator>> (istream& is, const AliFmLorentzVector<double>& v);
+template<> ostream& operator<< (ostream& os, const AliFmLorentzVector<double>& v);
+template<> istream& operator>> (istream& is, const AliFmLorentzVector<float>& v);
+template<> ostream& operator<< (ostream& os, const AliFmLorentzVector<float>& v);
+template<> double abs(const AliFmLorentzVector<double>& v);
+template<> float  abs(const AliFmLorentzVector<float>& v);
+#else
+//
+//   Non-member operators
+//
+template<class T, class X>
+AliFmLorentzVector<T>
+operator+ (const AliFmLorentzVector<T>& v1, const AliFmLorentzVector<X>& v2)
+{
+    return AliFmLorentzVector<T>(v1) += v2;
+}
+
+template<class T, class X>
+AliFmLorentzVector<T>
+operator- (const AliFmLorentzVector<T>& v1, const AliFmLorentzVector<X>& v2)
+{
+    return AliFmLorentzVector<T>(v1) -= v2;
+}
+
+template<class T, class X>
+T
+operator* (const AliFmLorentzVector<T>& v1, const AliFmLorentzVector<X>& v2)
+{
+    return v1.t()*v2.t() - v1.vect()*v2.vect();
+}
+
+template<class T>
+AliFmLorentzVector<T>
+operator* (const AliFmLorentzVector<T>& v, double c)
+{
+    return AliFmLorentzVector<T>(v) *= c;
+}
+
+template<class T>
+AliFmLorentzVector<T> operator* (double c, const AliFmLorentzVector<T>& v)
+{
+    return AliFmLorentzVector<T>(v) *= c;
+}
+
+template<class T, class X>
+AliFmLorentzVector<T> operator/ (const AliFmLorentzVector<T>& v, X c)
+{
+    return AliFmLorentzVector<T>(v) /= c;
+}
+
+template<class T>
+ostream& operator<< (ostream& os, const AliFmLorentzVector<T>& v)
+{
+    return os << v.vect() << "\t\t" << v.t();
+}
+
+template<class T>
+istream&  operator>>(istream& is, AliFmLorentzVector<T>& v)
+{
+    T  x, y, z, t;
+    is >> x >> y >> z >> t;
+    v.SetX(x);
+    v.SetY(y);
+    v.SetZ(z);
+    v.SetT(t);
+    return is;
+}
+
+//
+//        Non-member functions
+//
+template<class T>
+T abs(const AliFmLorentzVector<T>& v) {return v.m();}
+
+#endif /*  __CINT__ */
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFmLorentzVectorD.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFmLorentzVectorD.h
new file mode 100644 (file)
index 0000000..bbfab85
--- /dev/null
@@ -0,0 +1,22 @@
+/***************************************************************************
+ *
+ * $Id$
+ * $Log$
+ * Revision 1.1.1.1  2007/04/25 15:38:41  panos
+ * Importing the HBT code dir
+ *
+ * Revision 1.1.1.1  2007/03/07 10:14:49  mchojnacki
+ * First version on CVS
+ *
+ * Revision 1.6  2005/07/06 18:49:56  fisyak
+ * Replace AliFemtoHelixD, AliFemtoLorentzVectorD,AliFemtoLorentzVectorF,AliFemtoMatrixD,AliFemtoMatrixF,AliFemtoPhysicalHelixD,AliFemtoThreeVectorD,AliFemtoThreeVectorF by templated version
+ *
+
+****************************************************************************/
+#ifndef ALIFM_LORENTZ_VECTOR_D_HH
+#define ALIFM_LORENTZ_VECTOR_D_HH
+//#include "AliFemtoThreeVectorF.hh"
+#include "AliFmThreeVectorD.h"
+#include "AliFmLorentzVector.h"
+typedef AliFmLorentzVector<double> AliFmLorentzVectorD;
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFmPhysicalHelix.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliFmPhysicalHelix.cxx
new file mode 100644 (file)
index 0000000..8bf8122
--- /dev/null
@@ -0,0 +1,136 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFmHelix: a helper helix class                                      //
+// Includes all the operations and specifications of the helix. Can be   //
+// used to determine path lengths, distance of closest approach etc.     //
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+#include <math.h>
+#include "AliFmHelix.h"
+#include "AliFmPhysicalHelix.h"
+#include "PhysicalConstants.h" 
+#include "SystemOfUnits.h"
+#ifdef __ROOT__
+ClassImpT(AliFmPhysicalHelix,double);
+#endif
+AliFmPhysicalHelix::AliFmPhysicalHelix(){}
+
+AliFmPhysicalHelix::~AliFmPhysicalHelix() { /* nop */ }
+
+AliFmPhysicalHelix::AliFmPhysicalHelix(const AliFmThreeVector<double>& p,
+                                      const AliFmThreeVector<double>& o,
+                                      double B, double q)
+{
+  // Constructor from given parameters
+  fH = (q*B <= 0) ? 1 : -1;
+  if(p.y() == 0 && p.x() == 0)
+    SetPhase((M_PI/4)*(1-2.*fH));
+  else
+    SetPhase(atan2(p.y(),p.x())-fH*M_PI/2);
+  SetDipAngle(atan2(p.z(),p.Perp()));
+  fOrigin = o;
+  
+#ifndef ST_NO_NAMESPACES
+  {
+    using namespace units;
+#endif
+    SetCurvature(fabs((kCLight*nanosecond/meter*q*B/tesla)/
+                     (abs(p.Mag())/GeV*fCosDipAngle)/meter));   
+#ifndef ST_NO_NAMESPACES
+  }
+#endif
+}
+
+AliFmPhysicalHelix::AliFmPhysicalHelix(double c, double d, double phase,
+                                      const AliFmThreeVector<double>& o, int h)
+  : AliFmHelix(c, d, phase, o, h) { /* nop */}
+
+
+AliFmThreeVector<double> AliFmPhysicalHelix::Momentum(double B) const
+{
+  // momentum for given magnetic field
+  if (fSingularity)
+    return(AliFmThreeVector<double>(0,0,0));
+  else {
+#ifndef ST_NO_NAMESPACES
+    {
+           using namespace units;
+#endif
+           double pt = GeV*fabs(kCLight*nanosecond/meter*B/tesla)/(fabs(fCurvature)*meter);
+           
+           return (AliFmThreeVector<double>(pt*cos(fPhase+fH*M_PI/2),   // pos part pos field
+                                         pt*sin(fPhase+fH*M_PI/2),
+                                         pt*tan(fDipAngle)));
+#ifndef ST_NO_NAMESPACES
+       }
+#endif
+    }
+}
+
+AliFmThreeVector<double> AliFmPhysicalHelix::MomentumAt(double S, double B) const
+{
+    // Obtain phase-shifted momentum from phase-shift of origin
+    double xc = this->XCenter();
+    double yc = this->YCenter();
+    double rx = (Y(S)-yc)/(fOrigin.y()-yc);
+    double ry = (X(S)-xc)/(fOrigin.x()-xc);
+    return (this->Momentum(B)).PseudoProduct(rx,ry,1.0);
+}
+
+int AliFmPhysicalHelix::Charge(double B) const
+{
+  // charge
+    return (B > 0 ? -fH : fH);
+}
+
+double AliFmPhysicalHelix::GeometricSignedDistance(double x, double y)  
+{
+    // Geometric signed distance
+    double thePath = this->PathLength(x,y);
+    AliFmThreeVector<double> tDCA2dPosition = this->At(thePath);
+    tDCA2dPosition.SetZ(0);
+    AliFmThreeVector<double> position(x,y,0);
+    AliFmThreeVector<double> tDCAVec = (tDCA2dPosition-position);
+    AliFmThreeVector<double> momVec;
+    // Deal with straight tracks
+    if (this->fSingularity) {
+       momVec = this->At(1)- this->At(0);
+       momVec.SetZ(0);
+    }
+    else {
+       momVec = this->MomentumAt(thePath,1./tesla); // Don't care about Bmag.  Helicity is what matters.
+       momVec.SetZ(0);
+    }
+    
+    double cross = tDCAVec.x()*momVec.y() - tDCAVec.y()*momVec.x();
+    double theSign = (cross>=0) ? 1. : -1.;
+    return theSign*tDCAVec.Perp();
+}
+
+double AliFmPhysicalHelix::CurvatureSignedDistance(double x, double y) 
+{
+    // Protect against fH = 0 or zero field
+    if (this->fSingularity || abs(this->fH)<=0) {
+       return (this->GeometricSignedDistance(x,y));
+    }
+    else {
+       return (this->GeometricSignedDistance(x,y))/(this->fH);
+    }
+    
+}
+
+double AliFmPhysicalHelix::GeometricSignedDistance(const AliFmThreeVector<double>& pos) 
+{
+  // Geometric distance
+    double sdca2d = this->GeometricSignedDistance(pos.x(),pos.y());
+    double theSign = (sdca2d>=0) ? 1. : -1.;
+    return (this->Distance(pos))*theSign;
+}
+
+double AliFmPhysicalHelix::CurvatureSignedDistance(const AliFmThreeVector<double>& pos) 
+{
+  // Distance with the sign dependent on curvature sigm
+    double sdca2d = this->CurvatureSignedDistance(pos.x(),pos.y());
+    double theSign = (sdca2d>=0) ? 1. : -1.;
+    return (this->Distance(pos))*theSign;
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFmPhysicalHelix.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFmPhysicalHelix.h
new file mode 100644 (file)
index 0000000..ae62518
--- /dev/null
@@ -0,0 +1,45 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFmHelix: a helper helix class                                      //
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+#ifndef ALIFMPHYSICALHELIX_H
+#define ALIFMPHYSICALHELIX_H
+
+#include "AliFmThreeVector.h"
+#include "AliFmHelix.h"
+
+class AliFmPhysicalHelix : public AliFmHelix {
+ public:
+  // Requires: momentum, origin, signed Magnetic Field
+  //           and Charge of particle (+/- 1)
+  AliFmPhysicalHelix(const AliFmThreeVector<double>& v1,
+                    const AliFmThreeVector<double>& v2,
+                    double x, double y);
+    
+  // curvature, dip angle, phase, origin, h
+  AliFmPhysicalHelix(double curvature, double dipAngle, double phase,
+                    const AliFmThreeVector<double>& origin, int h=-1);
+  AliFmPhysicalHelix();
+  
+  ~AliFmPhysicalHelix();
+  
+  // Requires:  signed Magnetic Field
+  AliFmThreeVector<double> Momentum(double x) const;     // returns the momentum at origin
+  AliFmThreeVector<double> MomentumAt(double x, double y) const; // returns momemtum at S
+  int                   Charge(double x)   const;     // returns charge of particle
+  // 2d DCA to x,y point signed relative to curvature
+  double CurvatureSignedDistance(double x, double y) ;
+  // 2d DCA to x,y point signed relative to rotation 
+  double GeometricSignedDistance(double x, double y) ;
+  // 3d DCA to 3d point signed relative to curvature
+  double CurvatureSignedDistance(const AliFmThreeVector<double>& v) ;
+  // 3d DCA to 3d point signed relative to rotation
+  double GeometricSignedDistance(const AliFmThreeVector<double>& v) ;
+  
+#ifdef __ROOT__
+  ClassDef(AliFmPhysicalHelix,1)
+#endif
+};
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFmPhysicalHelixD.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFmPhysicalHelixD.h
new file mode 100644 (file)
index 0000000..0b4ae01
--- /dev/null
@@ -0,0 +1,22 @@
+/***************************************************************************
+ *
+ * $Id$
+ * $Log$
+ * Revision 1.1.1.1  2007/04/25 15:38:41  panos
+ * Importing the HBT code dir
+ *
+ * Revision 1.1.1.1  2007/03/07 10:14:49  mchojnacki
+ * First version on CVS
+ *
+ * Revision 1.4  2005/07/06 18:49:57  fisyak
+ * Replace AliFmHelixD, AliFmLorentzVectorD,AliFmLorentzVectorF,AliFmMatrixD,AliFmMatrixF,AliFmPhysicalHelixD,AliFmThreeVectorD,AliFmThreeVectorF by templated version
+ *
+
+****************************************************************************/
+#ifndef ST_PHYSICALHELIX_D_HH
+#define ST_PHYSICALHELIX_D_HH
+#include "AliFmThreeVectorD.h"
+#include "AliFmHelixD.h"
+#include "AliFmPhysicalHelix.h"
+typedef AliFmPhysicalHelix AliFmPhysicalHelixD;
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFmThreeVector.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFmThreeVector.h
new file mode 100644 (file)
index 0000000..810cda9
--- /dev/null
@@ -0,0 +1,858 @@
+/***************************************************************************
+ *
+ * $Id$
+ *
+ * Author: Brian Lasiuk, Thomas Ullrich, April 1998
+ ***************************************************************************
+ *
+ * Description:  
+ *
+ * Remarks:   Since not all compilers support member templates
+ *            we have to specialize the templated member on these
+ *            platforms. If member templates are not supported the
+ *            ST_NO_MEMBER_TEMPLATES flag has to be set. tu.
+ *
+ ***************************************************************************
+ *
+ * $Log$
+ * Revision 1.1.1.1  2007/04/25 15:38:41  panos
+ * Importing the HBT code dir
+ *
+ * Revision 1.1.1.1  2007/03/07 10:14:49  mchojnacki
+ * First version on CVS
+ *
+ * Revision 1.15  2005/09/22 20:09:20  fisyak
+ * Make AliFmLorentzVector persistent
+ *
+ * Revision 1.14  2005/07/19 22:27:11  perev
+ * Cleanup
+ *
+ * Revision 1.13  2005/07/06 18:49:57  fisyak
+ * Replace AliFmHelixD, AliFmLorentzVectorD,AliFmLorentzVectorF,AliFmMatrixD,AliFmMatrixF,AliFmPhysicalHelixD,AliFmThreeVectorD,AliFmThreeVectorF by templated version
+ *
+ * Revision 1.12  2005/03/28 06:03:41  perev
+ * Defence FPE added
+ *
+ * Revision 1.11  2004/12/02 20:07:32  fine
+ * define the valid method for both flavor of AliFmThreeVector
+ *
+ * Revision 1.10  2003/10/30 20:06:46  perev
+ * Check of quality added
+ *
+ * Revision 1.9  2003/09/02 17:59:35  perev
+ * gcc 3.2 updates + WarnOff
+ *
+ * Revision 1.8  2002/06/21 17:47:37  genevb
+ * Added pseudoProduct
+ *
+ * Revision 1.7  2000/01/04 19:56:05  ullrich
+ * Added cpp macro for CINT.
+ *
+ * Revision 1.6  1999/12/21 15:14:31  ullrich
+ * Modified to cope with new compiler version on Sun (CC5.0).
+ *
+ * Revision 1.5  1999/10/15 15:46:54  ullrich
+ * Changed output format in operator<<
+ *
+ * Revision 1.4  1999/06/04 18:00:05  ullrich
+ * Added new constructor which takes C-style array as argument.
+ * New operators operator() and operator[] which can be used
+ * as lvalues.
+ *
+ * Revision 1.3  1999/02/17 11:42:19  ullrich
+ * Removed specialization for 'long double'.
+ *
+ * Revision 1.2  1999/02/14 23:11:48  fisyak
+ * Fixes for Rootcint
+ *
+ * Revision 1.1  1999/01/30 03:59:05  fisyak
+ * Root Version of AliFmarClassLibrary
+ *
+ * Revision 1.1  1999/01/23 00:28:04  ullrich
+ * Initial Revision
+ *
+ **************************************************************************/
+#ifndef ST_THREE_VECTOR_HH
+#define ST_THREE_VECTOR_HH
+#ifdef __ROOT__
+#include "Rtypes.h"
+#endif
+#ifndef __CINT__
+#include <iostream>
+#include <fstream>
+#include <math.h>
+#ifdef GNU_GCC
+#    include <stddef.h>
+#endif
+#if defined (__SUNPRO_CC) && __SUNPRO_CC < 0x500
+#    include <stdcomp.h>
+#endif
+#ifndef ST_NO_EXCEPTIONS
+#    include <stdexcept>
+#    if !defined(ST_NO_NAMESPACES)
+using std::out_of_range;
+#    endif
+#endif
+#endif // __CINT__
+
+#ifdef WIN32
+#include "gcc2vs.h"
+#endif
+
+class TRootIOCtor;//nic nie rozumiem
+using namespace std;
+
+
+template<class T> class AliFmThreeVector {
+public:    
+    AliFmThreeVector(T = 0, T = 0, T = 0);
+  //                     ROOT_VERSION(5,03,01)
+#if ROOT_VERSION_CODE >= 328449
+   AliFmThreeVector(TRootIOCtor*) : mX1(0), mX2(0), mX3(0) {}
+#endif
+    virtual ~AliFmThreeVector();
+
+#ifndef ST_NO_MEMBER_TEMPLATES
+    template<class X> AliFmThreeVector(const AliFmThreeVector<X>&);
+    template<class X> AliFmThreeVector(const X*);  
+    template<class X> AliFmThreeVector<T>& operator=(const AliFmThreeVector<X>&);
+    // AliFmThreeVector(const AliFmThreeVector<T>&);                use default
+    // AliFmThreeVector<T>& operator=(const AliFmThreeVector<T>&);  use default
+#else    
+    AliFmThreeVector(const AliFmThreeVector<float>&);
+    AliFmThreeVector(const AliFmThreeVector<double>&);
+    
+    AliFmThreeVector(const float*); 
+    AliFmThreeVector(const double*);
+    
+    AliFmThreeVector<T>& operator=(const AliFmThreeVector<float>&);
+    AliFmThreeVector<T>& operator=(const AliFmThreeVector<double>&);
+#endif
+    
+    void SetX(T);
+    void SetY(T);
+    void SetZ(T);
+
+    void SetPhi(T);
+    void SetTheta(T);
+    void SetMag(T);
+    void SetMagnitude(T);
+    
+    T   x()                        const;
+    T   y()                        const;
+    T   z()                        const;
+    T   Theta()                    const;
+    T   CosTheta()                 const;
+    T   Phi()                      const;
+    T   Perp()                     const;
+    T   Perp2()                    const;
+    T   Magnitude()                const;
+    T   Mag()                      const;
+    T   Mag2()                     const;
+    T   PseudoRapidity()           const;
+    T   operator() (size_t)        const;
+    T   operator[] (size_t)        const;
+
+    T&  operator() (size_t);
+    T&  operator[] (size_t);
+    
+    T   MassHypothesis(T mass)     const;
+    
+    AliFmThreeVector<T>  unit()       const;
+    AliFmThreeVector<T>  orthogonal() const;
+
+    void  RotateX(T);
+    void  RotateY(T);
+    void  RotateZ(T);
+    
+    AliFmThreeVector<T>  operator- ();
+    AliFmThreeVector<T>  operator+ ();
+    AliFmThreeVector<T>& operator*= (double);
+    AliFmThreeVector<T>& operator/= (double);
+    AliFmThreeVector<T>  PseudoProduct(double,double,double) const;
+#ifndef ST_NO_MEMBER_TEMPLATES
+    template<class X> T                Angle(const AliFmThreeVector<X>&) const;
+    template<class X> AliFmThreeVector<T> Cross(const AliFmThreeVector<X>&) const;
+    template<class X> T                Dot  (const AliFmThreeVector<X>&) const;
+    template<class X> AliFmThreeVector<T> PseudoProduct(const AliFmThreeVector<X>&) const;
+    
+    template<class X> bool operator == (const AliFmThreeVector<X>& v) const;
+    template<class X> bool operator != (const AliFmThreeVector<X>& v) const;
+
+    template<class X> AliFmThreeVector<T>& operator+= (const AliFmThreeVector<X>&);
+    template<class X> AliFmThreeVector<T>& operator-= (const AliFmThreeVector<X>&);
+#else    
+    T                Angle(const AliFmThreeVector<float>&) const;
+    AliFmThreeVector<T> Cross(const AliFmThreeVector<float>&) const;
+    T                Dot  (const AliFmThreeVector<float>&) const;
+    AliFmThreeVector<T> PseudoProduct(const AliFmThreeVector<float>&) const;
+    
+    T                Angle(const AliFmThreeVector<double>&) const;
+    T                Dot  (const AliFmThreeVector<double>&) const;
+    AliFmThreeVector<T> Cross(const AliFmThreeVector<double>&) const;
+    AliFmThreeVector<T> PseudoProduct(const AliFmThreeVector<double>&) const;
+
+    bool operator == (const AliFmThreeVector<float>& v) const;
+    bool operator != (const AliFmThreeVector<float>& v) const;
+    AliFmThreeVector<T>& operator+= (const AliFmThreeVector<float>&);
+    AliFmThreeVector<T>& operator-= (const AliFmThreeVector<float>&);
+    
+    bool operator == (const AliFmThreeVector<double>& v) const;
+    bool operator != (const AliFmThreeVector<double>& v) const;
+    AliFmThreeVector<T>& operator+= (const AliFmThreeVector<double>&);
+    AliFmThreeVector<T>& operator-= (const AliFmThreeVector<double>&);
+#endif
+    int             Valid(double world = 1.e+5) const;
+    int               Bad(double world = 1.e+5) const;
+protected:
+    T    mX1, mX2, mX3;  // Vector components
+#ifdef __ROOT__
+  ClassDef(AliFmThreeVector,3)
+#endif /* __ROOT__ */
+};
+
+#ifndef __CINT__
+//
+//        Implementation of member functions
+//
+template<class T>
+inline AliFmThreeVector<T>::AliFmThreeVector(T ax, T ay, T az)
+    : mX1(ax), mX2(ay), mX3(az) {/* nop */}
+template<class T>
+inline AliFmThreeVector<T>::~AliFmThreeVector() {/* nop */}
+
+template<class T>
+inline void AliFmThreeVector<T>::SetX(T ax) {mX1 = ax;}
+
+template<class T>
+inline void AliFmThreeVector<T>::SetY(T ay) {mX2 = ay;}
+
+template<class T>
+inline void AliFmThreeVector<T>::SetZ(T az) {mX3 = az;}
+
+template<class T>
+void AliFmThreeVector<T>::SetPhi(T aAngle)
+{
+    double  r = Magnitude();
+    double th = Theta();
+    
+    mX1 = r*sin(th)*cos(aAngle);
+    mX2 = r*sin(th)*sin(aAngle);
+}
+
+template <class T>
+void AliFmThreeVector<T>::SetTheta(T aAngle)
+{
+    double r  = Magnitude();
+    double ph = Phi();
+
+    mX1 = r*sin(aAngle)*cos(ph);
+    mX2 = r*sin(aAngle)*sin(ph);
+    mX3 = r*cos(aAngle);
+}
+
+template <class T>
+void AliFmThreeVector<T>::SetMagnitude(T r)
+{
+    double th = Theta();
+    double ph = Phi();
+    
+    mX1 = r*sin(th)*cos(ph);
+    mX2 = r*sin(th)*sin(ph);
+    mX3 = r*cos(th);
+}
+
+template <class T>
+void AliFmThreeVector<T>::SetMag(T amag)
+{
+    SetMagnitude(amag);
+}
+
+template<class T>
+inline T AliFmThreeVector<T>::x() const {return mX1;}
+
+template<class T>
+inline T AliFmThreeVector<T>::y() const {return mX2;}
+
+template<class T>
+inline T AliFmThreeVector<T>::z() const {return mX3;}
+
+template<class T>
+inline T AliFmThreeVector<T>::Theta() const
+{
+  return acos(CosTheta());
+}
+
+template<class T>
+inline T AliFmThreeVector<T>::CosTheta() const
+{
+  return mX3/(Mag()+1e-20);
+}
+
+template<class T>
+inline T AliFmThreeVector<T>::Phi() const
+{
+    return atan2(mX2,mX1);
+}
+
+template<class T>
+inline T AliFmThreeVector<T>::PseudoRapidity() const
+{
+    //
+    // change code to more optimal:
+    // double m = Mag();
+    // return 0.5*::log( (m+z())/(m-z()) );
+    double tmp = tan(Theta()/2.); if (tmp <=0.) return 1e20;
+    return -::log(tmp);
+}
+
+template<class T>
+inline AliFmThreeVector<T> AliFmThreeVector<T>::unit() const
+{
+    double tmp = Mag(); if (tmp<=0.) tmp = 1e-20;
+    return *this/tmp;
+}
+
+template <class T>
+T AliFmThreeVector<T>::MassHypothesis(T mass) const
+{
+    return ::sqrt((*this)*(*this) + mass*mass);
+}
+
+template <class T>
+AliFmThreeVector<T> AliFmThreeVector<T>::orthogonal() const
+{
+    // Direct copy from CLHEP--it is probably better to
+    // use your own dot/cross product code...
+    double ax = (mX1 < 0.0) ? -mX1 : mX1;
+    double ay = (mX2 < 0.0) ? -mX2 : mX2;
+    double az = (mX3 < 0.0) ? -mX3 : mX3;
+    
+    if(ax<ay)
+       return ax < az ? AliFmThreeVector<T>(0,mX3,-mX2) :  AliFmThreeVector<T>(mX2,-mX1,0);
+    else
+       return  mX2 < mX3 ? AliFmThreeVector<T>(-mX3,0,mX1) :  AliFmThreeVector<T>(mX2,-mX1,0);
+}
+
+template <class T>
+void AliFmThreeVector<T>::RotateX(T aAngle)
+{
+    // may in the future make use of the AliFmRotation class!
+    double yPrime = cos(aAngle)*mX2 - sin(aAngle)*mX3;
+    double zPrime = sin(aAngle)*mX2 + cos(aAngle)*mX3;
+
+    mX2 = yPrime;
+    mX3 = zPrime;
+}
+
+template <class T>
+void AliFmThreeVector<T>::RotateY(T aAngle)
+{
+    // may in the future make use of the AliFmRotation class!
+    double zPrime = cos(aAngle)*mX3 - sin(aAngle)*mX1;
+    double xPrime = sin(aAngle)*mX3 + cos(aAngle)*mX1;
+
+    mX1 = xPrime;
+    mX3 = zPrime;
+}
+
+template <class T>
+void AliFmThreeVector<T>::RotateZ(T aAngle)
+{
+    // may in the future make use of the AliFmRotation class!
+    double xPrime = cos(aAngle)*mX1 - sin(aAngle)*mX2;
+    double yPrime = sin(aAngle)*mX1 + cos(aAngle)*mX2;
+
+    mX1 = xPrime;
+    mX2 = yPrime;
+}
+
+template<class T>
+inline T AliFmThreeVector<T>::Perp() const
+{
+    return ::sqrt(mX1*mX1+mX2*mX2);
+}
+
+template<class T>
+inline T AliFmThreeVector<T>::Perp2() const
+{
+    return mX1*mX1+mX2*mX2;
+}
+
+template<class T>
+inline T AliFmThreeVector<T>::Magnitude() const
+{
+    return Mag();
+}
+
+template<class T>
+inline T AliFmThreeVector<T>::Mag() const
+{
+    return ::sqrt(mX1*mX1+mX2*mX2+mX3*mX3);
+}
+
+template<class T>
+inline T AliFmThreeVector<T>::Mag2() const
+{
+    return mX1*mX1+mX2*mX2+mX3*mX3;
+}
+
+template<class T>
+inline T AliFmThreeVector<T>::operator() (size_t i) const
+{
+    if (i <= 2)  return (&mX1)[i];
+#ifndef ST_NO_EXCEPTIONS
+    throw out_of_range("AliFmThreeVector<T>::operator(): bad index");
+#else
+    cerr << "AliFmThreeVector<T>::operator(): bad index" << endl;
+#endif
+    return 0;
+}
+
+template<class T>
+inline T& AliFmThreeVector<T>::operator() (size_t i) 
+{
+    if (i <= 2)  return (&mX1)[i];
+#ifndef ST_NO_EXCEPTIONS
+    throw out_of_range("AliFmThreeVector<T>::operator(): bad index");
+#else
+    cerr << "AliFmThreeVector<T>::operator(): bad index" << endl;
+    return mX1;
+#endif
+}
+
+template<class T>
+inline T AliFmThreeVector<T>::operator[] (size_t i) const
+{
+    if (i <= 2)  return (&mX1)[i];
+#ifndef ST_NO_EXCEPTIONS
+      throw out_of_range("AliFmThreeVector<T>::operator[]: bad index"); 
+#else
+      cerr << "AliFmThreeVector<T>::operator[]: bad index" << endl;
+#endif
+      return 0;
+}
+
+template<class T>
+inline T &AliFmThreeVector<T>::operator[] (size_t i) 
+{
+    if (i <= 2)  return (&mX1)[i];
+#ifndef ST_NO_EXCEPTIONS
+      throw out_of_range("AliFmThreeVector<T>::operator[]: bad index"); 
+#else
+      cerr << "AliFmThreeVector<T>::operator[]: bad index" << endl;
+      return mX1;
+#endif
+}
+
+template<class T>
+inline AliFmThreeVector<T>& AliFmThreeVector<T>::operator*= (double c)
+{
+    mX1 *= c; mX2 *= c; mX3 *= c;
+    return *this;
+}
+
+template<class T>
+inline AliFmThreeVector<T>& AliFmThreeVector<T>::operator/= (double c)
+{
+    mX1 /= c; mX2 /= c; mX3 /= c;
+    return *this;
+}
+
+template<class T>
+inline AliFmThreeVector<T>
+AliFmThreeVector<T>::PseudoProduct(double ax,double ay,double az) const
+{
+    return AliFmThreeVector<T>(mX1*ax,mX2*ay,mX3*az);
+}
+
+template<class T>
+AliFmThreeVector<T> AliFmThreeVector<T>::operator- ()
+{
+    return AliFmThreeVector<T>(-mX1, -mX2, -mX3);
+}
+
+template<class T>
+AliFmThreeVector<T> AliFmThreeVector<T>::operator+ ()
+{
+    return *this;
+}
+
+#ifndef ST_NO_MEMBER_TEMPLATES
+#ifndef WIN32
+
+template<class T>
+template<class X>
+inline AliFmThreeVector<T>::AliFmThreeVector(const AliFmThreeVector<X>& v)
+    : mX1(v.x()), mX2(v.y()), mX3(v.z()) {/* nop */}
+
+template<class T>
+template<class X>
+inline AliFmThreeVector<T>::AliFmThreeVector(const X *a)
+{
+    mX1 = a[0];
+    mX2 = a[1];
+    mX3 = a[2];
+}
+
+template<class T>
+template<class X>
+inline AliFmThreeVector<T>&
+AliFmThreeVector<T>::operator=(const AliFmThreeVector<X>& v)
+{
+    mX1 = v.x();  mX2 = v.y();  mX3 = v.z();
+    return *this;
+}
+
+template<class T>
+template<class X>
+inline bool AliFmThreeVector<T>::operator== (const AliFmThreeVector<X>& v) const
+{
+    return mX1 == v.x() && mX2 == v.y() && mX3 == v.z();
+}
+
+template<class T>
+template<class X>
+inline bool AliFmThreeVector<T>::operator!= (const AliFmThreeVector<X>& v) const
+{
+    return !(*this == v);
+}
+
+template<class T>
+template<class X>
+inline AliFmThreeVector<T>&
+AliFmThreeVector<T>::operator+= (const AliFmThreeVector<X>& v)
+{
+    mX1 += v.x(); mX2 += v.y(); mX3 += v.z();
+    return *this;
+}
+
+template<class T>
+template<class X>
+inline AliFmThreeVector<T>&
+AliFmThreeVector<T>::operator-= (const AliFmThreeVector<X>& v)
+{
+    mX1 -= v.x(); mX2 -= v.y(); mX3 -= v.z();
+    return *this;
+}
+
+template<class T>
+template<class X>
+inline T AliFmThreeVector<T>::Dot(const AliFmThreeVector<X>& v) const
+{
+    return mX1*v.x() + mX2*v.y() + mX3*v.z();
+}
+
+template<class T>
+template<class X>
+inline AliFmThreeVector<T>
+AliFmThreeVector<T>::Cross(const AliFmThreeVector<X>& v) const
+{
+    return AliFmThreeVector<T>(mX2*v.z() - mX3*v.y(),
+                           mX3*v.x() - mX1*v.z(),
+                           mX1*v.y() - mX2*v.x());
+}
+
+template<class T>
+template<class X>
+inline T AliFmThreeVector<T>::Angle(const AliFmThreeVector<X>& vec) const
+{
+    double norm = this->Mag2()*vec.Mag2(); 
+    
+    return norm > 0 ? acos(this->Dot(vec)/(::sqrt(norm))) : 0;
+}
+
+template<class T>
+template<class X>
+inline AliFmThreeVector<T>
+AliFmThreeVector<T>::PseudoProduct(const AliFmThreeVector<X>& v) const
+{
+    return this->PseudoProduct(v.x(),v.y(),v.z());
+}
+
+#endif
+#else
+
+template<class T>
+inline AliFmThreeVector<T>::AliFmThreeVector(const AliFmThreeVector<float>& v)
+    : mX1(v.x()), mX2(v.y()), mX3(v.z()) {/* nop */}
+
+template<class T>
+inline AliFmThreeVector<T>::AliFmThreeVector(const AliFmThreeVector<double>& v)
+    : mX1(v.x()), mX2(v.y()), mX3(v.z()) {/* nop */}
+
+template<class T>
+inline AliFmThreeVector<T>::AliFmThreeVector(const float *a)
+{
+    mX1 = a[0];
+    mX2 = a[1];
+    mX3 = a[2];
+}
+
+template<class T>
+inline AliFmThreeVector<T>::AliFmThreeVector(const double *a)
+{
+    mX1 = a[0];
+    mX2 = a[1];
+    mX3 = a[2];
+}
+
+template<class T>
+inline AliFmThreeVector<T>&
+AliFmThreeVector<T>::operator=(const AliFmThreeVector<float>& v)
+{
+    mX1 = v.x();  mX2 = v.y();  mX3 = v.z();
+    return *this;
+}
+
+template<class T>
+inline AliFmThreeVector<T>&
+AliFmThreeVector<T>::operator=(const AliFmThreeVector<double>& v)
+{
+    mX1 = v.x();  mX2 = v.y();  mX3 = v.z();
+    return *this;
+}
+
+template<class T>
+inline bool
+AliFmThreeVector<T>::operator== (const AliFmThreeVector<float>& v) const
+{
+    return mX1 == v.x() && mX2 == v.y() && mX3 == v.z();
+}
+
+template<class T>
+inline bool
+AliFmThreeVector<T>::operator== (const AliFmThreeVector<double>& v) const
+{
+    return mX1 == v.x() && mX2 == v.y() && mX3 == v.z();
+}
+
+template<class T>
+inline bool
+AliFmThreeVector<T>::operator!= (const AliFmThreeVector<float>& v) const
+{
+    return !(*this == v);
+}
+
+template<class T>
+inline bool
+AliFmThreeVector<T>::operator!= (const AliFmThreeVector<double>& v) const
+{
+    return !(*this == v);
+}
+
+template<class T>
+inline AliFmThreeVector<T>&
+AliFmThreeVector<T>::operator+= (const AliFmThreeVector<float>& v)
+{
+    mX1 += v.x(); mX2 += v.y(); mX3 += v.z();
+    return *this;
+}
+
+template<class T>
+inline AliFmThreeVector<T>&
+AliFmThreeVector<T>::operator+= (const AliFmThreeVector<double>& v)
+{
+    mX1 += v.x(); mX2 += v.y(); mX3 += v.z();
+    return *this;
+}
+
+template<class T>
+inline AliFmThreeVector<T>&
+AliFmThreeVector<T>::operator-= (const AliFmThreeVector<float>& v)
+{
+    mX1 -= v.x(); mX2 -= v.y(); mX3 -= v.z();
+    return *this;
+}
+
+template<class T>
+inline AliFmThreeVector<T>&
+AliFmThreeVector<T>::operator-= (const AliFmThreeVector<double>& v)
+{
+    mX1 -= v.x(); mX2 -= v.y(); mX3 -= v.z();
+    return *this;
+}
+
+template<class T>
+inline T AliFmThreeVector<T>::Dot(const AliFmThreeVector<float>& v) const
+{
+    return mX1*v.x() + mX2*v.y() + mX3*v.z();
+}
+
+template<class T>
+inline T AliFmThreeVector<T>::Dot(const AliFmThreeVector<double>& v) const
+{
+    return mX1*v.x() + mX2*v.y() + mX3*v.z();
+}
+
+template<class T>
+inline AliFmThreeVector<T>
+AliFmThreeVector<T>::Cross(const AliFmThreeVector<float>& v) const
+{
+    return AliFmThreeVector<T>(mX2*v.z() - mX3*v.y(),
+                           mX3*v.x() - mX1*v.z(),
+                           mX1*v.y() - mX2*v.x());
+}
+
+template<class T>
+inline AliFmThreeVector<T>
+AliFmThreeVector<T>::Cross(const AliFmThreeVector<double>& v) const
+{
+    return AliFmThreeVector<T>(mX2*v.z() - mX3*v.y(),
+                           mX3*v.x() - mX1*v.z(),
+                           mX1*v.y() - mX2*v.x());
+}
+
+template<class T>
+inline T AliFmThreeVector<T>::Angle(const AliFmThreeVector<float>& v) const
+{
+    double tmp = Mag()*v.Mag(); if (tmp <=0) tmp = 1e-20;
+    return acos(this->Dot(v)/tmp);
+}
+
+template<class T>
+inline T AliFmThreeVector<T>::Angle(const AliFmThreeVector<double>& v) const
+{
+    double tmp = Mag()*v.Mag(); if (tmp <=0) tmp = 1e-20;
+    return acos(this->Dot(v)/tmp);
+}
+
+template<class T>
+inline AliFmThreeVector<T>
+AliFmThreeVector<T>::PseudoProduct(const AliFmThreeVector<float>& v) const
+{
+    return this->PseudoProduct(v.x(),v.y(),v.z());
+}
+
+template<class T>
+inline AliFmThreeVector<T>
+AliFmThreeVector<T>::PseudoProduct(const AliFmThreeVector<double>& v) const
+{
+    return this->PseudoProduct(v.x(),v.y(),v.z());
+}
+#endif  // ST_NO_MEMBER_TEMPLATES
+template<class T>
+inline int
+AliFmThreeVector<T>::Valid(double world) const  {return !Bad(world);}
+
+template<class T>
+inline int
+AliFmThreeVector<T>::Bad(double world) const
+{
+  for (int i=0;i<3;i++) {
+          if (!isfinite((&mX1)[i])      ) return 10+i;                 
+         if ( fabs  ((&mX1)[i])>world) return 20+i;            
+  }            
+  return 0;            
+}
+#endif /*! __CINT__ */
+#ifdef __CINT__
+template<> float abs(const AliFmThreeVector<float>& v);
+template<> double abs(const AliFmThreeVector<double>& v);
+template<> AliFmThreeVector<double> cross_product(const AliFmThreeVector<double>& v1, const AliFmThreeVector<double>& v2);
+template<> AliFmThreeVector<float>  cross_product(const AliFmThreeVector<float>&  v1, const AliFmThreeVector<float>& v2);
+template<> AliFmThreeVector<double> cross_product(const AliFmThreeVector<float>&  v1, const AliFmThreeVector<double>& v2);
+template<> AliFmThreeVector<double> cross_product(const AliFmThreeVector<double>& v1, const AliFmThreeVector<float>& v2);
+template<> AliFmThreeVector<double> operator+ (const AliFmThreeVector<double>& v1, const AliFmThreeVector<double>& v2);
+template<> AliFmThreeVector<float>  operator+ (const AliFmThreeVector<float>&  v1, const AliFmThreeVector<float>& v2);
+template<> AliFmThreeVector<double> operator+ (const AliFmThreeVector<double>& v1, const AliFmThreeVector<float>& v2);
+template<> AliFmThreeVector<double> operator+ (const AliFmThreeVector<float>&  v1, const AliFmThreeVector<double>& v2);
+template<> AliFmThreeVector<double> operator- (const AliFmThreeVector<double>& v1, const AliFmThreeVector<double>& v2);
+template<> AliFmThreeVector<float>  operator- (const AliFmThreeVector<float>&  v1, const AliFmThreeVector<float>& v2);
+template<> AliFmThreeVector<double> operator- (const AliFmThreeVector<double>& v1, const AliFmThreeVector<float>& v2);
+template<> AliFmThreeVector<double> operator- (const AliFmThreeVector<float>&  v1, const AliFmThreeVector<double>& v2);
+template<> AliFmThreeVector<double> operator* (const AliFmThreeVector<double>& v1, const AliFmThreeVector<double>& v2);
+template<> AliFmThreeVector<float>  operator* (const AliFmThreeVector<float>&  v1, const AliFmThreeVector<float>& v2);
+template<> AliFmThreeVector<double> operator* (const AliFmThreeVector<double>& v1, const AliFmThreeVector<float>& v2);
+template<> AliFmThreeVector<double> operator* (const AliFmThreeVector<float>&  v1, const AliFmThreeVector<double>& v2);
+template<> AliFmThreeVector<double> operator* (const double                 v1, const AliFmThreeVector<float>& v2);
+template<> AliFmThreeVector<double> operator* (const AliFmThreeVector<float>&  v1, const double v2);
+template<> AliFmThreeVector<double> operator* (const double                 v1, const AliFmThreeVector<double>& v2);
+template<> AliFmThreeVector<double> operator* (const AliFmThreeVector<double>& v1, const double v2);
+template<> AliFmThreeVector<double> operator/ (const AliFmThreeVector<double>& v1, const AliFmThreeVector<double>& v2);
+template<> AliFmThreeVector<float>  operator/ (const AliFmThreeVector<float>&  v1, const AliFmThreeVector<float>& v2);
+template<> AliFmThreeVector<double> operator/ (const AliFmThreeVector<double>& v1, const AliFmThreeVector<float>& v2);
+template<> AliFmThreeVector<double> operator/ (const AliFmThreeVector<float>&  v1, const AliFmThreeVector<double>& v2);
+template<> AliFmThreeVector<double> operator/ (const                double  v1, const AliFmThreeVector<double>& v2);
+template<> AliFmThreeVector<float>  operator/ (const                double  v1, const AliFmThreeVector<float>& v2);
+template<> AliFmThreeVector<double> operator/ (const AliFmThreeVector<double>& v1, const double v2);
+template<> AliFmThreeVector<double> operator/ (const AliFmThreeVector<float>&  v1, const double v2);
+template<> istream&  operator>>(istream& is,const AliFmThreeVector<double>& v);
+template<> istream&  operator>>(istream& is,const AliFmThreeVector<float>& v);
+template<> ostream&  operator<<(ostream& os,const AliFmThreeVector<double>& v);
+template<> ostream&  operator<<(ostream& os,const AliFmThreeVector<float>& v);
+#else
+//
+//        Non-member functions
+//
+template<class T>
+inline T abs(const AliFmThreeVector<T>& v) {return v.Mag();}
+
+template<class T, class X>
+inline AliFmThreeVector<T>
+cross_product(const AliFmThreeVector<T>& v1, const AliFmThreeVector<X>& v2)
+{
+    return v1.Cross(v2);
+}
+
+
+//
+//        Non-member operators
+//
+template<class T, class X>
+inline AliFmThreeVector<T>
+operator+ (const AliFmThreeVector<T>& v1, const AliFmThreeVector<X>& v2)
+{
+    return AliFmThreeVector<T>(v1) += v2;
+}
+
+template<class T, class X>
+inline AliFmThreeVector<T>
+operator- (const AliFmThreeVector<T>& v1, const AliFmThreeVector<X>& v2)
+{
+    return AliFmThreeVector<T>(v1) -= v2;
+}
+
+template<class T, class X>
+inline T operator* (const AliFmThreeVector<T>& v1, const AliFmThreeVector<X>& v2)
+{
+    return AliFmThreeVector<T>(v1).Dot(v2);
+}
+
+template<class T>
+inline AliFmThreeVector<T> operator* (const AliFmThreeVector<T>& v, double c)
+{
+    return AliFmThreeVector<T>(v) *= c;
+}
+
+template<class T>
+inline AliFmThreeVector<T> operator* (double c, const AliFmThreeVector<T>& v)
+{
+    return AliFmThreeVector<T>(v) *= c;
+}
+
+template<class T, class X>
+inline AliFmThreeVector<T> operator/ (const AliFmThreeVector<T>& v, X c)
+{
+    return AliFmThreeVector<T>(v) /= c;
+}
+
+template<class T>
+ostream&  operator<<(ostream& os, const AliFmThreeVector<T>& v)
+{
+    return os << v.x() << '\t' << v.y() << '\t' << v.z();
+}
+
+template<class T>
+istream&  operator>>(istream& is, AliFmThreeVector<T>& v)
+{
+    T  x, y, z;
+    is >> x >> y >> z;
+    v.SetX(x);
+    v.SetY(y);
+    v.SetZ(z);
+    return is;
+}
+#endif /* ! __CINT__ */
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFmThreeVectorD.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFmThreeVectorD.h
new file mode 100644 (file)
index 0000000..b230a23
--- /dev/null
@@ -0,0 +1,20 @@
+/***************************************************************************
+ *
+ * $Id$
+ * $Log$
+ * Revision 1.1.1.1  2007/04/25 15:38:41  panos
+ * Importing the HBT code dir
+ *
+ * Revision 1.1.1.1  2007/03/07 10:14:49  mchojnacki
+ * First version on CVS
+ *
+ * Revision 1.11  2005/07/06 18:49:57  fisyak
+ * Replace AliFemtoHelixD, AliFemtoLorentzVectorD,AliFemtoLorentzVectorF,AliFemtoMatrixD,AliFemtoMatrixF,AliFemtoPhysicalHelixD,AliFemtoThreeVectorD,AliFemtoThreeVectorF by templated version
+ *
+
+****************************************************************************/
+#ifndef ALIFM_THREE_VECTOR_D_HH
+#define ALIFM_THREE_VECTOR_D_HH
+#include "AliFmThreeVector.h"
+typedef AliFmThreeVector<double> AliFmThreeVectorD;
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliFmThreeVectorF.h b/PWGCF/FEMTOSCOPY/AliFemto/AliFmThreeVectorF.h
new file mode 100644 (file)
index 0000000..57bd517
--- /dev/null
@@ -0,0 +1,30 @@
+/***************************************************************************
+ *
+ * $Id$
+ *
+ * Author: Thomas Ullrich, Jan 1999
+ ***************************************************************************
+ *
+ * Description:  
+ *
+ * Remarks:   This is a 'handmade' specialisation of AliFmThreeVector<T>
+ *            for T=float. This code contains no templates.
+ *
+ ***************************************************************************
+ *
+ * $Log$
+ * Revision 1.1.1.1  2007/04/25 15:38:41  panos
+ * Importing the HBT code dir
+ *
+ * Revision 1.1.1.1  2007/03/07 10:14:49  mchojnacki
+ * First version on CVS
+ *
+ * Revision 1.14  2005/07/06 18:49:57  fisyak
+ * Replace AliFmHelixD, AliFmLorentzVectorD,AliFmLorentzVectorF,AliFmMatrixD,AliFmMatrixF,AliFmPhysicalHelixD,AliFmThreeVectorD,AliFmThreeVectorF by templated version
+ *
+ ****************************************************************************/
+#ifndef ST_THREE_VECTOR_F_HH
+#define ST_THREE_VECTOR_F_HH
+#include "AliFmThreeVector.h"
+typedef  AliFmThreeVector<float> AliFmThreeVectorF;
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliTwoTrackRes.cxx b/PWGCF/FEMTOSCOPY/AliFemto/AliTwoTrackRes.cxx
new file mode 100644 (file)
index 0000000..bedca68
--- /dev/null
@@ -0,0 +1,359 @@
+////////////////////////////////////////////////////////////////////////////////
+//345678901234567890123456789012345678901234567890123456789012345678901234567890
+//       1         2         3         4         5         6         7         8
+//
+// Tool to study two-track effects in ALICE for femtoscopic analyses
+// J. Mercado <mercado@physi.uni-heidelberg.de> Last modified: 20.01.2011
+//
+////////////////////////////////////////////////////////////////////////////////
+
+#include "AliTwoTrackRes.h"
+#include <iostream>
+#include <fstream>
+#include "TMath.h"
+#include "TROOT.h"
+#include "TFile.h"
+#include "TChain.h"
+#include "TLeaf.h"
+#include "TNtuple.h"
+#include "TRandom2.h"
+
+ClassImp(AliTwoTrackRes)
+
+//______________________________________________________________________________
+// Constructor(s)
+
+AliTwoTrackRes::AliTwoTrackRes(const char *name) : 
+  AliAnalysisTask(name,""), fChain(0), fESDEvent(0), 
+  fOutContainer(0), fTrackCuts(0), fNTuple1(0), 
+  fNTuple2(0), fP1(), fP2(), fPb1(), fPb2(), fP(), fQ(), fTpcEnt1(), fTpcEnt2(), 
+  fTpcDist(), fOutFilename()
+{
+  DefineInput(0, TChain::Class());     // Slot input 0 reads from a TChain  
+  DefineOutput(0, TObjArray::Class()); // Slot output 0 writes into a TObjArray
+}
+
+AliTwoTrackRes::AliTwoTrackRes(const AliTwoTrackRes& aTwoTrackRes) : 
+  AliAnalysisTask(aTwoTrackRes), fChain(0), fESDEvent(0), fOutContainer(0), 
+  fTrackCuts(0), fNTuple1(0), fNTuple2(0), fP1(), fP2(), fPb1(), fPb2(), fP(), 
+  fQ(), fTpcEnt1(), fTpcEnt2(), fTpcDist(), fOutFilename()
+{
+  //Copy constructor
+  fChain = aTwoTrackRes.fChain;
+  fESDEvent = aTwoTrackRes.fESDEvent;
+  fOutContainer = aTwoTrackRes.fOutContainer;
+  fTrackCuts = aTwoTrackRes.fTrackCuts;
+  fNTuple1 = aTwoTrackRes.fNTuple1;
+  fNTuple2 = aTwoTrackRes.fNTuple2;
+  fP1 = aTwoTrackRes.fP1;
+  fP2 = aTwoTrackRes.fP2;
+  fPb1 = aTwoTrackRes.fPb1;
+  fPb2 = aTwoTrackRes.fPb2;
+  fP = aTwoTrackRes.fP;
+  fQ = aTwoTrackRes.fQ;
+  fTpcEnt1 = aTwoTrackRes.fTpcEnt1;
+  fTpcEnt2 = aTwoTrackRes.fTpcEnt2;
+  fTpcDist = aTwoTrackRes.fTpcDist;
+  fOutFilename = aTwoTrackRes.fOutFilename;
+}
+
+AliTwoTrackRes& AliTwoTrackRes::operator=(const AliTwoTrackRes& aTwoTrackRes)
+{
+  // Assignment operator
+  if (this == &aTwoTrackRes)
+    return *this;
+  fChain = aTwoTrackRes.fChain;
+  fESDEvent = aTwoTrackRes.fESDEvent;
+  fOutContainer = aTwoTrackRes.fOutContainer;
+  fTrackCuts = aTwoTrackRes.fTrackCuts;
+  fNTuple1 = aTwoTrackRes.fNTuple1;
+  fNTuple2 = aTwoTrackRes.fNTuple2;
+  fP1 = aTwoTrackRes.fP1;
+  fP2 = aTwoTrackRes.fP2;
+  fPb1 = aTwoTrackRes.fPb1;
+  fPb2 = aTwoTrackRes.fPb2;
+  fP = aTwoTrackRes.fP;
+  fQ = aTwoTrackRes.fQ;
+  fTpcEnt1 = aTwoTrackRes.fTpcEnt1;
+  fTpcEnt2 = aTwoTrackRes.fTpcEnt2;
+  fTpcDist = aTwoTrackRes.fTpcDist;
+  fOutFilename = aTwoTrackRes.fOutFilename;
+  return *this;
+}
+
+AliTwoTrackRes::~AliTwoTrackRes() {printf("AliTwoTrackRes destroyed\n");}
+
+void AliTwoTrackRes::ConnectInputData(Option_t *) {  
+//______________________________________________________________________________
+// Connect input data and initialize track cuts
+
+  fChain = (TChain*)GetInputData(0);
+  fESDEvent = new AliESDEvent();
+  fESDEvent->ReadFromTree(fChain);
+
+  // Cuts to select primary tracks (ITS+TPC)
+  fTrackCuts = new AliESDtrackCuts("AliESDtrackCuts");
+  Double_t cov1, cov2, cov3, cov4, cov5; // diagonal cov. matrix elements
+  Double_t nSigma;                       // max. DCA to primary vertex
+  Int_t minNClustersTPC;                 // min. number of clusters per TPC tracks
+  Double_t maxChi2PerClusterTPC;         // max. chi2 per cluster per TPC track  
+  Int_t cutMode = 1;                     // select cut mode
+  if (cutMode == 1) {
+  cov1 = 2; cov2 = 2; cov3 = 0.5; cov4 = 0.5; cov5 = 2;
+  nSigma = 3; minNClustersTPC = 75; maxChi2PerClusterTPC = 3.5;
+  fTrackCuts->SetMaxCovDiagonalElements(cov1, cov2, cov3, cov4, cov5);
+  fTrackCuts->SetMaxNsigmaToVertex(nSigma);
+  fTrackCuts->SetRequireSigmaToVertex(kTRUE);
+  fTrackCuts->SetRequireTPCRefit(kTRUE);
+  fTrackCuts->SetAcceptKinkDaughters(kFALSE);
+  fTrackCuts->SetMinNClustersTPC(minNClustersTPC);
+  fTrackCuts->SetMaxChi2PerClusterTPC(maxChi2PerClusterTPC);  
+  TString tag("Global tracking");}
+}
+
+void AliTwoTrackRes::CreateOutputObjects() {
+//______________________________________________________________________________
+// Create output objects 
+
+  fNTuple1 = new TNtuple("nt1","True pairs",
+  "pt1:eta1:phi1:nsh1:pt2:eta2:phi2:nsh2:qinv:mindist:dist:corr:qfac");
+  fNTuple2 = new TNtuple("nt2","Mixed pairs",
+  "pt1:eta1:phi1:nsh1:pt2:eta2:phi2:nsh2:qinv:mindist:dist:corr:qfac");
+  Int_t c = 0;
+  fOutContainer = new TObjArray(2);
+  fOutContainer->AddAt(fNTuple1, c++);
+  fOutContainer->AddAt(fNTuple2, c++);
+}
+
+void AliTwoTrackRes::Exec(Option_t *) {
+//______________________________________________________________________________
+// Create true and mixed pairs keeping some track parameters
+
+  double bfield = 5.0;
+  static int nr=0;
+  if (nr == 0) printf("\tStarting event loop...\n");
+  printf("\rProcessing event %8d", nr);
+  Double_t mpi = 0.13957; // [GeV/c^2]
+  Double_t pidTrk1[AliPID::kSPECIES], pidTrk2[AliPID::kSPECIES];
+  Int_t tpcIn = 80;   // [cm]
+  Int_t tpcOut = 250; // [cm]
+  Double_t tdist[170];
+  Double_t tdistrot[170];
+  Double_t tpcEnt1[3], tpcEnt2[3], pos1[3];
+  TVector3 x1, x2, diff;
+  TBits clu1, clu2, sha1, sha2;
+  TRandom2 rnd;
+  Int_t  ntracks = fESDEvent->GetNumberOfTracks();
+  for(Int_t itrack = 0; itrack < ntracks; itrack++) {
+    AliESDtrack *track1 = fESDEvent->GetTrack(itrack);
+    AliExternalTrackParam *trp1 = const_cast<AliExternalTrackParam*> 
+      (track1->GetTPCInnerParam());
+    if (!trp1) continue;
+    if (!track1->IsOn(AliESDtrack::kTPCpid)) continue;
+    track1->GetTPCpid(pidTrk1);
+    Int_t q1 = trp1->Charge();
+    if (!((fTrackCuts->AcceptTrack(track1)) && (q1 == 1) &&
+         (pidTrk1[AliPID::kPion]+pidTrk1[AliPID::kMuon] > 0.5))) continue;
+    if (!track1->GetInnerXYZ(tpcEnt1)) continue;
+    clu1 = track1->GetTPCClusterMap();
+    sha1 = track1->GetTPCSharedMap();
+    SetTr1(track1->Pt(), track1->Eta(), track1->Phi(), mpi);
+    SetTpcEnt1(tpcEnt1[0], tpcEnt1[1], tpcEnt1[2]);
+    for(Int_t jtrack = 0; jtrack < itrack; jtrack++) {
+      AliESDtrack *track2 = fESDEvent->GetTrack(jtrack);
+      AliExternalTrackParam *trp2 = const_cast<AliExternalTrackParam*> 
+       (track2->GetTPCInnerParam());
+      if (!trp2) continue;
+      if (!track2->IsOn(AliESDtrack::kTPCpid)) continue;
+      track2->GetTPCpid(pidTrk2);
+      Int_t q2 = trp2->Charge();
+      if (!((fTrackCuts->AcceptTrack(track2)) && (q2 == 1) &&
+           (pidTrk2[AliPID::kPion]+pidTrk2[AliPID::kMuon] > 0.5))) continue;
+      if (!track2->GetInnerXYZ(tpcEnt2)) continue;
+      clu2 = track2->GetTPCClusterMap();
+      sha2 = track2->GetTPCSharedMap();
+      SetTr2(track2->Pt(), track2->Eta(), track2->Phi(), mpi);
+      SetTpcEnt2(tpcEnt2[0], tpcEnt2[1], tpcEnt2[2]);
+      for (Int_t i = tpcIn; i < tpcOut; i++) { // Minimum distance 
+       trp1->GetDistance(trp2, (double) i, pos1, bfield);
+       x1.SetXYZ(pos1[0], pos1[1], pos1[2]);
+       tdist[i-tpcIn] = x1.Mag();
+       x1.SetXYZ(-pos1[0], -pos1[1], pos1[2]);
+       tdistrot[i-tpcIn] = x1.Mag();
+      }
+      Double_t mindist = 100000;
+      Int_t jmin=0;
+      for (Int_t j = 0; j < tpcOut-tpcIn; j++) {
+       if (tdist[j] < mindist) {jmin=j;  mindist = tdist[j]; }
+      }
+      //      Double_t mindist = MinDist(track1, track2);
+      Double_t dist = Dist();
+      Double_t dphi = DPhi();
+      Double_t deta = DEta();
+      Int_t    nsh1 = GetNSha(clu1, sha1);
+      Int_t    nsh2 = GetNSha(clu2, sha2);
+      Double_t corr = Corr(clu1, clu2, sha1, sha2);
+      Double_t qfac = Qfac(clu1, clu2, sha1, sha2);
+      if ((TMath::Abs(track1->Eta())>0.8)&&(TMath::Abs(track2->Eta())>0.8)) continue;
+      if ((TMath::Abs(dphi)<0.35)&&(deta<0.35)) {
+      FillNTuple1(mindist,dist,corr,qfac,nsh1,nsh2);}    // True
+      Double_t tr2rot = RotTr2Phi();                // Rotate trck2
+      SetTr2(track2->Pt(), track2->Eta(), tr2rot, mpi);
+      tpcEnt2[0] = -tpcEnt2[0];
+      tpcEnt2[1] = -tpcEnt2[1];
+      Double_t distrot = Dist();
+      Double_t dphirot = DPhi();
+      Double_t mindistrot = 100000;
+      jmin=0;
+      for (Int_t j = 0; j < tpcOut-tpcIn; j++) {
+       if (tdistrot[j] < mindistrot) {jmin=j;  mindistrot = tdistrot[j]; }
+      }
+      if ((TMath::Abs(dphirot)<0.35)&&(deta<0.35)) {
+       if (rnd.Rndm() < 0.5) NoSwap();
+       else Swap(); 
+       FillNTuple2(mindistrot,distrot,corr,qfac,nsh1,nsh2);} // Mixed
+    }
+  }
+  PostData(0, fOutContainer);
+  nr++;
+}
+
+void AliTwoTrackRes::Terminate(Option_t *) {
+//______________________________________________________________________________
+// Write output and clean up
+
+  fOutContainer = (TObjArray*)GetOutputData(0);
+  TFile *f1  = new TFile( fOutFilename, "RECREATE" );
+  fOutContainer->Write();
+  f1->Flush();
+  f1->Close();
+  delete f1;
+  delete fChain;
+  delete fNTuple1;
+  delete fNTuple2;
+  printf("\n");
+}
+
+//______________________________________________________________________________
+// Miscellaneous methods
+
+// Set tracks 
+void AliTwoTrackRes::SetTr1(double pt1, double eta1, double phi1, double m) {
+  fP1.SetPtEtaPhiM(pt1, eta1, phi1, m);}
+void AliTwoTrackRes::SetTr2(double pt2, double eta2, double phi2, double m) {
+  fP2.SetPtEtaPhiM(pt2, eta2, phi2, m);}
+
+// Set nominal TPC entrance coordinates
+void AliTwoTrackRes::SetTpcEnt1(double x1, double y1, double z1) {
+  fTpcEnt1.SetX(x1); fTpcEnt1.SetY(y1); fTpcEnt1.SetZ(z1);}
+void AliTwoTrackRes::SetTpcEnt2(double x2, double y2, double z2) {
+  fTpcEnt2.SetX(x2); fTpcEnt2.SetY(y2); fTpcEnt2.SetZ(z2);}
+
+double AliTwoTrackRes::MinDist(AliExternalTrackParam *trk1,
+                              AliExternalTrackParam *trk2) {
+// Calculate minimum track separation within the TPC
+
+  int tpcIn = 0;   // [cm]
+  int tpcOut = 170; // [cm]
+  double tdist[170], pos[3];
+  TVector3 x;
+  for (int i = tpcIn; i < tpcOut; i++) {
+    trk1->GetDistance(trk2, i, pos, 5000);
+    x.SetXYZ(pos[0], pos[1], pos[2]);
+    tdist[i-tpcIn] = x.Mag();
+  }
+  double maxdist = 0.0;
+  for (int j = 0; j < tpcOut-tpcIn; j++) {
+    if (tdist[j] > maxdist) { maxdist = tdist[j]; }
+  }
+  double mindist = maxdist;
+  for (int j = 0; j < tpcOut-tpcIn; j++) {
+    if (tdist[j] < mindist) { mindist = tdist[j]; }
+  }
+  return mindist;}
+
+int AliTwoTrackRes::GetNSha(TBits cl, TBits sh) {
+// Get number of shared clusters
+
+  int ncl = cl.GetNbits();
+  int sum = 0; 
+  for(int i = 0; i < ncl; i++) {
+    if (!cl.TestBitNumber(i)) continue;
+    int n = sh.TestBitNumber(i);
+    sum += n;}
+  return sum;}
+
+double AliTwoTrackRes::Corr(TBits cl1,  TBits cl2, TBits sh1, TBits sh2) {
+// Calculate correlation coefficient
+
+  int ncl1 = cl1.GetNbits();
+  int ncl2 = cl2.GetNbits();
+  double sumN = 0;  double sumX = 0;  double sumY = 0;
+  double sumXX = 0; double sumYY = 0; double sumXY = 0; double corr = -2.0;
+  for(int i = 0; i < ncl1 && i < ncl2; i++) {
+    if (!(cl1.TestBitNumber(i)&&cl2.TestBitNumber(i))) continue;
+    int x = sh1.TestBitNumber(i);
+    int y = sh2.TestBitNumber(i);
+    sumN += 1.0;
+    sumX += x;
+    sumY += y;
+    sumXX += x*x;
+    sumYY += y*y;
+    sumXY += x*y;
+  }
+  double meanX = sumX/sumN;
+  double meanY = sumY/sumN;
+  double meanXX = sumXX/sumN;
+  double meanYY = sumYY/sumN;
+  double meanXY = sumXY/sumN;
+  double sX = TMath::Sqrt(TMath::Abs(meanXX-meanX*meanX));
+  double sY = TMath::Sqrt(TMath::Abs(meanYY-meanY*meanY));
+  if (sX*sY!=0) corr = (meanXY-meanX*meanY)/(sX*sY);
+  return corr;}
+
+double AliTwoTrackRes::Qfac(TBits cl1,  TBits cl2, TBits sh1, TBits sh2) {
+// Quality factor from AliFemto 
+
+  int ncl1 = cl1.GetNbits();
+  int ncl2 = cl2.GetNbits();
+  int sumCls = 0; int sumSha = 0; int sumQ = 0;
+  double shfrac = 0; double qfactor = 0;
+  for(int i = 0; i < ncl1 && i < ncl2; i++) {
+    if (cl1.TestBitNumber(i) && cl2.TestBitNumber(i)) { // Both clusters
+      if (sh1.TestBitNumber(i) && sh2.TestBitNumber(i)) { // Shared
+       sumQ++;
+       sumCls+=2;
+       sumSha+=2;}
+      else {sumQ--; sumCls+=2;}
+    }
+    else if (cl1.TestBitNumber(i) || cl2.TestBitNumber(i)) { // Non shared
+      sumQ++;
+      sumCls++;}
+  }
+  if (sumCls>0) {
+    qfactor = sumQ*1.0/sumCls;
+    shfrac = sumSha*1.0/sumCls;
+  }
+  return qfactor;
+}
+
+// Rotate second track for mixed pairs
+double AliTwoTrackRes::RotTr2Phi() {
+  double rot = TVector2::Phi_mpi_pi(fP2.Phi()+TMath::Pi());
+  fTpcEnt2.SetPhi(TVector2::Phi_mpi_pi(fTpcEnt2.Phi()+TMath::Pi())); 
+  return rot;}
+
+// Fill NTuples
+void AliTwoTrackRes::FillNTuple1(double minsep, double sep, double corr, 
+                                double qf, int ns1, int ns2) {
+  fNTuple1->Fill(fP1.Pt(),fP1.Eta(),fP1.Phi(),ns1,fP2.Pt(),fP2.Eta(),
+                fP2.Phi(),ns2,Qinv(),minsep,sep,corr,qf);}
+void AliTwoTrackRes::FillNTuple2(double minsep, double sep, double corr, 
+                                double qf, int ns1, int ns2) {
+  fNTuple2->Fill(fPb1.Pt(),fPb1.Eta(),fPb1.Phi(),ns1,fPb2.Pt(),fPb2.Eta(),
+                fPb2.Phi(),ns2,Qinv(),minsep,sep,corr,qf);}
+
+//______________________________________________________________________________
+// EOF
+
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/AliTwoTrackRes.h b/PWGCF/FEMTOSCOPY/AliFemto/AliTwoTrackRes.h
new file mode 100644 (file)
index 0000000..ed38594
--- /dev/null
@@ -0,0 +1,96 @@
+////////////////////////////////////////////////////////////////////////////////
+//345678901234567890123456789012345678901234567890123456789012345678901234567890
+//       1         2         3         4         5         6         7         8
+//
+// Class AliTwoTrackRes
+// J. Mercado <mercado@physi.uni-heidelberg.de> Last modified: 20.01.2011
+//
+////////////////////////////////////////////////////////////////////////////////
+
+#ifndef ALITWOTRACKRES_H
+#define ALITWOTRACKRES_H
+
+#include <TNtuple.h>
+#include <TObject.h>
+#include <TFile.h>
+#include <TTree.h>
+#include "TMath.h"
+#include "TBits.h"
+#include "TVector3.h"
+#include "TLorentzVector.h"
+#include "AliAnalysisTask.h"
+#include "AliESD.h"
+#include "AliESDEvent.h"
+#include "AliESDtrack.h"
+#include "AliESDtrackCuts.h"
+#include "AliExternalTrackParam.h"
+
+//______________________________________________________________________________
+class AliTwoTrackRes : public AliAnalysisTask {
+
+public:
+  
+  AliTwoTrackRes() : AliAnalysisTask("",""), fChain(0), fESDEvent(0), fOutContainer(0), 
+    fTrackCuts(0), fNTuple1(0), fNTuple2(0), fP1(), fP2(), fPb1(), fPb2(), fP(), 
+    fQ(), fTpcEnt1(), fTpcEnt2(), fTpcDist(), fOutFilename() {}
+  AliTwoTrackRes(const char *name);
+  AliTwoTrackRes(const AliTwoTrackRes& aTwoTrackRes);
+  virtual ~AliTwoTrackRes();
+
+  AliTwoTrackRes& operator=(const AliTwoTrackRes& aTwoTrackRes);
+
+  virtual void ConnectInputData(Option_t *);
+  virtual void CreateOutputObjects();
+  virtual void Exec(Option_t *opt = "");
+  virtual void Terminate(Option_t *opt = "");
+
+  void   SetTr1(double pt1, double eta1, double phi1, double m);
+  void   SetTr2(double pt2, double eta2, double phi2, double m);
+  void   SetTpcEnt1(double x1, double y1, double z1);
+  void   SetTpcEnt2(double x2, double y2, double z2);
+  double Qinv2()         {fQ = fP2 - fP1; return -1.*fQ.M2();}
+  double Qinv()          {return TMath::Sqrt(TMath::Abs(Qinv2()));}
+  double MinDist(AliExternalTrackParam *trk1, AliExternalTrackParam *trk2);
+  int    GetNSha(TBits cl, TBits sh);
+  double Corr(TBits cl1, TBits cl2, TBits sh1, TBits sh2);
+  double Qfac(TBits cl1, TBits cl2, TBits sh1, TBits sh2);
+  double RotTr2Phi();
+  double Dist()    {fTpcDist = fTpcEnt2 - fTpcEnt1; return fTpcDist.Mag();}
+  double DEta()    const {return TMath::Abs(fP2.Eta()-fP1.Eta());}
+  double DTheta()  const {return fP2.Theta()-fP1.Theta();}
+  double DPhi()    const {return TVector2::Phi_mpi_pi(fP2.Phi()-fP1.Phi());}
+  void   NoSwap()        {fPb1 = fP1; fPb2 = fP2;}
+  void   Swap()          {fPb1 = fP2; fPb2 = fP1;}
+  void   FillNTuple1(double minsep, double sep, double corr, double qf, 
+                    int ns1, int ns2);
+  void   FillNTuple2(double minsep, double sep, double corr, double qf, 
+                    int ns1, int ns2);
+  void   SetOutfile(char *outfil) {fOutFilename = outfil;}
+
+private:
+
+  TTree           *fChain;        // Chain of ESD trees
+  AliESDEvent     *fESDEvent;     // Leaves
+  TObjArray       *fOutContainer; // Output data container
+  AliESDtrackCuts *fTrackCuts;    // Track cuts
+  TNtuple         *fNTuple1;      // True pairs
+  TNtuple         *fNTuple2;      // Mixed pairs
+  TLorentzVector  fP1;            // Four-momentum of track 1 (lab)
+  TLorentzVector  fP2;            // Four-momentum of track 2 (lab)
+  TLorentzVector  fPb1;           // Buffer single-track 1 for swapping
+  TLorentzVector  fPb2;           // Buffer single-track 2 for swapping
+  TLorentzVector  fP;             // Total four-momentum (lab)
+  TLorentzVector  fQ;             // Four-momentum difference (lab)
+  TVector3        fTpcEnt1;       // Nominal TPC entrance point track 1
+  TVector3        fTpcEnt2;       // Nominal TPC entrance point track 2
+  TVector3        fTpcDist;       // Nominal TPC entrance separation 
+  TString         fOutFilename;   // Output filename
+
+  ClassDef(AliTwoTrackRes, 0);
+};
+#endif
+
+//______________________________________________________________________________
+// EOF
+
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/PhysicalConstants.h b/PWGCF/FEMTOSCOPY/AliFemto/PhysicalConstants.h
new file mode 100644 (file)
index 0000000..2e0c5d5
--- /dev/null
@@ -0,0 +1,146 @@
+/***************************************************************************
+ *
+ * $Id$
+ *
+ * Author: CLHEP (see below)
+ ***************************************************************************
+ *
+ * Description:  Taken as-is from CLHEP.
+ *               Modified original CVS-Id to retain version info. 
+ ***************************************************************************
+ *
+ * $Log$
+ * Revision 1.1.1.1  2007/04/25 15:38:41  panos
+ * Importing the HBT code dir
+ *
+ * Revision 1.1.1.1  2007/03/07 10:14:49  mchojnacki
+ * First version on CVS
+ *
+ * Revision 1.2  1999/02/22 16:52:47  didenko
+ * updates from Gene
+ *
+ * Revision 1.1  1999/01/30 03:58:59  fisyak
+ * Root Version of StarClassLibrary
+ *
+ * Revision 1.1  1999/01/23 00:27:34  ullrich
+ * Initial Revision
+ *
+ **************************************************************************/
+
+#ifndef HEP_PHYSICAL_CONSTANTS_H
+#define HEP_PHYSICAL_CONSTANTS_H
+
+#include "SystemOfUnits.h"
+
+#ifndef ST_NO_NAMESPACES
+using namespace std;
+using namespace units;
+#endif
+
+#include <math.h>
+#include <cmath>
+
+/*
+//
+#ifndef M_PI
+#define M_PI 3.14159265358979312
+#endif
+//
+//#ifdef MACOSX
+//extern const double     pi;    // from <math.h>
+//#else
+static const double     pi  = M_PI;    // from <math.h>
+//#endif
+static const double  twopi  = 2*pi;
+static const double halfpi  = pi/2;
+static const double    pi2  = pi*pi;
+
+//
+// 
+//
+static const double Avogadro = 6.0221367e+23/mole;
+*/
+//
+// c   = 299.792458 mm/ns
+// c^2 = 898.7404 (mm/ns)^2 
+//
+static const double kCLight   = 2.99792458e+8 * meter/second;
+static const double kCSquared = kCLight * kCLight;
+/*
+//
+// h     = 4.13566e-12 MeV*ns
+// hbar  = 6.58212e-13 MeV*ns
+// hbarc = 197.32705e-12 MeV*mm
+//
+static const double h_Planck      = 6.6260755e-34 * joule*second;
+static const double hbar_Planck   = h_Planck/twopi;
+static const double hbarc         = hbar_Planck * kCLight;
+static const double hbarcSquared = hbarc * hbarc;
+
+//
+//
+//
+static const double electron_charge = - eplus; // see SystemOfUnits.h
+static const double e_squared = eplus * eplus;
+
+*/
+//
+// amu_c2 - atomic equivalent mass unit
+// amu    - atomic mass unit
+//
+static const double   kElectronMassC2 = 0.51099906 * MeV;
+static const double     kProtonMassC2 = 938.27231 * MeV;
+static const double    kNeutronMassC2 = 939.56563 * MeV;
+static const double            kAmuC2 = 931.49432 * MeV;
+//static const double              amu = kAmuC2/cSquared;
+
+static const double    kKaon0ShortMassC2 = 497.672  * MeV;
+static const double      kPionPlusMassC2 = 139.5700 * MeV;
+static const double     kPionMinusMassC2 = 139.5700 * MeV;
+static const double        kLambdaMassC2 = 1115.684 * MeV;
+static const double    kAntiLambdaMassC2 = 1115.684 * MeV;
+static const double       kXiMinusMassC2 = 1321.32  * MeV;
+
+/*
+//
+// permeability of free space mu0    = 2.01334e-16 Mev*(ns*eplus)^2/mm
+// permittivity of free space epsil0 = 5.52636e+10 eplus^2/(MeV*mm)
+//
+static const double mu0      = 4*pi*1.e-7 * henry/meter;
+static const double epsilon0 = 1./(cSquared*mu0);
+
+//
+// electromagnetic coupling = 1.43996e-12 MeV*mm/(eplus^2)
+//
+static const double elm_coupling           = e_squared/(4*pi*epsilon0);
+static const double fine_structure_const   = elm_coupling/hbarc;
+static const double classic_electr_radius  = elm_coupling/kElectronMassC2;
+static const double electron_Compton_length = hbarc/kElectronMassC2;
+static const double Bohr_radius = electron_Compton_length/fine_structure_const;
+
+static const double alpha_rcl2 = fine_structure_const
+                                   *classic_electr_radius
+                                   *classic_electr_radius;
+
+static const double twopi_mc2_rcl2 = twopi*kElectronMassC2
+                                             *classic_electr_radius
+                                             *classic_electr_radius;
+//
+//
+//
+static const double k_Boltzmann = 8.617385e-11 * MeV/kelvin;
+
+//
+//
+//
+static const double STP_Temperature = 273.15*kelvin;
+static const double STP_Pressure    = 1.*atmosphere;
+static const double kGasThreshold   = 1.e-2*gram/centimeter3;
+*/
+
+#endif /* HEP_PHYSICAL_CONSTANTS_H */
+
+
+
+
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/SystemOfUnits.h b/PWGCF/FEMTOSCOPY/AliFemto/SystemOfUnits.h
new file mode 100644 (file)
index 0000000..b09fdb4
--- /dev/null
@@ -0,0 +1,313 @@
+/***************************************************************************
+ *
+ * $Id$
+ *
+ * Author: blasiuk adapted from CLHEP
+ ***************************************************************************
+ *
+ * Description:  This file is based on the SystemOfUnits provided
+ *               in the CLHEP library v1.2:  The units remain the same.
+ *               It is just the naming conventions that are different:
+ *
+ * 1) No single letter unit:
+ *    : m --> meter
+ *    : s --> second
+ *    : g --> gram
+ *
+ * 2) All prefixes are spelled out explicitly (except electron Volt):
+ *    : ns --> nanosecond
+ *    : mm --> millimeter
+ *
+ * 3) All units with proper names follow the international standard
+ *    of being lower case:
+ *    : farad --> farad
+ *    : volt  --> volt
+ *
+ * The basic units are :
+ *              centimeter              (centimeter)
+ *              second                  (second)
+ *              Giga electron Volt      (GeV)
+ *              positron charge         (eplus)
+ *              degree Kelvin           (kelvin)
+ *              the amount of substance (mole)
+ *              radian                  (radian)
+ *              steradian               (steradian)
+ ***************************************************************************
+ *
+ * $Log$
+ * Revision 1.1.2.1  2007/10/05 09:38:17  akisiel
+ * Fix stray colons
+ *
+ * Revision 1.1  2007/05/16 10:22:12  akisiel
+ * Making the directory structure of AliFemto flat. All files go into one common directory
+ *
+ * Revision 1.1.1.1  2007/04/25 15:38:41  panos
+ * Importing the HBT code dir
+ *
+ * Revision 1.1.1.1  2007/03/07 10:14:49  mchojnacki
+ * First version on CVS
+ *
+ * Revision 1.5  2003/09/02 17:59:35  perev
+ * gcc 3.2 updates + WarnOff
+ *
+ * Revision 1.4  1999/03/22 16:21:38  fisyak
+ * Add anti CINT flags
+ *
+ * Revision 1.3  1999/03/11 14:53:07  ullrich
+ * Added definition of inch.
+ *
+ * Revision 1.2  1999/03/02 20:15:08  ullrich
+ * Added millivolt.
+ *
+ * Revision 1.1  1999/01/30 03:59:06  fisyak
+ * Root Version of StarClassLibrary
+ *
+ * Revision 1.1  1999/01/23 00:28:08  ullrich
+ * Initial Revision
+ *
+ **************************************************************************/
+#ifndef HEP_SYSTEM_OF_UNITS_H
+#define HEP_SYSTEM_OF_UNITS_H
+
+
+#ifndef M_PI
+#define M_PI 3.14159265358979312
+#endif
+
+
+namespace units {
+    // new macro for CLHEP SystemOfUnits: at end of file
+    //  ST_ADD_OLD_CLHEP_SYSTEM_OF_UNITS
+    // 
+    // Length [L]
+    //
+    static const double millimeter  = 0.1;
+    static const double millimeter2 = millimeter*millimeter;
+    static const double millimeter3 = millimeter*millimeter*millimeter;
+
+    static const double centimeter  = 10*millimeter;
+    static const double centimeter2 = centimeter*centimeter;
+    static const double centimeter3 = centimeter*centimeter*centimeter;
+
+    static const double meter       = 100.*centimeter;
+    static const double meter2      = meter*meter;
+    static const double meter3      = meter*meter*meter;
+
+    static const double kilometer   = 1000.*meter;
+    static const double kilometer2  = kilometer*kilometer;
+    static const double kilometer3  = kilometer*kilometer*kilometer;
+
+    static const double micrometer  = 1.e-6*meter;
+    static const double nanometer   = 1.e-9*meter;
+    static const double femtometer  = 1.e-15*meter;
+    static const double fermi       = 1*femtometer;
+    
+    static const double      barn   = 1.e-28*meter2;
+    static const double millibarn   = 1.e-3*barn;
+    static const double microbarn   = 1.e-6*barn;
+    static const double  nanobarn   = 1.e-9*barn;
+    static const double      inch   = 2.54*centimeter;
+    
+    //
+    // Angle
+    //
+    static const double      radian = 1.;
+    static const double milliradian = 1.e-3*radian;
+#ifndef __CINT__
+    static const double      degree = (M_PI/180.0)*radian;
+#endif    
+    static const double   steradian = 1.;
+
+    //
+    // Time [T]
+    //
+    static const double      second = 1;
+    static const double millisecond = 1.e-3*second;
+    static const double microsecond = 1.e-3*millisecond;
+    static const double  nanosecond = 1.e-3*microsecond;
+    
+    static const double     hertz   = 1./second;
+    static const double kilohertz   = 1.e+3*hertz;
+    static const double Megahertz   = 1.e+6*hertz;
+    
+    // but these are also unambiguous and unlikely to be used as variable!
+    static const double  Hz         = 1*hertz;
+    static const double kHz         = 1*kilohertz;
+    static const double MHz         = 1*Megahertz;
+
+    //
+    // Electric charge [Q]
+    //
+    static const double eplus   = 1. ;                 // positron charge
+    static const double e_SI    = 1.60217733e-19;      // positron charge in coulomb
+    static const double coulomb = eplus/e_SI;
+    
+    //
+    // Energy [E]
+    //
+    static const double Gigaelectronvolt = 1.;
+    static const double Megaelectronvolt = 1.e-3*Gigaelectronvolt;
+    static const double     electronvolt = 1.e-6*Megaelectronvolt;
+    static const double kiloelectronvolt = 1.e+3*electronvolt;
+    static const double Teraelectronvolt = 1.e+3*Gigaelectronvolt;
+    
+    // but these are also unambiguous and unlikely to be used as variables
+    static const double MeV     = Megaelectronvolt;
+    static const double  eV     =     electronvolt;
+    static const double keV     = kiloelectronvolt;
+    static const double GeV     = Gigaelectronvolt;
+    static const double TeV     = Teraelectronvolt;
+    
+    static const double joule   = electronvolt/e_SI;
+    
+    //
+    // Mass [E][T^2][L^-2]
+    //
+    static const double  kilogram = joule*second*second/(meter*meter);
+    static const double      gram = 1.e-3*kilogram;
+    static const double milligram = 1.e-3*gram;
+
+    //
+    // Power [E][T^-1]
+    //
+    static const double watt    = joule/second;
+    
+    //
+    // Force [E][L^-1]
+    //
+    static const double newton  = joule/meter;
+
+    //
+    // Pressure [E][L^-3]
+    //
+#ifndef __CINT__    
+#define pascal hep_pascal       // a trick to avoid warnings 
+    static const double hep_pascal = newton/meter2;
+#else
+    static const double pascal     = newton/meter2;
+#endif
+    static const double bar        = 100000*pascal;
+    static const double atmosphere = 101325*pascal;
+
+    //
+    // Electric current [Q][T^-1]
+    //
+    static const double ampere   = coulomb/second;
+    
+    //
+    // Electric potential [E][Q^-1]
+    //
+    static const double Megavolt = MeV/eplus;
+    static const double kilovolt = 1.e-3*Megavolt;
+    static const double     volt = 1.e-6*Megavolt;
+    static const double millivolt = 1.e-3*volt;
+    
+    //
+    // Electric resistance [E][T][Q^-2]
+    //
+    static const double ohm = volt/ampere;
+    
+    //
+    // Electric capacitance [Q^2][E^-1]
+    //
+    static const double farad = coulomb/volt;
+    static const double millifarad = 1.e-3*farad;
+    static const double microfarad = 1.e-6*farad;
+    static const double  nanofarad = 1.e-9*farad;
+    static const double  picofarad = 1.e-12*farad;
+    
+    //
+    // Magnetic Flux [T][E][Q^-1]
+    //
+    static const double weber = volt*second;
+    
+    //
+    // Magnetic Field [T][E][Q^-1][L^-2]
+    //
+    static const double tesla     = volt*second/meter2;
+    
+    static const double gauss     = 1.e-4*tesla;
+    static const double kilogauss = 1.e-1*tesla;
+
+    //
+    // Inductance [T^2][E][Q^-2]
+    //
+    static const double henry = weber/ampere;
+
+    //
+    // Temperature
+    //
+    static const double kelvin = 1.;
+
+    //
+    // Amount of substance
+    //
+    static const double mole = 1.;
+    
+    //
+    // Activity [T^-1]
+    //
+    static const double becquerel = 1./second;
+    static const double curie = 3.7e+10 * becquerel;
+    
+    //
+    // Absorbed dose [L^2][T^-2]
+    //
+    static const double gray = joule/kilogram ;
+
+    //
+    // Miscellaneous
+    //
+    static const double perCent     = 0.01 ;
+    static const double perThousand = 0.001;
+    static const double perMillion  = 0.000001;
+
+#ifdef ST_ADD_OLD_CLHEP_SYSTEM_OF_UNITS
+
+    static const double mm  = 0.1;         // millimeter
+    static const double mm2 = mm*mm;
+    static const double mm3 = mm*mm*mm;
+    
+    static const double cm  = 10.*mm;      // centimeter
+    static const double cm2 = cm*cm;
+    static const double cm3 = cm*cm*cm;
+    
+    static const double m  = 1000.*mm;     // meter
+    static const double m2 = m*m;
+    static const double m3 = m*m*m;
+    
+    static const double km = 1000.*m;      // kilometer
+    static const double km2 = km*km;
+    static const double km3 = km*km*km;
+
+    static const double microm = 1.e-6*m;  // micro meter
+    static const double  nanom = 1.e-9*m;
+    //static const double  fermi = 1.e-15*m;
+
+    //
+    // Angle
+    //
+    static const double  rad = 1.;        // radian 
+    static const double mrad = 1.e-3*rad; // milliradian
+    static const double  deg = (M_PI/180.0)*rad;
+
+    static const double   st = 1.;         // steradian
+
+    //
+    // Time [T]
+    //
+    static const double  s = 1;           // second
+    static const double ns = 1.e-9*s;     // nano second
+    static const double ms = 1.e-3*s;     // milli second
+
+    // Mass [E][T^2][L^-2]
+    //
+    static const double kg = joule*second*second/(meter*meter);        // kg = 6.24150 e+24 * MeV*ns*ns/(mm*mm)   
+    static const double  g = 1.e-3*kg;
+    static const double mg = 1.e-3*g;
+
+#endif
+
+}
+using namespace units;
+#endif /* HEP_SYSTEM_OF_UNITS_H */
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/TpcLocalTransform.cxx b/PWGCF/FEMTOSCOPY/AliFemto/TpcLocalTransform.cxx
new file mode 100644 (file)
index 0000000..314b98d
--- /dev/null
@@ -0,0 +1,89 @@
+
+#include "AliFmThreeVectorD.h"
+// - not needed (which is good because we want no STAR-dependence! 25apr2006) - #include "StEvent/StTpcHit.h"
+#include "TMath.h"
+
+
+//__________________________________
+
+
+
+int TpcLocalTransform(AliFmThreeVectorD& aPoint, int& aSector, int& aRow, 
+                     float& aU, double& aPhi){
+  static int tNPadAtRow[45]={
+  88,96,104,112,118,126,134,142,150,158,166,174,182,
+  98,100,102,104,106,106,108,110,112,112,114,116,118,120,122,122,
+  124,126,128,128,130,132,134,136,138,138,140,142,144,144,144,144};
+  static double tSectToPhi[24]={2.,1.,0.,11.,10.,9.,8. ,7. ,6.,5.,4.,3.,
+                               4.,5.,6., 7., 8.,9.,10.,11.,0.,1.,2.,3.};
+  //static double tPhiToSect[24]={2.,1.,0.,11.,10.,9.,8. ,7. ,6.,5.,4.,3.,
+       //                      4.,5.,6., 7., 8.,9.,10.,11.,0.,1.,2.,3.};
+  static double tPadWidthInner = 0.335;
+  static double tPadWidthOuter = 0.67;
+
+  static double tPi = TMath::Pi();
+  // --- find sector number
+  aPhi = aPoint.Phi();
+  if(aPhi<0.) aPhi+=(2*tPi);
+  aPhi += tPi/12.;
+  if(aPhi>2*tPi) aPhi-=2*tPi;
+  int tiPhi = (int) (aPhi/tPi*6.);
+  if(aPoint.z()<0) {
+    aSector = (tiPhi<3)? 3-tiPhi : 15-tiPhi;
+  }
+  else{
+    aSector = (tiPhi<4)? 21+tiPhi : 9+tiPhi;
+  }
+  aPhi = tSectToPhi[aSector-1]*tPi/6.;
+  //if((fabs(aPhi-aPoint.phi())>(tPi/12)){
+  //cout << "Sector missmatch " << aPhi << " " << aPoint.phi() << " "
+  // << aSector << endl;
+  //}
+
+  // --- calculate local coordinate
+  float tR = aPoint.x()*cos(aPhi)+aPoint.y()*sin(aPhi);
+  aU =      -aPoint.x()*sin(aPhi)+aPoint.y()*cos(aPhi);
+
+  // --- find pad row 
+  if(tR<57.6) {
+    aRow = 0;
+    return 1;
+  }
+  float radmax = 62.4;
+  float spacing= 4.8;
+  aRow=1;
+  while(tR>radmax && aRow<46){
+    aRow++;
+    if(aRow==8){
+      radmax = 96.2;
+      spacing = 5.2;
+    }
+    else{
+      if (aRow==13){
+       radmax = 126.195; // lots of stuf in row 13!
+       spacing = 2.0;
+      }
+      else{
+       radmax+=spacing;
+      }
+    }
+  }
+  if(aRow>45){
+    //cout << "No pad row " << tR << endl;
+    return 2;
+  }
+  
+  // --- Check if u (=aU) inbound
+  double tPadWidth = aRow<14? tPadWidthInner : tPadWidthOuter;
+  if(fabs(aU) > tNPadAtRow[aRow-1]*tPadWidth/2.){
+    return 3;
+  }
+
+  return 0;
+}
+
+
+
+
+
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/TpcLocalTransform.h b/PWGCF/FEMTOSCOPY/AliFemto/TpcLocalTransform.h
new file mode 100644 (file)
index 0000000..e69de29
diff --git a/PWGCF/FEMTOSCOPY/AliFemto/phys_constants.h b/PWGCF/FEMTOSCOPY/AliFemto/phys_constants.h
new file mode 100644 (file)
index 0000000..3ef98c3
--- /dev/null
@@ -0,0 +1,21 @@
+// malisa - there was somewhere a "phys_constants.h" in the STAR hierarchy
+// the Strangeness HBT guys used very little of it, so I just put that stuff
+// in here...
+
+#ifndef _StHbt_phys_constants_h_
+#define _StHbt_phys_constants_h_
+
+#include "PhysicalConstants.h"  // from StarClassLibrary
+
+// the strangeness guys used a different naming system (of course)
+static const double kMLAMBDA        = kLambdaMassC2;
+static const double kMKAON0SHORT  = kKaon0ShortMassC2;
+static const double kMPROTON        = kProtonMassC2;
+static const double kMPIONPLUS     = kPionPlusMassC2;
+static const double kMPIONMINUS    = kPionMinusMassC2;
+static const double kMXIMINUS      = kXiMinusMassC2;
+static const double kMOMEGAMINUS   = 1672.45;
+static const double kMKAONMINUS    = 493.677;
+static const double kMKAONPLUS     = 493.677;
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoBPLCMS3DCorrFctnEMCIC.cxx b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoBPLCMS3DCorrFctnEMCIC.cxx
new file mode 100644 (file)
index 0000000..d977c45
--- /dev/null
@@ -0,0 +1,431 @@
+/***************************************************************************
+ *
+ * $Id: AliFemtoBPLCMS3DCorrFctnEMCIC.cxx  $
+ *
+ * Author: Nicolas Bock, Ohio State University, bock@mps.ohio-state.edu
+ ***************************************************************************
+ *
+ * Description: Calculates of the 3D Correlation Function, and also
+ *              produces histograms to calculate Energy Momentum Conservation
+ *              Induced Correlations  (EMCICs)
+ *
+ * This Class produces the following histograms as function of Qinv
+ * (for both real and mixed pairs):
+ *        1)   E1 + E2
+ *        2)   E1 * E2
+ *        3)   Pt1*Pt2
+ *        4)   Pz1*Pz2
+ *  
+ * The class is derived from AliFemtoBPLCMS3DCorrFctn, therefore it produces
+ * also the histograms in that class. 
+ * 
+ * NOTE: The EMCIC histograms are not averaged in this class, to obtain 
+ * the average, the user needs to divide the real pair histograms by 
+ * the numerator, and the mixed pair histograms by the denominator
+ *
+ ***************************************************************************
+ *
+ **************************************************************************/
+
+//////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFemtoBPLCMS3DCorrFctn: a class to calculate 3D correlation         //
+// for pairs of identical particles.                                     //
+// It also stored the weighted qinv per bin histogram for the coulomb    //
+// correction.                                                           //
+// In analysis the function should be first created in a macro, then     //
+// added to the analysis, and at the end of the macro the procedure to   //
+// write out histograms should be called.                                //
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+
+#include "AliFemtoBPLCMS3DCorrFctnEMCIC.h"
+#include "AliFemtoKTPairCut.h"
+#include "AliFemtoAnalysisReactionPlane.h"
+//#include "AliFemtoHisto.h"
+#include <cstdio>
+#include <TVector2.h>
+
+#ifdef __ROOT__ 
+ClassImp(AliFemtoBPLCMS3DCorrFctnEMCIC)
+#endif
+
+//____________________________
+AliFemtoBPLCMS3DCorrFctnEMCIC::AliFemtoBPLCMS3DCorrFctnEMCIC(char* title, const int& nbins, const float& QLo, const float& QHi)
+:
+AliFemtoCorrFctn(),
+//fEnergyTotalReal(0),  
+// fEnergyMultReal(0),        
+//fPzMultReal(0),      
+//fPtMultReal(0), 
+  fNumerator(0),
+  fDenominator(0),
+  fEnergyTotalMix(0),      
+  fEnergyMultMix(0),      
+  fPzMultMix(0),            
+  fPtMultMix(0),
+  fUseRPSelection(0)
+{
+  
+  // set up numerator
+  char tTitNum[101] = "Num";
+  strncat(tTitNum,title, 100);
+  fNumerator = new TH3D(tTitNum,title,nbins,QLo,QHi,nbins,QLo,QHi,nbins,QLo,QHi);
+  // set up denominator
+  char tTitDen[101] = "Den";
+  strncat(tTitDen,title, 100);
+  fDenominator = new TH3D(tTitDen,title,nbins,QLo,QHi,nbins,QLo,QHi,nbins,QLo,QHi);
+
+  //Setup EnergyTotalReal
+  /*char tTitNum1[100] = "ESumReal";
+  strncat(tTitNum1,title, 100);
+  fEnergyTotalReal = new TH3D(tTitNum1,title,nbins,QLo,QHi,nbins,QLo,QHi,nbins,QLo,QHi);
+  
+  //Setup EnergyMultReal
+  char tTitNum2[100] = "EMultReal";
+  strncat(tTitNum2,title, 100);
+  fEnergyMultReal = new TH3D(tTitNum2,title,nbins,QLo,QHi,nbins,QLo,QHi,nbins,QLo,QHi);
+  
+  //Setup Pz MultReal
+  char tTitNum3[100] = "PzMultReal";
+  strncat(tTitNum3,title, 100);
+  fPzMultReal = new TH3D(tTitNum3,title,nbins,QLo,QHi,nbins,QLo,QHi,nbins,QLo,QHi);
+  
+  //Setup Pt MultReal
+  char tTitNum4[100] = "PtMultReal";
+  strncat(tTitNum4,title, 100);
+  fPtMultReal = new TH3D(tTitNum4,title,nbins,QLo,QHi,nbins,QLo,QHi,nbins,QLo,QHi);  */
+  
+  //Setup EnergyTotalMix
+  char tTitNum5[101] = "ESumMix";
+  strncat(tTitNum5,title, 100);
+  fEnergyTotalMix = new TH3D(tTitNum5,title,nbins,QLo,QHi,nbins,QLo,QHi,nbins,QLo,QHi);
+  
+  //Setup EnergyMultMix
+  char tTitNum6[101] = "EMultMix";
+  strncat(tTitNum6,title, 100);
+  fEnergyMultMix = new TH3D(tTitNum6,title,nbins,QLo,QHi,nbins,QLo,QHi,nbins,QLo,QHi);
+  
+  //Setup Pz MultMix
+  char tTitNum7[101] = "PzMultMix";
+  strncat(tTitNum7,title, 100);
+  fPzMultMix = new TH3D(tTitNum7,title,nbins,QLo,QHi,nbins,QLo,QHi,nbins,QLo,QHi);
+  
+  //Setup Pt MultMix
+  char tTitNum8[101] = "PtMultMix";
+  strncat(tTitNum8,title, 100);
+  fPtMultMix = new TH3D(tTitNum8,title,nbins,QLo,QHi,nbins,QLo,QHi,nbins,QLo,QHi);
+  // To enable error bar calculation
+  
+  /*fEnergyTotalReal->Sumw2();
+  fEnergyMultReal->Sumw2();
+  fPzMultReal->Sumw2();
+  fPtMultReal->Sumw2();  */
+  fNumerator->Sumw2();
+  fDenominator->Sumw2();
+  fEnergyTotalMix->Sumw2();
+  fEnergyMultMix->Sumw2();
+  fPzMultMix->Sumw2();
+  fPtMultMix->Sumw2();
+  
+}
+
+
+// Variable bin size constructor :
+//qBins array of low-edges for each bin. This is an array of size nbins+1
+AliFemtoBPLCMS3DCorrFctnEMCIC::AliFemtoBPLCMS3DCorrFctnEMCIC(char* title, const int& nbins, const float* qBins):
+AliFemtoCorrFctn(),
+  fNumerator(0),
+  fDenominator(0),
+  fEnergyTotalMix(0),      
+  fEnergyMultMix(0),      
+  fPzMultMix(0),            
+  fPtMultMix(0),
+  fUseRPSelection(0)
+{
+  
+  // set up numerator
+  char tTitNum[101] = "Num";
+  strncat(tTitNum,title, 100);
+  fNumerator = new TH3D(tTitNum,title,nbins,qBins,nbins,qBins,nbins,qBins);
+  // set up denominator
+  char tTitDen[101] = "Den";
+  strncat(tTitDen,title, 100);
+  fDenominator = new TH3D(tTitDen,title,nbins,qBins,nbins,qBins,nbins,qBins);
+
+  //Setup EnergyTotalReal
+  /*char tTitNum1[100] = "ESumReal";
+  strncat(tTitNum1,title, 100);
+  fEnergyTotalReal = new TH3D(tTitNum1,title,nbins,qBins,nbins,qBins,nbins,qBins);
+  
+  //Setup EnergyMultReal
+  char tTitNum2[100] = "EMultReal";
+  strncat(tTitNum2,title, 100);
+  fEnergyMultReal = new TH3D(tTitNum2,title,nbins,qBins,nbins,qBins,nbins,qBins);
+  
+  //Setup Pz MultReal
+  char tTitNum3[100] = "PzMultReal";
+  strncat(tTitNum3,title, 100);
+  fPzMultReal = new TH3D(tTitNum3,title,nbins,qBins,nbins,qBins,nbins,qBins);
+  
+  //Setup Pt MultReal
+  char tTitNum4[100] = "PtMultReal";
+  strncat(tTitNum4,title, 100);
+  fPtMultReal = new TH3D(tTitNum4,title,nbins,qBins,nbins,qBins,nbins,qBins);  */
+  
+  //Setup EnergyTotalMix
+  char tTitNum5[101] = "ESumMix";
+  strncat(tTitNum5,title, 100);
+  fEnergyTotalMix = new TH3D(tTitNum5,title,nbins,qBins,nbins,qBins,nbins,qBins);
+  
+  //Setup EnergyMultMix
+  char tTitNum6[101] = "EMultMix";
+  strncat(tTitNum6,title, 100);
+  fEnergyMultMix = new TH3D(tTitNum6,title,nbins,qBins,nbins,qBins,nbins,qBins);
+  
+  //Setup Pz MultMix
+  char tTitNum7[101] = "PzMultMix";
+  strncat(tTitNum7,title, 100);
+  fPzMultMix = new TH3D(tTitNum7,title,nbins,qBins,nbins,qBins,nbins,qBins);
+  
+  //Setup Pt MultMix
+  char tTitNum8[101] = "PtMultMix";
+  strncat(tTitNum8,title, 100);
+  fPtMultMix = new TH3D(tTitNum8,title,nbins,qBins,nbins,qBins,nbins,qBins);
+  // To enable error bar calculation
+  
+  /*fEnergyTotalReal->Sumw2();
+  fEnergyMultReal->Sumw2();
+  fPzMultReal->Sumw2();
+  fPtMultReal->Sumw2();  */
+  fNumerator->Sumw2();
+  fDenominator->Sumw2();
+  fEnergyTotalMix->Sumw2();
+  fEnergyMultMix->Sumw2();
+  fPzMultMix->Sumw2();
+  fPtMultMix->Sumw2();
+}
+  
+
+
+
+
+
+
+AliFemtoBPLCMS3DCorrFctnEMCIC::AliFemtoBPLCMS3DCorrFctnEMCIC(const AliFemtoBPLCMS3DCorrFctnEMCIC& aCorrFctn) :
+  AliFemtoCorrFctn(aCorrFctn),
+  /*fEnergyTotalReal(0),  
+  fEnergyMultReal(0),        
+  fPzMultReal(0),      
+  fPtMultReal(0),*/     
+  fNumerator(0),
+  fDenominator(0),
+  fEnergyTotalMix (0),      
+  fEnergyMultMix (0),  
+  fPzMultMix(0),          
+  fPtMultMix(0),
+  fUseRPSelection(0)
+{
+  // Copy constructor
+  fNumerator = new TH3D(*aCorrFctn.fNumerator);
+  fDenominator = new TH3D(*aCorrFctn.fDenominator);
+  /*  fEnergyTotalReal = new TH3D(*aCorrFctn.fEnergyTotalReal);
+  fEnergyMultReal = new TH3D(*aCorrFctn.fEnergyMultReal);
+  fPzMultReal = new TH3D(*aCorrFctn.fPzMultReal);
+  fPtMultReal = new TH3D(*aCorrFctn.fPtMultReal);  */
+  fEnergyTotalMix = new TH3D(*aCorrFctn.fEnergyTotalMix);
+  fEnergyMultMix = new TH3D(*aCorrFctn.fEnergyMultMix);
+  fPzMultMix = new TH3D(*aCorrFctn.fPzMultMix);
+  fPtMultMix = new TH3D(*aCorrFctn.fPtMultMix);
+}
+//____________________________
+AliFemtoBPLCMS3DCorrFctnEMCIC::~AliFemtoBPLCMS3DCorrFctnEMCIC(){
+  // Destructor
+  /*  delete fEnergyTotalReal;
+  delete fEnergyMultReal;        
+  delete fPzMultReal;     
+  delete fPtMultReal;  */
+  delete fNumerator;
+  delete fDenominator;
+  delete fEnergyTotalMix;      
+  delete fEnergyMultMix; 
+  delete fPzMultMix;   
+  delete fPtMultMix;
+}
+//_________________________
+AliFemtoBPLCMS3DCorrFctnEMCIC& AliFemtoBPLCMS3DCorrFctnEMCIC::operator=(const AliFemtoBPLCMS3DCorrFctnEMCIC& aCorrFctn)
+{
+  // assignment operator
+  if (this == &aCorrFctn)
+    return *this;
+  if (fNumerator) delete fNumerator;
+  fNumerator = new TH3D(*aCorrFctn.fNumerator);
+  if (fDenominator) delete fDenominator;
+  fDenominator = new TH3D(*aCorrFctn.fDenominator);
+  //Emcics
+  /*  if (fEnergyTotalReal) delete fEnergyTotalReal;
+  fEnergyTotalReal = new TH3D(*aCorrFctn.fEnergyTotalReal);
+  if (fEnergyMultReal) delete fEnergyMultReal;
+  fEnergyMultReal = new TH3D(*aCorrFctn.fEnergyMultReal);
+  if (fPzMultReal) delete fPzMultReal;
+  fPzMultReal = new TH3D(*aCorrFctn.fPzMultReal);
+  if (fPtMultReal) delete fPtMultReal;
+  fPtMultReal = new TH3D(*aCorrFctn.fPtMultReal);  */
+  if (fEnergyTotalMix) delete fEnergyTotalMix;
+  fEnergyTotalMix = new TH3D(*aCorrFctn.fEnergyTotalMix);
+  if (fEnergyMultMix) delete fEnergyMultMix;
+  fEnergyMultMix = new TH3D(*aCorrFctn.fEnergyMultMix);
+  if (fPzMultMix) delete fPzMultMix;
+  fPzMultMix = new TH3D(*aCorrFctn.fPzMultMix);
+  if (fPtMultMix) delete fPtMultMix;
+  fPtMultMix = new TH3D(*aCorrFctn.fPtMultMix);
+  
+  fUseRPSelection = aCorrFctn.fUseRPSelection;
+
+  return *this;
+}
+
+//_________________________
+void AliFemtoBPLCMS3DCorrFctnEMCIC::WriteOutHistos(){
+  
+  fNumerator->Write();
+  fDenominator->Write();
+  //fEnergyTotalReal->Write();
+  //fEnergyMultReal->Write();        
+  //fPzMultReal->Write();      
+  //fPtMultReal->Write();            
+  fEnergyTotalMix->Write();      
+  fEnergyMultMix->Write();      
+  fPzMultMix->Write();            
+  fPtMultMix->Write(); 
+  //cout << "write histos emcics" << endl;
+}
+//______________________________
+TList* AliFemtoBPLCMS3DCorrFctnEMCIC::GetOutputList()
+{
+  // Prepare the list of objects to be written to the output
+  TList *tOutputList = new TList();
+  cout << "Getting list from CFemcic" << endl;
+  tOutputList->Add(fNumerator);
+  tOutputList->Add(fDenominator);
+  /*tOutputList->Add(fEnergyTotalReal);
+  tOutputList->Add(fEnergyMultReal);        
+  tOutputList->Add(fPzMultReal);      
+  tOutputList->Add(fPtMultReal);     */       
+  tOutputList->Add(fEnergyTotalMix );      
+  tOutputList->Add(fEnergyMultMix );      
+  tOutputList->Add(fPzMultMix);            
+  tOutputList->Add(fPtMultMix);
+  return tOutputList;
+}
+
+
+
+//____________________________
+void AliFemtoBPLCMS3DCorrFctnEMCIC::AddRealPair( AliFemtoPair* pair){
+  // perform operations on real pairs
+  
+  if (fPairCut){
+    if (fUseRPSelection) {
+      AliFemtoKTPairCut *ktc = dynamic_cast<AliFemtoKTPairCut *>(fPairCut);
+      if (!ktc) { 
+       cout << "RP aware cut requested, but not connected to the CF" << endl;
+       if (!(fPairCut->Pass(pair))) return;
+      }
+      else {
+       AliFemtoAnalysisReactionPlane *arp = dynamic_cast<AliFemtoAnalysisReactionPlane *> (HbtAnalysis());
+       if (!arp) {
+         cout << "RP aware cut requested, but not connected to the CF" << endl;
+         if (!(fPairCut->Pass(pair))) return;
+       }
+       else if (!(ktc->Pass(pair, arp->GetCurrentReactionPlane()))) return;
+      }
+    }
+    else
+      if (!(fPairCut->Pass(pair))) return;
+  }
+  
+  double qOut  = fabs(pair->QOutCMS());  
+  double qSide = fabs( pair->QSideCMS());
+  double qLong = fabs(pair->QLongCMS());
+
+  fNumerator->Fill(qOut,qSide,qLong);
+  
+  /*AliFemtoLorentzVector tMom1 = pair->Track1()->FourMomentum();
+  AliFemtoLorentzVector tMom2 = pair->Track2()->FourMomentum();
+  double tE1 = tMom1.e();
+  double tE2 = tMom2.e();
+  double tPz1 = tMom1.pz();
+  double tPz2 = tMom2.pz();
+  TVector2 tPt1;  
+  TVector2 tPt2; 
+  tPt1.Set(tMom1.px(),tMom1.py());
+  tPt2.Set(tMom2.px(),tMom2.py());
+  
+  
+  double tPt1DotPt2 = tPt1*tPt2;
+  
+  fEnergyTotalReal->Fill(qOut,qSide,qLong,tE1+tE2);
+  fEnergyMultReal->Fill(qOut,qSide,qLong,tE1*tE2);
+  fPzMultReal->Fill(qOut,qSide,qLong,tPz1*tPz2);
+  fPtMultReal->Fill(qOut,qSide,qLong,tPt1DotPt2); */
+}
+
+
+//____________________________
+void AliFemtoBPLCMS3DCorrFctnEMCIC::AddMixedPair( AliFemtoPair* pair){
+  // perform operations on mixed pairs
+//   if (fPairCut){
+//     if (!(fPairCut->Pass(pair))) return;
+//   }
+  if (fPairCut){
+    if (fUseRPSelection) {
+      AliFemtoKTPairCut *ktc = dynamic_cast<AliFemtoKTPairCut *>(fPairCut);
+      if (!ktc) { 
+       cout << "RP aware cut requested, but not connected to the CF" << endl;
+       if (!(fPairCut->Pass(pair))) return;
+      }
+      else {
+       AliFemtoAnalysisReactionPlane *arp = dynamic_cast<AliFemtoAnalysisReactionPlane *> (HbtAnalysis());
+       if (!arp) {
+         cout << "RP aware cut requested, but not connected to the CF" << endl;
+         if (!(fPairCut->Pass(pair))) return;
+       }
+       else if (!(ktc->Pass(pair, arp->GetCurrentReactionPlane()))) return;
+      }
+    }
+    else
+      if (!(fPairCut->Pass(pair))) return;
+  }
+
+  
+  double qOut = fabs(pair->QOutCMS());
+  double qSide = fabs(pair->QSideCMS());
+  double qLong = fabs(pair->QLongCMS());
+
+  fDenominator->Fill(qOut,qSide,qLong);
+
+  AliFemtoLorentzVector tMom1 = pair->Track1()->FourMomentum();
+  AliFemtoLorentzVector tMom2 = pair->Track2()->FourMomentum();
+  double tE1 = tMom1.e();
+  double tE2 = tMom2.e();
+  double tPz1 = tMom1.pz();
+  double tPz2 = tMom2.pz();
+  TVector2 tPt1;  
+  TVector2 tPt2; 
+  tPt1.Set(tMom1.px(),tMom1.py());
+  tPt2.Set(tMom2.px(),tMom2.py());
+  double tPt1DotPt2 = tPt1*tPt2;
+  
+  fEnergyTotalMix->Fill(qOut,qSide,qLong,tE1+tE2);
+  fEnergyMultMix->Fill(qOut,qSide,qLong,tE1*tE2);
+  fPzMultMix->Fill(qOut,qSide,qLong,tPz1*tPz2);
+  fPtMultMix->Fill(qOut,qSide,qLong,tPt1DotPt2);
+  
+}
+
+
+void AliFemtoBPLCMS3DCorrFctnEMCIC::SetUseRPSelection(unsigned short aRPSel)
+{
+  fUseRPSelection = aRPSel;
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoBPLCMS3DCorrFctnEMCIC.h b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoBPLCMS3DCorrFctnEMCIC.h
new file mode 100644 (file)
index 0000000..34acd9d
--- /dev/null
@@ -0,0 +1,89 @@
+/***************************************************************************
+ *
+ * $Id: AliFemtoBPLCMS3DCorrFctnEMCIC.h  $
+ *
+ * Author: Nicolas Bock, Ohio State University, bock@mps.ohio-state.edu
+ ***************************************************************************
+ *
+ * Description: Calculates of the 3D Correlation Function, and also
+ *              produces histograms to calculate Energy Momentum Conservation
+ *              Induced Correlations  (EMCICs)
+ *
+ * This Class produces the following histograms as function of Qinv
+ * (for both real and mixed pairs):
+ *        1)   E1 + E2
+ *        2)   E1 * E2
+ *        3)   Pt1*Pt2
+ *        4)   Pz1*Pz2
+ *  
+ * The class is derived from AliFemtoBPLCMS3DCorrFctn, therefore it produces
+ * also the histograms in that class. 
+ * 
+ * NOTE: The EMCIC histograms are not averaged in this class, to obtain 
+ * the average, the user needs to divide the real pair histograms by 
+ * the numerator, and the mixed pair histograms by the denominator
+ *
+ ***************************************************************************
+ *
+ **************************************************************************/
+
+
+#ifndef ALIFEMTOBPLCMS3DCORRFCTNEMCIC_H
+#define ALIFEMTOBPLCMS3DCORRFCTNEMCIC_H
+
+#include "AliFemtoCorrFctn.h"
+#include "AliFemtoPairCut.h"
+#include "TH3D.h"
+
+class AliFemtoBPLCMS3DCorrFctnEMCIC : public AliFemtoCorrFctn{
+public:
+  AliFemtoBPLCMS3DCorrFctnEMCIC(char* title, const int& nbins, const float& QLo, const float& QHi);
+  // Variable bin size constructor :
+  //qBins array of low-edges for each bin. This is an array of size nbins+1
+  AliFemtoBPLCMS3DCorrFctnEMCIC(char* title, const int& nbins, const float* qBins);
+  
+  AliFemtoBPLCMS3DCorrFctnEMCIC(const AliFemtoBPLCMS3DCorrFctnEMCIC& aCorrFctn);
+  virtual ~AliFemtoBPLCMS3DCorrFctnEMCIC();
+
+  AliFemtoBPLCMS3DCorrFctnEMCIC& operator = (const AliFemtoBPLCMS3DCorrFctnEMCIC& aCorrFctn);
+
+  virtual AliFemtoString Report();
+  virtual void Finish();
+  virtual void AddRealPair( AliFemtoPair* aPair);
+  virtual void AddMixedPair( AliFemtoPair* aPair);
+
+  void SetUseRPSelection(unsigned short aRPSel);
+
+
+  void WriteOutHistos();
+  virtual TList* GetOutputList();
+
+ private:
+  
+  TH3D* fNumerator;         // numerator
+  TH3D* fDenominator;       // denominator
+  //EMCIC histograms
+  //TH3D* fEnergyTotalReal;       // E1+E2 from real pairs
+  //TH3D* fEnergyMultReal;        // E1*E2
+  //TH3D* fPzMultReal;            // Pz1*Pz2
+  //TH3D* fPtMultReal;            // Pt1*Pt2
+  TH3D* fEnergyTotalMix;       // E1+E2 from mixed pairs
+  TH3D* fEnergyMultMix;        // E1*E2
+  TH3D* fPzMultMix;            // Pz1*Pz2
+  TH3D* fPtMultMix;            // Pt1*Pt2
+   
+ protected:
+  unsigned short fUseRPSelection;  // The pair cut uses RP selection
+  
+  
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoBPLCMS3DCorrFctnEMCIC, 1)
+#endif
+};
+
+inline AliFemtoString AliFemtoBPLCMS3DCorrFctnEMCIC::Report(){AliFemtoString r="";return r;}
+inline void AliFemtoBPLCMS3DCorrFctnEMCIC::Finish(){}
+
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoChi2CorrFctn.cxx b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoChi2CorrFctn.cxx
new file mode 100644 (file)
index 0000000..b18435f
--- /dev/null
@@ -0,0 +1,381 @@
+////////////////////////////////////////////////////////////////////////////////
+///                                                                          ///
+/// AliFemtoChi2CorrFctn - A correlation function that saves the correlation ///
+/// function as a function of single track quality (chi2/ndof) for its and   ///
+/// tpc                                                                      ///
+/// Authors: Adam Kisiel kisiel@mps.ohio-state.edu                           ///
+///                                                                          ///
+////////////////////////////////////////////////////////////////////////////////
+
+#include "AliFemtoChi2CorrFctn.h"
+//#include "AliFemtoHisto.hh"
+#include <cstdio>
+
+#ifdef __ROOT__ 
+ClassImp(AliFemtoChi2CorrFctn)
+#endif
+
+//____________________________
+AliFemtoChi2CorrFctn::AliFemtoChi2CorrFctn(char* title, const int& nbins, const float& QinvLo, const float& QinvHi):
+  AliFemtoCorrFctn(),
+  fChi2ITSSUMNumerator(0),
+  fChi2ITSSUMDenominator(0),
+  fChi2TPCSUMNumerator(0),
+  fChi2TPCSUMDenominator(0),
+  fChi2ITSONENumerator(0),
+  fChi2ITSONEDenominator(0),
+  fChi2TPCONENumerator(0),
+  fChi2TPCONEDenominator(0),
+  fSigmaToVertexNumerator(0),
+  fSigmaToVertexDenominator(0)
+{
+  // set up numerator
+  char tTitNum[101] = "NumChi2ITSSUM";
+  strncat(tTitNum,title, 100);
+  fChi2ITSSUMNumerator = new TH2D(tTitNum,title,nbins,QinvLo,QinvHi,200,0.0,6.0);
+  // set up denominator
+  char tTitDen[101] = "DenChi2ITSSUM";
+  strncat(tTitDen,title, 100);
+  fChi2ITSSUMDenominator = new TH2D(tTitDen,title,nbins,QinvLo,QinvHi,200,0.0,6.0);
+
+  // set up numerator
+  char tTit2Num[101] = "NumChi2TPCSUM";
+  strncat(tTit2Num,title, 100);
+  fChi2TPCSUMNumerator = new TH2D(tTit2Num,title,nbins,QinvLo,QinvHi,200,0.0,6.0);
+  // set up denominator
+  char tTit2Den[101] = "DenChi2TPCSUM";
+  strncat(tTit2Den,title, 100);
+  fChi2TPCSUMDenominator = new TH2D(tTit2Den,title,nbins,QinvLo,QinvHi,200,0.0,6.0);
+
+  // to enable error bar calculation...
+  fChi2ITSSUMNumerator->Sumw2();
+  fChi2ITSSUMDenominator->Sumw2();
+
+  fChi2TPCSUMNumerator->Sumw2();
+  fChi2TPCSUMDenominator->Sumw2();
+  // set up numerator
+  snprintf(tTitNum , 100, "%s%s","NumChi2ITSONE",title);
+  fChi2ITSONENumerator = new TH2D(tTitNum,title,nbins,QinvLo,QinvHi,200,0.0,6.0);
+  // set up denominator
+  snprintf(tTitDen , 100, "%s%s", "DenChi2ITSONE", title);
+  fChi2ITSONEDenominator = new TH2D(tTitDen,title,nbins,QinvLo,QinvHi,200,0.0,6.0);
+
+  // set up numerator
+  snprintf(tTit2Num , 100, "%s%s","NumChi2TPCONE",title);
+  fChi2TPCONENumerator = new TH2D(tTit2Num,title,nbins,QinvLo,QinvHi,200,0.0,6.0);
+  // set up denominator
+  snprintf(tTit2Den , 100, "%s%s", "DenChi2TPCONE", title);
+  fChi2TPCONEDenominator = new TH2D(tTit2Den,title,nbins,QinvLo,QinvHi,200,0.0,6.0);
+
+  // set up numerator
+  snprintf(tTit2Num , 100, "%s%s","NumSigmaToVertex",title);
+  fSigmaToVertexNumerator = new TH2D(tTit2Num,title,nbins,QinvLo,QinvHi,200,0.0,6.0);
+  // set up denominator
+  snprintf(tTit2Den , 100, "%s%s", "DenSigmaToVertex", title);
+  fSigmaToVertexDenominator = new TH2D(tTit2Den,title,nbins,QinvLo,QinvHi,200,0.0,6.0);
+
+  // to enable error bar calculation...
+  fChi2ITSONENumerator->Sumw2();
+  fChi2ITSONEDenominator->Sumw2();
+
+  fChi2TPCONENumerator->Sumw2();
+  fChi2TPCONEDenominator->Sumw2();
+}
+
+//____________________________
+AliFemtoChi2CorrFctn::AliFemtoChi2CorrFctn(const AliFemtoChi2CorrFctn& aCorrFctn) :
+  AliFemtoCorrFctn(),
+  fChi2ITSSUMNumerator(0),
+  fChi2ITSSUMDenominator(0),
+  fChi2TPCSUMNumerator(0),
+  fChi2TPCSUMDenominator(0),
+  fChi2ITSONENumerator(0),
+  fChi2ITSONEDenominator(0),
+  fChi2TPCONENumerator(0),
+  fChi2TPCONEDenominator(0),
+  fSigmaToVertexNumerator(0),
+  fSigmaToVertexDenominator(0)
+{
+  // copy constructor
+  if (aCorrFctn.fChi2ITSSUMNumerator)
+    fChi2ITSSUMNumerator = new TH2D(*aCorrFctn.fChi2ITSSUMNumerator);
+  if (aCorrFctn.fChi2ITSSUMDenominator)
+    fChi2ITSSUMDenominator = new TH2D(*aCorrFctn.fChi2ITSSUMDenominator);
+  if (aCorrFctn.fChi2TPCSUMNumerator)
+    fChi2TPCSUMNumerator = new TH2D(*aCorrFctn.fChi2TPCSUMNumerator);
+  if (aCorrFctn.fChi2TPCSUMDenominator)
+    fChi2TPCSUMDenominator = new TH2D(*aCorrFctn.fChi2TPCSUMDenominator);
+  if (aCorrFctn.fChi2ITSONENumerator)
+    fChi2ITSONENumerator = new TH2D(*aCorrFctn.fChi2ITSONENumerator);
+  if (aCorrFctn.fChi2ITSONEDenominator)
+    fChi2ITSONEDenominator = new TH2D(*aCorrFctn.fChi2ITSONEDenominator);
+  if (aCorrFctn.fChi2TPCONENumerator)
+    fChi2TPCONENumerator = new TH2D(*aCorrFctn.fChi2TPCONENumerator);
+  if (aCorrFctn.fChi2TPCONEDenominator)
+    fChi2TPCONEDenominator = new TH2D(*aCorrFctn.fChi2TPCONEDenominator);
+  if (aCorrFctn.fSigmaToVertexNumerator)
+    fSigmaToVertexNumerator = new TH2D(*aCorrFctn.fSigmaToVertexNumerator);
+  if (aCorrFctn.fSigmaToVertexDenominator)
+    fSigmaToVertexDenominator = new TH2D(*aCorrFctn.fSigmaToVertexDenominator);
+}
+//____________________________
+AliFemtoChi2CorrFctn::~AliFemtoChi2CorrFctn(){
+  // destructor
+  delete fChi2ITSSUMNumerator;
+  delete fChi2ITSSUMDenominator;
+  delete fChi2TPCSUMNumerator;
+  delete fChi2TPCSUMDenominator;
+  delete fChi2ITSONENumerator;
+  delete fChi2ITSONEDenominator;
+  delete fChi2TPCONENumerator;
+  delete fChi2TPCONEDenominator;
+  delete fSigmaToVertexNumerator;
+  delete fSigmaToVertexDenominator;
+}
+//_________________________
+AliFemtoChi2CorrFctn& AliFemtoChi2CorrFctn::operator=(const AliFemtoChi2CorrFctn& aCorrFctn)
+{
+  // assignment operator
+  if (this == &aCorrFctn)
+    return *this;
+
+  if (aCorrFctn.fChi2ITSSUMNumerator)
+    fChi2ITSSUMNumerator = new TH2D(*aCorrFctn.fChi2ITSSUMNumerator);
+  else
+    fChi2ITSSUMNumerator = 0;
+  if (aCorrFctn.fChi2ITSSUMDenominator)
+    fChi2ITSSUMDenominator = new TH2D(*aCorrFctn.fChi2ITSSUMDenominator);
+  else
+    fChi2ITSSUMDenominator = 0;
+  if (aCorrFctn.fChi2TPCSUMNumerator)
+    fChi2TPCSUMNumerator = new TH2D(*aCorrFctn.fChi2TPCSUMNumerator);
+  else
+    fChi2TPCSUMNumerator = 0;
+  if (aCorrFctn.fChi2TPCSUMDenominator)
+    fChi2TPCSUMDenominator = new TH2D(*aCorrFctn.fChi2TPCSUMDenominator);
+  else
+    fChi2TPCSUMDenominator = 0;
+  if (aCorrFctn.fChi2ITSONENumerator)
+    fChi2ITSONENumerator = new TH2D(*aCorrFctn.fChi2ITSONENumerator);
+  else
+    fChi2ITSONENumerator = 0;
+  if (aCorrFctn.fChi2ITSONEDenominator)
+    fChi2ITSONEDenominator = new TH2D(*aCorrFctn.fChi2ITSONEDenominator);
+  else
+    fChi2ITSONEDenominator = 0;
+  if (aCorrFctn.fChi2TPCONENumerator)
+    fChi2TPCONENumerator = new TH2D(*aCorrFctn.fChi2TPCONENumerator);
+  else
+    fChi2TPCONENumerator = 0;
+  if (aCorrFctn.fChi2TPCONEDenominator)
+    fChi2TPCONEDenominator = new TH2D(*aCorrFctn.fChi2TPCONEDenominator);
+  else
+    fChi2TPCONEDenominator = 0;
+  if (aCorrFctn.fSigmaToVertexNumerator)
+    fSigmaToVertexNumerator = new TH2D(*aCorrFctn.fSigmaToVertexNumerator);
+  else
+    fSigmaToVertexNumerator = 0;
+  if (aCorrFctn.fSigmaToVertexDenominator)
+    fSigmaToVertexDenominator = new TH2D(*aCorrFctn.fSigmaToVertexDenominator);
+  else
+    fSigmaToVertexDenominator = 0;
+
+  return *this;
+}
+//_________________________
+void AliFemtoChi2CorrFctn::Finish(){
+  // here is where we should normalize, fit, etc...
+  // we should NOT Draw() the histos (as I had done it below),
+  // since we want to insulate ourselves from root at this level
+  // of the code.  Do it instead at root command line with browser.
+  //  mShareNumerator->Draw();
+  //mShareDenominator->Draw();
+  //mRatio->Draw();
+
+}
+
+//____________________________
+AliFemtoString AliFemtoChi2CorrFctn::Report(){
+  // create report
+  string stemp = "ITS and TPC quality Correlation Function Report:\n";
+  char ctemp[100];
+  snprintf(ctemp , 100, "Number of entries in numerator:\t%E\n",fChi2ITSSUMNumerator->GetEntries());
+  stemp += ctemp;
+  snprintf(ctemp , 100, "Number of entries in denominator:\t%E\n",fChi2ITSSUMDenominator->GetEntries());
+  stemp += ctemp;
+  //  stemp += mCoulombWeight->Report();
+  AliFemtoString returnThis = stemp;
+  return returnThis;
+}
+//____________________________
+void AliFemtoChi2CorrFctn::AddRealPair( AliFemtoPair* pair){
+  // add real (effect) pair
+  double tQinv = fabs(pair->QInv());   // note - qInv() will be negative for identical pairs...
+
+  if ((pair->Track1()->Track()->ITSncls() == 0) && (pair->Track2()->Track()->ITSncls() == 0))
+    fChi2ITSSUMNumerator->Fill(tQinv, 1000.0);
+  else 
+    fChi2ITSSUMNumerator->Fill(tQinv, 
+                              (pair->Track1()->Track()->ITSchi2() + 
+                               pair->Track2()->Track()->ITSchi2())/
+                              (pair->Track1()->Track()->ITSncls() +
+                               pair->Track2()->Track()->ITSncls()));
+  if ((pair->Track1()->Track()->TPCncls() == 0) && (pair->Track2()->Track()->TPCncls() == 0))
+    fChi2TPCSUMNumerator->Fill(tQinv, 1000.0);
+  else
+    fChi2TPCSUMNumerator->Fill(tQinv, 
+                              (pair->Track1()->Track()->TPCchi2() +
+                               pair->Track2()->Track()->TPCchi2())/
+                              (pair->Track1()->Track()->TPCncls() +
+                               pair->Track2()->Track()->TPCncls()));
+  double chi2perpointITS1, chi2perpointITS2;
+  if (pair->Track1()->Track()->ITSncls() == 0)
+    chi2perpointITS1 = 1000.0;
+  else
+    chi2perpointITS1 = pair->Track1()->Track()->ITSchi2()/pair->Track1()->Track()->ITSncls();
+
+  if (pair->Track2()->Track()->ITSncls() == 0)
+    chi2perpointITS2 = 1000.0;
+  else
+    chi2perpointITS2 = pair->Track2()->Track()->ITSchi2()/pair->Track2()->Track()->ITSncls();
+
+
+  if (chi2perpointITS1 > chi2perpointITS2) {
+    fChi2ITSONENumerator->Fill(tQinv, chi2perpointITS1);
+  }
+  else {
+    fChi2ITSONENumerator->Fill(tQinv, chi2perpointITS2);
+  }
+
+  double chi2perpointTPC1, chi2perpointTPC2;
+  if (pair->Track1()->Track()->TPCncls() == 0)
+    chi2perpointTPC1 = 1000.0;
+  else
+    chi2perpointTPC1 = pair->Track1()->Track()->TPCchi2()/pair->Track1()->Track()->TPCncls();
+
+  if (pair->Track2()->Track()->TPCncls() == 0)
+    chi2perpointTPC2 = 1000.0;
+  else
+    chi2perpointTPC2 = pair->Track2()->Track()->TPCchi2()/pair->Track2()->Track()->TPCncls();
+
+
+  if (chi2perpointTPC1 > chi2perpointTPC2) {
+    fChi2TPCONENumerator->Fill(tQinv, chi2perpointTPC1);
+  }
+  else {
+    fChi2TPCONENumerator->Fill(tQinv, chi2perpointTPC2);
+  }
+
+  if (pair->Track1()->Track()->SigmaToVertex() > pair->Track2()->Track()->SigmaToVertex()) {
+    fSigmaToVertexNumerator->Fill(tQinv, 
+                                 pair->Track1()->Track()->SigmaToVertex());
+  }
+  else {
+    fSigmaToVertexNumerator->Fill(tQinv, 
+                                 pair->Track2()->Track()->SigmaToVertex());
+  }
+}
+//____________________________
+void AliFemtoChi2CorrFctn::AddMixedPair( AliFemtoPair* pair){
+  // add mixed (background) pair
+  double tQinv = fabs(pair->QInv());   // note - qInv() will be negative for identical pairs...
+
+  if ((pair->Track1()->Track()->ITSncls() == 0) && (pair->Track2()->Track()->ITSncls() == 0))
+    fChi2ITSSUMDenominator->Fill(tQinv, 1000.0);
+  else 
+    fChi2ITSSUMDenominator->Fill(tQinv, 
+                                (pair->Track1()->Track()->ITSchi2() + 
+                                 pair->Track2()->Track()->ITSchi2())/
+                                (pair->Track1()->Track()->ITSncls() +
+                                 pair->Track2()->Track()->ITSncls()));
+  if ((pair->Track1()->Track()->TPCncls() == 0) && (pair->Track2()->Track()->TPCncls() == 0))
+    fChi2TPCSUMDenominator->Fill(tQinv, 1000.0);
+  else
+    fChi2TPCSUMDenominator->Fill(tQinv, 
+                                (pair->Track1()->Track()->TPCchi2() +
+                                 pair->Track2()->Track()->TPCchi2())/
+                                (pair->Track1()->Track()->TPCncls() +
+                                 pair->Track2()->Track()->TPCncls()));
+  double chi2perpointITS1, chi2perpointITS2;
+  if (pair->Track1()->Track()->ITSncls() == 0)
+    chi2perpointITS1 = 1000.0;
+  else
+    chi2perpointITS1 = pair->Track1()->Track()->ITSchi2()/pair->Track1()->Track()->ITSncls();
+
+  if (pair->Track2()->Track()->ITSncls() == 0)
+    chi2perpointITS2 = 1000.0;
+  else
+    chi2perpointITS2 = pair->Track2()->Track()->ITSchi2()/pair->Track2()->Track()->ITSncls();
+
+
+  if (chi2perpointITS1 > chi2perpointITS2) {
+    fChi2ITSONEDenominator->Fill(tQinv, chi2perpointITS1);
+  }
+  else {
+    fChi2ITSONEDenominator->Fill(tQinv, chi2perpointITS2);
+  }
+
+  double chi2perpointTPC1, chi2perpointTPC2;
+  if (pair->Track1()->Track()->TPCncls() == 0)
+    chi2perpointTPC1 = 1000.0;
+  else
+    chi2perpointTPC1 = pair->Track1()->Track()->TPCchi2()/pair->Track1()->Track()->TPCncls();
+
+  if (pair->Track2()->Track()->TPCncls() == 0)
+    chi2perpointTPC2 = 1000.0;
+  else
+    chi2perpointTPC2 = pair->Track2()->Track()->TPCchi2()/pair->Track2()->Track()->TPCncls();
+
+
+  if (chi2perpointTPC1 > chi2perpointTPC2) {
+    fChi2TPCONEDenominator->Fill(tQinv, chi2perpointTPC1);
+  }
+  else {
+    fChi2TPCONEDenominator->Fill(tQinv, chi2perpointTPC2);
+  }
+  if (pair->Track1()->Track()->SigmaToVertex() > pair->Track2()->Track()->SigmaToVertex()) {
+    fSigmaToVertexDenominator->Fill(tQinv, 
+                                 pair->Track1()->Track()->SigmaToVertex());
+  }
+  else {
+    fSigmaToVertexDenominator->Fill(tQinv, 
+                                 pair->Track2()->Track()->SigmaToVertex());
+  }
+}
+
+
+void AliFemtoChi2CorrFctn::WriteHistos()
+{
+  // Write out result histograms
+  fChi2ITSSUMNumerator->Write();
+  fChi2ITSSUMDenominator->Write();
+  fChi2TPCSUMNumerator->Write();
+  fChi2TPCSUMDenominator->Write();
+  fChi2ITSONENumerator->Write();
+  fChi2ITSONEDenominator->Write();
+  fChi2TPCONENumerator->Write();
+  fChi2TPCONEDenominator->Write();
+  fSigmaToVertexNumerator->Write();
+  fSigmaToVertexDenominator->Write();
+  
+}
+
+TList* AliFemtoChi2CorrFctn::GetOutputList()
+{
+  // Prepare the list of objects to be written to the output
+  TList *tOutputList = new TList();
+
+  tOutputList->Add(fChi2ITSSUMNumerator);
+  tOutputList->Add(fChi2ITSSUMDenominator);
+  tOutputList->Add(fChi2TPCSUMNumerator);
+  tOutputList->Add(fChi2TPCSUMDenominator);
+  tOutputList->Add(fChi2ITSONENumerator);
+  tOutputList->Add(fChi2ITSONEDenominator);
+  tOutputList->Add(fChi2TPCONENumerator);
+  tOutputList->Add(fChi2TPCONEDenominator);
+  tOutputList->Add(fSigmaToVertexNumerator);
+  tOutputList->Add(fSigmaToVertexDenominator);
+  
+  return tOutputList;
+
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoChi2CorrFctn.h b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoChi2CorrFctn.h
new file mode 100644 (file)
index 0000000..f38032b
--- /dev/null
@@ -0,0 +1,57 @@
+////////////////////////////////////////////////////////////////////////////////
+///                                                                          ///
+/// AliFemtoChi2CorrFctn - A correlation function that saves the correlation ///
+/// function as a function of single track quality (chi2/ndof) for its and   ///
+/// tpc                                                                      ///
+/// Authors: Adam Kisiel kisiel@mps.ohio-state.edu                           ///
+///                                                                          ///
+////////////////////////////////////////////////////////////////////////////////
+
+#ifndef ALIFEMTOCHI2CORRFCTN_H
+#define ALIFEMTOCHI2CORRFCTN_H
+
+#include "TH1D.h"
+#include "TH2D.h"
+#include "AliFemtoCorrFctn.h"
+
+class AliFemtoChi2CorrFctn : public AliFemtoCorrFctn {
+public:
+  AliFemtoChi2CorrFctn(char* title, const int& nbins, const float& QinvLo, const float& QinvHi);
+  AliFemtoChi2CorrFctn(const AliFemtoChi2CorrFctn& aCorrFctn);
+  virtual ~AliFemtoChi2CorrFctn();
+
+  AliFemtoChi2CorrFctn& operator=(const AliFemtoChi2CorrFctn& aCorrFctn);
+
+  virtual AliFemtoString Report();
+  virtual void AddRealPair(AliFemtoPair* aPair);
+  virtual void AddMixedPair(AliFemtoPair* aPair);
+
+  virtual void Finish();
+
+  void WriteHistos();
+  virtual TList* GetOutputList();
+private:
+  
+  TH2D *fChi2ITSSUMNumerator;        // Numerator as a function of ITS quality sum for the pair
+  TH2D *fChi2ITSSUMDenominator;      // Denominator as a function of ITS quality sum for the pair
+  TH2D *fChi2TPCSUMNumerator;        // Numerator as a function of TPC quality sum for the pair
+  TH2D *fChi2TPCSUMDenominator;      // Denominator as a function of TPC quality sum for the pair
+
+  TH2D *fChi2ITSONENumerator;        // Numerator as a function of ITS quality for the worse track
+  TH2D *fChi2ITSONEDenominator;      // Denominator as a function of ITS quality for the worse track
+  TH2D *fChi2TPCONENumerator;        // Numerator as a function of TPC quality for the worse track
+  TH2D *fChi2TPCONEDenominator;      // Denominator as a function of TPC quality for the worse track
+
+  TH2D *fSigmaToVertexNumerator;     // Numerator as a function of sigma to vertex
+  TH2D *fSigmaToVertexDenominator;   // Numerator as a function of sigma to vertex
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoChi2CorrFctn, 1)
+#endif
+};
+
+
+#endif
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCorrFctn3DSphericalEMCIC.cxx b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCorrFctn3DSphericalEMCIC.cxx
new file mode 100644 (file)
index 0000000..f354635
--- /dev/null
@@ -0,0 +1,365 @@
+/***************************************************************************
+ *
+ * $Id: AliFemtoCorrFctn3DSphercicalEMCIC.h  $
+ *
+ * Author: Nicolas Bock, Ohio State University, bock@mps.ohio-state.edu
+ ***************************************************************************
+ *
+ * Description: Calculates of the 3D Correlation Function in Spherical
+ *              coordinates, and also produces histograms to calculate 
+ *              Energy Momentum Conservation Induced Correlations  (EMCICs)
+ *
+ * This Class produces the following histograms as function of Q, theta, phi
+ * (for both real and mixed pairs):
+ *        1)   E1 + E2
+ *        2)   E1 * E2
+ *        3)   Pt1*Pt2
+ *        4)   Pz1*Pz2
+ *  
+ * This class is similar to AliFemtoCorrFctn3DSpherical, but it uses Q
+ * instead of K to do the binning. 
+ * 
+ * NOTE: The EMCIC histograms are not averaged in this class, to obtain 
+ * the average, the user needs to divide the real pair histograms by 
+ * the numerator, and the mixed pair histograms by the denominator.
+ *
+ ***************************************************************************
+ *
+ **************************************************************************/
+
+#include "AliFemtoCorrFctn3DSphericalEMCIC.h"
+#include "AliFemtoKTPairCut.h"
+#include <TMath.h>
+#include <TVector2.h>
+#include <cstdio>
+
+#ifdef __ROOT__ 
+ClassImp(AliFemtoCorrFctn3DSphericalEMCIC)
+#endif
+
+
+//____________________________
+AliFemtoCorrFctn3DSphericalEMCIC::AliFemtoCorrFctn3DSphericalEMCIC(char* title, const int& nqbins, const float& QLo, const float& QHi, const int& nphibins, const int& ncthetabins):
+  AliFemtoCorrFctn(),
+  fNumerator(0),
+  fDenominator(0),
+/*fEnergyTotalReal(0),  
+  fEnergyMultReal(0),        
+  fPzMultReal(0),      
+  fPtMultReal(0),*/            
+  fEnergyTotalMix (0),      
+  fEnergyMultMix (0),      
+  fPzMultMix(0),            
+  fPtMultMix(0),
+  fPairCut(0x0)
+{
+  
+  // To better sample on phi shift bin low edge by binsize/2 = Pi/numBins.
+  Double_t shiftPhi=TMath::Pi()/nphibins;
+  // set up numerator
+  char tTitNum[101] = "Num";
+  strncat(tTitNum,title, 100);
+  fNumerator = new TH3D(tTitNum,title,nqbins,QLo,QHi,nphibins,
+                       -TMath::Pi()-shiftPhi,TMath::Pi()-shiftPhi,ncthetabins,-1.0,1.0);
+  // set up denominator
+  char tTitDen[101] = "Den";
+  strncat(tTitDen,title, 100);
+  fDenominator = new TH3D(tTitDen,title,nqbins,QLo,QHi,nphibins,
+                         -TMath::Pi()-shiftPhi,TMath::Pi()-shiftPhi,ncthetabins,-1.0,1.0);
+
+  //Added histograms to calculate EMCICs , Nicolas Bock 19.01.2010
+  //Setup EnergyTotalReal
+  /*char tTitNum1[101] = "ESumReal";
+  strncat(tTitNum1,title, 100);
+  fEnergyTotalReal = new TH3D(tTitNum1,title,nqbins,QLo,QHi,nphibins,
+                             -TMath::Pi()-shiftPhi,TMath::Pi()-shiftPhi,ncthetabins,-1.0,1.0);
+  //Setup EnergyMultReal
+  char tTitNum2[101] = "EMultReal";
+  strncat(tTitNum2,title, 100);
+  fEnergyMultReal = new TH3D(tTitNum2,title,nqbins,QLo,QHi,nphibins,
+                            -TMath::Pi()-shiftPhi,TMath::Pi()-shiftPhi,ncthetabins,-1.0,1.0);
+  
+  //Setup Pz MultReal
+  char tTitNum3[101] = "PzMultReal";
+  strncat(tTitNum3,title, 100);
+  fPzMultReal = new TH3D(tTitNum3,title,nqbins,QLo,QHi,nphibins,
+                        -TMath::Pi()-shiftPhi,TMath::Pi()-shiftPhi,ncthetabins,-1.0,1.0);
+
+  //Setup Pt MultReal
+  char tTitNum4[101] = "PtMultReal";
+  strncat(tTitNum4,title, 100);
+  fPtMultReal = new TH3D(tTitNum4,title,nqbins,QLo,QHi,nphibins,
+                        -TMath::Pi()-shiftPhi,TMath::Pi()-shiftPhi,ncthetabins,-1.0,1.0);
+  */ 
+
+
+  //Setup EnergyTotalMix
+  char tTitNum5[101] = "ESumMix";
+  strncat(tTitNum5,title, 100);
+  fEnergyTotalMix = new TH3D(tTitNum5,title,nqbins,QLo,QHi,nphibins,
+                            -TMath::Pi()-shiftPhi,TMath::Pi()-shiftPhi,ncthetabins,-1.0,1.0);
+  
+  //Setup EnergyMultMix
+  char tTitNum6[101] = "EMultMix";
+  strncat(tTitNum6,title, 100);
+  fEnergyMultMix = new TH3D(tTitNum6,title,nqbins,QLo,QHi,nphibins,
+                           -TMath::Pi()-shiftPhi,TMath::Pi()-shiftPhi,ncthetabins,-1.0,1.0);
+  
+  //Setup Pz MultMix
+  char tTitNum7[101] = "PzMultMix";
+  strncat(tTitNum7,title, 100);
+  fPzMultMix = new TH3D(tTitNum7,title,nqbins,QLo,QHi,nphibins,
+                       -TMath::Pi()-shiftPhi,TMath::Pi()-shiftPhi,ncthetabins,-1.0,1.0);
+
+  //Setup Pt MultMix
+  char tTitNum8[101] = "PtMultMix";
+  strncat(tTitNum8,title, 100);
+  fPtMultMix = new TH3D(tTitNum8,title,nqbins,QLo,QHi,nphibins,
+                       -TMath::Pi()-shiftPhi,TMath::Pi()-shiftPhi,
+                       ncthetabins,-1.0,1.0);
+
+  // to enable error bar calculation...
+  fNumerator->Sumw2();
+  fDenominator->Sumw2();
+  /*fEnergyTotalReal->Sumw2();
+  fEnergyMultReal->Sumw2();
+  fPzMultReal->Sumw2();
+  fPtMultReal->Sumw2();  */
+  fEnergyTotalMix->Sumw2();
+  fEnergyMultMix->Sumw2();
+  fPzMultMix->Sumw2();
+  fPtMultMix->Sumw2();
+
+
+}
+
+AliFemtoCorrFctn3DSphericalEMCIC::AliFemtoCorrFctn3DSphericalEMCIC(const AliFemtoCorrFctn3DSphericalEMCIC& aCorrFctn) :
+  AliFemtoCorrFctn(),
+  fNumerator(0),
+  fDenominator(0),
+  /*fEnergyTotalReal(0),
+  fEnergyMultReal(0),        
+  fPzMultReal(0),      
+  fPtMultReal(0),            */
+  fEnergyTotalMix (0),      
+  fEnergyMultMix (0),      
+  fPzMultMix(0),            
+  fPtMultMix(0),
+  fPairCut(0x0)
+{
+  // Copy constructor
+  fNumerator = new TH3D(*aCorrFctn.fNumerator);
+  fDenominator = new TH3D(*aCorrFctn.fDenominator);
+  /*fEnergyTotalReal = new TH3D(*aCorrFctn.fEnergyTotalReal);
+  fEnergyMultReal = new TH3D(*aCorrFctn.fEnergyMultReal);
+  fPzMultReal = new TH3D(*aCorrFctn.fPzMultReal);
+  fPtMultReal = new TH3D(*aCorrFctn.fPtMultReal);*/
+  fEnergyTotalMix = new TH3D(*aCorrFctn.fEnergyTotalMix);
+  fEnergyMultMix = new TH3D(*aCorrFctn.fEnergyMultMix);
+  fPzMultMix = new TH3D(*aCorrFctn.fPzMultMix);
+  fPtMultMix = new TH3D(*aCorrFctn.fPtMultMix);
+  fPairCut = aCorrFctn.fPairCut;
+}
+//____________________________
+AliFemtoCorrFctn3DSphericalEMCIC::~AliFemtoCorrFctn3DSphericalEMCIC(){
+  // Destructor
+  delete fNumerator;
+  delete fDenominator;
+  /*delete fEnergyTotalReal;
+  delete fEnergyMultReal;        
+  delete fPzMultReal;     
+  delete fPtMultReal;            */
+  delete fEnergyTotalMix;      
+  delete fEnergyMultMix; 
+  delete fPzMultMix;   
+  delete fPtMultMix;
+}
+//_________________________
+AliFemtoCorrFctn3DSphericalEMCIC& AliFemtoCorrFctn3DSphericalEMCIC::operator=(const AliFemtoCorrFctn3DSphericalEMCIC& aCorrFctn)
+{
+  // assignment operator
+  if (this == &aCorrFctn)
+    return *this;
+
+  if (fNumerator) delete fNumerator;
+  fNumerator = new TH3D(*aCorrFctn.fNumerator);
+  if (fDenominator) delete fDenominator;
+  fDenominator = new TH3D(*aCorrFctn.fDenominator);
+  /*  if (fEnergyTotalReal) delete fEnergyTotalReal;
+  fEnergyTotalReal = new TH3D(*aCorrFctn.fEnergyTotalReal);
+  if (fEnergyMultReal) delete fEnergyMultReal;
+  fEnergyMultReal = new TH3D(*aCorrFctn.fEnergyMultReal);
+  if (fPzMultReal) delete fPzMultReal;
+  fPzMultReal = new TH3D(*aCorrFctn.fPzMultReal);
+  if (fPtMultReal) delete fPtMultReal;
+  fPtMultReal = new TH3D(*aCorrFctn.fPtMultReal);  */
+  if (fEnergyTotalMix) delete fEnergyTotalMix;
+  fEnergyTotalMix = new TH3D(*aCorrFctn.fEnergyTotalMix);
+  if (fEnergyMultMix) delete fEnergyMultMix;
+  fEnergyMultMix = new TH3D(*aCorrFctn.fEnergyMultMix);
+  if (fPzMultMix) delete fPzMultMix;
+  fPzMultMix = new TH3D(*aCorrFctn.fPzMultMix);
+  if (fPtMultMix) delete fPtMultMix;
+  fPtMultMix = new TH3D(*aCorrFctn.fPtMultMix);
+  fPairCut = aCorrFctn.fPairCut;
+  
+  return *this;
+}
+
+//_________________________
+void AliFemtoCorrFctn3DSphericalEMCIC::WriteOutHistos(){
+  // Write out all histograms to file
+  fNumerator->Write();
+  fDenominator->Write();
+  /*fEnergyTotalReal->Write();
+  fEnergyMultReal->Write();        
+  fPzMultReal->Write();      
+  fPtMultReal->Write();            */
+  fEnergyTotalMix->Write();      
+  fEnergyMultMix->Write();      
+  fPzMultMix->Write();            
+  fPtMultMix->Write();
+}
+//______________________________
+TList* AliFemtoCorrFctn3DSphericalEMCIC::GetOutputList()
+{
+  // Prepare the list of objects to be written to the output
+  TList *tOutputList = new TList();
+
+  tOutputList->Add(fNumerator); 
+  tOutputList->Add(fDenominator);  
+  /*  tOutputList->Add(fEnergyTotalReal);
+  tOutputList->Add(fEnergyMultReal);        
+  tOutputList->Add(fPzMultReal);      
+  tOutputList->Add(fPtMultReal);            */
+  tOutputList->Add(fEnergyTotalMix );      
+  tOutputList->Add(fEnergyMultMix );      
+  tOutputList->Add(fPzMultMix);            
+  tOutputList->Add(fPtMultMix);
+  return tOutputList;
+}
+
+//_________________________
+void AliFemtoCorrFctn3DSphericalEMCIC::Finish(){
+  // here is where we should normalize, fit, etc...
+}
+
+//____________________________
+AliFemtoString AliFemtoCorrFctn3DSphericalEMCIC::Report(){
+  // Construct the report
+  string stemp = "PRF Frame SphericalEMCIC 3D Correlation Function Report:\n";
+  char ctemp[100];
+  snprintf(ctemp , 100, "Number of entries in numerator:\t%E\n",fNumerator->GetEntries());
+  stemp += ctemp;
+  snprintf(ctemp , 100, "Number of entries in denominator:\t%E\n",fDenominator->GetEntries());
+  stemp += ctemp;
+
+  if (fPairCut){
+    snprintf(ctemp , 100, "Here is the PairCut specific to this CorrFctn\n");
+    stemp += ctemp;
+    stemp += fPairCut->Report();
+  }
+  else{
+    snprintf(ctemp , 100, "No PairCut specific to this CorrFctn\n");
+    stemp += ctemp;
+  }
+
+  //  
+  AliFemtoString returnThis = stemp;
+  return returnThis;
+}
+//____________________________
+void AliFemtoCorrFctn3DSphericalEMCIC::AddRealPair( AliFemtoPair* pair){
+  // perform operations on real pairs
+  if (fPairCut){
+    AliFemtoKTPairCut *ktc = dynamic_cast<AliFemtoKTPairCut *>(fPairCut);
+    if (!ktc){
+      if (!(fPairCut->Pass(pair))) return;
+    }
+    else
+      if (!(ktc->Pass(pair))) return;
+  }
+
+  //                          
+  double tQO = pair->QOutCMS();  
+  double tQS = pair->QSideCMS();  
+  double tQL = pair->QLongCMS();  
+
+  double tQR = sqrt(tQO*tQO + tQS*tQS + tQL*tQL);
+  double tQC = 0;
+  if ( fabs(tQR) < 1e-10 ) tQC = 0.0;
+  else tQC = tQL/tQR;
+  double tQP = atan2(tQS,tQO);
+
+  fNumerator->Fill(tQR,tQP,tQC);
+  
+  // EMCICs  
+  /*AliFemtoLorentzVector tMom1 = pair->Track1()->FourMomentum();
+  AliFemtoLorentzVector tMom2 = pair->Track2()->FourMomentum();
+  double tE1 = tMom1.e();
+  double tE2 = tMom2.e();
+  double tPz1 = tMom1.pz();
+  double tPz2 = tMom2.pz();
+  
+  TVector2 tPt1;  
+  TVector2 tPt2; 
+  tPt1.Set(tMom1.px(),tMom1.py());
+  tPt2.Set(tMom2.px(),tMom2.py());
+  double tPt1DotPt2 = tPt1*tPt2;
+  
+  fEnergyTotalReal->Fill(tQR,tQP,tQC,tE1+tE2);
+  fEnergyMultReal->Fill(tQR,tQP,tQC,tE1*tE2);
+  fPzMultReal->Fill(tQR,tQP,tQC,tPz1*tPz2);
+  fPtMultReal->Fill(tQR,tQP,tQC,tPt1DotPt2);*/
+   
+
+}
+//____________________________
+void AliFemtoCorrFctn3DSphericalEMCIC::AddMixedPair( AliFemtoPair* pair){
+  // perform operations on mixed pairs
+  if (fPairCut){
+    AliFemtoKTPairCut *ktc = dynamic_cast<AliFemtoKTPairCut *>(fPairCut);
+    if (!ktc){
+      if (!(fPairCut->Pass(pair))) return;
+    }
+    else
+      if (!(ktc->Pass(pair))) return;
+  }
+  
+
+
+ //                          //Changed K to Q to be in LCMS, N. Bock
+  double tQO = pair->QOutCMS();  
+  double tQS = pair->QSideCMS();   
+  double tQL = pair->QLongCMS();  
+
+  double tQR = sqrt(tQO*tQO + tQS*tQS + tQL*tQL);
+  double tQC;
+  if ( fabs(tQR) < 1e-10 ) tQC = 0.0;
+  else tQC=tQL/tQR;
+  double tQP=atan2(tQS,tQO);
+
+  fDenominator->Fill(tQR,tQP,tQC);
+
+  // EMCICs   
+  AliFemtoLorentzVector tMom1 = pair->Track1()->FourMomentum();
+  AliFemtoLorentzVector tMom2 = pair->Track2()->FourMomentum();
+  double tE1 = tMom1.e();
+  double tE2 = tMom2.e();
+  double tPz1 = tMom1.pz();
+  double tPz2 = tMom2.pz();
+  
+  TVector2 tPt1;  
+  TVector2 tPt2; 
+  tPt1.Set(tMom1.px(),tMom1.py());
+  tPt2.Set(tMom2.px(),tMom2.py());
+  double tPt1DotPt2 = tPt1*tPt2;
+  
+  fEnergyTotalMix->Fill(tQR,tQP,tQC,tE1+tE2);
+  fEnergyMultMix->Fill(tQR,tQP,tQC,tE1*tE2);
+  fPzMultMix->Fill(tQR,tQP,tQC,tPz1*tPz2);
+  fPtMultMix->Fill(tQR,tQP,tQC,tPt1DotPt2);
+  
+}
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCorrFctn3DSphericalEMCIC.h b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCorrFctn3DSphericalEMCIC.h
new file mode 100644 (file)
index 0000000..9231a15
--- /dev/null
@@ -0,0 +1,60 @@
+
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFemtoCorrFctn3DSpherical: a class to calculate 3D correlation      //
+// for pairs of identical particles, binned in spherical coordinates     //
+// (q_inv, phi, cos(theta))
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+
+#ifndef ALIFEMTOCORRFCTN3DSPHERICALEMCIC_H
+#define ALIFEMTOCORRFCTN3DSPHERICALEMCIC_H
+
+#include "AliFemtoCorrFctn.h"
+#include "AliFemtoPairCut.h"
+#include "TH3D.h"
+
+class AliFemtoCorrFctn3DSphericalEMCIC : public AliFemtoCorrFctn{
+public:
+  AliFemtoCorrFctn3DSphericalEMCIC(char* title, 
+                             const int& nqbins, const float& QLo, const float& QHi,
+                             const int& nphibins, const int& ncthetabins);
+  AliFemtoCorrFctn3DSphericalEMCIC(const AliFemtoCorrFctn3DSphericalEMCIC& aCorrFctn);
+  virtual ~AliFemtoCorrFctn3DSphericalEMCIC();
+
+  AliFemtoCorrFctn3DSphericalEMCIC& operator=(const AliFemtoCorrFctn3DSphericalEMCIC& aCorrFctn);
+
+  virtual AliFemtoString Report();
+  virtual void AddRealPair( AliFemtoPair* aPair);
+  virtual void AddMixedPair( AliFemtoPair* aPair);
+
+  virtual void Finish();
+
+  void WriteOutHistos();
+  virtual TList* GetOutputList();
+
+  void SetSpecificPairCut(AliFemtoPairCut* aCut);
+
+ private:
+  
+  TH3D* fNumerator;         // numerator
+  TH3D* fDenominator;       // denominator
+  //EMCIC histograms:
+  /*TH3D* fEnergyTotalReal;       // E1+E2 from real pairs
+  TH3D* fEnergyMultReal;        // E1*E2
+  TH3D* fPzMultReal;            // Pz1*Pz2
+  TH3D* fPtMultReal;            // Pt1*Pt2  */
+  TH3D* fEnergyTotalMix;       // E1+E2 from mixed pairs
+  TH3D* fEnergyMultMix;        // E1*E2
+  TH3D* fPzMultMix;            // Pz1*Pz2
+  TH3D* fPtMultMix;            // Pt1*Pt2
+  AliFemtoPairCut* fPairCut;    //! this is a PairCut specific to THIS CorrFctn, not the Analysis
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoCorrFctn3DSphericalEMCIC, 1)
+#endif
+};
+
+inline  void AliFemtoCorrFctn3DSphericalEMCIC::SetSpecificPairCut(AliFemtoPairCut* pc){fPairCut=pc;}
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCorrFctnDEtaDPhi.cxx b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCorrFctnDEtaDPhi.cxx
new file mode 100644 (file)
index 0000000..a452e85
--- /dev/null
@@ -0,0 +1,389 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoCorrFctnDEtaDPhi - A correlation function that analyzes            //
+// two particle correlations with respect to the azimuthal angle (phi)        //
+// and pseudorapidity (eta) difference                                        //
+//                                                                            //
+// Authors: Adam Kisiel Adam.Kisiel@cern.ch                                   //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+
+#include "AliFemtoCorrFctnDEtaDPhi.h"
+#include "AliFemtoModelHiddenInfo.h"
+//#include "AliFemtoHisto.hh"
+#include <cstdio>
+#include <TMath.h>
+
+#ifdef __ROOT__ 
+ClassImp(AliFemtoCorrFctnDEtaDPhi)
+#endif
+  
+#define PIH 1.57079632679489656
+#define PIT 6.28318530717958623
+#define PIQ 4.71238898038468967
+
+//____________________________
+AliFemtoCorrFctnDEtaDPhi::AliFemtoCorrFctnDEtaDPhi(char* title, const int& aPhiBins=20, const int& aEtaBins=20):
+  AliFemtoCorrFctn(),
+  fDPhiDEtaNumerator(0),
+  fDPhiDEtaDenominator(0),
+  fDPhiNumerator(0),
+  fDPhiDenominator(0),
+  fDCosNumerator(0),
+  fDCosDenominator(0),
+  fDoPtAnalysis(0),
+  fDPhiPtNumerator(0),
+  fDPhiPtDenominator(0),
+  fDCosPtNumerator(0),
+  fDCosPtDenominator(0)
+{
+  // set up numerator
+  char tTitNumD[101] = "NumDPhiDEta";
+  strncat(tTitNumD,title, 100);
+  fDPhiDEtaNumerator = new TH2D(tTitNumD,title,aPhiBins,-0.5*TMath::Pi(),1.5*TMath::Pi(),aEtaBins,-2.5,2.5);
+  // set up denominator
+  char tTitDenD[101] = "DenDPhiDEta";
+  strncat(tTitDenD,title, 100);
+  fDPhiDEtaDenominator = new TH2D(tTitDenD,title,aPhiBins,-0.5*TMath::Pi(),1.5*TMath::Pi(),aEtaBins,-2.5,2.5);
+
+  // set up numerator
+  char tTitNumDPhi[101] = "NumDPhi";
+  strncat(tTitNumDPhi,title, 100);
+  fDPhiNumerator = new TH1D(tTitNumDPhi,title,aPhiBins*2,-0.5*TMath::Pi(),1.5*TMath::Pi());
+  // set up denominator
+  char tTitDenDPhi[101] = "DenDPhi";
+  strncat(tTitDenDPhi,title, 100);
+  fDPhiDenominator = new TH1D(tTitDenDPhi,title,aPhiBins*2,-0.5*TMath::Pi(),1.5*TMath::Pi());
+
+  // set up numerator
+  char tTitNumDCos[101] = "NumDCos";
+  strncat(tTitNumDCos,title, 100);
+  fDCosNumerator = new TH1D(tTitNumDCos,title,aPhiBins*2,-1.0,1.0);
+  // set up denominator
+  char tTitDenDCos[101] = "DenDCos";
+  strncat(tTitDenDCos,title, 100);
+  fDCosDenominator = new TH1D(tTitDenDCos,title,aPhiBins*2,-1.0,1.0);
+
+  // to enable error bar calculation...
+  fDPhiDEtaNumerator->Sumw2();
+  fDPhiDEtaDenominator->Sumw2();
+  fDPhiNumerator->Sumw2();
+  fDPhiDenominator->Sumw2();
+  fDCosNumerator->Sumw2();
+  fDCosDenominator->Sumw2();
+}
+
+//____________________________
+AliFemtoCorrFctnDEtaDPhi::AliFemtoCorrFctnDEtaDPhi(const AliFemtoCorrFctnDEtaDPhi& aCorrFctn) :
+  AliFemtoCorrFctn(),
+  fDPhiDEtaNumerator(0),
+  fDPhiDEtaDenominator(0),
+  fDPhiNumerator(0),
+  fDPhiDenominator(0),
+  fDCosNumerator(0),
+  fDCosDenominator(0),
+  fDoPtAnalysis(0),
+  fDPhiPtNumerator(0),
+  fDPhiPtDenominator(0),
+  fDCosPtNumerator(0),
+  fDCosPtDenominator(0)
+{
+  // copy constructor
+  if (aCorrFctn.fDPhiDEtaNumerator)
+    fDPhiDEtaNumerator = new TH2D(*aCorrFctn.fDPhiDEtaNumerator);
+  else
+    fDPhiDEtaNumerator = 0;
+  if (aCorrFctn.fDPhiDEtaDenominator)
+    fDPhiDEtaDenominator = new TH2D(*aCorrFctn.fDPhiDEtaDenominator);
+  else
+    fDPhiDEtaDenominator = 0;
+
+  if (aCorrFctn.fDPhiNumerator)
+    fDPhiNumerator = new TH1D(*aCorrFctn.fDPhiNumerator);
+  else
+    fDPhiNumerator = 0;
+  if (aCorrFctn.fDPhiDenominator)
+    fDPhiDenominator = new TH1D(*aCorrFctn.fDPhiDenominator);
+  else
+    fDPhiDenominator = 0;
+
+  if (aCorrFctn.fDCosNumerator)
+    fDCosNumerator = new TH1D(*aCorrFctn.fDCosNumerator);
+  else
+    fDCosNumerator = 0;
+  if (aCorrFctn.fDCosDenominator)
+    fDCosDenominator = new TH1D(*aCorrFctn.fDCosDenominator);
+  else
+    fDCosDenominator = 0;
+
+  if (aCorrFctn.fDPhiPtNumerator)
+    fDPhiPtNumerator = new TH2D(*aCorrFctn.fDPhiPtNumerator);
+  else
+    fDPhiPtNumerator = 0;
+  if (aCorrFctn.fDPhiPtDenominator)
+    fDPhiPtDenominator = new TH2D(*aCorrFctn.fDPhiPtDenominator);
+  else
+    fDPhiPtDenominator = 0;
+
+  if (aCorrFctn.fDCosPtNumerator)
+    fDCosPtNumerator = new TH2D(*aCorrFctn.fDCosPtNumerator);
+  else
+    fDCosPtNumerator = 0;
+  if (aCorrFctn.fDCosPtDenominator)
+    fDCosPtDenominator = new TH2D(*aCorrFctn.fDCosPtDenominator);
+  else
+    fDCosPtDenominator = 0;
+
+}
+//____________________________
+AliFemtoCorrFctnDEtaDPhi::~AliFemtoCorrFctnDEtaDPhi(){
+  // destructor
+  delete fDPhiDEtaNumerator;
+  delete fDPhiDEtaDenominator;
+  delete fDPhiNumerator;
+  delete fDPhiDenominator;
+  delete fDCosNumerator;
+  delete fDCosDenominator;
+  if (fDoPtAnalysis) {
+    delete fDPhiPtNumerator;
+    delete fDPhiPtDenominator;
+    delete fDCosPtNumerator;
+    delete fDCosPtDenominator;
+  }
+}
+//_________________________
+AliFemtoCorrFctnDEtaDPhi& AliFemtoCorrFctnDEtaDPhi::operator=(const AliFemtoCorrFctnDEtaDPhi& aCorrFctn)
+{
+  // assignment operator
+  if (this == &aCorrFctn)
+    return *this;
+
+  if (aCorrFctn.fDPhiDEtaNumerator)
+    fDPhiDEtaNumerator = new TH2D(*aCorrFctn.fDPhiDEtaNumerator);
+  else
+    fDPhiDEtaNumerator = 0;
+  if (aCorrFctn.fDPhiDEtaDenominator)
+    fDPhiDEtaDenominator = new TH2D(*aCorrFctn.fDPhiDEtaDenominator);
+  else
+    fDPhiDEtaDenominator = 0;
+
+  if (aCorrFctn.fDPhiNumerator)
+    fDPhiNumerator = new TH1D(*aCorrFctn.fDPhiNumerator);
+  else
+    fDPhiNumerator = 0;
+  if (aCorrFctn.fDPhiDenominator)
+    fDPhiDenominator = new TH1D(*aCorrFctn.fDPhiDenominator);
+  else
+    fDPhiDenominator = 0;
+
+  if (aCorrFctn.fDCosNumerator)
+    fDCosNumerator = new TH1D(*aCorrFctn.fDCosNumerator);
+  else
+    fDCosNumerator = 0;
+  if (aCorrFctn.fDCosDenominator)
+    fDCosDenominator = new TH1D(*aCorrFctn.fDCosDenominator);
+  else
+    fDCosDenominator = 0;
+
+  if (aCorrFctn.fDPhiPtNumerator)
+    fDPhiPtNumerator = new TH2D(*aCorrFctn.fDPhiPtNumerator);
+  else
+    fDPhiPtNumerator = 0;
+  if (aCorrFctn.fDPhiPtDenominator)
+    fDPhiPtDenominator = new TH2D(*aCorrFctn.fDPhiPtDenominator);
+  else
+    fDPhiPtDenominator = 0;
+
+  if (aCorrFctn.fDCosPtNumerator)
+    fDCosPtNumerator = new TH2D(*aCorrFctn.fDCosPtNumerator);
+  else
+    fDCosPtNumerator = 0;
+  if (aCorrFctn.fDCosPtDenominator)
+    fDCosPtDenominator = new TH2D(*aCorrFctn.fDCosPtDenominator);
+  else
+    fDCosPtDenominator = 0;
+
+  return *this;
+}
+//_________________________
+void AliFemtoCorrFctnDEtaDPhi::Finish(){
+  // here is where we should normalize, fit, etc...
+  // we should NOT Draw() the histos (as I had done it below),
+  // since we want to insulate ourselves from root at this level
+  // of the code.  Do it instead at root command line with browser.
+  //  mShareNumerator->Draw();
+  //mShareDenominator->Draw();
+  //mRatio->Draw();
+
+}
+
+//____________________________
+AliFemtoString AliFemtoCorrFctnDEtaDPhi::Report(){
+  // create report
+  string stemp = "TPC Ncls Correlation Function Report:\n";
+  char ctemp[100];
+  snprintf(ctemp , 100, "Number of entries in numerator:\t%E\n",fDPhiDEtaNumerator->GetEntries());
+  stemp += ctemp;
+  snprintf(ctemp , 100, "Number of entries in denominator:\t%E\n",fDPhiDEtaDenominator->GetEntries());
+  stemp += ctemp;
+  //  stemp += mCoulombWeight->Report();
+  AliFemtoString returnThis = stemp;
+  return returnThis;
+}
+//____________________________
+void AliFemtoCorrFctnDEtaDPhi::AddRealPair( AliFemtoPair* pair){
+  // add real (effect) pair
+  if (fPairCut)
+    if (!fPairCut->Pass(pair)) return;
+
+  double phi1 = pair->Track1()->Track()->P().Phi();
+  double phi2 = pair->Track2()->Track()->P().Phi();
+  double eta1 = pair->Track1()->Track()->P().PseudoRapidity();
+  double eta2 = pair->Track2()->Track()->P().PseudoRapidity();
+
+  double dphi = phi1 - phi2;
+  while (dphi<-PIH) dphi+=PIT;
+  while (dphi>PIQ) dphi-=PIT;
+
+  double deta = eta1 - eta2;
+
+//   double px1 = pair->Track1()->Track()->P().x();
+//   double py1 = pair->Track1()->Track()->P().y();
+//   double pz1 = pair->Track1()->Track()->P().z();
+
+//   double px2 = pair->Track2()->Track()->P().x();
+//   double py2 = pair->Track2()->Track()->P().y();
+//   double pz2 = pair->Track2()->Track()->P().z();
+
+//   double pt1 = TMath::Hypot(px1, py1);
+//   double pt2 = TMath::Hypot(px2, py2);
+//   double ptmin = pt1>pt2 ? pt2 : pt1;
+
+//   double cosphi = (px1*px2 + py1*py2 + pz1*pz2)/
+//     sqrt((px1*px1 + py1*py1 + pz1*pz1)*(px2*px2 + py2*py2 + pz2*pz2));
+
+  fDPhiDEtaNumerator->Fill(dphi, deta);
+
+  fDPhiNumerator->Fill(dphi);
+//   fDCosNumerator->Fill(cosphi);
+
+  if (fDoPtAnalysis) {
+//     fDPhiPtNumerator->Fill(dphi, ptmin);
+//     fDCosPtNumerator->Fill(cosphi, ptmin);
+  }
+
+}
+//____________________________
+void AliFemtoCorrFctnDEtaDPhi::AddMixedPair( AliFemtoPair* pair){
+  // add mixed (background) pair
+  if (fPairCut)
+    if (!fPairCut->Pass(pair)) return;
+
+  double phi1 = pair->Track1()->Track()->P().Phi();
+  double phi2 = pair->Track2()->Track()->P().Phi();
+  double eta1 = pair->Track1()->Track()->P().PseudoRapidity();
+  double eta2 = pair->Track2()->Track()->P().PseudoRapidity();
+
+  double dphi = phi1 - phi2;
+  while (dphi<-PIH) dphi+=PIT;
+  while (dphi>PIQ) dphi-=PIT;
+
+  double deta = eta1 - eta2;
+
+//   double px1 = pair->Track1()->Track()->P().x();
+//   double py1 = pair->Track1()->Track()->P().y();
+//   double pz1 = pair->Track1()->Track()->P().z();
+
+//   double px2 = pair->Track2()->Track()->P().x();
+//   double py2 = pair->Track2()->Track()->P().y();
+//   double pz2 = pair->Track2()->Track()->P().z();
+
+//   double pt1 = TMath::Hypot(px1, py1);
+//   double pt2 = TMath::Hypot(px2, py2);
+//   double ptmin = pt1>pt2 ? pt2 : pt1;
+
+//   double cosphi = (px1*px2 + py1*py2 + pz1*pz2)/
+//     sqrt((px1*px1 + py1*py1 + pz1*pz1)*(px2*px2 + py2*py2 + pz2*pz2));
+
+  fDPhiDEtaDenominator->Fill(dphi, deta);
+
+  fDPhiDenominator->Fill(dphi);
+//   fDCosDenominator->Fill(cosphi);
+
+  if (fDoPtAnalysis) {
+    //   fDPhiPtDenominator->Fill(dphi, ptmin);
+    //   fDCosPtDenominator->Fill(cosphi, ptmin);
+  }
+}
+
+
+void AliFemtoCorrFctnDEtaDPhi::WriteHistos()
+{
+  // Write out result histograms
+  fDPhiDEtaNumerator->Write();
+  fDPhiDEtaDenominator->Write();
+  fDPhiNumerator->Write();
+  fDPhiDenominator->Write();
+  fDCosNumerator->Write();
+  fDCosDenominator->Write();
+  if (fDoPtAnalysis) {
+    fDPhiPtNumerator->Write();
+    fDPhiPtDenominator->Write();
+    fDCosPtNumerator->Write();
+    fDCosPtDenominator->Write();
+  }
+}
+
+TList* AliFemtoCorrFctnDEtaDPhi::GetOutputList()
+{
+  // Prepare the list of objects to be written to the output
+  TList *tOutputList = new TList();
+
+  tOutputList->Add(fDPhiDEtaNumerator);
+  tOutputList->Add(fDPhiDEtaDenominator);
+  tOutputList->Add(fDPhiNumerator);
+  tOutputList->Add(fDPhiDenominator);
+  tOutputList->Add(fDCosNumerator);
+  tOutputList->Add(fDCosDenominator);
+  if (fDoPtAnalysis) {
+    tOutputList->Add(fDPhiPtNumerator);
+    tOutputList->Add(fDPhiPtDenominator);
+    tOutputList->Add(fDCosPtNumerator);
+    tOutputList->Add(fDCosPtDenominator);
+  }
+
+  return tOutputList;
+
+}
+
+void AliFemtoCorrFctnDEtaDPhi::SetDoPtAnalysis(int do2d)
+{
+  fDoPtAnalysis = do2d;
+  
+  int aPhiBins = fDPhiDEtaNumerator->GetNbinsX();
+  const char *title = fDPhiDEtaNumerator->GetTitle();
+
+  // set up numerator
+  char tTitNumDPhiPt[101] = "NumDPhiPt";
+  strncat(tTitNumDPhiPt,title, 100);
+  fDPhiPtNumerator = new TH2D(tTitNumDPhiPt,title,aPhiBins*2,-0.5*TMath::Pi(),1.5*TMath::Pi(), 30, 0.0, 3.0);
+  // set up denominator
+  char tTitDenDPhiPt[101] = "DenDPhiPt";
+  strncat(tTitDenDPhiPt,title, 100);
+  fDPhiPtDenominator = new TH2D(tTitDenDPhiPt,title,aPhiBins*2,-0.5*TMath::Pi(),1.5*TMath::Pi(), 30, 0.0, 3.0);
+
+  // set up numerator
+  char tTitNumDCosPt[101] = "NumDCosPt";
+  strncat(tTitNumDCosPt,title, 100);
+  fDCosPtNumerator = new TH2D(tTitNumDCosPt,title,aPhiBins*2,-1.0,1.0, 30, 0.0, 3.0);
+  // set up denominator
+  char tTitDenDCosPt[101] = "DenDCosPt";
+  strncat(tTitDenDCosPt,title, 100);
+  fDCosPtDenominator = new TH2D(tTitDenDCosPt,title,aPhiBins*2,-1.0,1.0, 30, 0.0, 3.0);
+
+  fDPhiPtNumerator->Sumw2();
+  fDPhiPtDenominator->Sumw2();
+  fDCosPtNumerator->Sumw2();
+  fDCosPtDenominator->Sumw2();
+  
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCorrFctnDEtaDPhi.h b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCorrFctnDEtaDPhi.h
new file mode 100644 (file)
index 0000000..bff3e3d
--- /dev/null
@@ -0,0 +1,61 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoCorrFctnDEtaDPhi - A correlation function that analyzes            //
+// two particle correlations with respect to the azimuthal angle (phi)        //
+// and pseudorapidity (eta) difference                                        //
+//                                                                            //
+// Authors: Adam Kisiel Adam.Kisiel@cern.ch                                   //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+
+#ifndef ALIFEMTOCORRFCTNDETADPHI_H
+#define ALIFEMTOCORRFCTNDETADPHI_H
+
+#include "TH1D.h"
+#include "TH2D.h"
+#include "AliFemtoCorrFctn.h"
+
+class AliFemtoCorrFctnDEtaDPhi : public AliFemtoCorrFctn {
+public:
+  AliFemtoCorrFctnDEtaDPhi(char* title, const int& aPhiBins, const int& aEtaBins);
+  AliFemtoCorrFctnDEtaDPhi(const AliFemtoCorrFctnDEtaDPhi& aCorrFctn);
+  virtual ~AliFemtoCorrFctnDEtaDPhi();
+
+  AliFemtoCorrFctnDEtaDPhi& operator=(const AliFemtoCorrFctnDEtaDPhi& aCorrFctn);
+
+  virtual AliFemtoString Report();
+  virtual void AddRealPair(AliFemtoPair* aPair);
+  virtual void AddMixedPair(AliFemtoPair* aPair);
+
+  virtual void Finish();
+  void SetDoPtAnalysis(int do2d);
+
+  void WriteHistos();
+  virtual TList* GetOutputList();
+private:
+  
+  TH2D *fDPhiDEtaNumerator;          // Numerator of dEta dPhi function
+  TH2D *fDPhiDEtaDenominator;        // Denominator of dEta dPhi function
+
+  TH1D *fDPhiNumerator;              // Numerator of dPhi correlation
+  TH1D *fDPhiDenominator;            // Denominator of dPhi correlation
+
+  TH1D *fDCosNumerator;              // Numerator of colinearity correlation
+  TH1D *fDCosDenominator;            // Denominator of colinearity correlation
+
+  int   fDoPtAnalysis;               // set to 1 to do 2D Pt analysis
+
+  TH2D *fDPhiPtNumerator;            // Numerator of dPhi correlation vs. Pt min
+  TH2D *fDPhiPtDenominator;          // Denominator of dPhi correlation vs. Pt min
+
+  TH2D *fDCosPtNumerator;            // Numerator of colinearity correlation vs. Pt min
+  TH2D *fDCosPtDenominator;          // Denominator of colinearity correlation vs. Pt min
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoCorrFctnDEtaDPhi, 1)
+#endif
+};
+
+
+#endif
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCorrFctnDirectYlm.cxx b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCorrFctnDirectYlm.cxx
new file mode 100644 (file)
index 0000000..f6aadb1
--- /dev/null
@@ -0,0 +1,1001 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoCorrFctnDirectYlm - Correlation function that is binned in Ylms    //
+// directly. Provides a way to store the numerator and denominator            //
+// in Ylms directly and correctly calculate the correlation                   //
+// function from them.                                                        //
+//                                                                            //
+// Authors: Adam Kisiel kisiel@mps.ohio-state.edu                             //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+#include "AliFemtoCorrFctnDirectYlm.h"
+#include <TMath.h>
+#include <iostream>
+
+using namespace std;
+
+AliFemtoCorrFctnDirectYlm::AliFemtoCorrFctnDirectYlm(const char *name, int maxl, int ibin=30, double vmin=0.0, double vmax=0.3, int aUseLCMS=0):
+  fnumsreal(0),
+  fnumsimag(0),
+  fdensreal(0),
+  fdensimag(0),
+  fbinctn(0),
+  fbinctd(0),
+  fcovnum(0),
+  fcovden(0),
+  fcovmnum(0),
+  fcovmden(0),
+  fMaxL(0),
+  fMaxJM(0),
+  fels(0),
+  fems(0),
+  felsi(0),
+  femsi(0),
+  fYlmBuffer(0),
+  factorials(0),
+  fSout(0.0),
+  fSside(0.0),
+  fSlong(0.0),
+  fUseLCMS(aUseLCMS)
+{
+  // Main constructor
+  fMaxL = maxl;
+  fMaxJM = (maxl+1)*(maxl+1);
+
+  // *DEB*  cout <<  "Size is " << sizeof(double) << " " << sizeof(complex<double>) << endl;
+
+  // Fill in factorials table
+  factorials = (double *) malloc(sizeof(double) * (4 * (maxl + 1)));
+  int fac = 1;
+  factorials[0] = 1;
+  for (int iter=1; iter<4*(maxl+1); iter++)
+    {
+      fac *= iter;
+      factorials[iter] = fac;
+    }
+
+  // Fill in els and ems table
+  int el = 0;
+  int em = 0;
+  int il = 0;
+  fels = (double *) malloc(sizeof(double) * (fMaxJM));
+  fems = (double *) malloc(sizeof(double) * (fMaxJM));
+  felsi = (int *) malloc(sizeof(int) * (fMaxJM));
+  femsi = (int *) malloc(sizeof(int) * (fMaxJM));
+  do {
+    fels[il] = el;
+    fems[il] = em;
+    felsi[il] = (int) el;
+    femsi[il] = (int) em;
+
+    // *DEB*    cout << "il el em " << il << " " << felsi[il] << " " << femsi[il] << endl;
+    em++;
+    il++;
+    if (em > el) {
+      el++;
+      em = -el;
+    }
+  }
+  while (el <= maxl);
+  
+  // *DEB*  for (il=0; il<fMaxJM; il++)
+  // *DEB*    cout << "il el em " << il << " " << felsi[il] << " " << femsi[il] << endl;
+
+  // Create numerator and denominator historgrams
+  //  int sthp = sizeof(TH1D *);
+  //  fnumsreal = (TH1D **) malloc(sthp * fMaxJM);
+//   fnumsreal = new TH1D * [fMaxJM];
+//   fnumsimag = new TH1D * [fMaxJM];
+//   fdensreal = new TH1D * [fMaxJM];
+//   fdensimag = new TH1D * [fMaxJM];
+  fnumsreal = (TH1D **) malloc(sizeof(TH1D *) * fMaxJM);
+  fnumsimag = (TH1D **) malloc(sizeof(TH1D *) * fMaxJM);
+  fdensreal = (TH1D **) malloc(sizeof(TH1D *) * fMaxJM);
+  fdensimag = (TH1D **) malloc(sizeof(TH1D *) * fMaxJM);
+  
+  char bufname[200];
+  for (int ihist=0; ihist<fMaxJM; ihist++) {
+    snprintf(bufname , 200,  "NumReYlm%i%i%s", felsi[ihist], femsi[ihist]<0 ? felsi[ihist]-femsi[ihist] : femsi[ihist], name);
+    fnumsreal[ihist] = new TH1D(bufname, bufname, ibin, vmin, vmax);
+    snprintf(bufname , 200,  "NumImYlm%i%i%s", felsi[ihist], femsi[ihist]<0 ? felsi[ihist]-femsi[ihist] : femsi[ihist], name);
+    fnumsimag[ihist] = new TH1D(bufname, bufname, ibin, vmin, vmax);
+    snprintf(bufname , 200,  "DenReYlm%i%i%s", felsi[ihist], femsi[ihist]<0 ? felsi[ihist]-femsi[ihist] : femsi[ihist], name);
+    fdensreal[ihist] = new TH1D(bufname, bufname, ibin, vmin, vmax);
+    snprintf(bufname , 200,  "DenImYlm%i%i%s", felsi[ihist], femsi[ihist]<0 ? felsi[ihist]-femsi[ihist] : femsi[ihist], name);
+    fdensimag[ihist] = new TH1D(bufname, bufname, ibin, vmin, vmax);
+
+    fnumsreal[ihist]->Sumw2();
+    fnumsimag[ihist]->Sumw2();
+    fdensreal[ihist]->Sumw2();
+    fdensimag[ihist]->Sumw2();
+  }
+
+  snprintf(bufname , 200,  "BinCountNum%s", name);
+  fbinctn = new TH1D(bufname, bufname, ibin, vmin, vmax);
+
+  snprintf(bufname , 200,  "BinCountDen%s", name);
+  fbinctd = new TH1D(bufname, bufname, ibin, vmin, vmax);
+
+  fYlmBuffer = (complex<double> *) malloc(sizeof(complex<double>) * fMaxJM);
+  
+  // Covariance matrices
+  fcovmnum = (double *) malloc(sizeof(double) * fMaxJM * fMaxJM * 4 * ibin);
+  fcovmden = (double *) malloc(sizeof(double) * fMaxJM * fMaxJM * 4 * ibin);
+
+  fcovnum = 0;
+  fcovden = 0;
+
+  AliFemtoYlm::InitializeYlms();
+}
+
+
+AliFemtoCorrFctnDirectYlm::AliFemtoCorrFctnDirectYlm():
+  fnumsreal(0),
+  fnumsimag(0),
+  fdensreal(0),
+  fdensimag(0),
+  fbinctn(0),
+  fbinctd(0),
+  fcovnum(0),
+  fcovden(0),
+  fcovmnum(0),
+  fcovmden(0),
+  fMaxL(0),
+  fMaxJM(0),
+  fels(0),
+  fems(0),
+  felsi(0),
+  femsi(0),
+  fYlmBuffer(0),
+  factorials(0),
+  fSout(0.0),
+  fSside(0.0),
+  fSlong(0.0),
+  fUseLCMS(0)
+{
+  // Default constructor
+  AliFemtoCorrFctnDirectYlm("AliFemtoCorrFctnDirectYlm",2);
+}
+
+AliFemtoCorrFctnDirectYlm::AliFemtoCorrFctnDirectYlm(const AliFemtoCorrFctnDirectYlm& aCorrFctn):
+  AliFemtoCorrFctn(),
+  fnumsreal(0),
+  fnumsimag(0),
+  fdensreal(0),
+  fdensimag(0),
+  fbinctn(0),
+  fbinctd(0),
+  fcovnum(0),
+  fcovden(0),
+  fcovmnum(0),
+  fcovmden(0),
+  fMaxL(0),
+  fMaxJM(0),
+  fels(0),
+  fems(0),
+  felsi(0),
+  femsi(0),
+  fYlmBuffer(0),
+  factorials(0),
+  fSout(0.0),
+  fSside(0.0),
+  fSlong(0.0),
+  fUseLCMS(0)
+{
+  // Copy constructor
+  int ibin = 0;
+  if (aCorrFctn.fbinctn)
+    ibin = aCorrFctn.fbinctn->GetNbinsX();
+
+  fMaxL = aCorrFctn.fMaxL;
+  fMaxJM = (fMaxL+1)*(fMaxL+1);
+
+  // Fill in factorials table
+  factorials = (double *) malloc(sizeof(double) * (4 * (fMaxL + 1)));
+  for (int iter=1; iter<4*(fMaxL+1); iter++)
+    {
+      factorials[iter] = aCorrFctn.factorials[iter];
+    }
+
+  // Fill in els and ems table
+  int el = 0;
+  int em = 0;
+  int il = 0;
+  fels = (double *) malloc(sizeof(double) * (fMaxJM));
+  fems = (double *) malloc(sizeof(double) * (fMaxJM));
+  felsi = (int *) malloc(sizeof(int) * (fMaxJM));
+  femsi = (int *) malloc(sizeof(int) * (fMaxJM));
+  do {
+    fels[il] = el;
+    fems[il] = em;
+    felsi[il] = (int) el;
+    femsi[il] = (int) em;
+
+    em++;
+    il++;
+    if (em > el) {
+      el++;
+      em = -el;
+    }
+  }
+  while (el <= fMaxL);
+  
+  fnumsreal = (TH1D **) malloc(sizeof(TH1D *) * fMaxJM);
+  fnumsimag = (TH1D **) malloc(sizeof(TH1D *) * fMaxJM);
+  fdensreal = (TH1D **) malloc(sizeof(TH1D *) * fMaxJM);
+  fdensimag = (TH1D **) malloc(sizeof(TH1D *) * fMaxJM);
+  
+  for (int ihist=0; ihist<fMaxJM; ihist++) {
+    if (aCorrFctn.fnumsreal[ihist])
+      fnumsreal[ihist] = new TH1D(*aCorrFctn.fnumsreal[ihist]);
+    else
+      fnumsreal[ihist] = 0;
+    if (aCorrFctn.fnumsimag[ihist])
+      fnumsimag[ihist] = new TH1D(*aCorrFctn.fnumsimag[ihist]);
+    else
+      fnumsimag[ihist] = 0;
+    if (aCorrFctn.fdensreal[ihist])
+      fdensreal[ihist] = new TH1D(*aCorrFctn.fdensreal[ihist]);
+    else
+      fdensreal[ihist] = 0;
+    if (aCorrFctn.fdensimag[ihist])
+      fdensimag[ihist] = new TH1D(*aCorrFctn.fdensimag[ihist]);
+    else
+      fdensimag[ihist] = 0;
+  }
+
+  if (aCorrFctn.fbinctn) 
+    fbinctn = new TH1D(*aCorrFctn.fbinctn);
+  else
+    fbinctn = 0;
+  if (aCorrFctn.fbinctd) 
+    fbinctd = new TH1D(*aCorrFctn.fbinctd);
+  else
+    fbinctd = 0;
+
+  fYlmBuffer = (complex<double> *) malloc(sizeof(complex<double>) * fMaxJM);
+  
+  // Covariance matrices
+  fcovmnum = (double *) malloc(sizeof(double) * fMaxJM * fMaxJM * 4 * ibin);
+  fcovmden = (double *) malloc(sizeof(double) * fMaxJM * fMaxJM * 4 * ibin);
+
+  for (int iter=0; iter<fMaxJM * fMaxJM * 4 * ibin; iter++) {
+    fcovmnum[iter] = aCorrFctn.fcovmnum[iter];
+    fcovmden[iter] = aCorrFctn.fcovmden[iter];
+  }
+
+  if (aCorrFctn.fcovnum)
+    fcovnum = new TH3D(*aCorrFctn.fcovnum);
+  else
+    fcovnum = 0;
+  if (aCorrFctn.fcovden)
+    fcovden = new TH3D(*aCorrFctn.fcovden);
+  else
+    fcovden = 0;
+
+  fSout = aCorrFctn.fSout;
+  fSside = aCorrFctn.fSside;
+  fSlong = aCorrFctn.fSlong;
+
+  if (aCorrFctn.fPairCut)
+    fPairCut = aCorrFctn.fPairCut;
+
+  fUseLCMS = aCorrFctn.fUseLCMS;
+}
+
+AliFemtoCorrFctnDirectYlm& AliFemtoCorrFctnDirectYlm::operator=(const AliFemtoCorrFctnDirectYlm& aCorrFctn)
+{
+  // assignment operator
+  if (this == &aCorrFctn)
+    return *this;
+  
+  int ibin = 0;
+  if (aCorrFctn.fbinctn)
+    ibin = aCorrFctn.fbinctn->GetNbinsX();
+
+  fMaxL = aCorrFctn.fMaxL;
+  fMaxJM = (fMaxL+1)*(fMaxL+1);
+
+  // Fill in factorials table
+  if (factorials) free (factorials);
+  factorials = (double *) malloc(sizeof(double) * (4 * (fMaxL + 1)));
+  for (int iter=1; iter<4*(fMaxL+1); iter++)
+    {
+      factorials[iter] = aCorrFctn.factorials[iter];
+    }
+
+  // Fill in els and ems table
+  int el = 0;
+  int em = 0;
+  int il = 0;
+  
+  if (fels) free (fels);
+  if (fems) free (fems);
+  if (felsi) free (felsi);
+  if (femsi) free (femsi);
+
+  fels = (double *) malloc(sizeof(double) * (fMaxJM));
+  fems = (double *) malloc(sizeof(double) * (fMaxJM));
+  felsi = (int *) malloc(sizeof(int) * (fMaxJM));
+  femsi = (int *) malloc(sizeof(int) * (fMaxJM));
+  do {
+    fels[il] = el;
+    fems[il] = em;
+    felsi[il] = (int) el;
+    femsi[il] = (int) em;
+
+    em++;
+    il++;
+    if (em > el) {
+      el++;
+      em = -el;
+    }
+  }
+  while (el <= fMaxL);
+  
+  if (fnumsreal) free (fnumsreal);
+  if (fnumsimag) free (fnumsimag);  
+  if (fdensreal) free (fdensreal);   
+  if (fdensimag) free (fdensimag);   
+
+  fnumsreal = (TH1D **) malloc(sizeof(TH1D *) * fMaxJM);
+  fnumsimag = (TH1D **) malloc(sizeof(TH1D *) * fMaxJM);
+  fdensreal = (TH1D **) malloc(sizeof(TH1D *) * fMaxJM);
+  fdensimag = (TH1D **) malloc(sizeof(TH1D *) * fMaxJM);
+  
+  for (int ihist=0; ihist<fMaxJM; ihist++) {
+    if (aCorrFctn.fnumsreal[ihist])
+      fnumsreal[ihist] = new TH1D(*aCorrFctn.fnumsreal[ihist]);
+    else
+      fnumsreal[ihist] = 0;
+    if (aCorrFctn.fnumsimag[ihist])
+      fnumsimag[ihist] = new TH1D(*aCorrFctn.fnumsimag[ihist]);
+    else
+      fnumsimag[ihist] = 0;
+    if (aCorrFctn.fdensreal[ihist])
+      fdensreal[ihist] = new TH1D(*aCorrFctn.fdensreal[ihist]);
+    else
+      fdensreal[ihist] = 0;
+    if (aCorrFctn.fdensimag[ihist])
+      fdensimag[ihist] = new TH1D(*aCorrFctn.fdensimag[ihist]);
+    else
+      fdensimag[ihist] = 0;
+  }
+
+  if (aCorrFctn.fbinctn) 
+    fbinctn = new TH1D(*aCorrFctn.fbinctn);
+  else
+    fbinctn = 0;
+  if (aCorrFctn.fbinctd) 
+    fbinctd = new TH1D(*aCorrFctn.fbinctd);
+  else
+    fbinctd = 0;
+
+  if (fYlmBuffer) free (fYlmBuffer);
+
+  fYlmBuffer = (complex<double> *) malloc(sizeof(complex<double>) * fMaxJM);
+  
+  // Covariance matrices
+
+  if (fcovmnum) free (fcovmnum);
+  if (fcovmden) free (fcovmden);  
+
+  fcovmnum = (double *) malloc(sizeof(double) * fMaxJM * fMaxJM * 4 * ibin);
+  fcovmden = (double *) malloc(sizeof(double) * fMaxJM * fMaxJM * 4 * ibin);
+
+  for (int iter=0; iter<fMaxJM * fMaxJM * 4 * ibin; iter++) {
+    fcovmnum[iter] = aCorrFctn.fcovmnum[iter];
+    fcovmden[iter] = aCorrFctn.fcovmden[iter];
+  }
+
+  if (aCorrFctn.fcovnum)
+    fcovnum = new TH3D(*aCorrFctn.fcovnum);
+  else
+    fcovnum = 0;
+  if (aCorrFctn.fcovden)
+    fcovden = new TH3D(*aCorrFctn.fcovden);
+  else
+    fcovden = 0;
+
+  fSout = aCorrFctn.fSout;
+  fSside = aCorrFctn.fSside;
+  fSlong = aCorrFctn.fSlong;
+
+  if (aCorrFctn.fPairCut) 
+    fPairCut = aCorrFctn.fPairCut;
+
+  fUseLCMS = aCorrFctn.fUseLCMS;
+
+  return *this;
+}
+
+AliFemtoCorrFctnDirectYlm::~AliFemtoCorrFctnDirectYlm()
+{
+  // Destructor
+  for (int ihist=0; ihist<fMaxJM; ihist++) {
+    delete fnumsreal[ihist];
+    delete fnumsimag[ihist];
+    delete fdensreal[ihist];
+    delete fdensimag[ihist];
+  }
+
+  delete fbinctn;
+  delete fbinctd;
+
+  //  delete fnumsreal;
+  //  delete fnumsimag;
+  //  delete fdensreal;
+  //  delete fdensimag;
+
+  free( fnumsreal);
+  free( fnumsimag);
+  free( fdensreal);
+  free( fdensimag);
+
+  free(factorials);
+  free(fels);
+  free(fems);
+  free(felsi);
+  free(femsi);
+  free(fYlmBuffer);
+
+  free(fcovmnum);
+  free(fcovmden);
+
+  if (fcovnum) delete fcovnum;
+  if (fcovden) delete fcovden;
+
+  if (fPairCut) delete fPairCut;
+}
+
+double AliFemtoCorrFctnDirectYlm::ClebschGordan(double aJot1, double aEm1, double aJot2, double aEm2, double aJot, double aEm)
+{
+  // Calculate Clebsh-Gordan coefficient
+  int mint, maxt;
+  double cgc = 0.0;
+  int titer;
+  double coef;
+
+  maxt = lrint(aJot1 + aJot2 - aJot);
+  mint = 0;
+  if (lrint(aJot1 - aEm1) < maxt) maxt = lrint(aJot1 - aEm1);
+  if (lrint(aJot2 + aEm2) < maxt) maxt = lrint(aJot2 + aEm2);
+  if (lrint(-(aJot-aJot2+aEm1)) > mint) mint = lrint(-(aJot-aJot2+aEm1));
+  if (lrint(-(aJot-aJot1-aEm2)) > mint) mint = lrint(-(aJot-aJot1-aEm2));
+
+  for (titer = mint; titer<=maxt; titer ++)
+    {
+      coef = TMath::Power(-1, titer);
+      coef *= TMath::Sqrt((2*aJot+1)*
+                         factorials[lrint(aJot1+aEm1)] *
+                         factorials[lrint(aJot1-aEm1)] *
+                         factorials[lrint(aJot2+aEm2)] *
+                         factorials[lrint(aJot2-aEm2)] *
+                         factorials[lrint(aJot+aEm)] *
+                         factorials[lrint(aJot-aEm)]);
+      coef /= (factorials[titer] *
+              factorials[lrint(aJot1+aJot2-aJot-titer)] *
+              factorials[lrint(aJot1-aEm1-titer)] *
+              factorials[lrint(aJot2+aEm2-titer)] *
+              factorials[lrint(aJot-aJot2+aEm1+titer)] *
+              factorials[lrint(aJot-aJot1-aEm2+titer)]);
+      
+      cgc += coef;
+    }
+
+  cgc *= DeltaJ(aJot1, aJot2, aJot);
+
+  return cgc;
+}
+
+double AliFemtoCorrFctnDirectYlm::DeltaJ(double aJot1, double aJot2, double aJot)
+{
+  // Calculate J for the Clebsh-Gordan coefficient
+  if ((aJot1+aJot2-aJot) < 0) {
+    //    cout << "J1+J2-J3 < 0 !!!" << " " << aJot1 << " " << aJot2 << " " << aJot << endl;
+    return 0;
+  }
+  if ((aJot1-aJot2+aJot) < 0) {
+    //    cout << "J1-J2+J3 < 0 !!!" << " " << aJot1 << " " << aJot2 << " " << aJot << endl;
+    return 0;
+  }
+  if ((-aJot1+aJot2+aJot) < 0) {
+    //    cout << "-J1+J2+J3 < 0 !!!" << " " << aJot1 << " " << aJot2 << " " << aJot << endl;
+    return 0;
+  }
+  if ((aJot1+aJot2+aJot+1) < 0) {
+    //    cout << "J1+J2+J3+1 < 0 !!!" << " " << aJot1 << " " << aJot2 << " " << aJot << endl;
+    return 0;
+  }
+  double res = TMath::Sqrt(1.0 * 
+                          factorials[lrint(aJot1+aJot2-aJot)] * 
+                          factorials[lrint(aJot1-aJot2+aJot)] * 
+                          factorials[lrint(-aJot1+aJot2+aJot)] / 
+                          factorials[lrint(aJot1+aJot2+aJot+1)]);
+  
+  return res;
+}
+
+double AliFemtoCorrFctnDirectYlm::WignerSymbol(double aJot1, double aEm1, double aJot2, double aEm2, double aJot, double aEm)
+{
+  // Get Wigner symbol
+  if (lrint(aEm1+aEm2+aEm) != 0.0) 
+    return 0.0;
+  double cge = ClebschGordan(aJot1, aEm1, aJot2, aEm2, aJot, -aEm);
+  if (lrint(abs(aJot1 - aJot2 - aEm)) % 2) 
+    cge *= -1.0;
+  cge /= sqrt(2*aJot + 1);
+
+  if (cge == -0.0) cge = 0.0;
+
+  return cge;
+}
+
+
+void AliFemtoCorrFctnDirectYlm::GetMtilde(complex<double> *aMat, double *aMTilde)
+{
+  // Create the Mtilde for a given q bin
+  double lzero, mzero;
+  double lprim, mprim;
+  double lbis, mbis;
+  int lzeroi, mzeroi;
+  int lprimi, mprimi;
+  int lbisi, mbisi;
+
+  complex<double> mcomp;
+
+  for (int izero = 0; izero<GetMaxJM(); izero++) {
+    GetElEmForIndex(izero, &lzero, &mzero);
+    GetElEmForIndex(izero, &lzeroi, &mzeroi);
+    for (int ibis = 0; ibis<GetMaxJM(); ibis++) {
+      GetElEmForIndex(ibis, &lbis, &mbis);
+      GetElEmForIndex(ibis, &lbisi, &mbisi);
+      complex<double> val = complex<double>(0.0, 0.0);
+      for (int iprim = 0; iprim<GetMaxJM(); iprim++) {
+
+       GetElEmForIndex(iprim, &lprim, &mprim);
+       GetElEmForIndex(iprim, &lprimi, &mprimi);
+
+       if (abs(mzeroi) % 2) mcomp = complex<double>(-1.0, 0.0); // (-1)^m
+       else mcomp = complex<double>(1.0, 0.0);
+       
+       mcomp *= sqrt((2*lzero+1)*(2*lprim+1)*(2*lbis+1));   // P1
+       mcomp *= WignerSymbol(lzero, 0, lprim, 0, lbis, 0); // W1
+       mcomp *= WignerSymbol(lzero, -mzero, lprim, mprim, lbis, mbis); // W2
+       mcomp *= aMat[iprim];
+       val += mcomp;
+      }
+      aMTilde[(izero*2)*(2*GetMaxJM()) + (ibis*2)]     =  real(val);
+      aMTilde[(izero*2+1)*(2*GetMaxJM()) + (ibis*2)]   =  imag(val);
+      if (imag(val) != 0.0)
+       aMTilde[(izero*2)*(2*GetMaxJM()) + (ibis*2+1)]   = -imag(val);
+      else 
+       aMTilde[(izero*2)*(2*GetMaxJM()) + (ibis*2+1)]   = 0.0;
+      aMTilde[(izero*2+1)*(2*GetMaxJM()) + (ibis*2+1)] =  real(val);
+      
+    }
+  }
+}
+
+int  AliFemtoCorrFctnDirectYlm::GetMaxJM() const
+{ return fMaxJM; }
+
+void AliFemtoCorrFctnDirectYlm::GetElEmForIndex(int aIndex, double *aEl, double *aEm) const
+{
+  // Get l,m for a given index
+  *aEl = fels[aIndex];
+  *aEm = fems[aIndex];
+}
+
+void AliFemtoCorrFctnDirectYlm::GetElEmForIndex(int aIndex, int *aEl, int *aEm) const
+{
+  // Get l,m for a given index
+  *aEl = felsi[aIndex];
+  *aEm = femsi[aIndex];
+}
+
+int AliFemtoCorrFctnDirectYlm::GetBin(int qbin, int ilmzero, int zeroimag, int ilmprim, int primimag)
+{
+  return (qbin*GetMaxJM()*GetMaxJM()*4 +
+         (ilmprim*2 + primimag) * GetMaxJM()*2 +
+         ilmzero*2 + zeroimag);
+}
+
+void AliFemtoCorrFctnDirectYlm::AddRealPair(double qout, double qside, double qlong, double weight)
+{
+  // Fill numerator
+  double kv = sqrt(qout*qout + qside*qside + qlong*qlong);
+  int nqbin = fbinctn->GetXaxis()->FindFixBin(kv) - 1;
+  
+  // Use saved ylm values for same qout, qside, qlong
+  if ((qout != fSout) || (qside != fSside) || (qlong != fSlong)) {
+    AliFemtoYlm::YlmUpToL(fMaxL, qout, qside, qlong, fYlmBuffer);
+    fSout = qout; fSside = qside; fSlong = qlong;
+  }
+  for (int ilm=0; ilm<GetMaxJM(); ilm++) {
+    //    fYlmBuffer[ilm] = AliFemtoYlm::Ylm(elsi[ilm], emsi[ilm], qout, qside, qlong);
+
+    fnumsreal[ilm]->Fill(kv, real(fYlmBuffer[ilm])*weight);
+    fnumsimag[ilm]->Fill(kv, -imag(fYlmBuffer[ilm])*weight);
+
+    fbinctn->Fill(kv, 1.0);
+  }
+
+  // Fill in the error matrix
+  //  int tabshift = nqbin*GetMaxJM()*GetMaxJM()*4;
+  if (nqbin < fbinctn->GetNbinsX())
+    for (int ilmzero=0; ilmzero<GetMaxJM(); ilmzero++)
+      for (int ilmprim=0; ilmprim<GetMaxJM(); ilmprim++) {
+       fcovmnum[GetBin(nqbin, ilmzero, 0, ilmprim, 0)] += real(fYlmBuffer[ilmzero])*real(fYlmBuffer[ilmprim])*weight*weight;
+       fcovmnum[GetBin(nqbin, ilmzero, 0, ilmprim, 1)] += real(fYlmBuffer[ilmzero])*-imag(fYlmBuffer[ilmprim])*weight*weight;
+       fcovmnum[GetBin(nqbin, ilmzero, 1, ilmprim, 0)] += -imag(fYlmBuffer[ilmzero])*real(fYlmBuffer[ilmprim])*weight*weight;
+       fcovmnum[GetBin(nqbin, ilmzero, 1, ilmprim, 1)] += -imag(fYlmBuffer[ilmzero])*-imag(fYlmBuffer[ilmprim])*weight*weight;
+       
+      }
+  
+}
+
+void AliFemtoCorrFctnDirectYlm::AddMixedPair(double qout, double qside, double qlong, double weight)
+{
+  // Fill denominator
+  double kv = sqrt(qout*qout + qside*qside + qlong*qlong);
+  
+  // Use saved ylm values for same qout, qside, qlong
+  if ((qout != fSout) || (qside != fSside) || (qlong != fSlong)) {
+    AliFemtoYlm::YlmUpToL(fMaxL, qout, qside, qlong, fYlmBuffer);
+    fSout = qout; fSside = qside; fSlong = qlong;
+  }
+  for (int ilm=0; ilm<GetMaxJM(); ilm++) {
+    //    fYlmBuffer[ilm] = AliFemtoYlm::Ylm(elsi[ilm], emsi[ilm], qout, qside, qlong);
+
+    fdensreal[ilm]->Fill(kv, real(fYlmBuffer[ilm])*weight);
+    fdensimag[ilm]->Fill(kv, -imag(fYlmBuffer[ilm])*weight);
+
+    fbinctd->Fill(kv, 1.0);
+  }
+
+  // Fill in the error matrix
+  int nqbin = fbinctn->GetXaxis()->FindFixBin(kv) - 1;
+  //  int tabshift = nqbin*GetMaxJM()*GetMaxJM()*4;
+  if (nqbin < fbinctn->GetNbinsX())
+    for (int ilmzero=0; ilmzero<GetMaxJM(); ilmzero++)
+      for (int ilmprim=0; ilmprim<GetMaxJM(); ilmprim++) {
+       fcovmden[GetBin(nqbin, ilmzero, 0, ilmprim, 0)] += real(fYlmBuffer[ilmzero])*real(fYlmBuffer[ilmprim]);
+       fcovmden[GetBin(nqbin, ilmzero, 0, ilmprim, 1)] += real(fYlmBuffer[ilmzero])*-imag(fYlmBuffer[ilmprim]);
+       fcovmden[GetBin(nqbin, ilmzero, 1, ilmprim, 0)] += -imag(fYlmBuffer[ilmzero])*real(fYlmBuffer[ilmprim]);
+       fcovmden[GetBin(nqbin, ilmzero, 1, ilmprim, 1)] += -imag(fYlmBuffer[ilmzero])*-imag(fYlmBuffer[ilmprim]);
+       
+    }
+}
+
+void AliFemtoCorrFctnDirectYlm::AddRealPair(double *qvec, double weight) {
+  AddRealPair(qvec[0], qvec[1], qvec[2], weight);
+}
+
+void AliFemtoCorrFctnDirectYlm::AddMixedPair(double *qvec, double weight) {
+  AddMixedPair(qvec[0], qvec[1], qvec[2], weight);
+}
+
+void AliFemtoCorrFctnDirectYlm::Finish()
+{
+  PackCovariances();
+}
+
+void AliFemtoCorrFctnDirectYlm::Write()
+{
+  // Write out output histograms
+  if ((!fcovnum) || (!fcovden))
+    PackCovariances();
+
+  for (int ilm=0; ilm<fMaxJM; ilm++) {
+    fnumsreal[ilm]->Write();
+    fdensreal[ilm]->Write();
+    fnumsimag[ilm]->Write();
+    fdensimag[ilm]->Write();
+  }
+  if (fcovnum) fcovnum->Write();
+  if (fcovden) fcovden->Write();
+}
+
+TList* AliFemtoCorrFctnDirectYlm::GetOutputList()
+{
+  // Prepare the list of objects to be written to the output
+  if ((!fcovnum) || (!fcovden))
+    PackCovariances();
+
+  TList *tOutputList = new TList();
+
+  for (int ilm=0; ilm<fMaxJM; ilm++) {
+    tOutputList->Add(fnumsreal[ilm]);
+    tOutputList->Add(fdensreal[ilm]);
+    tOutputList->Add(fnumsimag[ilm]);
+    tOutputList->Add(fdensimag[ilm]);
+  }
+  if (fcovnum) tOutputList->Add(fcovnum);
+  if (fcovden) tOutputList->Add(fcovden);
+
+  return tOutputList;
+}
+
+
+void AliFemtoCorrFctnDirectYlm::ReadFromFile(TFile *infile, const char *name, int maxl)
+{
+  // Raad in the numerator and denominator from file
+  if (maxl != fMaxL) {
+    cout << "Cannot read function for L " << maxl << " into a container with L "<< fMaxL << endl;
+    return;
+  }
+  cout << "Reading in numerators and denominators" << endl;
+
+  char bufname[200];
+  for (int ihist=0; ihist<fMaxJM; ihist++) {
+    snprintf(bufname , 200,  "NumReYlm%i%i%s", felsi[ihist], femsi[ihist]<0 ? felsi[ihist]-femsi[ihist] : femsi[ihist], name);
+    if (fnumsreal[ihist]) delete fnumsreal[ihist];
+    fnumsreal[ihist] = new TH1D(*((TH1D *) infile->Get(bufname)));
+
+    snprintf(bufname , 200,  "NumImYlm%i%i%s", felsi[ihist], femsi[ihist]<0 ? felsi[ihist]-femsi[ihist] : femsi[ihist], name);
+    if (fnumsimag[ihist]) delete fnumsimag[ihist];
+    fnumsimag[ihist] = new TH1D(*((TH1D *) infile->Get(bufname)));
+
+    snprintf(bufname , 200,  "DenReYlm%i%i%s", felsi[ihist], femsi[ihist]<0 ? felsi[ihist]-femsi[ihist] : femsi[ihist], name);
+    if (fdensreal[ihist]) delete fdensreal[ihist];
+    fdensreal[ihist] = new TH1D(*((TH1D *) infile->Get(bufname)));
+
+    snprintf(bufname , 200,  "DenImYlm%i%i%s", felsi[ihist], femsi[ihist]<0 ? felsi[ihist]-femsi[ihist] : femsi[ihist], name);
+    if (fdensimag[ihist]) delete fdensimag[ihist];
+    fdensimag[ihist] = new TH1D(*((TH1D *) infile->Get(bufname)));
+  }
+
+  if (fcovnum) delete fcovnum;
+  snprintf(bufname , 200,  "covNum%s", name);
+  fcovnum = new TH3D (*((TH3D *) infile->Get(bufname)));
+
+  if (fcovden) delete fcovden;
+  snprintf(bufname , 200,  "CovDen%s", name);
+  fcovden = new TH3D (*((TH3D *) infile->Get(bufname)));
+
+  if ((fcovnum) && (fcovden)) {
+    cout << "Unpacking covariance matrices from file " << endl;
+    UnpackCovariances();
+  }
+  else {
+
+    cout << "Creating fake covariance matrices" << endl;
+  
+    for (int ibin=1; ibin<=fnumsreal[0]->GetNbinsX(); ibin++) {
+      double nent = fnumsreal[0]->GetEntries();
+      double nentd = fdensreal[0]->GetEntries();
+      for (int ilmx=0; ilmx<GetMaxJM(); ilmx++) {
+       for (int ilmy=0; ilmy<GetMaxJM(); ilmy++) {
+         double t1t2rr = fnumsreal[ilmx]->GetBinContent(ibin)*fnumsreal[ilmy]->GetBinContent(ibin)/nent/nent;
+         double t1t2ri = fnumsreal[ilmx]->GetBinContent(ibin)*fnumsimag[ilmy]->GetBinContent(ibin)/nent/nent;
+         double t1t2ir = fnumsimag[ilmx]->GetBinContent(ibin)*fnumsreal[ilmy]->GetBinContent(ibin)/nent/nent;
+         double t1t2ii = fnumsimag[ilmx]->GetBinContent(ibin)*fnumsimag[ilmy]->GetBinContent(ibin)/nent/nent;
+         if (ilmx == ilmy) {
+           fcovmnum[GetBin(ibin-1, ilmx, 0, ilmy, 0)] = nent*(TMath::Power(fnumsreal[ilmx]->GetBinError(ibin)/nent,2)*(nent-1) + t1t2rr);
+           fcovmnum[GetBin(ibin-1, ilmx, 0, ilmy, 1)] = nent*t1t2ri;
+           fcovmnum[GetBin(ibin-1, ilmx, 1, ilmy, 0)] = nent*t1t2ir;
+           fcovmnum[GetBin(ibin-1, ilmx, 1, ilmy, 1)] = nent*(TMath::Power(fnumsimag[ilmx]->GetBinError(ibin)/nent,2)*(nent-1) + t1t2rr);
+         }
+         else {
+           fcovmnum[GetBin(ibin-1, ilmx, 0, ilmy, 0)] = nent*t1t2rr;
+           fcovmnum[GetBin(ibin-1, ilmx, 0, ilmy, 1)] = nent*t1t2ri;
+           fcovmnum[GetBin(ibin-1, ilmx, 1, ilmy, 0)] = nent*t1t2ir;
+           fcovmnum[GetBin(ibin-1, ilmx, 1, ilmy, 1)] = nent*t1t2ii;
+         }
+         t1t2rr = fdensreal[ilmx]->GetBinContent(ibin)*fdensreal[ilmy]->GetBinContent(ibin)/nentd/nentd;
+         t1t2ri = fdensreal[ilmx]->GetBinContent(ibin)*fdensimag[ilmy]->GetBinContent(ibin)/nentd/nentd;
+         t1t2ir = fdensimag[ilmx]->GetBinContent(ibin)*fdensreal[ilmy]->GetBinContent(ibin)/nentd/nentd;
+         t1t2ii = fdensimag[ilmx]->GetBinContent(ibin)*fdensimag[ilmy]->GetBinContent(ibin)/nentd/nentd;
+         
+         fcovmden[GetBin(ibin-1, ilmx, 0, ilmy, 0)] = nentd*t1t2rr;
+         fcovmden[GetBin(ibin-1, ilmx, 0, ilmy, 1)] = nentd*t1t2ri;
+         fcovmden[GetBin(ibin-1, ilmx, 1, ilmy, 0)] = nentd*t1t2ir;
+         fcovmden[GetBin(ibin-1, ilmx, 1, ilmy, 1)] = nentd*t1t2ii;
+       }
+      }
+    }
+  }
+
+  // Recalculating the correlation functions
+  Finish();
+}
+
+int AliFemtoCorrFctnDirectYlm::PackYlmVector(const double *invec, double *outvec)
+{
+  // Pack a vector in l,m into an array using
+  // only independent components
+  int ioutcount = 0;
+  int em, el;
+  for (int ilm=0; ilm<GetMaxJM(); ilm++) {
+    GetElEmForIndex(ilm, &el, &em);
+    outvec[ioutcount++] = invec[ilm*2];
+    if (em == 0)
+      continue;
+    outvec[ioutcount++] = invec[ilm*2 + 1];
+  }
+  
+  return ioutcount;
+}
+
+int AliFemtoCorrFctnDirectYlm::PackYlmMatrix(const double *inmat, double *outmat)
+{
+  // Pack a matrix in l,m x l,m into an array using
+  // only independent components
+  int ioutcountz = 0;
+  int ioutcountp = 0;
+  int emz, elz;
+  int emp, elp;
+  int finalsize = 0;
+
+  for (int ilm=0; ilm<GetMaxJM(); ilm++) {
+    GetElEmForIndex(ilm, &elz, &emz);
+    finalsize++;
+    if (emz == 0) continue;
+    finalsize++;
+  }
+
+  for (int ilmz=0; ilmz<GetMaxJM(); ilmz++) {
+    GetElEmForIndex(ilmz, &elz, &emz);
+    ioutcountp = 0;
+    for (int ilmp=0; ilmp<GetMaxJM(); ilmp++) {
+      GetElEmForIndex(ilmp, &elp, &emp);
+      outmat[ioutcountz*finalsize + ioutcountp] = inmat[GetBin(0, ilmz, 0, ilmp, 0)];
+      ioutcountp++;
+      if (emp == 0) continue;
+      outmat[ioutcountz*finalsize + ioutcountp] = inmat[GetBin(0, ilmz, 0, ilmp, 1)];
+      ioutcountp++;
+    }
+    ioutcountz++;
+
+    if (emz == 0) continue;
+    ioutcountp = 0;
+    for (int ilmp=0; ilmp<GetMaxJM(); ilmp++) {
+      GetElEmForIndex(ilmp, &elp, &emp);
+      outmat[ioutcountz*finalsize + ioutcountp] = inmat[GetBin(0, ilmz, 1, ilmp, 0)];
+      ioutcountp++;
+      if (emp == 0) continue;
+      outmat[ioutcountz*finalsize + ioutcountp] = inmat[GetBin(0, ilmz, 1, ilmp, 1)];
+      ioutcountp++;
+    }
+    ioutcountz++;    
+  }    
+  
+  return ioutcountz;  
+}
+
+void AliFemtoCorrFctnDirectYlm::PackCovariances()
+{
+  // Migrate the covariance matrix into a 3D histogram for storage
+  char bufname[200];
+  snprintf(bufname , 200,  "CovNum%s", fnumsreal[0]->GetName()+10);
+
+  //  if (fcovnum) delete fcovnum;
+  if (!fcovnum) 
+    fcovnum = new TH3D(bufname,bufname, 
+                      fnumsreal[0]->GetNbinsX(), fnumsreal[0]->GetXaxis()->GetXmin(), fnumsreal[0]->GetXaxis()->GetXmax(),
+                      GetMaxJM()*2, -0.5, GetMaxJM()*2 - 0.5,
+                      GetMaxJM()*2, -0.5, GetMaxJM()*2 - 0.5);
+  
+  for (int ibin=1; ibin<=fcovnum->GetNbinsX(); ibin++)
+    for (int ilmz=0; ilmz<GetMaxJM()*2; ilmz++)
+      for (int ilmp=0; ilmp<GetMaxJM()*2; ilmp++)
+       fcovnum->SetBinContent(ibin, ilmz+1, ilmp+1, fcovmnum[GetBin(ibin-1, ilmz/2, ilmz%2, ilmp/2, ilmp%2)]);
+
+  snprintf(bufname , 100,  "CovDen%s", fnumsreal[0]->GetName()+10);
+
+  //  if (fcovden) delete fcovden;
+  if (!fcovden)
+    fcovden  = new TH3D(bufname,bufname, 
+                       fdensreal[0]->GetNbinsX(), fdensreal[0]->GetXaxis()->GetXmin(), fdensreal[0]->GetXaxis()->GetXmax(),
+                       GetMaxJM()*2, -0.5, GetMaxJM()*2 - 0.5,
+                       GetMaxJM()*2, -0.5, GetMaxJM()*2 - 0.5);
+                    
+  for (int ibin=1; ibin<=fcovden->GetNbinsX(); ibin++)
+    for (int ilmz=0; ilmz<GetMaxJM()*2; ilmz++)
+      for (int ilmp=0; ilmp<GetMaxJM()*2; ilmp++)
+       fcovden->SetBinContent(ibin, ilmz+1, ilmp+1, fcovmden[GetBin(ibin-1, ilmz/2, ilmz%2, ilmp/2, ilmp%2)]);
+
+}
+
+void AliFemtoCorrFctnDirectYlm::UnpackCovariances()
+{
+  // Extract the covariance matrices from storage
+  if (fcovnum) {
+    for (int ibin=1; ibin<=fcovnum->GetNbinsX(); ibin++)
+      for (int ilmz=0; ilmz<GetMaxJM()*2; ilmz++)
+       for (int ilmp=0; ilmp<GetMaxJM()*2; ilmp++)
+         fcovmnum[GetBin(ibin-1, ilmz/2, ilmz%2, ilmp/2, ilmp%2)] = fcovnum->GetBinContent(ibin, ilmz+1, ilmp+1);
+    
+  }
+  if (fcovden) {
+    for (int ibin=1; ibin<=fcovden->GetNbinsX(); ibin++)
+      for (int ilmz=0; ilmz<GetMaxJM()*2; ilmz++)
+       for (int ilmp=0; ilmp<GetMaxJM()*2; ilmp++)
+         fcovmden[GetBin(ibin-1, ilmz/2, ilmz%2, ilmp/2, ilmp%2)] = fcovden->GetBinContent(ibin, ilmz+1, ilmp+1);
+  }
+}
+
+int AliFemtoCorrFctnDirectYlm::GetIndexForLM(int el, int em) const
+{
+  // Get array index for a given l,m
+  for (int iter=0; iter<fMaxJM; iter++)
+    if ((el == felsi[iter]) && (em == femsi[iter]))
+      return iter;
+  return -1;
+}
+
+TH1D *AliFemtoCorrFctnDirectYlm::GetNumRealHist(int el, int em)
+{
+  // Get numerator hist for a given l,m
+  if (GetIndexForLM(el, em)>=0)
+    return fnumsreal[GetIndexForLM(el, em)];
+  else 
+    return 0;
+}
+TH1D *AliFemtoCorrFctnDirectYlm::GetNumImagHist(int el, int em)
+{
+  // Get numerator hist for a given l,m
+  if (GetIndexForLM(el, em)>=0)
+    return fnumsimag[GetIndexForLM(el, em)];
+  else 
+    return 0;
+}
+
+TH1D *AliFemtoCorrFctnDirectYlm::GetDenRealHist(int el, int em)
+{
+  // Get denominator hist for a given l,m
+  if (GetIndexForLM(el, em)>=0)
+    return fdensreal[GetIndexForLM(el, em)];
+  else 
+    return 0;
+}
+TH1D *AliFemtoCorrFctnDirectYlm::GetDenImagHist(int el, int em)
+{
+  // Get denominator hist for a given l,m
+  if (GetIndexForLM(el, em)>=0)
+    return fdensimag[GetIndexForLM(el, em)];
+  else 
+    return 0;
+}
+
+AliFemtoString AliFemtoCorrFctnDirectYlm::Report()
+{
+  return "AliFemtoCorrFctnDirectYlm::Finish";
+}
+
+void AliFemtoCorrFctnDirectYlm::AddRealPair(AliFemtoPair* aPair)
+{
+  // Fill in the numerator
+  if (fPairCut)
+    if (!fPairCut->Pass(aPair)) return;
+
+  if (fUseLCMS)
+    AddRealPair(aPair->QOutCMS(), aPair->QSideCMS(), aPair->QLongCMS(), 1.0);
+  else
+    AddRealPair(aPair->KOut(), aPair->KSide(), aPair->KLong(), 1.0);
+}
+
+void AliFemtoCorrFctnDirectYlm::AddMixedPair(AliFemtoPair* aPair)
+{
+  // Fill in the denominator
+  if (fPairCut)
+    if (!fPairCut->Pass(aPair)) return;
+  
+  if (fUseLCMS)
+    AddMixedPair(aPair->QOutCMS(), aPair->QSideCMS(), aPair->QLongCMS(), 1.0);
+  else
+    AddMixedPair(aPair->KOut(), aPair->KSide(), aPair->KLong(), 1.0);
+}
+
+void AliFemtoCorrFctnDirectYlm::SetUseLCMS(int aUseLCMS)
+{
+  fUseLCMS = aUseLCMS;
+}
+
+int  AliFemtoCorrFctnDirectYlm::GetUseLCMS()
+{
+  return fUseLCMS;
+}
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCorrFctnDirectYlm.h b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCorrFctnDirectYlm.h
new file mode 100644 (file)
index 0000000..e0533bf
--- /dev/null
@@ -0,0 +1,115 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoCorrFctnDirectYlm - Correlation function that is binned in Ylms    //
+// directly. Provides a way to store the numerator and denominator            //
+// in Ylms directly and correctly calculate the correlation                   //
+// function from them.                                                        //
+// Added the option to use q components in LCMS for identical particles       //
+//                                                                            //
+// Authors: Adam Kisiel kisiel@mps.ohio-state.edu                             //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+#ifndef ALIFEMTOCORRFCTNDIRECTYLM_H
+#define ALIFEMTOCORRFCTNDIRECTYLM_H
+
+#include <math.h>
+#include <complex>
+#include <TH1D.h>
+#include <TH3D.h>
+#include <TFile.h>
+#include "AliFemtoCorrFctn.h"
+#include "AliFemtoYlm.h"
+#include "AliFemtoPairCut.h"
+
+using namespace std;
+
+class AliFemtoCorrFctnDirectYlm: public AliFemtoCorrFctn {
+ public:
+  AliFemtoCorrFctnDirectYlm();
+  AliFemtoCorrFctnDirectYlm(const char *name, int maxl, int ibin, double vmin, double vmax, int aUseLCMS);
+  AliFemtoCorrFctnDirectYlm(const AliFemtoCorrFctnDirectYlm& aCorrFctn);
+  ~AliFemtoCorrFctnDirectYlm();
+
+  AliFemtoCorrFctnDirectYlm& operator=(const AliFemtoCorrFctnDirectYlm& aCorrFctn);
+
+  void AddRealPair(double *qvec, double weight=1.0);
+  void AddMixedPair(double *qvec, double weight=1.0);
+
+  void AddRealPair(double qout, double qside, double qlong, double weight=1.0);
+  void AddMixedPair(double qout, double qside, double qlong, double weight=1.0);
+
+  virtual AliFemtoString Report();
+
+  virtual void AddRealPair(AliFemtoPair* aPair);
+  virtual void AddMixedPair(AliFemtoPair* aPair);
+
+  virtual void Finish();
+  virtual TList* GetOutputList();
+
+  void Write();
+
+  void ReadFromFile(TFile *infile, const char *name, int maxl);
+
+  TH1D *GetNumRealHist(int el, int em);
+  TH1D *GetNumImagHist(int el, int em);
+
+  TH1D *GetDenRealHist(int el, int em);
+  TH1D *GetDenImagHist(int el, int em);
+
+  void SetUseLCMS(int aUseLCMS);
+  int  GetUseLCMS();
+
+ private:
+  double ClebschGordan(double aJot1, double aEm1, double aJot2, double aEm2, double aJot, double aEm);
+  double DeltaJ(double aJot1, double aJot2, double aJot);
+  double WignerSymbol(double aJot1, double aEm1, double aJot2, double aEm2, double aJot, double aEm);
+  
+  void GetMtilde(complex<double>* aMat, double *aMTilde); 
+  
+  int  GetMaxJM() const;
+  void GetElEmForIndex(int aIndex, double *aEl, double *aEm) const;
+  void GetElEmForIndex(int aIndex, int *aEl, int *aEm) const;
+  int  GetBin(int qbin, int ilmzero, int zeroimag, int ilmprim, int primimag);
+
+  int  PackYlmVector(const double *invec, double *outvec);
+  int  PackYlmMatrix(const double *inmat, double *outmat);
+
+  int GetIndexForLM(int el, int em) const;
+
+  void PackCovariances();
+  void UnpackCovariances();
+
+  TH1D **fnumsreal;            // Real parts of Ylm components of the numerator
+  TH1D **fnumsimag;            // Imaginary parts of Ylm components of the numerator
+  TH1D **fdensreal;            // Real parts of Ylm components of the denominator          
+  TH1D **fdensimag;            // Imaginary parts of Ylm components of the denominator
+
+  TH1D *fbinctn;               // Bin occupation for the numerator
+  TH1D *fbinctd;               // Bin occupation for the denominator
+
+  TH3D *fcovnum;               // Numerator covariance matrix packed into TH3D
+  TH3D *fcovden;               // Denominator covariance matrix packed into TH3D
+
+  double *fcovmnum;            // Covariance matrix for the numerator
+  double *fcovmden;            // Covariance matrix for the denominator
+
+  int fMaxL;                  // l cut-off of the decomposition
+
+  int    fMaxJM;               // number of l-m combinations
+  double *fels;                // table of l's
+  double *fems;                // table of m's
+  int    *felsi;               // table of integer l's
+  int    *femsi;               // table of integer m's
+
+  complex<double> *fYlmBuffer; // buffer for ylm calculation
+  double *factorials;         // Helper table of factorials
+
+  double fSout;                // Save last calculated qout
+  double fSside;               // Save last calculated qside
+  double fSlong;               // Save last calculated qlong
+
+  int    fUseLCMS;             // 0 - Use PRF, 1 - Use LCMS
+};
+
+#endif
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCorrFctnGammaMonitor.cxx b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCorrFctnGammaMonitor.cxx
new file mode 100644 (file)
index 0000000..5c20d50
--- /dev/null
@@ -0,0 +1,208 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoGammaMonitor - A correlation function that analyzes            //
+// two particle correlations with respect to the azimuthal angle (phi)        //
+// and pseudorapidity (eta) difference                                        //
+//                                                                            //
+// Authors: Adam Kisiel Adam.Kisiel@cern.ch                                   //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+
+#include "AliFemtoCorrFctnGammaMonitor.h"
+//#include "AliFemtoHisto.hh"
+#include <cstdio>
+#include <TMath.h>
+
+#ifdef __ROOT__ 
+ClassImp(AliFemtoCorrFctnGammaMonitor)
+#endif
+
+//____________________________
+AliFemtoCorrFctnGammaMonitor::AliFemtoCorrFctnGammaMonitor(char* title, const int& aMinvBins=20, const int& aDThetaBins=20):
+  AliFemtoCorrFctn(),
+  fNumPMinvDTheta(0),
+  fDenPMinvDTheta(0),
+  fNumNMinvDTheta(0),
+  fDenNMinvDTheta(0)
+{
+  // set up numerator
+  char tTitNumD[101] = "NumPMinvTheta";
+  strncat(tTitNumD,title, 100);
+  fNumPMinvDTheta = new TH2D(tTitNumD,title,aMinvBins,0.0,0.2,aDThetaBins,0.0,0.2);
+  // set up denominator
+  char tTitDenD[101] = "DenPMinvTheta";
+  strncat(tTitDenD,title, 100);
+  fDenPMinvDTheta = new TH2D(tTitDenD,title,aMinvBins,0.0,0.2,aDThetaBins,0.0,0.2);
+
+  // set up numerator
+  char tTitNumR[101] = "NumNMinvTheta";
+  strncat(tTitNumR,title, 100);
+  fNumNMinvDTheta = new TH2D(tTitNumR,title,aMinvBins,0.0,0.2,aDThetaBins,0.0,0.2);
+  // set up denominator
+  char tTitDenR[101] = "DenNMinvTheta";
+  strncat(tTitDenR,title, 100);
+  fDenNMinvDTheta = new TH2D(tTitDenR,title,aMinvBins,0.0,0.2,aDThetaBins,0.0,0.2);
+
+  // to enable error bar calculation...
+  fNumPMinvDTheta->Sumw2();
+  fDenPMinvDTheta->Sumw2();
+  fNumNMinvDTheta->Sumw2();
+  fDenNMinvDTheta->Sumw2();
+}
+
+//____________________________
+AliFemtoCorrFctnGammaMonitor::AliFemtoCorrFctnGammaMonitor(const AliFemtoCorrFctnGammaMonitor& aCorrFctn) :
+  AliFemtoCorrFctn(),
+  fNumPMinvDTheta(0),
+  fDenPMinvDTheta(0),
+  fNumNMinvDTheta(0),
+  fDenNMinvDTheta(0)
+{
+  // copy constructor
+  if (aCorrFctn.fNumPMinvDTheta)
+    fNumPMinvDTheta = new TH2D(*aCorrFctn.fNumPMinvDTheta);
+  else
+    fNumPMinvDTheta = 0;
+  if (aCorrFctn.fDenPMinvDTheta)
+    fDenPMinvDTheta = new TH2D(*aCorrFctn.fDenPMinvDTheta);
+  else
+    fDenPMinvDTheta = 0;
+
+  if (aCorrFctn.fNumNMinvDTheta)
+    fNumNMinvDTheta = new TH2D(*aCorrFctn.fNumNMinvDTheta);
+  else
+    fNumNMinvDTheta = 0;
+  if (aCorrFctn.fDenNMinvDTheta)
+    fDenNMinvDTheta = new TH2D(*aCorrFctn.fDenNMinvDTheta);
+  else
+    fDenNMinvDTheta = 0;
+
+}
+//____________________________
+AliFemtoCorrFctnGammaMonitor::~AliFemtoCorrFctnGammaMonitor(){
+  // destructor
+  delete fNumPMinvDTheta;
+  delete fDenPMinvDTheta;
+  delete fNumNMinvDTheta;
+  delete fDenNMinvDTheta;
+}
+//_________________________
+AliFemtoCorrFctnGammaMonitor& AliFemtoCorrFctnGammaMonitor::operator=(const AliFemtoCorrFctnGammaMonitor& aCorrFctn)
+{
+  // assignment operator
+  if (this == &aCorrFctn)
+    return *this;
+
+  if (aCorrFctn.fNumPMinvDTheta)
+    fNumPMinvDTheta = new TH2D(*aCorrFctn.fNumPMinvDTheta);
+  else
+    fNumPMinvDTheta = 0;
+  if (aCorrFctn.fDenPMinvDTheta)
+    fDenPMinvDTheta = new TH2D(*aCorrFctn.fDenPMinvDTheta);
+  else
+    fDenPMinvDTheta = 0;
+
+  if (aCorrFctn.fNumNMinvDTheta)
+    fNumNMinvDTheta = new TH2D(*aCorrFctn.fNumNMinvDTheta);
+  else
+    fNumNMinvDTheta = 0;
+  if (aCorrFctn.fDenNMinvDTheta)
+    fDenNMinvDTheta = new TH2D(*aCorrFctn.fDenNMinvDTheta);
+  else
+    fDenNMinvDTheta = 0;
+
+
+  return *this;
+}
+//_________________________
+void AliFemtoCorrFctnGammaMonitor::Finish(){
+  // here is where we should normalize, fit, etc...
+  // we should NOT Draw() the histos (as I had done it below),
+  // since we want to insulate ourselves from root at this level
+  // of the code.  Do it instead at root command line with browser.
+  //  mShareNumerator->Draw();
+  //mShareDenominator->Draw();
+  //mRatio->Draw();
+
+}
+
+//____________________________
+AliFemtoString AliFemtoCorrFctnGammaMonitor::Report(){
+  // create report
+  string stemp = "Gamma Monitor Function Report:\n";
+  char ctemp[100];
+  snprintf(ctemp , 100, "Number of entries in numerator:\t%E\n",fNumPMinvDTheta->GetEntries());
+  stemp += ctemp;
+  snprintf(ctemp , 100, "Number of entries in denominator:\t%E\n",fDenPMinvDTheta->GetEntries());
+  stemp += ctemp;
+  //  stemp += mCoulombWeight->Report();
+  AliFemtoString returnThis = stemp;
+  return returnThis;
+}
+//____________________________
+void AliFemtoCorrFctnGammaMonitor::AddRealPair( AliFemtoPair* pair){
+  // add real (effect) pair
+  double me = 0.000511;
+
+  double theta1 = pair->Track1()->Track()->P().Theta();
+  double theta2 = pair->Track2()->Track()->P().Theta();
+  double dtheta = TMath::Abs(theta1 - theta2);
+
+  double e1 = TMath::Sqrt(me*me + pair->Track1()->Track()->P().Mag2());
+  double e2 = TMath::Sqrt(me*me + pair->Track2()->Track()->P().Mag2());
+
+  double minv = 2*me*me + 2*(e1*e2 - 
+                            pair->Track1()->Track()->P().x()*pair->Track2()->Track()->P().x() -
+                            pair->Track1()->Track()->P().y()*pair->Track2()->Track()->P().y() -
+                            pair->Track1()->Track()->P().z()*pair->Track2()->Track()->P().z());
+
+  if (pair->KSide()>0.0) 
+    fNumPMinvDTheta->Fill(minv, dtheta);
+  else
+    fNumNMinvDTheta->Fill(minv, dtheta);
+}
+//____________________________
+void AliFemtoCorrFctnGammaMonitor::AddMixedPair( AliFemtoPair* pair){
+  // add mixed (background) pair
+  double me = 0.000511;
+
+  double theta1 = pair->Track1()->Track()->P().Theta();
+  double theta2 = pair->Track2()->Track()->P().Theta();
+  double dtheta = TMath::Abs(theta1 - theta2);
+
+  double e1 = TMath::Sqrt(me*me + pair->Track1()->Track()->P().Mag2());
+  double e2 = TMath::Sqrt(me*me + pair->Track2()->Track()->P().Mag2());
+
+  double minv = 2*me*me + 2*(e1*e2 - 
+                            pair->Track1()->Track()->P().x()*pair->Track2()->Track()->P().x() -
+                            pair->Track1()->Track()->P().y()*pair->Track2()->Track()->P().y() -
+                            pair->Track1()->Track()->P().z()*pair->Track2()->Track()->P().z());
+
+  if (pair->KSide()>0.0) 
+    fDenPMinvDTheta->Fill(minv, dtheta);
+  else
+    fDenNMinvDTheta->Fill(minv, dtheta);
+}
+
+
+void AliFemtoCorrFctnGammaMonitor::WriteHistos()
+{
+  // Write out result histograms
+  fNumPMinvDTheta->Write();
+  fDenPMinvDTheta->Write();
+  fNumNMinvDTheta->Write();
+  fDenNMinvDTheta->Write();
+}
+
+TList* AliFemtoCorrFctnGammaMonitor::GetOutputList()
+{
+  // Prepare the list of objects to be written to the output
+  TList *tOutputList = new TList();
+
+  tOutputList->Add(fNumPMinvDTheta);
+  tOutputList->Add(fDenPMinvDTheta);
+  tOutputList->Add(fNumNMinvDTheta);
+  tOutputList->Add(fDenNMinvDTheta);
+
+  return tOutputList;
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCorrFctnGammaMonitor.h b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCorrFctnGammaMonitor.h
new file mode 100644 (file)
index 0000000..dc1a62c
--- /dev/null
@@ -0,0 +1,49 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoCorrFctnGammaMonitor - A correlation function that analyzes            //
+// two particle correlations with respect to the azimuthal angle (phi)        //
+// and pseudorapidity (eta) difference                                        //
+//                                                                            //
+// Authors: Adam Kisiel Adam.Kisiel@cern.ch                                   //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+
+#ifndef ALIFEMTOCORRFCTNGAMMAMONITOR_H
+#define ALIFEMTOCORRFCTNGAMMAMONITOR_H
+
+#include "TH1D.h"
+#include "TH2D.h"
+#include "AliFemtoCorrFctn.h"
+
+class AliFemtoCorrFctnGammaMonitor : public AliFemtoCorrFctn {
+public:
+  AliFemtoCorrFctnGammaMonitor(char* title, const int& aMinvBins, const int& aDThetaBins);
+  AliFemtoCorrFctnGammaMonitor(const AliFemtoCorrFctnGammaMonitor& aCorrFctn);
+  virtual ~AliFemtoCorrFctnGammaMonitor();
+
+  AliFemtoCorrFctnGammaMonitor& operator=(const AliFemtoCorrFctnGammaMonitor& aCorrFctn);
+
+  virtual AliFemtoString Report();
+  virtual void AddRealPair(AliFemtoPair* aPair);
+  virtual void AddMixedPair(AliFemtoPair* aPair);
+
+  virtual void Finish();
+
+  void WriteHistos();
+  virtual TList* GetOutputList();
+private:
+  
+  TH2D *fNumPMinvDTheta;        // Numerator Minv vs. DTheta Positive kSide
+  TH2D *fDenPMinvDTheta;        // Denominator Minv vs. DTheta Positive kSide
+
+  TH2D *fNumNMinvDTheta;        // Numerator Minv vs. DTheta Negative kSide
+  TH2D *fDenNMinvDTheta;        // Denominator Minv vs. DTheta Negative kSide
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoCorrFctnGammaMonitor, 1)
+#endif
+};
+
+
+#endif
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCorrFctnTPCNcls.cxx b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCorrFctnTPCNcls.cxx
new file mode 100644 (file)
index 0000000..cc9ff95
--- /dev/null
@@ -0,0 +1,138 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoCorrFctnTPCNcls - A correlation function that saves the correlation//
+// function as a function of number of TPC clusters of the track              //
+//                                                                            //
+// Authors: Adam Kisiel kisiel@mps.ohio-state.edu                             //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+
+#include "AliFemtoCorrFctnTPCNcls.h"
+//#include "AliFemtoHisto.hh"
+#include <cstdio>
+
+#ifdef __ROOT__ 
+ClassImp(AliFemtoCorrFctnTPCNcls)
+#endif
+
+//____________________________
+AliFemtoCorrFctnTPCNcls::AliFemtoCorrFctnTPCNcls(char* title, const int& nbins, const float& QinvLo, const float& QinvHi):
+  AliFemtoCorrFctn(),
+  fNclsTPCMinNumerator(0),
+  fNclsTPCMinDenominator(0)
+{
+  // set up numerator
+  char tTitNum[101] = "NumNclsTPCMin";
+  strncat(tTitNum,title, 100);
+  fNclsTPCMinNumerator = new TH2D(tTitNum,title,nbins,QinvLo,QinvHi,159,0.5,159.5);
+  // set up denominator
+  char tTitDen[101] = "DenNclsTPCMin";
+  strncat(tTitDen,title, 100);
+  fNclsTPCMinDenominator = new TH2D(tTitDen,title,nbins,QinvLo,QinvHi,159,0.5,159.5);
+
+  // to enable error bar calculation...
+  fNclsTPCMinNumerator->Sumw2();
+  fNclsTPCMinDenominator->Sumw2();
+}
+
+//____________________________
+AliFemtoCorrFctnTPCNcls::AliFemtoCorrFctnTPCNcls(const AliFemtoCorrFctnTPCNcls& aCorrFctn) :
+  AliFemtoCorrFctn(),
+  fNclsTPCMinNumerator(0),
+  fNclsTPCMinDenominator(0)
+{
+  // copy constructor
+  if (aCorrFctn.fNclsTPCMinNumerator)
+    fNclsTPCMinNumerator = new TH2D(*aCorrFctn.fNclsTPCMinNumerator);
+  if (aCorrFctn.fNclsTPCMinDenominator)
+    fNclsTPCMinDenominator = new TH2D(*aCorrFctn.fNclsTPCMinDenominator);
+}
+//____________________________
+AliFemtoCorrFctnTPCNcls::~AliFemtoCorrFctnTPCNcls(){
+  // destructor
+  delete fNclsTPCMinNumerator;
+  delete fNclsTPCMinDenominator;
+}
+//_________________________
+AliFemtoCorrFctnTPCNcls& AliFemtoCorrFctnTPCNcls::operator=(const AliFemtoCorrFctnTPCNcls& aCorrFctn)
+{
+  // assignment operator
+  if (this == &aCorrFctn)
+    return *this;
+
+  if (aCorrFctn.fNclsTPCMinNumerator)
+    fNclsTPCMinNumerator = new TH2D(*aCorrFctn.fNclsTPCMinNumerator);
+  else
+    fNclsTPCMinNumerator = 0;
+  if (aCorrFctn.fNclsTPCMinDenominator)
+    fNclsTPCMinDenominator = new TH2D(*aCorrFctn.fNclsTPCMinDenominator);
+  else
+    fNclsTPCMinDenominator = 0;
+
+  return *this;
+}
+//_________________________
+void AliFemtoCorrFctnTPCNcls::Finish(){
+  // here is where we should normalize, fit, etc...
+  // we should NOT Draw() the histos (as I had done it below),
+  // since we want to insulate ourselves from root at this level
+  // of the code.  Do it instead at root command line with browser.
+  //  mShareNumerator->Draw();
+  //mShareDenominator->Draw();
+  //mRatio->Draw();
+
+}
+
+//____________________________
+AliFemtoString AliFemtoCorrFctnTPCNcls::Report(){
+  // create report
+  string stemp = "TPC Ncls Correlation Function Report:\n";
+  char ctemp[100];
+  snprintf(ctemp , 100, "Number of entries in numerator:\t%E\n",fNclsTPCMinNumerator->GetEntries());
+  stemp += ctemp;
+  snprintf(ctemp , 100, "Number of entries in denominator:\t%E\n",fNclsTPCMinDenominator->GetEntries());
+  stemp += ctemp;
+  //  stemp += mCoulombWeight->Report();
+  AliFemtoString returnThis = stemp;
+  return returnThis;
+}
+//____________________________
+void AliFemtoCorrFctnTPCNcls::AddRealPair( AliFemtoPair* pair){
+  // add real (effect) pair
+  double tQinv = fabs(pair->QInv());   // note - qInv() will be negative for identical pairs...
+
+  if (pair->Track1()->Track()->TPCncls()>pair->Track2()->Track()->TPCncls())
+    fNclsTPCMinNumerator->Fill(tQinv, pair->Track2()->Track()->TPCncls());
+  else
+    fNclsTPCMinNumerator->Fill(tQinv, pair->Track1()->Track()->TPCncls());
+}
+//____________________________
+void AliFemtoCorrFctnTPCNcls::AddMixedPair( AliFemtoPair* pair){
+  // add mixed (background) pair
+  double tQinv = fabs(pair->QInv());   // note - qInv() will be negative for identical pairs...
+
+  if (pair->Track1()->Track()->TPCncls()>pair->Track2()->Track()->TPCncls())
+    fNclsTPCMinDenominator->Fill(tQinv, pair->Track2()->Track()->TPCncls());
+  else
+    fNclsTPCMinDenominator->Fill(tQinv, pair->Track1()->Track()->TPCncls());
+}
+
+
+void AliFemtoCorrFctnTPCNcls::WriteHistos()
+{
+  // Write out result histograms
+  fNclsTPCMinNumerator->Write();
+  fNclsTPCMinDenominator->Write();
+}
+
+TList* AliFemtoCorrFctnTPCNcls::GetOutputList()
+{
+  // Prepare the list of objects to be written to the output
+  TList *tOutputList = new TList();
+
+  tOutputList->Add(fNclsTPCMinNumerator);
+  tOutputList->Add(fNclsTPCMinDenominator);
+  
+  return tOutputList;
+
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCorrFctnTPCNcls.h b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCorrFctnTPCNcls.h
new file mode 100644 (file)
index 0000000..edd193c
--- /dev/null
@@ -0,0 +1,45 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoCorrFctnTPCNcls - A correlation function that saves the correlation//
+// function as a function of number of TPC clusters of the track              //
+//                                                                            //
+// Authors: Adam Kisiel kisiel@mps.ohio-state.edu                             //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+
+#ifndef ALIFEMTOCORRFCTNTPCNCLS_H
+#define ALIFEMTOCORRFCTNTPCNCLS_H
+
+#include "TH1D.h"
+#include "TH2D.h"
+#include "AliFemtoCorrFctn.h"
+
+class AliFemtoCorrFctnTPCNcls : public AliFemtoCorrFctn {
+public:
+  AliFemtoCorrFctnTPCNcls(char* title, const int& nbins, const float& QinvLo, const float& QinvHi);
+  AliFemtoCorrFctnTPCNcls(const AliFemtoCorrFctnTPCNcls& aCorrFctn);
+  virtual ~AliFemtoCorrFctnTPCNcls();
+
+  AliFemtoCorrFctnTPCNcls& operator=(const AliFemtoCorrFctnTPCNcls& aCorrFctn);
+
+  virtual AliFemtoString Report();
+  virtual void AddRealPair(AliFemtoPair* aPair);
+  virtual void AddMixedPair(AliFemtoPair* aPair);
+
+  virtual void Finish();
+
+  void WriteHistos();
+  virtual TList* GetOutputList();
+private:
+  
+  TH2D *fNclsTPCMinNumerator;        // Numerator as a function of lower TPC Ncls of the pair 
+  TH2D *fNclsTPCMinDenominator;      // Denominator as a function of lower TPC Ncls of the pair
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoCorrFctnTPCNcls, 1)
+#endif
+};
+
+
+#endif
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCutMonitorParticleEtCorr.cxx b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCutMonitorParticleEtCorr.cxx
new file mode 100644 (file)
index 0000000..d40b91f
--- /dev/null
@@ -0,0 +1,175 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoCutMonitorParticleEtCorr - the cut monitor for particles           //
+// which saves particles' et histogram and makes the bin-by-bin correlation   //
+//                                                                            //
+// Author: Adam.Kisiel@cern.ch                                                //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+#include "AliFemtoCutMonitorParticleEtCorr.h"
+#include "AliFemtoModelHiddenInfo.h"
+#include <TH1D.h>
+#include <TH2D.h>
+#include <TList.h>
+#include <TMath.h>
+
+AliFemtoCutMonitorParticleEtCorr::AliFemtoCutMonitorParticleEtCorr():
+  AliFemtoCutMonitor(),
+  fPhiBins(60),
+  fPtPerPhi(0),     
+  fPtCovPerPhi(0),
+  fPtMultPerPhi(0),
+  fNEventsProcessed(0)
+{
+  // Default constructor
+  for (int ib=0; ib<200; ib++) {
+    fPtSumEvent[ib] = 0; 
+    fMultSumEvent[ib] = 0;
+  }
+}
+
+AliFemtoCutMonitorParticleEtCorr::AliFemtoCutMonitorParticleEtCorr(const char *aName, int aPhiBins):
+  AliFemtoCutMonitor(),
+  fPhiBins(aPhiBins),
+  fPtPerPhi(0),     
+  fPtCovPerPhi(0),
+  fPtMultPerPhi(0),
+  fNEventsProcessed(0)
+{
+  // Normal constructor
+  char name[200];
+  snprintf(name, 200, "EtCorrAvgPt%s", aName);
+  fPtPerPhi = new TH1D(name, "Average Pt Per Phi", aPhiBins, -0.5, aPhiBins-0.5);
+  snprintf(name, 200, "EtCorrMult%s", aName);
+  fPtMultPerPhi = new TH2D(name, "Multiplicity Per Phi", aPhiBins, -0.5, aPhiBins-0.5, aPhiBins, -0.5, aPhiBins-0.5);
+  snprintf(name, 200, "EtCorrAvgPtCov%s", aName);
+  fPtCovPerPhi = new TH2D(name, "Covariance of Average Pt Per Phi", aPhiBins, -0.5, aPhiBins-0.5, aPhiBins, -0.5, aPhiBins-0.5);
+
+  fPtPerPhi->Sumw2();
+  fPtCovPerPhi->Sumw2();
+  fPtMultPerPhi->Sumw2();
+  fPhiBins = aPhiBins;
+
+  for (int ib=0; ib<200; ib++) {
+    fPtSumEvent[ib] = 0; 
+    fMultSumEvent[ib] = 0;
+  }
+
+}
+
+AliFemtoCutMonitorParticleEtCorr::AliFemtoCutMonitorParticleEtCorr(const AliFemtoCutMonitorParticleEtCorr &aCut):
+  AliFemtoCutMonitor(),
+  fPhiBins(0),
+  fPtPerPhi(0),     
+  fPtCovPerPhi(0),
+  fPtMultPerPhi(0),
+  fNEventsProcessed(0)
+{
+  // copy constructor
+  if (fPtCovPerPhi) delete fPtCovPerPhi;
+  fPtCovPerPhi = new TH2D(*aCut.fPtCovPerPhi);
+  if (fPtPerPhi) delete fPtPerPhi;
+  fPtPerPhi = new TH1D(*aCut.fPtPerPhi);
+  if (fPtMultPerPhi) delete fPtMultPerPhi;
+  fPtMultPerPhi = new TH2D(*aCut.fPtMultPerPhi);
+  fPhiBins = aCut.fPhiBins;
+  fNEventsProcessed = aCut.fNEventsProcessed;
+
+  for (int ib=0; ib<200; ib++) {
+    fPtSumEvent[ib] = 0; 
+    fMultSumEvent[ib] = 0;
+  }
+}
+
+AliFemtoCutMonitorParticleEtCorr::~AliFemtoCutMonitorParticleEtCorr()
+{
+  // Destructor
+  delete fPtPerPhi;
+  delete fPtMultPerPhi;
+  delete fPtCovPerPhi;
+}
+
+AliFemtoCutMonitorParticleEtCorr& AliFemtoCutMonitorParticleEtCorr::operator=(const AliFemtoCutMonitorParticleEtCorr& aCut)
+{
+  // assignment operator
+  if (this == &aCut) 
+    return *this;
+
+  if (fPtCovPerPhi) delete fPtCovPerPhi;
+  fPtCovPerPhi = new TH2D(*aCut.fPtCovPerPhi);
+  if (fPtPerPhi) delete fPtPerPhi;
+  fPtPerPhi = new TH1D(*aCut.fPtPerPhi);
+  if (fPtMultPerPhi) delete fPtMultPerPhi;
+  fPtMultPerPhi = new TH2D(*aCut.fPtMultPerPhi);
+  fPhiBins = aCut.fPhiBins;
+  fNEventsProcessed = aCut.fNEventsProcessed;
+  
+  return *this;
+}
+
+AliFemtoString AliFemtoCutMonitorParticleEtCorr::Report(){ 
+  // Prepare report from the execution
+  string stemp = "*** AliFemtoCutMonitorParticleEtCorr report"; 
+  AliFemtoString returnThis = stemp;
+  return returnThis; 
+}
+
+void AliFemtoCutMonitorParticleEtCorr::Fill(const AliFemtoTrack* aTrack)
+{
+  // Fill in the monitor histograms with the values from the current track
+  //  float tEnergy = ::sqrt(aTrack->P().mag2()+fMass*fMass);
+  //  float tRapidity = 0.5*::log((tEnergy+aTrack->P().z())/(tEnergy-aTrack->P().z()));
+  float tPt = ::sqrt((aTrack->P().x())*(aTrack->P().x())+(aTrack->P().y())*(aTrack->P().y()));
+  //  float tEta = -TMath::Log(TMath::Tan(aTrack->P().theta()/2.0));
+  float tPhi = aTrack->P().Phi();
+  Double_t tPiTwo = TMath::Pi()*2;
+
+  while (tPhi > tPiTwo) tPhi -= tPiTwo;
+  while (tPhi < 0) tPhi += tPiTwo;
+
+  int nbin = (int) floor(tPhi * fPhiBins / tPiTwo);
+  fPtSumEvent[nbin] += tPt;
+  fMultSumEvent[nbin] += 1;
+}
+
+void AliFemtoCutMonitorParticleEtCorr::Write()
+{
+  // Write out the relevant histograms
+  fPtPerPhi->Write();
+  fPtCovPerPhi->Write();
+  fPtMultPerPhi->Write();
+}
+
+TList *AliFemtoCutMonitorParticleEtCorr::GetOutputList()
+{
+  TList *tOutputList = new TList();
+  tOutputList->Add(fPtPerPhi);
+  tOutputList->Add(fPtCovPerPhi);
+  tOutputList->Add(fPtMultPerPhi);
+
+  return tOutputList;
+}
+
+void AliFemtoCutMonitorParticleEtCorr::EventBegin(const AliFemtoEvent* aEvent)
+{
+  if (aEvent)
+    for (int iter=0; iter<fPhiBins; iter++) {
+      fPtSumEvent[iter] = 0;
+      fMultSumEvent[iter] = 0;
+    }
+}
+
+void AliFemtoCutMonitorParticleEtCorr::EventEnd(const AliFemtoEvent* aEvent)
+{
+  if (aEvent) {
+    for (int ispt=0; ispt<fPhiBins; ispt++) {
+      fPtPerPhi->Fill(ispt, fPtSumEvent[ispt]);
+      for (int ispt2=0; ispt2<fPhiBins; ispt2++) {
+       fPtCovPerPhi->Fill(ispt, ispt2, fPtSumEvent[ispt]*fPtSumEvent[ispt2]);
+       fPtMultPerPhi->Fill(ispt, ispt2, fMultSumEvent[ispt]*fMultSumEvent[ispt2]);
+      }
+    }
+    fNEventsProcessed++;
+  }
+}
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCutMonitorParticleEtCorr.h b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCutMonitorParticleEtCorr.h
new file mode 100644 (file)
index 0000000..270ab1e
--- /dev/null
@@ -0,0 +1,61 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoCutMonitorParticleEtCorr - the cut monitor for particles           //
+// which saves particles' et histogram and makes the bin-by-bin correlation   //
+//                                                                            //
+// Author: Adam.Kisiel@cern.ch                                                //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+#ifndef AliFemtoCutMonitorParticleEtCorr_hh
+#define AliFemtoCutMonitorParticleEtCorr_hh
+
+class AliFemtoEvent;
+class AliFemtoTrack;
+class AliFemtoV0;
+class AliFemtoKink;
+class AliFemtoPair; // Gael 12/04/02
+class TH1D;
+class TH2D;
+class TList;
+#include "AliFemtoString.h"
+#include "AliFemtoParticleCollection.h"
+#include "AliFemtoCutMonitor.h"
+
+class AliFemtoCutMonitorParticleEtCorr : public AliFemtoCutMonitor{
+  
+public:
+  AliFemtoCutMonitorParticleEtCorr();
+  AliFemtoCutMonitorParticleEtCorr(const char *aName, int aPhiBins);
+  AliFemtoCutMonitorParticleEtCorr(const AliFemtoCutMonitorParticleEtCorr &aCut);
+  virtual ~AliFemtoCutMonitorParticleEtCorr();
+
+  AliFemtoCutMonitorParticleEtCorr& operator=(const AliFemtoCutMonitorParticleEtCorr& aCut);
+
+  virtual void EventBegin(const AliFemtoEvent* aEvent);
+  virtual void EventEnd(const AliFemtoEvent* aEvent);
+
+  virtual AliFemtoString Report();
+  virtual void Fill(const AliFemtoEvent* aEvent) {AliFemtoCutMonitor::Fill(aEvent);}
+  virtual void Fill(const AliFemtoTrack* aTrack);
+  virtual void Fill(const AliFemtoV0* aV0) {AliFemtoCutMonitor::Fill(aV0);}
+  virtual void Fill(const AliFemtoKink* aKink) {AliFemtoCutMonitor::Fill(aKink);}
+  virtual void Fill(const AliFemtoPair* aPair) {AliFemtoCutMonitor::Fill(aPair);}
+  virtual void Fill(const AliFemtoParticleCollection* aCollection) {AliFemtoCutMonitor::Fill(aCollection);}
+  virtual void Fill(const AliFemtoEvent* aEvent,const AliFemtoParticleCollection* aCollection)
+  {AliFemtoCutMonitor::Fill(aEvent, aCollection);}
+
+  void Write();
+
+  virtual TList *GetOutputList();
+
+private:
+  Double_t fPtSumEvent[200];      // A table where Pt sum per event is stored
+  Double_t fMultSumEvent[200];    // A table where mult sum per event is stored
+  Int_t    fPhiBins;              // Number of Phi bins
+  TH1D    *fPtPerPhi;             // Histogram storing per-bin sum pt
+  TH2D    *fPtCovPerPhi;          // Histogram storing per-bin covariance
+  TH2D    *fPtMultPerPhi;         // Histogram storing per-bin multiplicity
+  Int_t    fNEventsProcessed;     // Count processed events
+};
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCutMonitorParticleMomRes.cxx b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCutMonitorParticleMomRes.cxx
new file mode 100644 (file)
index 0000000..b27b37d
--- /dev/null
@@ -0,0 +1,179 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoCutMonitorParticleMomRes - the cut monitor for particles to study    //
+// the difference between reconstructed and true momentum                     //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+#include "AliFemtoCutMonitorParticleMomRes.h"
+#include <TH1D.h>
+#include <TH2D.h>
+#include <TH3D.h>
+#include <TList.h>
+#include "AliFemtoModelHiddenInfo.h"
+
+AliFemtoCutMonitorParticleMomRes::AliFemtoCutMonitorParticleMomRes():
+  fMomRes3D(0),
+  fMomResXvsP(0),
+  fMomResYvsP(0),
+  fMomResZvsP(0),
+  fImpactXY(0),
+  fImpactZ(0),
+  fSigma(0)
+{
+  // Default constructor
+  fMomRes3D = new TH3D("MomRes3D", "Momentum resolution", 100, -0.05, 0.05, 100, -0.05, 0.05, 100, -0.05, 0.05);
+  fMomResXvsP = new TH2D("MomResXvsP", "X momentum resolution vs P", 100, 0.1, 2.0, 100, -0.05, 0.05);
+  fMomResYvsP = new TH2D("MomResYvsP", "Y momentum resolution vs P", 100, 0.1, 2.0, 100, -0.05, 0.05);
+  fMomResZvsP = new TH2D("MomResZvsP", "Z momentum resolution vs P", 100, 0.1, 2.0, 100, -0.05, 0.05);
+  fImpactXY   = new TH2D("ImpactXY", "XY impact parameter vs P", 100, 0.1, 2.0, 200, -1.0, 1.0);
+  fImpactZ    = new TH2D("ImpactZ",  "Z impact parameter vs P" , 100, 0.1, 2.0, 200, -1.0, 1.0);
+  fSigma      = new TH2D("Sigma",     "Sigma to vertex vs P" , 100, 0.1, 2.0, 200, -5.0, 5.0);
+}
+
+AliFemtoCutMonitorParticleMomRes::AliFemtoCutMonitorParticleMomRes(const char *aName):
+  fMomRes3D(0),
+  fMomResXvsP(0),
+  fMomResYvsP(0),
+  fMomResZvsP(0),
+  fImpactXY(0),
+  fImpactZ(0),
+  fSigma(0)
+{
+  // Normal constructor
+  char name[200];
+  snprintf(name, 200, "MomRes3D%s", aName);
+  fMomRes3D = new TH3D(name, "Momentum resolution", 100, -0.05, 0.05, 100, -0.05, 0.05, 100, -0.05, 0.05);
+  snprintf(name, 200, "MomResXvsP%s", aName);
+  fMomResXvsP = new TH2D(name, "X momentum resolution vs P", 100, 0.1, 2.0, 100, -0.05, 0.05);
+  snprintf(name, 200, "MomResYvsP%s", aName);
+  fMomResYvsP = new TH2D(name, "Y momentum resolution vs P", 100, 0.1, 2.0, 100, -0.05, 0.05);
+  snprintf(name, 200, "MomResZvsP%s", aName);
+  fMomResZvsP = new TH2D(name, "Z momentum resolution vs P", 100, 0.1, 2.0, 100, -0.05, 0.05);
+  snprintf(name, 200, "ImpactXY%s", aName);
+  fImpactXY   = new TH2D(name, "XY impact parameter vs P", 100, 0.1, 2.0, 200, -1.0, 1.0);
+  snprintf(name, 200, "ImpactZ%s", aName);
+  fImpactZ    = new TH2D(name,  "Z impact parameter vs P" , 100, 0.1, 2.0, 200, -1.0, 1.0);
+  snprintf(name, 200, "Sigma%s", aName);
+  fSigma    = new TH2D(name,  "Z impact parameter vs P" , 100, 0.1, 2.0, 200, -5.0, 5.0);
+}
+
+AliFemtoCutMonitorParticleMomRes::AliFemtoCutMonitorParticleMomRes(const AliFemtoCutMonitorParticleMomRes &aCut):
+  AliFemtoCutMonitor(),
+  fMomRes3D(0),
+  fMomResXvsP(0),
+  fMomResYvsP(0),
+  fMomResZvsP(0),
+  fImpactXY(0),
+  fImpactZ(0),
+  fSigma(0)
+{
+  // copy constructor
+  if (fMomRes3D) delete fMomRes3D;
+  fMomRes3D = new TH3D(*aCut.fMomRes3D);
+  if (fMomResXvsP) delete fMomResXvsP;
+  fMomResXvsP = new TH2D(*aCut.fMomResXvsP);
+  if (fMomResYvsP) delete fMomResYvsP;
+  fMomResYvsP = new TH2D(*aCut.fMomResYvsP);
+  if (fMomResZvsP) delete fMomResZvsP;
+  fMomResZvsP = new TH2D(*aCut.fMomResZvsP);
+  if (fImpactXY) delete fImpactXY;
+  fImpactXY = new TH2D(*aCut.fImpactXY);
+  if (fImpactZ) delete fImpactZ;
+  fImpactZ = new TH2D(*aCut.fImpactZ);
+  if (fSigma) delete fSigma;
+  fSigma = new TH2D(*aCut.fSigma);
+}
+
+AliFemtoCutMonitorParticleMomRes::~AliFemtoCutMonitorParticleMomRes()
+{
+  // Destructor
+  delete fMomRes3D;
+  delete fMomResXvsP;
+  delete fMomResYvsP;
+  delete fMomResZvsP;
+  delete fImpactXY;
+  delete fImpactZ;
+  delete fSigma;
+}
+
+AliFemtoCutMonitorParticleMomRes& AliFemtoCutMonitorParticleMomRes::operator=(const AliFemtoCutMonitorParticleMomRes& aCut)
+{
+  // assignment operator
+  if (this == &aCut) 
+    return *this;
+
+  if (fMomRes3D) delete fMomRes3D;
+  fMomRes3D = new TH3D(*aCut.fMomRes3D);
+  if (fMomResXvsP) delete fMomResXvsP;
+  fMomResXvsP = new TH2D(*aCut.fMomResXvsP);
+  if (fMomResYvsP) delete fMomResYvsP;
+  fMomResYvsP = new TH2D(*aCut.fMomResYvsP);
+  if (fMomResZvsP) delete fMomResZvsP;
+  fMomResZvsP = new TH2D(*aCut.fMomResZvsP);
+  if (fImpactXY) delete fImpactXY;
+  fImpactXY = new TH2D(*aCut.fImpactXY);
+  if (fImpactZ) delete fImpactZ;
+  fImpactZ = new TH2D(*aCut.fImpactZ);
+  if (fSigma) delete fSigma;
+  fSigma = new TH2D(*aCut.fSigma);
+  
+  return *this;
+}
+
+AliFemtoString AliFemtoCutMonitorParticleMomRes::Report(){ 
+  // Prepare report from the execution
+  string stemp = "*** AliFemtoCutMonitorParticleMomRes report"; 
+  AliFemtoString returnThis = stemp;
+  return returnThis; 
+}
+
+void AliFemtoCutMonitorParticleMomRes::Fill(const AliFemtoTrack* aTrack)
+{
+  // Fill momentum resolution histograms for the particle
+  AliFemtoModelHiddenInfo *tInf = ( AliFemtoModelHiddenInfo *) aTrack->GetHiddenInfo();
+  if (tInf) {
+    fMomRes3D->Fill(tInf->GetTrueMomentum()->x() - aTrack->P().x(),
+                   tInf->GetTrueMomentum()->y() - aTrack->P().y(),
+                   tInf->GetTrueMomentum()->z() - aTrack->P().z());
+    
+    fMomResXvsP->Fill(aTrack->P().Mag(),
+                     tInf->GetTrueMomentum()->x() - aTrack->P().x());
+    fMomResYvsP->Fill(aTrack->P().Mag(),
+                     tInf->GetTrueMomentum()->y() - aTrack->P().y());
+    fMomResZvsP->Fill(aTrack->P().Mag(),
+                     tInf->GetTrueMomentum()->z() - aTrack->P().z());
+    fImpactXY->Fill(aTrack->P().Mag(),
+                   aTrack->ImpactD());
+    fImpactZ->Fill(aTrack->P().Mag(),
+                  aTrack->ImpactZ());
+    fSigma->Fill(aTrack->P().Mag(),
+                aTrack->SigmaToVertex());
+  }
+}
+
+void AliFemtoCutMonitorParticleMomRes::Write()
+{
+  // Write out the relevant histograms
+  fMomRes3D->Write();
+  fMomResXvsP->Write();
+  fMomResYvsP->Write();
+  fMomResZvsP->Write();
+  fImpactXY->Write();
+  fImpactZ->Write();
+  fSigma->Write();
+}
+
+TList *AliFemtoCutMonitorParticleMomRes::GetOutputList()
+{
+  // Get the list of histograms to write
+  TList *tOutputList = new TList();
+  tOutputList->Add(fMomRes3D);
+  tOutputList->Add(fMomResXvsP);
+  tOutputList->Add(fMomResYvsP);
+  tOutputList->Add(fMomResZvsP);
+  tOutputList->Add(fImpactXY);
+  tOutputList->Add(fImpactZ);
+  tOutputList->Add(fSigma);
+
+  return tOutputList;
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCutMonitorParticleMomRes.h b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCutMonitorParticleMomRes.h
new file mode 100644 (file)
index 0000000..068e931
--- /dev/null
@@ -0,0 +1,56 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoCutMonitorParticleMomRes - the cut monitor for particles to study  //
+// the difference between reconstructed and true momentum                     //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+#ifndef AliFemtoCutMonitorParticleMomRes_H
+#define AliFemtoCutMonitorParticleMomRes_H
+
+class AliFemtoEvent;
+class AliFemtoTrack;
+class AliFemtoV0;
+class AliFemtoKink;
+class AliFemtoPair; // Gael 12/04/02
+class TH1D;
+class TH2D;
+class TH3D;
+class TList;
+#include "AliFemtoString.h"
+#include "AliFemtoParticleCollection.h"
+#include "AliFemtoCutMonitor.h"
+
+class AliFemtoCutMonitorParticleMomRes : public AliFemtoCutMonitor{
+  
+public:
+  AliFemtoCutMonitorParticleMomRes();
+  AliFemtoCutMonitorParticleMomRes(const char *aName);
+  AliFemtoCutMonitorParticleMomRes(const AliFemtoCutMonitorParticleMomRes &aCut);
+  virtual ~AliFemtoCutMonitorParticleMomRes();
+
+  AliFemtoCutMonitorParticleMomRes& operator=(const AliFemtoCutMonitorParticleMomRes& aCut);
+
+  virtual AliFemtoString Report();
+   virtual void Fill(const AliFemtoEvent* aEvent) {AliFemtoCutMonitor::Fill(aEvent);}
+  virtual void Fill(const AliFemtoTrack* aTrack);
+  virtual void Fill(const AliFemtoV0* aV0) {AliFemtoCutMonitor::Fill(aV0);}
+  virtual void Fill(const AliFemtoKink* aKink) {AliFemtoCutMonitor::Fill(aKink);}
+  virtual void Fill(const AliFemtoPair* aPair) {AliFemtoCutMonitor::Fill(aPair);}
+  virtual void Fill(const AliFemtoParticleCollection* aCollection) {AliFemtoCutMonitor::Fill(aCollection);}
+  virtual void Fill(const AliFemtoEvent* aEvent,const AliFemtoParticleCollection* aCollection)
+  {AliFemtoCutMonitor::Fill(aEvent, aCollection);}
+  void Write();
+
+  virtual TList *GetOutputList();
+
+private:
+  TH3D *fMomRes3D;    // 3D momentum resolution
+  TH2D *fMomResXvsP;  // X resolution vs momentum
+  TH2D *fMomResYvsP;  // Y resolution vs momentum
+  TH2D *fMomResZvsP;  // Z resolution vs momentum
+  TH2D *fImpactXY;    // XY impact parameter
+  TH2D *fImpactZ;     // Z impact parameter
+  TH2D *fSigma;       // Sigma to vertex vs momentum
+};
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCutMonitorParticlePtPDG.cxx b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCutMonitorParticlePtPDG.cxx
new file mode 100644 (file)
index 0000000..bed9bd7
--- /dev/null
@@ -0,0 +1,296 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoCutMonitorParticlePtPDG - the cut monitor for particles to study    //
+// the difference between reconstructed and true momentum                     //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+#include "AliFemtoCutMonitorParticlePtPDG.h"
+#include "AliFemtoModelHiddenInfo.h"
+#include <TH1D.h>
+#include <TH2D.h>
+#include <TList.h>
+#include <TMath.h>
+
+AliFemtoCutMonitorParticlePtPDG::AliFemtoCutMonitorParticlePtPDG():
+  fPtPDG(0),ftpcHist(0),fPtGoodPi(0),fPtFakePi(0),fPtGoodK(0),fPtFakeK(0),
+  fPtGoodP(0),fPtFakeP(0),fPtRPi(0),fPtRK(0),fPtRP(0),
+  fPtContP(0),
+  fPtContPi(0),
+  fPtContMup(0),
+  fPtContElp(0),
+  fMass(0.13957)
+{
+  // Default constructor
+}
+
+AliFemtoCutMonitorParticlePtPDG::AliFemtoCutMonitorParticlePtPDG(const char *aName, float aMass):
+  AliFemtoCutMonitor(),
+  fPtPDG(0),ftpcHist(0),fPtGoodPi(0),fPtFakePi(0),fPtGoodK(0),fPtFakeK(0),
+  fPtGoodP(0),fPtFakeP(0),fPtRPi(0),fPtRK(0),fPtRP(0),
+  fPtContP(0),
+  fPtContPi(0),
+  fPtContMup(0),
+  fPtContElp(0),
+  fMass(aMass)
+{
+  // Normal constructor
+  char name[200];
+  snprintf(name, 200, "PtPDG%s", aName);
+  fPtPDG = new TH2D(name, "PDG vs Pt", 10, 0.0, 5.0, 100, 0.1, 2.0);
+  snprintf(name, 200, "tpcHist%s", aName);
+  ftpcHist=new TH2D(name,"TPC dE/dX vs momentum",100,0.1,2.7,100,0.,6.);
+  snprintf(name, 200, "PtGoodPi%s", aName);
+  fPtGoodPi = new TH1D(name, "good pions Pt",                    100, 0.1, 2.0);
+  snprintf(name, 200, "PtFakePi%s", aName);
+  fPtFakePi = new TH1D(name, "fake pions Pt",              100, 0.1, 2.0);
+  snprintf(name, 200, "PtRPi%s", aName);
+  fPtRPi = new TH1D(name, "right pdg pions Pt",               100, 0.1, 2.0);
+  snprintf(name, 200, "PtGoodK%s", aName);
+  fPtGoodK = new TH1D(name, "good kaons Pt",                     100, 0.1, 2.0);
+  snprintf(name, 200, "PtFakeK%s", aName);
+  fPtFakeK = new TH1D(name, "fake kaons Pt",                100, 0.1, 2.0);
+  snprintf(name, 200, "PtRK%s", aName);
+  fPtRK = new TH1D(name, "right pdg kaons Pt",                 100, 0.1, 2.0);  
+   snprintf(name, 200, "PtGoodP%s", aName);
+  fPtGoodP = new TH1D(name, "good protons Pt",                     100, 0.1, 2.0);
+  snprintf(name, 200, "PtFakeP%s", aName);
+  fPtFakeP = new TH1D(name, "fake protons Pt",                100, 0.1, 2.0);
+  snprintf(name, 200, "PtRP%s", aName);
+  fPtRP = new TH1D(name, "right pdg protons Pt",                 100, 0.1, 2.0);   
+
+  snprintf(name, 200, "PtContP%s", aName);
+  fPtContP = new TH1D(name, "contamination",                 100, 0.1, 2.0);   
+  snprintf(name, 200, "PtContPi%s", aName);
+  fPtContPi = new TH1D(name, "contamination",                 100, 0.1, 2.0);   
+  snprintf(name, 200, "PtContMup%s", aName);
+  fPtContMup = new TH1D(name, "contamination",                 100, 0.1, 2.0);   
+  snprintf(name, 200, "PtContElp%s", aName);
+  fPtContElp = new TH1D(name, "contamination",                 100, 0.1, 2.0);   
+}
+
+AliFemtoCutMonitorParticlePtPDG::AliFemtoCutMonitorParticlePtPDG(const AliFemtoCutMonitorParticlePtPDG &aCut):
+  AliFemtoCutMonitor(),
+  fPtPDG(0),ftpcHist(0),fPtGoodPi(0),fPtFakePi(0),fPtGoodK(0),fPtFakeK(0),
+  fPtGoodP(0),fPtFakeP(0),fPtRPi(0),fPtRK(0),fPtRP(0),
+  fPtContP(0),
+  fPtContPi(0),
+  fPtContMup(0),
+  fPtContElp(0), 
+  fMass(0.13957)
+{
+  // copy constructor
+  if (fPtPDG) delete fPtPDG;
+  fPtPDG = new TH2D(*aCut.fPtPDG);
+  ftpcHist= new TH2D(*aCut.ftpcHist);
+  fPtGoodPi= new TH1D(*aCut.fPtGoodPi);
+  fPtFakePi= new TH1D(*aCut.fPtFakePi);
+  fPtGoodK= new TH1D(*aCut.fPtGoodK);
+  fPtFakeK= new TH1D(*aCut.fPtFakePi);
+  fPtGoodP= new TH1D(*aCut.fPtGoodP);
+  fPtFakeP= new TH1D(*aCut.fPtFakePi);
+  fPtRPi= new TH1D(*aCut.fPtRPi);
+  fPtRK= new TH1D(*aCut.fPtRK);
+  fPtRP= new TH1D(*aCut.fPtRP);  
+  
+  fPtContP= new TH1D(*aCut.fPtContP);
+  fPtContPi= new TH1D(*aCut.fPtContPi);
+  fPtContMup= new TH1D(*aCut.fPtContMup);
+  fPtContElp= new TH1D(*aCut.fPtContElp);
+  
+  fMass = aCut.fMass; 
+}
+
+AliFemtoCutMonitorParticlePtPDG::~AliFemtoCutMonitorParticlePtPDG()
+{
+  // Destructor
+  delete fPtPDG;
+  delete ftpcHist;
+  delete fPtGoodPi;
+  delete fPtFakePi;
+  delete fPtGoodK;
+  delete fPtFakeK;
+  delete fPtGoodP;
+  delete fPtFakeP; 
+  delete fPtRPi;
+  delete fPtRK;
+  delete fPtRP;
+
+  delete fPtContP;
+  delete fPtContPi;
+  delete fPtContMup;
+  delete fPtContElp;
+
+}
+
+AliFemtoCutMonitorParticlePtPDG& AliFemtoCutMonitorParticlePtPDG::operator=(const AliFemtoCutMonitorParticlePtPDG& aCut)
+{
+  // assignment operator
+  if (this == &aCut) 
+    return *this;
+
+  if (fPtPDG) delete fPtPDG;
+  fPtPDG = new TH2D(*aCut.fPtPDG);
+  
+  if (ftpcHist) delete ftpcHist;
+  ftpcHist = new TH2D(*aCut.ftpcHist);
+  
+   if (fPtGoodPi) delete fPtGoodPi;
+  fPtGoodPi = new TH1D(*aCut.fPtGoodPi);
+  
+   if (fPtFakePi) delete fPtFakePi;
+  fPtFakePi = new TH1D(*aCut.fPtFakePi);
+  
+   if (fPtRPi) delete fPtRPi;
+  fPtRPi = new TH1D(*aCut.fPtRPi);
+  
+  if (fPtGoodK) delete fPtGoodK;
+  fPtGoodK = new TH1D(*aCut.fPtGoodK);
+  
+   if (fPtFakeK) delete fPtFakeK;
+  fPtFakeK = new TH1D(*aCut.fPtFakeK);
+  
+   if (fPtRK) delete fPtRK;
+  fPtRK = new TH1D(*aCut.fPtRK);  
+   
+  if (fPtGoodP) delete fPtGoodP;
+  fPtGoodP = new TH1D(*aCut.fPtGoodP);
+  
+   if (fPtFakeP) delete fPtFakeP;
+  fPtFakeP = new TH1D(*aCut.fPtFakeP);
+  
+   if (fPtRP) delete fPtRP;
+  fPtRP = new TH1D(*aCut.fPtRP);
+   if (fPtContP) delete fPtContP;
+  fPtContP = new TH1D(*aCut.fPtContP);
+
+   if (fPtContPi) delete fPtContPi;
+  fPtContPi = new TH1D(*aCut.fPtContPi);
+  
+     if (fPtContMup) delete fPtContMup;
+  fPtContMup = new TH1D(*aCut.fPtContMup);
+
+     if (fPtContElp) delete fPtContElp;
+  fPtContElp = new TH1D(*aCut.fPtContElp);
+  
+  return *this;
+}
+
+AliFemtoString AliFemtoCutMonitorParticlePtPDG::Report(){ 
+  // Prepare report from the execution
+  string stemp = "*** AliFemtoCutMonitorParticlePtPDG report"; 
+  AliFemtoString returnThis = stemp;
+  return returnThis; 
+}
+
+void AliFemtoCutMonitorParticlePtPDG::Fill(const AliFemtoTrack* aTrack)
+{
+  // Fill in the monitor histograms with the values from the current track
+  //  float tEnergy = ::sqrt(aTrack->P().mag2()+fMass*fMass);
+  //  float tRapidity = 0.5*::log((tEnergy+aTrack->P().z())/(tEnergy-aTrack->P().z()));
+  float tPt = ::sqrt((aTrack->P().x())*(aTrack->P().x())+(aTrack->P().y())*(aTrack->P().y()));
+  //  float tEta = -TMath::Log(TMath::Tan(aTrack->P().theta()/2.0));
+  //  float tPhi = aTrack->P().phi();
+  float tP = ::sqrt((aTrack->P().z())*(aTrack->P().z())+(aTrack->P().x())*(aTrack->P().x())+(aTrack->P().y())*(aTrack->P().y()));;
+  float dedx = aTrack->TPCsignalN();
+  float w[10];
+  w[0] = aTrack->PidProbElectron();
+  w[1] = aTrack->PidProbMuon();
+  w[2] = aTrack->PidProbPion();
+  w[3] = aTrack->PidProbKaon(); 
+  w[4] = aTrack->PidProbProton();
+  
+   Int_t pdg1=0;
+  AliFemtoModelHiddenInfo *info = ( AliFemtoModelHiddenInfo *) aTrack->GetHiddenInfo();
+  if(info)pdg1 = info->GetPDGPid();
+
+
+//most probable particle  
+  fPtGoodPi->Fill(tPt);
+  fPtGoodP->Fill(tPt);
+  fPtGoodK->Fill(tPt);
+
+//contaminations 
+  if (abs(pdg1)!=321)fPtFakeK->Fill(tPt);
+  if (abs(pdg1)!=211)fPtFakePi->Fill(tPt);
+  if (abs(pdg1)!=2212)fPtFakeP->Fill(tPt);
+
+               
+//contaminations for kaons 
+  if (abs(pdg1)==2212)fPtContP->Fill(tPt);
+  if (abs(pdg1)==211)fPtContPi->Fill(tPt);
+  if (abs(pdg1)==13)fPtContMup->Fill(tPt);
+  if (abs(pdg1)==11)fPtContElp->Fill(tPt);
+             
+  Float_t pdg=-1.0;
+  if(abs(pdg1)==211){
+   pdg=2.0;
+   fPtRPi->Fill(tPt);
+  }
+
+  if(abs(pdg1)==321){
+   pdg=3.0;
+   fPtRK->Fill(tPt);
+   }
+  
+  if(abs(pdg1)==2212){
+   pdg=4.0;
+   fPtRP->Fill(tPt);
+   }
+  
+  if(abs(pdg1)==11)pdg=0.0; //+-electron
+  if(abs(pdg1)==13)pdg=1.0;  //+-muon
+  
+  //cout<<"pdg from CutMonitor.."<<pdg1<<"pdg"<<pdg<<endl;
+   
+  fPtPDG->Fill(pdg, tPt);
+  ftpcHist->Fill(tP,dedx);
+  
+}
+
+void AliFemtoCutMonitorParticlePtPDG::Write()
+{
+  // Write out the relevant histograms
+  
+  fPtPDG->Write();
+  ftpcHist->Write();
+  fPtGoodPi->Write();
+  fPtFakePi->Write();
+  fPtGoodK->Write();
+  fPtFakeK->Write();
+  fPtGoodP->Write();
+  fPtFakeP->Write(); 
+  fPtRPi->Write();
+  fPtRK->Write();
+  fPtRP->Write();
+  fPtContP->Write();
+  fPtContPi->Write();
+  fPtContMup->Write();
+  fPtContElp->Write();
+}
+
+TList *AliFemtoCutMonitorParticlePtPDG::GetOutputList()
+{
+  TList *tOutputList = new TList();
+  tOutputList->Add(fPtPDG);
+  tOutputList->Add(ftpcHist);
+  tOutputList->Add(fPtGoodPi);
+  tOutputList->Add(fPtFakePi);
+  tOutputList->Add(fPtGoodK);
+  tOutputList->Add(fPtFakeK);
+  tOutputList->Add(fPtGoodP);
+  tOutputList->Add(fPtFakeP); 
+  tOutputList->Add(fPtRPi);
+  tOutputList->Add(fPtRK);
+  tOutputList->Add(fPtRP);
+  tOutputList->Add(fPtContP);
+  tOutputList->Add(fPtContPi);
+  tOutputList->Add(fPtContMup);
+  tOutputList->Add(fPtContElp); 
+
+  return tOutputList;
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCutMonitorParticlePtPDG.h b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCutMonitorParticlePtPDG.h
new file mode 100644 (file)
index 0000000..71502e5
--- /dev/null
@@ -0,0 +1,74 @@
+////////////////////////////////////////////////////////////////////////////////
+///                                                                          ///
+/// AliFemtoCutMonitorParticlePtPDG - the cut monitor for particles to study  ///
+/// the difference between reconstructed and true momentum    ///
+///                                                                          ///
+////////////////////////////////////////////////////////////////////////////////
+#ifndef ALIFEMTOCUTMONITORPARTICLEPTPDG_H
+#define ALIFEMTOCUTMONITORPARTICLEPTPDG_H
+
+class AliFemtoEvent;
+class AliFemtoTrack;
+class AliFemtoV0;
+class AliFemtoKink;
+class AliFemtoPair; // Gael 12/04/02
+class TH1D;
+class TH2D;
+class TList;
+#include "AliFemtoString.h"
+#include "AliFemtoParticleCollection.h"
+#include "AliFemtoCutMonitor.h"
+
+class AliFemtoCutMonitorParticlePtPDG : public AliFemtoCutMonitor{
+  
+public:
+  AliFemtoCutMonitorParticlePtPDG();
+  AliFemtoCutMonitorParticlePtPDG(const char *aName, float aMass);
+  AliFemtoCutMonitorParticlePtPDG(const AliFemtoCutMonitorParticlePtPDG &aCut);
+  virtual ~AliFemtoCutMonitorParticlePtPDG();
+
+  AliFemtoCutMonitorParticlePtPDG& operator=(const AliFemtoCutMonitorParticlePtPDG& aCut);
+
+  virtual AliFemtoString Report();
+  virtual void Fill(const AliFemtoEvent* aEvent) {AliFemtoCutMonitor::Fill(aEvent);}
+  virtual void Fill(const AliFemtoTrack* aTrack);
+  virtual void Fill(const AliFemtoV0* aV0) {AliFemtoCutMonitor::Fill(aV0);}
+  virtual void Fill(const AliFemtoKink* aKink) {AliFemtoCutMonitor::Fill(aKink);}
+  virtual void Fill(const AliFemtoPair* aPair) {AliFemtoCutMonitor::Fill(aPair);}
+  virtual void Fill(const AliFemtoParticleCollection* aCollection) {AliFemtoCutMonitor::Fill(aCollection);}
+  virtual void Fill(const AliFemtoEvent* aEvent,const AliFemtoParticleCollection* aCollection)
+  {AliFemtoCutMonitor::Fill(aEvent, aCollection);}
+
+
+  void Write();
+
+  virtual TList *GetOutputList();
+
+private:
+  TH2D *fPtPDG;    // Rapidity vs. Pt monitor
+  TH2D *ftpcHist;  // TPC histogram
+  TH1D *fPtGoodPi; // Good pions
+  TH1D *fPtFakePi; // Fake pions
+  TH1D *fPtGoodK;  // Good kaons
+  TH1D *fPtFakeK;  // Fake kaons
+  TH1D *fPtGoodP;  // Good protons
+  TH1D *fPtFakeP;  // Fake protons
+  TH1D *fPtRPi;    // Pions pt 
+  TH1D *fPtRK;     // Kaons pt
+  TH1D *fPtRP;     // Protons pt
+  
+  TH1D *fPtContP;  // Contamination protons
+  TH1D *fPtContPi; // Contamination pions
+  TH1D *fPtContMup;// Contamination muons
+  TH1D *fPtContElp;// Contamination electrons
+  
+  
+  //TH2D *fYPhi;   // Rapidity cs. Phi monitor
+  //TH2D *fPtPhi;  // Pt vs. Phi monitor
+  //TH2D *fEtaPhi; // Pseudorapidity vs. Phi monitor
+  //TH2D *fEtaPt;  // Pseudorapidity vs. Pt monitor
+  float fMass;   // Mass hypothesis
+};
+
+#endif
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCutMonitorTrackTPCchiNdof.cxx b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCutMonitorTrackTPCchiNdof.cxx
new file mode 100644 (file)
index 0000000..e185010
--- /dev/null
@@ -0,0 +1,104 @@
+////////////////////////////////////////////////////////////////////////////////
+///                                                                          ///
+/// AliFemtoCutMonitorTrackTPCchiNdof - the cut monitor for tracks to study  ///
+/// the number of TPC clusters distribution.                                 ///
+///                                                                          ///
+////////////////////////////////////////////////////////////////////////////////
+#include "AliFemtoCutMonitorTrackTPCchiNdof.h"
+#include "AliFemtoModelHiddenInfo.h"
+#include "AliFemtoEvent.h"
+#include <TH1D.h>
+#include <TH2D.h>
+#include <TList.h>
+
+
+AliFemtoCutMonitorTrackTPCchiNdof::AliFemtoCutMonitorTrackTPCchiNdof():
+  fTrTPCchiNdof(0)
+{
+  // Default constructor
+  fTrTPCchiNdof = new TH1D("TrTPCchiNdof", "Track TPC Clusters", 5001, -0.5, 5000.5);
+}
+
+AliFemtoCutMonitorTrackTPCchiNdof::AliFemtoCutMonitorTrackTPCchiNdof(const char *aName):
+  AliFemtoCutMonitor(),
+  fTrTPCchiNdof(0)
+{
+  // Normal constructor
+  char name[200];
+  snprintf(name, 200, "TrTPCchiNdof%s", aName);
+  fTrTPCchiNdof = new TH1D(name, "Track TPC Clusters", 5001, -0.5, 5000.5);
+}
+
+AliFemtoCutMonitorTrackTPCchiNdof::AliFemtoCutMonitorTrackTPCchiNdof(const AliFemtoCutMonitorTrackTPCchiNdof &aCut):
+  AliFemtoCutMonitor(),
+  fTrTPCchiNdof(0)
+{
+  // copy constructor
+  if (fTrTPCchiNdof) delete fTrTPCchiNdof;
+  fTrTPCchiNdof = new TH1D(*aCut.fTrTPCchiNdof);
+}
+
+AliFemtoCutMonitorTrackTPCchiNdof::~AliFemtoCutMonitorTrackTPCchiNdof()
+{
+  // Destructor
+  delete fTrTPCchiNdof;
+}
+
+AliFemtoCutMonitorTrackTPCchiNdof& AliFemtoCutMonitorTrackTPCchiNdof::operator=(const AliFemtoCutMonitorTrackTPCchiNdof& aCut)
+{
+  // assignment operator
+  if (this == &aCut) 
+    return *this;
+
+  if (fTrTPCchiNdof) delete fTrTPCchiNdof;
+  fTrTPCchiNdof = new TH1D(*aCut.fTrTPCchiNdof);
+  
+  return *this;
+}
+
+AliFemtoString AliFemtoCutMonitorTrackTPCchiNdof::Report(){ 
+  // Prepare report from the execution
+  string stemp = "*** AliFemtoCutMonitorTrackTPCchiNdof report"; 
+  AliFemtoString returnThis = stemp;
+  return returnThis; 
+}
+
+void AliFemtoCutMonitorTrackTPCchiNdof::Fill(const AliFemtoTrack* aTrack)
+{
+  // Fill in the monitor histograms with the values from the current track
+  if (aTrack->TPCncls() > 0) {
+    fTrTPCchiNdof->Fill(aTrack->TPCchi2()/aTrack->TPCncls());
+  }
+}
+
+void AliFemtoCutMonitorTrackTPCchiNdof::Write()
+{
+  // Write out the relevant histograms
+  fTrTPCchiNdof->Write();
+}
+
+TList *AliFemtoCutMonitorTrackTPCchiNdof::GetOutputList()
+{
+  TList *tOutputList = new TList();
+  tOutputList->Add(fTrTPCchiNdof);
+
+  return tOutputList;
+}
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCutMonitorTrackTPCchiNdof.h b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCutMonitorTrackTPCchiNdof.h
new file mode 100644 (file)
index 0000000..a4a1f85
--- /dev/null
@@ -0,0 +1,50 @@
+////////////////////////////////////////////////////////////////////////////////
+///                                                                          ///
+/// AliFemtoCutMonitorTrackTPCchiNdof - the cut monitor for tracks to study  ///
+/// the number of TPC Clusters distribution.                                 ///
+///                                                                          ///
+////////////////////////////////////////////////////////////////////////////////
+#ifndef AliFemtoCutMonitorTrackTPCchiNdof_hh
+#define AliFemtoCutMonitorTrackTPCchiNdof_hh
+
+class AliFemtoEvent;
+class AliFemtoTrack;
+class AliFemtoV0;
+class AliFemtoKink;
+class AliFemtoPair; 
+class TH1D;
+class TH2D;
+class TList;
+#include "AliFemtoString.h"
+#include "AliFemtoParticleCollection.h"
+#include "AliFemtoCutMonitor.h"
+
+class AliFemtoCutMonitorTrackTPCchiNdof : public AliFemtoCutMonitor{
+  
+public:
+  AliFemtoCutMonitorTrackTPCchiNdof();
+  AliFemtoCutMonitorTrackTPCchiNdof(const char *aName);
+  AliFemtoCutMonitorTrackTPCchiNdof(const AliFemtoCutMonitorTrackTPCchiNdof &aCut);
+  virtual ~AliFemtoCutMonitorTrackTPCchiNdof();
+
+  AliFemtoCutMonitorTrackTPCchiNdof& operator=(const AliFemtoCutMonitorTrackTPCchiNdof& aCut);
+
+  virtual AliFemtoString Report();
+  virtual void Fill(const AliFemtoEvent* aEvent) {AliFemtoCutMonitor::Fill(aEvent);}
+  virtual void Fill(const AliFemtoTrack* aTrack); 
+  virtual void Fill(const AliFemtoV0* aV0) {AliFemtoCutMonitor::Fill(aV0);}
+  virtual void Fill(const AliFemtoKink* aKink) {AliFemtoCutMonitor::Fill(aKink);}
+  virtual void Fill(const AliFemtoPair* aPair) {AliFemtoCutMonitor::Fill(aPair);}
+  virtual void Fill(const AliFemtoParticleCollection* aCollection) {AliFemtoCutMonitor::Fill(aCollection);}
+  virtual void Fill(const AliFemtoEvent* aEvent,const AliFemtoParticleCollection* aCollection)
+  {AliFemtoCutMonitor::Fill(aEvent, aCollection);}
+
+  void Write();
+
+  virtual TList *GetOutputList();
+
+private:
+  TH1D *fTrTPCchiNdof;    // TPC track TPC clusters distribution
+};
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCutMonitorTrackTPCncls.cxx b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCutMonitorTrackTPCncls.cxx
new file mode 100755 (executable)
index 0000000..a279058
--- /dev/null
@@ -0,0 +1,102 @@
+////////////////////////////////////////////////////////////////////////////////
+///                                                                          ///
+/// AliFemtoCutMonitorTrackTPCncls - the cut monitor for tracks to study     ///
+/// the number of TPC clusters distribution.                                 ///
+///                                                                          ///
+////////////////////////////////////////////////////////////////////////////////
+#include "AliFemtoCutMonitorTrackTPCncls.h"
+#include "AliFemtoModelHiddenInfo.h"
+#include "AliFemtoEvent.h"
+#include <TH1D.h>
+#include <TH2D.h>
+#include <TList.h>
+
+
+AliFemtoCutMonitorTrackTPCncls::AliFemtoCutMonitorTrackTPCncls():
+  fTrTPCncls(0)
+{
+  // Default constructor
+  fTrTPCncls = new TH1D("TrTPCncls", "Track TPC Clusters", 5001, -0.5, 5000.5);
+}
+
+AliFemtoCutMonitorTrackTPCncls::AliFemtoCutMonitorTrackTPCncls(const char *aName):
+  AliFemtoCutMonitor(),
+  fTrTPCncls(0)
+{
+  // Normal constructor
+  char name[200];
+  snprintf(name, 200, "TrTPCncls%s", aName);
+  fTrTPCncls = new TH1D(name, "Track TPC Clusters", 5001, -0.5, 5000.5);
+}
+
+AliFemtoCutMonitorTrackTPCncls::AliFemtoCutMonitorTrackTPCncls(const AliFemtoCutMonitorTrackTPCncls &aCut):
+  AliFemtoCutMonitor(),
+  fTrTPCncls(0)
+{
+  // copy constructor
+  if (fTrTPCncls) delete fTrTPCncls;
+  fTrTPCncls = new TH1D(*aCut.fTrTPCncls);
+}
+
+AliFemtoCutMonitorTrackTPCncls::~AliFemtoCutMonitorTrackTPCncls()
+{
+  // Destructor
+  delete fTrTPCncls;
+}
+
+AliFemtoCutMonitorTrackTPCncls& AliFemtoCutMonitorTrackTPCncls::operator=(const AliFemtoCutMonitorTrackTPCncls& aCut)
+{
+  // assignment operator
+  if (this == &aCut) 
+    return *this;
+
+  if (fTrTPCncls) delete fTrTPCncls;
+  fTrTPCncls = new TH1D(*aCut.fTrTPCncls);
+  
+  return *this;
+}
+
+AliFemtoString AliFemtoCutMonitorTrackTPCncls::Report(){ 
+  // Prepare report from the execution
+  string stemp = "*** AliFemtoCutMonitorTrackTPCncls report"; 
+  AliFemtoString returnThis = stemp;
+  return returnThis; 
+}
+
+void AliFemtoCutMonitorTrackTPCncls::Fill(const AliFemtoTrack* aTrack)
+{
+  // Fill in the monitor histograms with the values from the current track
+  fTrTPCncls->Fill(aTrack->TPCncls());
+}
+
+void AliFemtoCutMonitorTrackTPCncls::Write()
+{
+  // Write out the relevant histograms
+  fTrTPCncls->Write();
+}
+
+TList *AliFemtoCutMonitorTrackTPCncls::GetOutputList()
+{
+  TList *tOutputList = new TList();
+  tOutputList->Add(fTrTPCncls);
+
+  return tOutputList;
+}
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCutMonitorTrackTPCncls.h b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoCutMonitorTrackTPCncls.h
new file mode 100755 (executable)
index 0000000..1d4714b
--- /dev/null
@@ -0,0 +1,50 @@
+////////////////////////////////////////////////////////////////////////////////
+///                                                                          ///
+/// AliFemtoCutMonitorTrackTPCncls - the cut monitor for tracks to study     ///
+/// the number of TPC Clusters distribution.                                 ///
+///                                                                          ///
+////////////////////////////////////////////////////////////////////////////////
+#ifndef AliFemtoCutMonitorTrackTPCncls_hh
+#define AliFemtoCutMonitorTrackTPCncls_hh
+
+class AliFemtoEvent;
+class AliFemtoTrack;
+class AliFemtoV0;
+class AliFemtoKink;
+class AliFemtoPair; 
+class TH1D;
+class TH2D;
+class TList;
+#include "AliFemtoString.h"
+#include "AliFemtoParticleCollection.h"
+#include "AliFemtoCutMonitor.h"
+
+class AliFemtoCutMonitorTrackTPCncls : public AliFemtoCutMonitor{
+  
+public:
+  AliFemtoCutMonitorTrackTPCncls();
+  AliFemtoCutMonitorTrackTPCncls(const char *aName);
+  AliFemtoCutMonitorTrackTPCncls(const AliFemtoCutMonitorTrackTPCncls &aCut);
+  virtual ~AliFemtoCutMonitorTrackTPCncls();
+
+  AliFemtoCutMonitorTrackTPCncls& operator=(const AliFemtoCutMonitorTrackTPCncls& aCut);
+
+  virtual AliFemtoString Report();
+  virtual void Fill(const AliFemtoEvent* aEvent) {AliFemtoCutMonitor::Fill(aEvent);}
+  virtual void Fill(const AliFemtoTrack* aTrack); 
+  virtual void Fill(const AliFemtoV0* aV0) {AliFemtoCutMonitor::Fill(aV0);}
+  virtual void Fill(const AliFemtoKink* aKink) {AliFemtoCutMonitor::Fill(aKink);}
+  virtual void Fill(const AliFemtoPair* aPair) {AliFemtoCutMonitor::Fill(aPair);}
+  virtual void Fill(const AliFemtoParticleCollection* aCollection) {AliFemtoCutMonitor::Fill(aCollection);}
+  virtual void Fill(const AliFemtoEvent* aEvent,const AliFemtoParticleCollection* aCollection)
+  {AliFemtoCutMonitor::Fill(aEvent, aCollection);}
+
+  void Write();
+
+  virtual TList *GetOutputList();
+
+private:
+  TH1D *fTrTPCncls;    // TPC track TPC clusters distribution
+};
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoESDTrackCut.cxx b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoESDTrackCut.cxx
new file mode 100644 (file)
index 0000000..1faa0c5
--- /dev/null
@@ -0,0 +1,923 @@
+/*
+***************************************************************************
+*
+* $Id$ 
+*
+* 
+***************************************************************************
+*
+* 
+*              
+*
+***************************************************************************
+*
+* $Log$
+* Revision 1.3  2007/05/22 09:01:42  akisiel
+* Add the possibiloity to save cut settings in the ROOT file
+*
+* Revision 1.2  2007/05/21 10:38:25  akisiel
+* More coding rule conformance
+*
+* Revision 1.1  2007/05/16 10:25:06  akisiel
+* Making the directory structure of AliFemtoUser flat. All files go into one common directory
+*
+* Revision 1.4  2007/05/03 09:46:10  akisiel
+* Fixing Effective C++ warnings
+*
+* Revision 1.3  2007/04/27 07:25:59  akisiel
+* Make revisions needed for compilation from the main AliRoot tree
+*
+* Revision 1.1.1.1  2007/04/25 15:38:41  panos
+* Importing the HBT code dir
+*
+* Revision 1.4  2007-04-03 16:00:08  mchojnacki
+* Changes to iprove memory managing
+*
+* Revision 1.3  2007/03/13 15:30:03  mchojnacki
+* adding reader for simulated data
+*
+* Revision 1.2  2007/03/08 14:58:03  mchojnacki
+* adding some alice stuff
+*
+* Revision 1.1.1.1  2007/03/07 10:14:49  mchojnacki
+* First version on CVS
+*
+**************************************************************************/
+
+#include "AliFemtoESDTrackCut.h"
+#include <cstdio>
+
+#ifdef __ROOT__ 
+ClassImp(AliFemtoESDTrackCut)
+#endif
+
+
+// electron
+// 0.13 - 1.8
+// 0       7.594129e-02    8.256141e-03
+// 1       -5.535827e-01   8.170825e-02
+// 2       1.728591e+00    3.104210e-01
+// 3       -2.827893e+00   5.827802e-01
+// 4       2.503553e+00    5.736207e-01
+// 5       -1.125965e+00   2.821170e-01
+// 6       2.009036e-01    5.438876e-02
+
+// pion
+// 0.13 - 2.0
+// 0       1.063457e+00    8.872043e-03
+// 1       -4.222208e-01   2.534402e-02
+// 2       1.042004e-01    1.503945e-02
+
+// kaon
+// 0.18 - 2.0
+// 0       -7.289406e-02   1.686074e-03
+// 1       4.415666e-01    1.143939e-02
+// 2       -2.996790e-01   1.840964e-02
+// 3       6.704652e-02    7.783990e-03
+
+// proton
+// 0.26 - 2.0
+// 0       -3.730200e-02   2.347311e-03
+// 1       1.163684e-01    1.319316e-02
+// 2       8.354116e-02    1.997948e-02
+// 3       -4.608098e-02   8.336400e-03
+
+
+  AliFemtoESDTrackCut::AliFemtoESDTrackCut() :
+    fCharge(0),
+    fLabel(0),
+    fStatus(0),
+    fPIDMethod(knSigma),
+    fminTPCclsF(0),
+    fminTPCncls(0),
+    fminITScls(0),
+    fMaxITSchiNdof(1000.0),
+    fMaxTPCchiNdof(1000.0),
+    fMaxSigmaToVertex(1000.0),
+    fNTracksPassed(0),
+    fNTracksFailed(0),
+    fRemoveKinks(kFALSE),
+    fRemoveITSFake(kFALSE),
+    fMostProbable(0), 
+    fMaxImpactXY(1000.0),
+    fMaxImpactZ(1000.0),
+    fMaxImpactXYPtOff(1000.0),
+    fMaxImpactXYPtNrm(1000.0),
+    fMaxImpactXYPtPow(1000.0),
+    fMinPforTOFpid(0.0),
+    fMaxPforTOFpid(10000.0),
+    fMinPforTPCpid(0.0),
+    fMaxPforTPCpid(10000.0),
+    fMinPforITSpid(0.0),
+    fMaxPforITSpid(10000.0)
+{
+  // Default constructor
+  fNTracksPassed = fNTracksFailed = 0;
+  fCharge = 0;  // takes both charges 0
+  fPt[0]=0.0;              fPt[1] = 100.0;//100
+  fRapidity[0]=-2;       fRapidity[1]=2;//-2 2
+  fEta[0]=-2;       fEta[1]=2;//-2 2
+  fPidProbElectron[0]=-1;fPidProbElectron[1]=2;
+  fPidProbPion[0]=-1;    fPidProbPion[1]=2;
+  fPidProbKaon[0]=-1;fPidProbKaon[1]=2;
+  fPidProbProton[0]=-1;fPidProbProton[1]=2;
+  fPidProbMuon[0]=-1;fPidProbMuon[1]=2;
+  fLabel=false;
+  fStatus=0;
+  fminTPCclsF=0;
+  fminITScls=0;
+  fPIDMethod=knSigma;
+}
+//------------------------------
+AliFemtoESDTrackCut::~AliFemtoESDTrackCut(){
+  /* noop */
+}
+//------------------------------
+bool AliFemtoESDTrackCut::Pass(const AliFemtoTrack* track)
+{
+  // test the particle and return 
+  // true if it meets all the criteria
+  // false if it doesn't meet at least one of the criteria
+  float tMost[5];
+  
+  //cout<<"AliFemtoESD  cut"<<endl;
+  //cout<<fPidProbPion[0]<<" < pi ="<<track->PidProbPion()<<" <"<<fPidProbPion[1]<<endl;
+  if (fStatus!=0)
+    {
+      //cout<<" status "<<track->Label()<<" "<<track->Flags()<<" "<<track->TPCnclsF()<<" "<<track->ITSncls()<<endl;
+      if ((track->Flags()&fStatus)!=fStatus)
+       {
+         //      cout<<track->Flags()<<" "<<fStatus<<" no go through status"<<endl;
+         return false;
+       }
+       
+    }
+  if (fRemoveKinks) {
+    if ((track->KinkIndex(0)) || (track->KinkIndex(1)) || (track->KinkIndex(2)))
+      return false;
+  }
+  if (fRemoveITSFake) {
+    if (track->ITSncls() < 0)
+      return false;
+  }
+  if (fminTPCclsF>track->TPCnclsF())
+    {
+      //cout<<" No go because TPC Number of ClsF"<<fminTPCclsF<< " "<<track->TPCnclsF()<<endl;
+      return false;
+    }
+  if (fminTPCncls>track->TPCncls())
+    {
+      //cout<<" No go because TPC Number of ClsF"<<fminTPCclsF<< " "<<track->TPCnclsF()<<endl;
+      return false;
+    }
+  if (fminITScls>track->ITSncls())
+    {
+      //cout<<" No go because ITS Number of Cls"<<fminITScls<< " "<<track->ITSncls()<<endl;
+      return false;
+    }
+
+  if (fMaxImpactXY < TMath::Abs(track->ImpactD()))
+    return false;
+
+  if (fMaxImpactZ < TMath::Abs(track->ImpactZ()))
+    return false;
+  
+  if (fMaxSigmaToVertex < track->SigmaToVertex()) {
+    return false;
+  }
+  
+  if (track->ITSncls() > 0) 
+    if ((track->ITSchi2()/track->ITSncls()) > fMaxITSchiNdof) {
+      return false;
+    }
+
+  if (track->TPCncls() > 0)
+    if ((track->TPCchi2()/track->TPCncls()) > fMaxTPCchiNdof) {
+      return false;
+    }
+
+  if (fLabel)
+    {
+      //cout<<"labels"<<endl;
+      if(track->Label()<0)
+       {
+         fNTracksFailed++;
+         //   cout<<"No Go Through the cut"<<endl;
+         //  cout<<fLabel<<" Label="<<track->Label()<<endl;
+         return false;
+       }    
+    }
+  if (fCharge!=0)
+    {              
+      //cout<<"AliFemtoESD  cut ch "<<endl;
+      //cout<<fCharge<<" Charge="<<track->Charge()<<endl;
+      if (track->Charge()!= fCharge)   
+       {
+         fNTracksFailed++;
+         //  cout<<"No Go Through the cut"<<endl;
+         // cout<<fCharge<<" Charge="<<track->Charge()<<endl;
+         return false;
+       }
+    }
+  Bool_t tTPCPidIn = (track->Flags()&AliFemtoTrack::kTPCpid)>0;
+  Bool_t tITSPidIn = (track->Flags()&AliFemtoTrack::kITSpid)>0;
+  Bool_t tTOFPidIn = (track->Flags()&AliFemtoTrack::kTOFpid)>0;
+  
+  if(fMinPforTOFpid > 0 && track->P().Mag() > fMinPforTOFpid &&
+     track->P().Mag() < fMaxPforTOFpid && !tTOFPidIn)
+    {
+      fNTracksFailed++;
+      return false;
+    }
+  
+  if(fMinPforTPCpid > 0 && track->P().Mag() > fMinPforTPCpid &&
+     track->P().Mag() < fMaxPforTPCpid && !tTPCPidIn)
+    {
+      fNTracksFailed++;
+      return false;
+    }
+  
+  if(fMinPforITSpid > 0 && track->P().Mag() > fMinPforITSpid &&
+     track->P().Mag() < fMaxPforITSpid && !tITSPidIn)
+    {
+      fNTracksFailed++;
+      return false;
+    }
+  
+
+  float tEnergy = ::sqrt(track->P().Mag2()+fMass*fMass);
+  float tRapidity = 0.5*::log((tEnergy+track->P().z())/(tEnergy-track->P().z()));
+  float tPt = ::sqrt((track->P().x())*(track->P().x())+(track->P().y())*(track->P().y()));
+  float tEta = track->P().PseudoRapidity();
+  
+  if (fMaxImpactXYPtOff < 999.0) {
+    if ((fMaxImpactXYPtOff + fMaxImpactXYPtNrm*TMath::Power(tPt, fMaxImpactXYPtPow)) < TMath::Abs(track->ImpactD())) {
+      fNTracksFailed++;
+      return false;
+    }
+  }
+
+  if ((tRapidity<fRapidity[0])||(tRapidity>fRapidity[1]))
+    {
+      fNTracksFailed++;
+      //cout<<"No Go Through the cut"<<endl;   
+      //cout<<fRapidity[0]<<" < Rapidity ="<<tRapidity<<" <"<<fRapidity[1]<<endl;
+      return false;
+    }
+  if ((tEta<fEta[0])||(tEta>fEta[1]))
+    {
+      fNTracksFailed++;
+      //cout<<"No Go Through the cut"<<endl;   
+      //cout<<fEta[0]<<" < Eta ="<<tEta<<" <"<<fEta[1]<<endl;
+      return false;
+    }
+  if ((tPt<fPt[0])||(tPt>fPt[1]))
+    {
+      fNTracksFailed++;
+      //cout<<"No Go Through the cut"<<endl;
+      //cout<<fPt[0]<<" < Pt ="<<Pt<<" <"<<fPt[1]<<endl;
+      return false;
+    }
+  //   cout << "Track has pids: " 
+  //        << track->PidProbElectron() << " " 
+  //        << track->PidProbMuon() << " " 
+  //        << track->PidProbPion() << " " 
+  //        << track->PidProbKaon() << " " 
+  //        << track->PidProbProton() << " " 
+  //        << track->PidProbElectron()+track->PidProbMuon()+track->PidProbPion()+track->PidProbKaon()+track->PidProbProton() << endl;
+
+    
+  if ((track->PidProbElectron()<fPidProbElectron[0])||(track->PidProbElectron()>fPidProbElectron[1]))
+    {
+      fNTracksFailed++;
+      //cout<<"No Go Through the cut"<<endl;
+      //cout<<fPidProbElectron[0]<<" < e ="<<track->PidProbElectron()<<" <"<<fPidProbElectron[1]<<endl;
+      return false;
+    }
+  if ((track->PidProbPion()<fPidProbPion[0])||(track->PidProbPion()>fPidProbPion[1]))
+    {
+      fNTracksFailed++;
+      //cout<<"No Go Through the cut"<<endl;
+      //cout<<fPidProbPion[0]<<" < pi ="<<track->PidProbPion()<<" <"<<fPidProbPion[1]<<endl;
+      return false;
+    }
+  if ((track->PidProbKaon()<fPidProbKaon[0])||(track->PidProbKaon()>fPidProbKaon[1]))
+    {
+      fNTracksFailed++;
+      //cout<<"No Go Through the cut"<<endl;
+      //cout<<fPidProbKaon[0]<<" < k ="<<track->PidProbKaon()<<" <"<<fPidProbKaon[1]<<endl;
+      return false;
+    }
+  if ((track->PidProbProton()<fPidProbProton[0])||(track->PidProbProton()>fPidProbProton[1]))
+    {
+      fNTracksFailed++;
+      //cout<<"No Go Through the cut"<<endl;
+      //cout<<fPidProbProton[0]<<" < p  ="<<track->PidProbProton()<<" <"<<fPidProbProton[1]<<endl;
+      return false;
+    }
+  if ((track->PidProbMuon()<fPidProbMuon[0])||(track->PidProbMuon()>fPidProbMuon[1]))
+    {
+      fNTracksFailed++;
+      //cout<<"No Go Through the cut"<<endl;
+      //cout<<fPidProbMuon[0]<<" <  mi="<<track->PidProbMuon()<<" <"<<fPidProbMuon[1]<<endl;
+      return false;
+    }
+
+  if (fMostProbable) {
+    int imost=0;
+    tMost[0] = track->PidProbElectron()*PidFractionElectron(track->P().Mag());
+    tMost[1] = 0.0;
+    tMost[2] = track->PidProbPion()*PidFractionPion(track->P().Mag());
+    tMost[3] = track->PidProbKaon()*PidFractionKaon(track->P().Mag());
+    tMost[4] = track->PidProbProton()*PidFractionProton(track->P().Mag());
+    float ipidmax = 0.0;
+
+
+    //****N Sigma Method****
+       if(fPIDMethod==0){
+         // Looking for pions
+         if (fMostProbable == 2) {
+           if (IsPionNSigma(track->P().Mag(), track->NSigmaTPCPi(), track->NSigmaTOFPi()))
+             imost = 2;
+
+         }
+         else if (fMostProbable == 3) { 
+           if (IsKaonNSigma(track->P().Mag(), track->NSigmaTPCK(), track->NSigmaTOFK())){
+             imost = 3;
+           }
+  
+         }
+         else if (fMostProbable == 4) { // proton nsigma-PID required contour adjusting
+           if (IsProtonNSigma(track->P().Mag(), track->NSigmaTPCP(), track->NSigmaTOFP()) && IsProtonTPCdEdx(track->P().Mag(), track->TPCsignal()))
+             imost = 4;
+         }
+
+       }
+
+    //****Contour Method****
+       if(fPIDMethod==1){
+         for (int ip=0; ip<5; ip++)
+           if (tMost[ip] > ipidmax) { ipidmax = tMost[ip]; imost = ip; };
+
+         // Looking for pions
+         if (fMostProbable == 2) {
+           if (imost == 2) {
+             // Using the TPC to reject non-pions
+             if (!(IsPionTPCdEdx(track->P().Mag(), track->TPCsignal())))
+               imost = 0;
+             if (0) {
+               // Using the TOF to reject non-pions
+               if (track->P().Mag() < 0.6) {
+                 if (tTOFPidIn)
+                   if (!IsPionTOFTime(track->P().Mag(), track->TOFpionTime()))
+                     imost = 0;
+               }
+               else {
+                 if (tTOFPidIn) {
+                   if (!IsPionTOFTime(track->P().Mag(), track->TOFpionTime()))
+                     imost = 0;
+                 }
+                 else {
+                   imost = 0;
+                 }
+               }
+             }
+           }
+         }
+
+         // Looking for kaons
+         else if (fMostProbable == 3) {
+           //       if (imost == 3) {
+           // Using the TPC to reject non-kaons
+           if (track->P().Mag() < 0.6) {
+             if (!(IsKaonTPCdEdx(track->P().Mag(), track->TPCsignal())))
+               imost = 0;
+             else imost = 3;
+             if (1) {
+               // Using the TOF to reject non-kaons
+               if (tTOFPidIn)
+                 if (!IsKaonTOFTime(track->P().Mag(), track->TOFkaonTime()))
+                   imost = 0;
+             }
+           }
+           else {
+             if (1) {
+               if (tTOFPidIn) {
+                 if (!IsKaonTOFTime(track->P().Mag(), track->TOFkaonTime()))
+                   imost = 0;
+                 else
+                   imost = 3;
+               }
+               else {
+                 if (!(IsKaonTPCdEdx(track->P().Mag(), track->TPCsignal())))
+                   imost = 0;
+                 else 
+                   imost = 3;
+               }
+             }
+           }
+           //       }
+         }
+    
+         // Looking for protons
+         else if (fMostProbable == 4) {
+           //       if (imost == 3) {
+           // Using the TPC to reject non-kaons
+           if (track->P().Mag() < 0.8) {
+             if (!(IsProtonTPCdEdx(track->P().Mag(), track->TPCsignal())))
+               imost = 0;
+             else imost = 4;
+             if (0) {
+               // Using the TOF to reject non-kaons
+               if (tTOFPidIn)
+                 if (!IsKaonTOFTime(track->P().Mag(), track->TOFkaonTime()))
+                   imost = 0;
+             }
+           }
+           else {
+             if (0) {
+               if (tTOFPidIn) {
+                 if (!IsKaonTOFTime(track->P().Mag(), track->TOFkaonTime()))
+                   imost = 0;
+                 else
+                   imost = 3;
+               }
+               else {
+                 if (!(IsKaonTPCdEdx(track->P().Mag(), track->TPCsignal())))
+                   imost = 0;
+                 else 
+                   imost = 3;
+               }
+             }
+           }
+           //       }
+         }
+       }
+    if (imost != fMostProbable) return false;
+  }
+  
+  //fan
+  //cout<<"****** Go Through the cut ******"<<endl;
+  // cout<<fLabel<<" Label="<<track->Label()<<endl;
+  // cout<<fCharge<<" Charge="<<track->Charge()<<endl;
+  // cout<<fPt[0]<<" < Pt ="<<Pt<<" <"<<fPt[1]<<endl;
+  //cout<<fRapidity[0]<<" < Rapidity ="<<tRapidity<<" <"<<fRapidity[1]<<endl;
+  //cout<<fPidProbElectron[0]<<" <  e="<<track->PidProbElectron()<<" <"<<fPidProbElectron[1]<<endl;
+  //cout<<fPidProbPion[0]<<" <  pi="<<track->PidProbPion()<<" <"<<fPidProbPion[1]<<endl;
+  //cout<<fPidProbKaon[0]<<" <  k="<<track->PidProbKaon()<<" <"<<fPidProbKaon[1]<<endl;
+  //cout<<fPidProbProton[0]<<" <  p="<<track->PidProbProton()<<" <"<<fPidProbProton[1]<<endl;
+  //cout<<fPidProbMuon[0]<<" <  mi="<<track->PidProbMuon()<<" <"<<fPidProbMuon[1]<<endl;
+  fNTracksPassed++ ;
+  return true;
+    
+    
+}
+//------------------------------
+AliFemtoString AliFemtoESDTrackCut::Report()
+{
+  // Prepare report from the execution
+  string tStemp;
+  char tCtemp[100];
+  snprintf(tCtemp , 100, "Particle mass:\t%E\n",this->Mass());
+  tStemp=tCtemp;
+  snprintf(tCtemp , 100, "Particle charge:\t%d\n",fCharge);
+  tStemp+=tCtemp;
+  snprintf(tCtemp , 100, "Particle pT:\t%E - %E\n",fPt[0],fPt[1]);
+  tStemp+=tCtemp;
+  snprintf(tCtemp , 100, "Particle rapidity:\t%E - %E\n",fRapidity[0],fRapidity[1]);
+  tStemp+=tCtemp; 
+  snprintf(tCtemp , 100, "Particle eta:\t%E - %E\n",fEta[0],fEta[1]);
+  tStemp+=tCtemp;
+  snprintf(tCtemp , 100, "Number of tracks which passed:\t%ld  Number which failed:\t%ld\n",fNTracksPassed,fNTracksFailed);
+  tStemp += tCtemp;
+  AliFemtoString returnThis = tStemp;
+  return returnThis;
+}
+TList *AliFemtoESDTrackCut::ListSettings()
+{
+  // return a list of settings in a writable form
+  TList *tListSetttings = new TList();
+  char buf[200];
+  snprintf(buf, 200, "AliFemtoESDTrackCut.mass=%f", this->Mass());
+  tListSetttings->AddLast(new TObjString(buf));
+
+  snprintf(buf, 200, "AliFemtoESDTrackCut.charge=%i", fCharge);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoESDTrackCut.pidprobpion.minimum=%f", fPidProbPion[0]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoESDTrackCut.pidprobpion.maximum=%f", fPidProbPion[1]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoESDTrackCut.pidprobkaon.minimum=%f", fPidProbKaon[0]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoESDTrackCut.pidprobkaon.maximum=%f", fPidProbKaon[1]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoESDTrackCut.pidprobproton.minimum=%f", fPidProbProton[0]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoESDTrackCut.pidprobproton.maximum=%f", fPidProbProton[1]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoESDTrackCut.pidprobelectron.minimum=%f", fPidProbElectron[0]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoESDTrackCut.pidprobelectron.maximum=%f", fPidProbElectron[1]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoESDTrackCut.pidprobMuon.minimum=%f", fPidProbMuon[0]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoESDTrackCut.pidprobMuon.maximum=%f", fPidProbMuon[1]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoESDTrackCut.minimumtpcclusters=%i", fminTPCclsF);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoESDTrackCut.minimumitsclusters=%i", fminTPCclsF);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoESDTrackCut.pt.minimum=%f", fPt[0]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoESDTrackCut.pt.maximum=%f", fPt[1]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoESDTrackCut.rapidity.minimum=%f", fRapidity[0]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoESDTrackCut.rapidity.maximum=%f", fRapidity[1]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoESDTrackCut.removekinks=%i", fRemoveKinks);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoESDTrackCut.maxitschindof=%f", fMaxITSchiNdof);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoESDTrackCut.maxtpcchindof=%f", fMaxTPCchiNdof);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoESDTrackCut.maxsigmatovertex=%f", fMaxSigmaToVertex);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoESDTrackCut.maximpactxy=%f", fMaxImpactXY);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoESDTrackCut.maximpactz=%f", fMaxImpactZ);
+  tListSetttings->AddLast(new TObjString(buf));
+  if (fMostProbable) {
+    if (fMostProbable == 2)
+      snprintf(buf, 200, "AliFemtoESDTrackCut.mostprobable=%s", "Pion");
+    if (fMostProbable == 3)
+      snprintf(buf, 200, "AliFemtoESDTrackCut.mostprobable=%s", "Kaon");
+    if (fMostProbable == 4)
+      snprintf(buf, 200, "AliFemtoESDTrackCut.mostprobable=%s", "Proton");
+    tListSetttings->AddLast(new TObjString(buf));
+  }
+  return tListSetttings;
+}
+void AliFemtoESDTrackCut::SetRemoveKinks(const bool& flag)
+{
+  fRemoveKinks = flag;
+}
+                           
+void AliFemtoESDTrackCut::SetRemoveITSFake(const bool& flag)
+{
+  fRemoveITSFake = flag;
+}
+                           
+// electron
+// 0.13 - 1.8
+// 0       7.594129e-02    8.256141e-03
+// 1       -5.535827e-01   8.170825e-02
+// 2       1.728591e+00    3.104210e-01
+// 3       -2.827893e+00   5.827802e-01
+// 4       2.503553e+00    5.736207e-01
+// 5       -1.125965e+00   2.821170e-01
+// 6       2.009036e-01    5.438876e-02
+float AliFemtoESDTrackCut::PidFractionElectron(float mom) const
+{
+  // Provide a parameterized fraction of electrons dependent on momentum
+  if (mom<0.13) 
+    return (7.594129e-02 
+           -5.535827e-01*0.13     
+           +1.728591e+00*0.13*0.13    
+           -2.827893e+00*0.13*0.13*0.13 
+           +2.503553e+00*0.13*0.13*0.13*0.13      
+           -1.125965e+00*0.13*0.13*0.13*0.13*0.13      
+           +2.009036e-01*0.13*0.13*0.13*0.13*0.13*0.13);   
+
+  if (mom>1.8)
+    return (7.594129e-02 
+           -5.535827e-01*1.8      
+           +1.728591e+00*1.8*1.8    
+           -2.827893e+00*1.8*1.8*1.8 
+           +2.503553e+00*1.8*1.8*1.8*1.8          
+           -1.125965e+00*1.8*1.8*1.8*1.8*1.8      
+           +2.009036e-01*1.8*1.8*1.8*1.8*1.8*1.8);   
+  return (7.594129e-02 
+         -5.535827e-01*mom        
+         +1.728591e+00*mom*mom    
+         -2.827893e+00*mom*mom*mom 
+         +2.503553e+00*mom*mom*mom*mom    
+         -1.125965e+00*mom*mom*mom*mom*mom      
+         +2.009036e-01*mom*mom*mom*mom*mom*mom);   
+}
+
+// pion
+// 0.13 - 2.0
+// 0       1.063457e+00    8.872043e-03
+// 1       -4.222208e-01   2.534402e-02
+// 2       1.042004e-01    1.503945e-02
+float AliFemtoESDTrackCut::PidFractionPion(float mom) const
+{
+  // Provide a parameterized fraction of pions dependent on momentum
+  if (mom<0.13) 
+    return ( 1.063457e+00
+            -4.222208e-01*0.13
+            +1.042004e-01*0.0169);
+  if (mom>2.0) 
+    return ( 1.063457e+00
+            -4.222208e-01*2.0
+            +1.042004e-01*4.0);
+  return ( 1.063457e+00
+          -4.222208e-01*mom
+          +1.042004e-01*mom*mom);
+}
+
+// kaon
+// 0.18 - 2.0
+// 0       -7.289406e-02   1.686074e-03
+// 1       4.415666e-01    1.143939e-02
+// 2       -2.996790e-01   1.840964e-02
+// 3       6.704652e-02    7.783990e-03
+float AliFemtoESDTrackCut::PidFractionKaon(float mom) const
+{
+  // Provide a parameterized fraction of kaons dependent on momentum
+  if (mom<0.18) 
+    return (-7.289406e-02
+           +4.415666e-01*0.18     
+           -2.996790e-01*0.18*0.18    
+           +6.704652e-02*0.18*0.18*0.18);
+  if (mom>2.0) 
+    return (-7.289406e-02
+           +4.415666e-01*2.0      
+           -2.996790e-01*2.0*2.0    
+           +6.704652e-02*2.0*2.0*2.0);
+  return (-7.289406e-02
+         +4.415666e-01*mom        
+         -2.996790e-01*mom*mom    
+         +6.704652e-02*mom*mom*mom);
+}
+
+// proton
+// 0.26 - 2.0
+// 0       -3.730200e-02   2.347311e-03
+// 1       1.163684e-01    1.319316e-02
+// 2       8.354116e-02    1.997948e-02
+// 3       -4.608098e-02   8.336400e-03
+float AliFemtoESDTrackCut::PidFractionProton(float mom) const
+{
+  // Provide a parameterized fraction of protons dependent on momentum
+  if (mom<0.26) return  0.0;
+  if (mom>2.0) 
+    return (-3.730200e-02  
+           +1.163684e-01*2.0         
+           +8.354116e-02*2.0*2.0       
+           -4.608098e-02*2.0*2.0*2.0);
+  return (-3.730200e-02  
+         +1.163684e-01*mom           
+         +8.354116e-02*mom*mom       
+         -4.608098e-02*mom*mom*mom);  
+}
+
+void AliFemtoESDTrackCut::SetMomRangeTOFpidIs(const float& minp, const float& maxp)
+{
+  fMinPforTOFpid = minp;
+  fMaxPforTOFpid = maxp;
+}
+
+void AliFemtoESDTrackCut::SetMomRangeTPCpidIs(const float& minp, const float& maxp)
+{
+  fMinPforTPCpid = minp;
+  fMaxPforTPCpid = maxp;
+}
+
+void AliFemtoESDTrackCut::SetMomRangeITSpidIs(const float& minp, const float& maxp)
+{
+  fMinPforITSpid = minp;
+  fMaxPforITSpid = maxp;
+}
+
+bool AliFemtoESDTrackCut::IsPionTPCdEdx(float mom, float dEdx)
+{
+  //   double a1 = -95.4545, b1 = 86.5455;
+  //   double a2 = 0.0,      b2 = 56.0;
+  double a1 = -343.75,  b1 = 168.125;
+  double a2 = 0.0,      b2 = 65.0;
+
+  if (mom < 0.32) {
+    if (dEdx < a1*mom+b1) return true;
+  }
+  if (dEdx < a2*mom+b2) return true;
+
+  return false;
+}
+
+bool AliFemtoESDTrackCut::IsKaonTPCdEdx(float mom, float dEdx)
+{
+
+//   double a1 = -547.0; double b1 =  297.0;
+//   double a2 = -125.0; double b2 =  145.0;
+//   double a3 = -420.0; double b3 =  357.0;
+//   double a4 = -110.0; double b4 =  171.0;
+//   double b5 =   72.0;
+
+//   if (mom<0.2) return false;
+
+//   if (mom<0.36) {
+//     if (dEdx < a1*mom+b1) return false;
+//     if (dEdx > a3*mom+b3) return false;
+//   }
+//   else if (mom<0.6) {
+//     if (dEdx < a2*mom+b2) return false;
+//     if (dEdx > a3*mom+b3) return false;
+//   }
+//   else if (mom<0.9) {
+//     if (dEdx > a4*mom+b4) return false;
+//     if (dEdx <        b5) return false;
+//   }
+//   else 
+//     return false;
+//   //   else {
+//   //     if (dEdx > b5) return false;
+//   //   }
+   
+//   return true;
+
+  double a1 = -268.896; double b1 =  198.669;
+  double a2 = -49.0012;  double b2 =  88.7214;
+
+  if (mom<0.2) return false;
+
+  if (mom>0.3 && mom<0.5) {
+    if (dEdx < a1*mom+b1) return false;
+  }
+  else  if (mom<1.2) {
+    if (dEdx < a2*mom+b2) return false;
+  }
+
+  return true;
+
+}
+
+bool AliFemtoESDTrackCut::IsProtonTPCdEdx(float mom, float dEdx)
+{
+  double a1 = -1800.0; double b1 =  940.0;
+  double a2 = -500.0;  double b2 =  420.0;
+  double a3 = -216.7;  double b3 =  250.0;
+
+  if (mom<0.2) return false;
+
+  if (mom>0.3 && mom<0.4) {
+    if (dEdx < a1*mom+b1) return false;
+  }
+  else  if (mom<0.6) {
+    if (dEdx < a2*mom+b2) return false;
+  }
+  else  if (mom<0.9) {
+    if (dEdx < a3*mom+b3) return false;
+  }
+
+  return true;
+   
+}
+
+bool AliFemtoESDTrackCut::IsPionTOFTime(float mom, float ttof)
+{
+  double a1 = -427.0; double b1 =  916.0;
+  double a2 =  327.0; double b2 = -888.0;
+  if (mom<0.3) return kFALSE;
+  if (mom>2.0) return kFALSE;
+  if (ttof > a1*mom+b1) return kFALSE;
+  if (ttof < a2*mom+b2) return kFALSE;
+
+  return kTRUE;
+}
+
+bool AliFemtoESDTrackCut::IsKaonTOFTime(float mom, float ttof)
+{
+  double a1 =   000.0; double b1 =  -500.0;
+  double a2 =   000.0; double b2 =   500.0;
+  double a3 =   850.0; double b3 = -1503.0;
+  double a4 = -1637.0; double b4 =  3621.0;
+
+  if (mom<0.3) return kFALSE;
+  if (mom>2.06) return kFALSE;
+  if (mom<1.2) {
+    if (ttof > a2*mom+b2) return kFALSE;
+    if (ttof < a1*mom+b1) return kFALSE;
+  }
+  if (mom<1.9) {
+    if (ttof > a2*mom+b2) return kFALSE;
+    if (ttof < a3*mom+b3) return kFALSE;
+  }
+  if (mom<2.06) {
+    if (ttof > a4*mom+b4) return kFALSE;
+    if (ttof < a3*mom+b3) return kFALSE;
+  }
+  return kTRUE;
+}
+
+bool AliFemtoESDTrackCut::IsProtonTOFTime(float mom, float ttof)
+{
+  double a1 =   000.0; double b1 =  -915.0;
+  double a2 =   000.0; double b2 =   600.0;
+  double a3 =   572.0; double b3 = -1715.0;
+
+  if (mom<0.3) return kFALSE;
+  if (mom>3.0) return kFALSE;
+  if (mom<1.4) {
+    if (ttof > a2*mom+b2) return kFALSE;
+    if (ttof < a1*mom+b1) return kFALSE;
+  }
+  if (mom<3.0) {
+    if (ttof > a2*mom+b2) return kFALSE;
+    if (ttof < a3*mom+b3) return kFALSE;
+  }
+  return kTRUE;
+}
+
+
+
+
+bool AliFemtoESDTrackCut::IsKaonTPCdEdxNSigma(float mom, float nsigmaK)
+{
+  cout<<" AliFemtoESDTrackCut::IsKaonTPCdEdxNSigma "<<mom<<" "<<nsigmaK<<endl;
+
+
+  if(mom<0.35 && TMath::Abs(nsigmaK)<5.0)return true;
+  if(mom>=0.35 && mom<0.5 && TMath::Abs(nsigmaK)<3.0)return true; 
+  if(mom>=0.5 && mom<0.7 && TMath::Abs(nsigmaK)<2.0)return true;
+
+  return false;
+}
+
+
+bool AliFemtoESDTrackCut::IsKaonTOFNSigma(float mom, float nsigmaK)
+{
+  cout<<" AliFemtoESDTrackCut::IsKaonTPCdEdxNSigma "<<mom<<" "<<nsigmaK<<endl;
+  //fan
+  //  if(mom<1.5 && TMath::Abs(nsigmaK)<3.0)return true;
+  if(mom>=1.5 && TMath::Abs(nsigmaK)<2.0)return true; 
+  return false;
+}
+
+//ML according with Roberto Preghenella talk
+
+bool AliFemtoESDTrackCut::IsKaonNSigma(float mom, float nsigmaTPCK, float nsigmaTOFK)
+{
+  //cout<<"//////// AliFemtoESDTrackCut::IsKaonNSigma "<<mom<<" tpc "<<nsigmaTPCK<<" tof "<<nsigmaTOFK<<endl;
+
+
+  if(TMath::Abs(nsigmaTOFK)<3.0 && mom<1.5 && TMath::Abs(nsigmaTPCK)<3.0)return true;
+  if(TMath::Abs(nsigmaTOFK)<2.0 && mom>1.5 && TMath::Abs(nsigmaTPCK)<3.0)return true;
+
+  //no TOF signal
+
+  if(nsigmaTOFK<=-1000.){
+    //cout<<"//////// AliFemtoESDTrackCut::IsKaonNSigma P= "<<mom<<" tpc "<<nsigmaTPCK<<" tof "<<nsigmaTOFK<<endl;
+    //cout <<"/////////////// AliFemtoESDTrackCut::IsKaonNSigma  NO TOF SIGNAL ////////////" <<endl;
+    if(mom<0.4 && TMath::Abs(nsigmaTPCK)<1.0)return true;
+    if(mom>=0.4 && mom<0.5 && TMath::Abs(nsigmaTPCK)<2.0)return true;
+    if(mom>=0.5 && mom<0.6 && TMath::Abs(nsigmaTPCK)<2.0)return true;
+  }
+
+  return false;
+}
+
+
+
+bool AliFemtoESDTrackCut::IsPionNSigma(float mom, float nsigmaTPCPi, float nsigmaTOFPi)
+{
+  // cout<<" AliFemtoESDTrackCut::IsKaonNSigma "<<mom<<" tpc "<<nsigmaTPCK<<" tof "<<nsigmaTOFK<<endl;
+  //TOF signal
+  if(TMath::Abs(nsigmaTOFPi)<3.0 && mom<1.5 && TMath::Abs(nsigmaTPCPi)<5.0)return true;
+  if(TMath::Abs(nsigmaTOFPi)<2.0 && mom>1.5 && TMath::Abs(nsigmaTPCPi)<5.0)return true;
+
+
+  //no TOF signal
+  if(nsigmaTOFPi<-999.){
+    if(mom<0.35 && TMath::Abs(nsigmaTPCPi)<5.0)return true;
+    if(mom>=0.35 && mom<0.5 && TMath::Abs(nsigmaTPCPi)<3.0)return true;
+    if(mom>=0.5 && TMath::Abs(nsigmaTPCPi)<2.0)return true;
+  }
+  return false;
+}
+
+
+bool AliFemtoESDTrackCut::IsProtonNSigma(float mom, float nsigmaTPCP, float nsigmaTOFP)
+{
+  // cout<<" AliFemtoESDTrackCut::IsKaonNSigma "<<mom<<" tpc "<<nsigmaTPCK<<" tof "<<nsigmaTOFK<<endl;
+
+  //TOF signal
+  if(TMath::Abs(nsigmaTOFP)<3.0 && mom<1.5 && TMath::Abs(nsigmaTPCP)<3.0)return true;
+  if(TMath::Abs(nsigmaTOFP)<2.0 && mom>1.5 && TMath::Abs(nsigmaTPCP)<3.0)return true;
+
+  //no TOF signal
+  if(nsigmaTOFP<-999.){
+    if(mom<0.5 && TMath::Abs(nsigmaTPCP)<3.0)return true;
+    if(mom>=0.5 && mom<0.8 && TMath::Abs(nsigmaTPCP)<2.0)return true;
+  }
+
+  return false;
+}
+
+
+void AliFemtoESDTrackCut::SetPIDMethod(ReadPIDMethodType newMethod)
+{
+  fPIDMethod = newMethod;
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoESDTrackCut.h b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoESDTrackCut.h
new file mode 100644 (file)
index 0000000..c87f622
--- /dev/null
@@ -0,0 +1,160 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFemtoESDTrackCut: A basic track cut that used information from     //
+// ALICE ESD to accept or reject the track.                              //  
+// Enables the selection on charge, transverse momentum, rapidity,       //
+// pid probabilities, number of ITS and TPC clusters                     //
+// Author: Marek Chojnacki (WUT), mchojnacki@knf.pw.edu.pl               //
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+
+#ifndef ALIFEMTOESDTRACKCUT_H
+#define ALIFEMTOESDTRACKCUT_H
+
+//#ifndef StMaker_H
+//#include "StMaker.h"
+//#endif
+
+#include "AliFemtoTrackCut.h"
+
+class AliFemtoESDTrackCut : public AliFemtoTrackCut 
+{
+  public:
+
+  enum PIDMethodType {knSigma=0, kContour=1};
+  typedef enum PIDMethodType ReadPIDMethodType; 
+
+  AliFemtoESDTrackCut();
+  virtual ~AliFemtoESDTrackCut();
+
+  virtual bool Pass(const AliFemtoTrack* aTrack);
+
+  virtual AliFemtoString Report();
+  virtual TList *ListSettings();
+  virtual AliFemtoParticleType Type(){return hbtTrack;}
+
+  void SetPt(const float& lo, const float& hi);
+  void SetRapidity(const float& lo, const float& hi);
+  void SetEta(const float& lo, const float& hi);
+  void SetCharge(const int& ch);
+  void SetPidProbElectron(const float& lo, const float& hi);
+  void SetPidProbPion(const float& lo, const float& hi);
+  void SetPidProbKaon(const float& lo, const float& hi);
+  void SetPidProbProton(const float& lo, const float& hi);
+  void SetPidProbMuon(const float& lo, const float& hi);
+  void SetLabel(const bool& flag);
+  void SetStatus(const long& w);
+  void SetminTPCclsF(const short& s);
+  void SetminTPCncls(const short& s);
+  void SetminITScls(const int& s);
+  void SetRemoveKinks(const bool& flag);
+  void SetRemoveITSFake(const bool& flag);
+  void SetMaxITSChiNdof(const float& maxchi);
+  void SetMaxTPCChiNdof(const float& maxchi);
+  void SetMaxSigmaToVertex(const float& maxsig);
+  void SetMaxImpactXY(const float& maximpxy);
+  void SetMaxImpactZ(const float& maximpz);
+  void SetMaxImpactXYPtDep(const float& maxoff, const float& maxnrm, const float& maxpow);
+  void SetMostProbablePion();
+  void SetMostProbableKaon();
+  void SetMostProbableProton();
+  void SetNoMostProbable(); 
+  void SetPIDMethod(ReadPIDMethodType newMethod);
+
+  void SetMomRangeTOFpidIs(const float& minp, const float& maxp);
+  void SetMomRangeTPCpidIs(const float& minp, const float& maxp);
+  void SetMomRangeITSpidIs(const float& minp, const float& maxp);
+
+ private:   // here are the quantities I want to cut on...
+
+  int               fCharge;             // particle charge
+  float             fPt[2];              // bounds for transverse momentum
+  float             fRapidity[2];        // bounds for rapidity
+  float             fEta[2];             // bounds for pseudorapidity
+  float             fPidProbElectron[2]; // bounds for electron probability
+  float             fPidProbPion[2];     // bounds for pion probability
+  float             fPidProbKaon[2];     // bounds for kaon probability
+  float             fPidProbProton[2];   // bounds for proton probability
+  float             fPidProbMuon[2];     // bounds for muon probability 
+  bool              fLabel;              // if true label<0 will not pass throught 
+  long              fStatus;             // staus flag
+  ReadPIDMethodType fPIDMethod;          // which PID mehod to use. 0 - nsgima, 1 - contour 
+
+  short             fminTPCclsF;         // min number of findable clusters in the TPC
+  short             fminTPCncls;         // min number of clusters in the TPC
+  int               fminITScls;          // min number of clusters assigned in the ITS 
+  float             fMaxITSchiNdof;      // maximum allowed chi2/ndof for ITS clusters
+  float             fMaxTPCchiNdof;      // maximum allowed chi2/ndof for TPC clusters
+  float             fMaxSigmaToVertex;   // maximum allowed sigma to primary vertex
+  long              fNTracksPassed;      // passed tracks count
+  long              fNTracksFailed;      // failed tracks count
+  bool              fRemoveKinks;        // if true particles with any kink label will not pass
+  bool              fRemoveITSFake;      // if true particles with ITS fake flag will not pass
+  int               fMostProbable;       // this particle type is required to be most probable
+
+  float             fMaxImpactXY;        // Max XY impact parameter
+  float             fMaxImpactZ;         // Max Z impact parameter
+
+  float             fMaxImpactXYPtOff;   // Max XY DCA Pt dependent offset
+  float             fMaxImpactXYPtNrm;   // Max XY DCA Pt dependent normalization
+  float             fMaxImpactXYPtPow;   // Max XY DCA Pt dependent power
+
+  float             fMinPforTOFpid;  // momentum from which TOF PID is requested
+  float             fMaxPforTOFpid;  // momentum till which TOF PID is requested
+  float             fMinPforTPCpid;  // momentum from which TPC PID is requested
+  float             fMaxPforTPCpid;  // momentum till which TPC PID is requested
+  float             fMinPforITSpid;  // momentum from which ITS PID is requested
+  float             fMaxPforITSpid;  // momentum till which ITS PID is requested
+
+  float PidFractionElectron(float mom) const;
+  float PidFractionPion(float mom) const;
+  float PidFractionKaon(float mom) const;
+  float PidFractionProton(float mom) const;
+
+  bool IsPionTPCdEdx(float mom, float dEdx);
+  bool IsKaonTPCdEdx(float mom, float dEdx);
+  bool IsProtonTPCdEdx(float mom, float dEdx);
+
+  bool IsPionTOFTime(float mom, float ttof);
+  bool IsKaonTOFTime(float mom, float ttof);
+  bool IsProtonTOFTime(float mom, float ttof);
+
+  bool IsKaonTPCdEdxNSigma(float mom, float nsigma);
+  bool IsKaonTOFNSigma(float mom, float nsigma);
+  bool IsKaonNSigma(float mom, float nsigmaTPC, float nsigmaTOF);
+  bool IsPionNSigma(float mom, float nsigmaTPC, float nsigmaTOF);
+  bool IsProtonNSigma(float mom, float nsigmaTPC, float nsigmaTOF);
+
+#ifdef __ROOT__ 
+  ClassDef(AliFemtoESDTrackCut, 1)
+#endif
+    };
+
+
+inline void AliFemtoESDTrackCut::SetPt(const float& lo, const float& hi){fPt[0]=lo; fPt[1]=hi;}
+inline void AliFemtoESDTrackCut::SetRapidity(const float& lo,const float& hi){fRapidity[0]=lo; fRapidity[1]=hi;}
+inline void AliFemtoESDTrackCut::SetEta(const float& lo,const float& hi){fEta[0]=lo; fEta[1]=hi;}
+inline void AliFemtoESDTrackCut::SetCharge(const int& ch){fCharge = ch;}
+inline void AliFemtoESDTrackCut::SetPidProbElectron(const float& lo,const float& hi){fPidProbElectron[0]=lo; fPidProbElectron[1]=hi;}
+inline void AliFemtoESDTrackCut::SetPidProbPion(const float& lo,const float& hi){fPidProbPion[0]=lo; fPidProbPion[1]=hi;}
+inline void AliFemtoESDTrackCut::SetPidProbKaon(const float& lo,const float& hi){fPidProbKaon[0]=lo; fPidProbKaon[1]=hi;}
+inline void AliFemtoESDTrackCut::SetPidProbProton(const float& lo,const float& hi){fPidProbProton[0]=lo; fPidProbProton[1]=hi;}
+inline void AliFemtoESDTrackCut::SetPidProbMuon(const float& lo,const float& hi){fPidProbMuon[0]=lo; fPidProbMuon[1]=hi;}
+inline void AliFemtoESDTrackCut::SetLabel(const bool& flag){fLabel=flag;}
+inline void AliFemtoESDTrackCut::SetStatus(const long& status){fStatus=status;}
+inline void AliFemtoESDTrackCut::SetminTPCclsF(const short& minTPCclsF){fminTPCclsF=minTPCclsF;}
+inline void AliFemtoESDTrackCut::SetminTPCncls(const short& s){fminTPCncls=s;}
+inline void AliFemtoESDTrackCut::SetminITScls(const int& minITScls){fminITScls=minITScls;}
+inline void AliFemtoESDTrackCut::SetMostProbablePion() { fMostProbable = 2; }
+inline void AliFemtoESDTrackCut::SetMostProbableKaon() { fMostProbable = 3; }
+inline void AliFemtoESDTrackCut::SetMostProbableProton() { fMostProbable = 4; }
+inline void AliFemtoESDTrackCut::SetNoMostProbable() { fMostProbable = 0; }
+inline void AliFemtoESDTrackCut::SetMaxITSChiNdof(const float& maxchi) { fMaxITSchiNdof = maxchi; }
+inline void AliFemtoESDTrackCut::SetMaxTPCChiNdof(const float& maxchi) { fMaxTPCchiNdof = maxchi; }
+inline void AliFemtoESDTrackCut::SetMaxSigmaToVertex(const float& maxsig) { fMaxSigmaToVertex = maxsig; }
+inline void AliFemtoESDTrackCut::SetMaxImpactXY(const float& maximpxy) { fMaxImpactXY = maximpxy; }
+inline void AliFemtoESDTrackCut::SetMaxImpactXYPtDep(const float& maxoff, const float& maxnrm, const float& maxpow) { fMaxImpactXYPtOff = maxoff; fMaxImpactXYPtNrm = maxnrm; fMaxImpactXYPtPow = maxpow; }
+inline void AliFemtoESDTrackCut::SetMaxImpactZ(const float& maximpz) { fMaxImpactZ = maximpz; }
+
+#endif
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoEventReaderESDKine.cxx b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoEventReaderESDKine.cxx
new file mode 100644 (file)
index 0000000..658ce5a
--- /dev/null
@@ -0,0 +1,602 @@
+////////////////////////////////////////////////////////////////////////////////
+///                                                                          ///
+/// AliFemtoEventReaderESDKine - the reader class for the Alice ESD              ///
+/// Reads in ESD information and converts it into internal AliFemtoEvent     ///
+/// Reads in AliESDfriend to create shared hit/quality information           ///
+/// Authors: Marek Chojnacki mchojnacki@knf.pw.edu.pl                        ///
+///          Adam Kisiel kisiel@mps.ohio-state.edu                           ///
+///                                                                          ///
+////////////////////////////////////////////////////////////////////////////////
+
+/*
+ *$Id$
+ *$Log$
+ *Revision 1.1  2007/05/25 12:42:54  akisiel
+ *Adding a reader for the Kine information
+ *
+ *Revision 1.2  2007/05/22 09:01:42  akisiel
+ *Add the possibiloity to save cut settings in the ROOT file
+ *
+ *Revision 1.1  2007/05/16 10:22:11  akisiel
+ *Making the directory structure of AliFemto flat. All files go into one common directory
+ *
+ *Revision 1.5  2007/05/03 09:45:20  akisiel
+ *Fixing Effective C++ warnings
+ *
+ *Revision 1.4  2007/04/27 07:28:34  akisiel
+ *Remove event number reading due to interface changes
+ *
+ *Revision 1.3  2007/04/27 07:25:16  akisiel
+ *Make revisions needed for compilation from the main AliRoot tree
+ *
+ *Revision 1.1.1.1  2007/04/25 15:38:41  panos
+ *Importing the HBT code dir
+ *
+ */
+
+#include "AliFemtoEventReaderESDKine.h"
+
+#include "TFile.h"
+#include "TChain.h"
+#include "AliESDEvent.h"
+#include "AliESDtrack.h"
+#include "AliESDVertex.h"
+#include "AliStack.h"
+//#include "AliAODParticle.h"
+#include "TParticle.h"
+
+//#include "TSystem.h"
+
+#include "AliFmPhysicalHelixD.h"
+#include "AliFmThreeVectorF.h"
+
+#include "SystemOfUnits.h"
+
+#include "AliFemtoEvent.h"
+
+#include "TMath.h"
+#include "TParticle.h"
+#include "AliFemtoModelHiddenInfo.h"
+#include "AliFemtoModelGlobalHiddenInfo.h"
+#include "AliGenHijingEventHeader.h"
+
+ClassImp(AliFemtoEventReaderESDKine)
+
+#if !(ST_NO_NAMESPACES)
+  using namespace units;
+#endif
+
+using namespace std;
+//____________________________
+//constructor with 0 parameters , look at default settings 
+AliFemtoEventReaderESDKine::AliFemtoEventReaderESDKine():
+  fInputFile(" "),
+  fFileName(" "),
+  fConstrained(true),
+  fNumberofEvent(0),
+  fCurEvent(0),
+  fCurRLEvent(0),
+  fTree(0x0),
+  fEvent(0x0),
+  fRunLoader(0x0)
+{
+}
+
+AliFemtoEventReaderESDKine::AliFemtoEventReaderESDKine(const AliFemtoEventReaderESDKine &aReader) :
+  AliFemtoEventReader(),
+  fInputFile(" "),
+  fFileName(" "),
+  fConstrained(true),
+  fNumberofEvent(0),
+  fCurEvent(0),
+  fCurRLEvent(0),
+  fTree(0x0),
+  fEvent(0x0),
+  fRunLoader(0x0)
+{
+  // copy constructor
+  fInputFile = aReader.fInputFile;
+  fFileName  = aReader.fFileName;
+  fConstrained = aReader.fConstrained;
+  fNumberofEvent = aReader.fNumberofEvent;
+  fCurEvent = aReader.fCurEvent;
+  fEvent = new AliESDEvent();
+}
+//__________________
+//Destructor
+AliFemtoEventReaderESDKine::~AliFemtoEventReaderESDKine()
+{
+  // destructor
+  //delete fListOfFiles;
+  delete fTree;
+  delete fEvent;
+  if (fRunLoader) delete fRunLoader;
+}
+
+//__________________
+AliFemtoEventReaderESDKine& AliFemtoEventReaderESDKine::operator=(const AliFemtoEventReaderESDKine& aReader)
+{
+  // assignment operator
+  if (this == &aReader)
+    return *this;
+
+  fInputFile = aReader.fInputFile;
+  fFileName  = aReader.fFileName;
+  fConstrained = aReader.fConstrained;
+  fNumberofEvent = aReader.fNumberofEvent;
+  fCurEvent = aReader.fCurEvent;
+  fCurRLEvent = aReader.fCurRLEvent;
+  if (fTree) delete fTree;
+  //  fTree = aReader.fTree->CloneTree();
+  if (fEvent) delete fEvent;
+  fEvent = new AliESDEvent();
+  if (fRunLoader) delete fRunLoader;
+  fRunLoader = new AliRunLoader(*aReader.fRunLoader);
+
+  return *this;
+}
+//__________________
+AliFemtoString AliFemtoEventReaderESDKine::Report()
+{
+  // create reader report
+  AliFemtoString temp = "\n This is the AliFemtoEventReaderESDKine\n";
+  return temp;
+}
+
+//__________________
+void AliFemtoEventReaderESDKine::SetInputFile(const char* inputFile)
+{
+  //setting the name of file where names of ESD file are written 
+  //it takes only this files which have good trees
+  char buffer[256];
+  fInputFile=string(inputFile);
+  cout<<"Input File set on "<<fInputFile<<endl;
+  ifstream infile(inputFile);
+
+  fTree = new TChain("esdTree");
+
+  if(infile.good()==true)
+    { 
+      //checking if all give files have good tree inside
+      while (infile.eof()==false)
+       {
+         infile.getline(buffer,256);
+         //ifstream test_file(buffer);
+         TFile *esdFile=TFile::Open(buffer,"READ");
+         if (esdFile!=0x0)
+           {   
+             TTree* tree = (TTree*) esdFile->Get("esdTree");
+             if (tree!=0x0)
+               {
+                 cout<<"putting file  "<<string(buffer)<<" into analysis"<<endl;
+                 fTree->AddFile(buffer);
+                 delete tree;
+               }
+             esdFile->Close(); 
+           }
+         delete esdFile;
+       }
+    }
+}
+
+void AliFemtoEventReaderESDKine::SetConstrained(const bool constrained)
+{
+  fConstrained=constrained;
+}
+
+bool AliFemtoEventReaderESDKine::GetConstrained() const
+{
+  return fConstrained;
+}
+
+AliFemtoEvent* AliFemtoEventReaderESDKine::ReturnHbtEvent()
+{
+  // read in a next hbt event from the chain
+  // convert it to AliFemtoEvent and return
+  // for further analysis
+  AliFemtoEvent *hbtEvent = 0;
+  TString tGAliceFilename;
+
+  if (fCurEvent==fNumberofEvent)//open next file  
+    {
+      if (fNumberofEvent == 0) {
+       fEvent=new AliESDEvent();
+               
+         //ESD data
+//       fEsdFile=TFile::Open(fFileName.c_str(),"READ");
+//       fTree = (TTree*) fEsdFile->Get("esdTree");                    
+
+         fTree->SetBranchStatus("MuonTracks*",0);
+         fTree->SetBranchStatus("PmdTracks*",0);
+         fTree->SetBranchStatus("TrdTracks*",0);
+         fTree->SetBranchStatus("V0s*",0);
+         fTree->SetBranchStatus("Cascades*",0);
+         fTree->SetBranchStatus("Kinks*",0);
+         fTree->SetBranchStatus("CaloClusters*",0);
+         fTree->SetBranchStatus("AliRawDataErrorLogs*",0);
+         fTree->SetBranchStatus("ESDfriend*",0);
+         fEvent->ReadFromTree(fTree);
+
+//       chain->SetBranchStatus("*",0);
+//       chain->SetBranchStatus("fUniqueID",1);
+//       chain->SetBranchStatus("fTracks",1);
+//       chain->SetBranchStatus("fTracks.*",1);
+//       chain->SetBranchStatus("fTracks.fTPCindex[160]",1);
+//       fTree->SetBranchStatus("fTracks.fCalibContainer",0);
+
+
+       fNumberofEvent=fTree->GetEntries();
+
+       if (fNumberofEvent == 0) {
+         cout<<"no event in input "<<endl;
+         fReaderStatus=1;
+         return hbtEvent; 
+       }
+
+       cout<<"Number of Entries in the input "<<fNumberofEvent<<endl;
+       fCurEvent=0;
+       // simulation data reading setup
+       
+      }
+      else //no more data to read
+       {
+         cout<<"no more files "<<hbtEvent<<endl;
+         fReaderStatus=1;
+         return hbtEvent; 
+       }
+    }          
+  cout<<"starting to read event "<<fCurEvent<<endl;
+  fTree->GetEvent(fCurEvent);//getting next event
+  //  vector<int> tLabelTable;//to check labels
+  
+  cout << "fFileName is " << fFileName.Data() << endl;
+  cout << "Current file is " << fTree->GetCurrentFile()->GetName() << endl;
+  if (fFileName.CompareTo(fTree->GetCurrentFile()->GetName())) {
+    fFileName = fTree->GetCurrentFile()->GetName();
+    tGAliceFilename = fFileName;
+    tGAliceFilename.ReplaceAll("AliESDs","galice");
+    cout << "Reading RunLoader from " << tGAliceFilename.Data() << endl;
+    if (fRunLoader) delete fRunLoader;
+    fRunLoader = AliRunLoader::Open(tGAliceFilename.Data());
+    if (fRunLoader==0x0)
+      {
+       cout << "No Kine tree in file " << tGAliceFilename.Data() << endl;
+       exit(0);
+      }
+    if(fRunLoader->LoadHeader())
+      {
+       cout << "Could not read RunLoader header in file " << tGAliceFilename.Data() << endl;
+       exit(0);
+      }
+    fRunLoader->LoadKinematics();
+    fCurRLEvent = 0;
+  }
+
+  fRunLoader->GetEvent(fCurRLEvent);
+  AliStack* tStack = 0x0;
+  tStack = fRunLoader->Stack();
+       
+  hbtEvent = new AliFemtoEvent;
+  //setting basic things
+  //  hbtEvent->SetEventNumber(fEvent->GetEventNumber());
+  hbtEvent->SetRunNumber(fEvent->GetRunNumber());
+  //hbtEvent->SetNumberOfTracks(fEvent->GetNumberOfTracks());
+  hbtEvent->SetMagneticField(fEvent->GetMagneticField()*kilogauss);//to check if here is ok
+  hbtEvent->SetZDCN1Energy(fEvent->GetZDCN1Energy());
+  hbtEvent->SetZDCP1Energy(fEvent->GetZDCP1Energy());
+  hbtEvent->SetZDCN2Energy(fEvent->GetZDCN2Energy());
+  hbtEvent->SetZDCP2Energy(fEvent->GetZDCP2Energy());
+  hbtEvent->SetZDCEMEnergy(fEvent->GetZDCEMEnergy());
+  hbtEvent->SetZDCParticipants(fEvent->GetZDCParticipants());
+  hbtEvent->SetTriggerMask(fEvent->GetTriggerMask());
+  hbtEvent->SetTriggerCluster(fEvent->GetTriggerCluster());
+       
+  //Vertex
+  double fV1[3];
+  double fVCov[6];
+  if (fUseTPCOnly) {
+    fEvent->GetPrimaryVertexTPC()->GetXYZ(fV1);
+    fEvent->GetPrimaryVertexTPC()->GetCovMatrix(fVCov);
+    if (!fEvent->GetPrimaryVertexTPC()->GetStatus())
+      fVCov[4] = -1001.0;
+  }
+  else {
+    fEvent->GetPrimaryVertex()->GetXYZ(fV1);
+    fEvent->GetPrimaryVertex()->GetCovMatrix(fVCov);
+    if (!fEvent->GetPrimaryVertex()->GetStatus())
+      fVCov[4] = -1001.0;
+  }
+
+  AliFmThreeVectorF vertex(fV1[0],fV1[1],fV1[2]);
+  hbtEvent->SetPrimVertPos(vertex);
+  hbtEvent->SetPrimVertCov(fVCov);
+
+  AliGenHijingEventHeader *hdh = dynamic_cast<AliGenHijingEventHeader *> (fGenHeader);
+       
+  Double_t tReactionPlane = 0;
+  if (hdh)
+    {
+      tReactionPlane = hdh->ReactionPlaneAngle();
+    }
+  //starting to reading tracks
+  int nofTracks=0;  //number of reconstructed tracks in event
+  nofTracks=fEvent->GetNumberOfTracks();
+  int realnofTracks=0;//number of track which we use ina analysis
+
+  Int_t *motherids;
+  motherids = new Int_t[fStack->GetNtrack()];
+  for (int ip=0; ip<fStack->GetNtrack(); ip++) motherids[ip] = 0;
+
+  // Read in mother ids
+  TParticle *motherpart;
+  for (int ip=0; ip<fStack->GetNtrack(); ip++) {
+    motherpart = fStack->Particle(ip);
+    if (motherpart->GetDaughter(0) > 0)
+      motherids[motherpart->GetDaughter(0)] = ip;
+    if (motherpart->GetDaughter(1) > 0)
+      motherids[motherpart->GetDaughter(1)] = ip;
+
+//     if (motherpart->GetPdgCode() == 211) {
+//       cout << "Mother " << ip << " has daughters " 
+//        << motherpart->GetDaughter(0) << " " 
+//        << motherpart->GetDaughter(1) << " " 
+//        << motherpart->Vx() << " " 
+//        << motherpart->Vy() << " " 
+//        << motherpart->Vz() << " " 
+//        << endl;
+      
+//     }
+  }
+
+  for (int i=0;i<nofTracks;i++)
+    {
+      bool  tGoodMomentum=true; //flaga to chcek if we can read momentum of this track
+               
+      AliFemtoTrack* trackCopy = new AliFemtoTrack();  
+      const AliESDtrack *esdtrack=fEvent->GetTrack(i);//getting next track
+      //      const AliESDfriendTrack *tESDfriendTrack = esdtrack->GetFriendTrack();
+
+      trackCopy->SetCharge((short)esdtrack->GetSign());
+
+      //in aliroot we have AliPID 
+      //0-electron 1-muon 2-pion 3-kaon 4-proton 5-photon 6-pi0 7-neutron 8-kaon0 9-eleCon   
+      //we use only 5 first
+      double esdpid[5];
+      esdtrack->GetESDpid(esdpid);
+      trackCopy->SetPidProbElectron(esdpid[0]);
+      trackCopy->SetPidProbMuon(esdpid[1]);
+      trackCopy->SetPidProbPion(esdpid[2]);
+      trackCopy->SetPidProbKaon(esdpid[3]);
+      trackCopy->SetPidProbProton(esdpid[4]);
+                                               
+      double pxyz[3];
+      double rxyz[3];
+      double impact[2];
+      double covimpact[3];
+      
+      if (fUseTPCOnly) {
+       if (!esdtrack->GetTPCInnerParam()) {
+         delete trackCopy;
+         continue;
+       }
+
+       AliExternalTrackParam *param = new AliExternalTrackParam(*esdtrack->GetTPCInnerParam());
+       param->GetXYZ(rxyz);
+       param->PropagateToDCA(fEvent->GetPrimaryVertexTPC(), (fEvent->GetMagneticField()), 10000, impact, covimpact);
+       param->GetPxPyPz(pxyz);//reading noconstarined momentum
+
+       AliFemtoThreeVector v(pxyz[0],pxyz[1],pxyz[2]);
+       if (v.mag() < 0.0001) {
+         //    cout << "Found 0 momentum ???? " <<endl;
+         delete trackCopy;
+         continue;
+       }
+       trackCopy->SetP(v);//setting momentum
+       trackCopy->SetPt(sqrt(pxyz[0]*pxyz[0]+pxyz[1]*pxyz[1]));
+
+       const AliFmThreeVectorD kP(pxyz[0],pxyz[1],pxyz[2]);
+       const AliFmThreeVectorD kOrigin(fV1[0],fV1[1],fV1[2]);
+       //setting helix I do not if it is ok
+       AliFmPhysicalHelixD helix(kP,kOrigin,(double)(fEvent->GetMagneticField())*kilogauss,(double)(trackCopy->Charge())); 
+       trackCopy->SetHelix(helix);
+
+       //some stuff which could be useful 
+       trackCopy->SetImpactD(impact[0]);
+       trackCopy->SetImpactZ(impact[1]);
+       trackCopy->SetCdd(covimpact[0]);
+       trackCopy->SetCdz(covimpact[1]);
+       trackCopy->SetCzz(covimpact[2]);
+       trackCopy->SetSigmaToVertex(GetSigmaToVertex(impact, covimpact));       
+
+       delete param;
+      }
+      else {
+       if (fConstrained==true)             
+         tGoodMomentum=esdtrack->GetConstrainedPxPyPz(pxyz); //reading constrained momentum
+       else
+         tGoodMomentum=esdtrack->GetPxPyPz(pxyz);//reading noconstarined momentum
+       
+       AliFemtoThreeVector v(pxyz[0],pxyz[1],pxyz[2]);
+       if (v.mag() < 0.0001) {
+         //    cout << "Found 0 momentum ???? " <<endl;
+         delete trackCopy;
+         continue;
+       }
+       trackCopy->SetP(v);//setting momentum
+       trackCopy->SetPt(sqrt(pxyz[0]*pxyz[0]+pxyz[1]*pxyz[1]));
+       const AliFmThreeVectorD kP(pxyz[0],pxyz[1],pxyz[2]);
+       const AliFmThreeVectorD kOrigin(fV1[0],fV1[1],fV1[2]);
+       //setting helix I do not if it is ok
+       AliFmPhysicalHelixD helix(kP,kOrigin,(double)(fEvent->GetMagneticField())*kilogauss,(double)(trackCopy->Charge())); 
+       trackCopy->SetHelix(helix);
+       
+       //some stuff which could be useful 
+       float imp[2];
+       float cim[3];
+       esdtrack->GetImpactParameters(imp,cim);
+
+       impact[0] = imp[0];
+       impact[1] = imp[1];
+       covimpact[0] = cim[0];
+       covimpact[1] = cim[1];
+       covimpact[2] = cim[2];
+
+       trackCopy->SetImpactD(impact[0]);
+       trackCopy->SetImpactZ(impact[1]);
+       trackCopy->SetCdd(covimpact[0]);
+       trackCopy->SetCdz(covimpact[1]);
+       trackCopy->SetCzz(covimpact[2]);
+       trackCopy->SetSigmaToVertex(GetSigmaToVertex(impact,covimpact));
+      }
+               
+      trackCopy->SetTrackId(esdtrack->GetID());
+      trackCopy->SetFlags(esdtrack->GetStatus());
+      trackCopy->SetLabel(esdtrack->GetLabel());
+               
+      trackCopy->SetITSchi2(esdtrack->GetITSchi2());    
+      trackCopy->SetITSncls(esdtrack->GetNcls(0));     
+      trackCopy->SetTPCchi2(esdtrack->GetTPCchi2());       
+      trackCopy->SetTPCncls(esdtrack->GetTPCNcls());       
+      trackCopy->SetTPCnclsF(esdtrack->GetTPCNclsF());      
+      trackCopy->SetTPCsignalN((short)esdtrack->GetTPCsignalN()); //due to bug in aliesdtrack class   
+      trackCopy->SetTPCsignalS(esdtrack->GetTPCsignalSigma()); 
+
+
+      trackCopy->SetTPCClusterMap(esdtrack->GetTPCClusterMap());
+      trackCopy->SetTPCSharedMap(esdtrack->GetTPCSharedMap());
+
+      double xtpc[3];
+      esdtrack->GetInnerXYZ(xtpc);
+      xtpc[2] -= fV1[2];
+      trackCopy->SetNominalTPCEntrancePoint(xtpc);
+
+      esdtrack->GetOuterXYZ(xtpc);
+      xtpc[2] -= fV1[2];
+      trackCopy->SetNominalTPCExitPoint(xtpc);
+
+      int indexes[3];
+      for (int ik=0; ik<3; ik++) {
+       indexes[ik] = esdtrack->GetKinkIndex(ik);
+      }
+      trackCopy->SetKinkIndexes(indexes);
+
+      // Fill the hidden information with the simulated data
+      TParticle *tPart = fStack->Particle(TMath::Abs(esdtrack->GetLabel()));
+
+      // Check the mother information
+
+      // Using the new way of storing the freeze-out information
+      // Final state particle is stored twice on the stack
+      // one copy (mother) is stored with original freeze-out information
+      //   and is not tracked
+      // the other one (daughter) is stored with primary vertex position
+      //   and is tracked
+       
+      // Freeze-out coordinates
+      double fpx=0.0, fpy=0.0, fpz=0.0, fpt=0.0;
+      fpx = tPart->Vx() - fV1[0];
+      fpy = tPart->Vy() - fV1[1];
+      fpz = tPart->Vz() - fV1[2];
+      fpt = tPart->T();
+
+      AliFemtoModelGlobalHiddenInfo *tInfo = new AliFemtoModelGlobalHiddenInfo();
+      tInfo->SetGlobalEmissionPoint(fpx, fpy, fpz);
+
+      if (motherids[TMath::Abs(esdtrack->GetLabel())]>0) {
+       TParticle *mother = fStack->Particle(motherids[TMath::Abs(esdtrack->GetLabel())]);
+       // Check if this is the same particle stored twice on the stack
+       if ((mother->GetPdgCode() == tPart->GetPdgCode() || (mother->Px() == tPart->Px()))) {
+         // It is the same particle
+         // Read in the original freeze-out information
+         // and convert it from to [fm]
+         fpx = mother->Vx()*1e13;
+         fpy = mother->Vy()*1e13;
+         fpz = mother->Vz()*1e13;
+         fpt = mother->T()*1e13*3e10;
+         
+       }
+      }
+
+      tInfo->SetPDGPid(tPart->GetPdgCode());
+      tInfo->SetTrueMomentum(tPart->Px(), tPart->Py(), tPart->Pz());
+      Double_t mass2 = (tPart->Energy() *tPart->Energy() -
+                       tPart->Px()*tPart->Px() -
+                       tPart->Py()*tPart->Py() -
+                       tPart->Pz()*tPart->Pz());
+      if (mass2>0.0)
+       tInfo->SetMass(TMath::Sqrt(mass2));
+      else 
+       tInfo->SetMass(0.0);
+
+      tInfo->SetEmissionPoint(fpx, fpy, fpz, fpt);
+      trackCopy->SetHiddenInfo(tInfo);
+      
+      //decision if we want this track
+      //if we using diffrent labels we want that this label was use for first time 
+      //if we use hidden info we want to have match between sim data and ESD
+      if (tGoodMomentum==true)
+       {
+         hbtEvent->TrackCollection()->push_back(trackCopy);//adding track to analysis
+         realnofTracks++;//real number of tracks
+         //      delete trackCopy;
+       }
+      else
+       {
+         delete  trackCopy;
+       }
+               
+    }
+
+  hbtEvent->SetNumberOfTracks(realnofTracks);//setting number of track which we read in event  
+  fCurEvent++; 
+  fCurRLEvent++;
+  cout<<"end of reading nt "<<nofTracks<<" real number "<<realnofTracks<<endl;
+  if (fCurEvent== fNumberofEvent)//if end of current file close all
+    {   
+      fTree->Reset(); 
+      delete fTree;
+    }
+  return hbtEvent; 
+}
+//____________________________________________________________________
+Float_t AliFemtoEventReaderESDKine::GetSigmaToVertex(const AliESDtrack* esdTrack)
+{
+  // Calculates the number of sigma to the vertex.
+
+  Float_t b[2];
+  Float_t bRes[2];
+  Float_t bCov[3];
+
+  b[0] = impact[0];
+  b[1] = impact[1];
+  bCov[0] = covar[0];
+  bCov[1] = covar[1];
+  bCov[2] = covar[2];
+
+  bRes[0] = TMath::Sqrt(bCov[0]);
+  bRes[1] = TMath::Sqrt(bCov[2]);
+
+  // -----------------------------------
+  // How to get to a n-sigma cut?
+  //
+  // The accumulated statistics from 0 to d is
+  //
+  // ->  Erf(d/Sqrt(2)) for a 1-dim gauss (d = n_sigma)
+  // ->  1 - Exp(-d**2) for a 2-dim gauss (d*d = dx*dx + dy*dy != n_sigma)
+  //
+  // It means that for a 2-dim gauss: n_sigma(d) = Sqrt(2)*ErfInv(1 - Exp((-x**2)/2)
+  // Can this be expressed in a different way?
+
+  if (bRes[0] == 0 || bRes[1] ==0)
+    return -1;
+
+  Float_t d = TMath::Sqrt(TMath::Power(b[0]/bRes[0],2) + TMath::Power(b[1]/bRes[1],2));
+
+  // stupid rounding problem screws up everything:
+  // if d is too big, TMath::Exp(...) gets 0, and TMath::ErfInverse(1) that should be infinite, gets 0 :(
+  if (TMath::Exp(-d * d / 2) < 1e-10)
+    return 1000;
+
+  d = TMath::ErfInverse(1 - TMath::Exp(-d * d / 2)) * TMath::Sqrt(2);
+  return d;
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoEventReaderESDKine.h b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoEventReaderESDKine.h
new file mode 100644 (file)
index 0000000..76ffdd6
--- /dev/null
@@ -0,0 +1,88 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoEventReaderESDKine - the reader class for the Alice ESD            //
+// Reads in ESD information and converts it into internal AliFemtoEvent       //
+// Reads in AliESDfriend to create shared hit/quality information             //
+// Reads in Kine information and stores it in the hidden info                 //
+// Authors: Marek Chojnacki mchojnacki@knf.pw.edu.pl                          //
+//          Adam Kisiel kisiel@mps.ohio-state.edu                             //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+
+/*
+ *$Id$
+ *$Log$
+ *Revision 1.1  2007/05/25 12:42:54  akisiel
+ *Adding a reader for the Kine information
+ *
+ *Revision 1.1  2007/05/16 10:22:11  akisiel
+ *Making the directory structure of AliFemto flat. All files go into one common directory
+ *
+ *Revision 1.4  2007/05/03 09:45:20  akisiel
+ *Fixing Effective C++ warnings
+ *
+ *Revision 1.3  2007/04/27 07:25:16  akisiel
+ *Make revisions needed for compilation from the main AliRoot tree
+ *
+ *Revision 1.1.1.1  2007/04/25 15:38:41  panos
+ *Importing the HBT code dir
+ *
+ */
+  
+
+#ifndef ALIFEMTOEVENTREADERESDKINE_H
+#define ALIFEMTOEVENTREADERESDKINE_H
+#include "AliFemtoEventReader.h"
+#include "AliFemtoEnumeration.h"
+
+#include <string>
+#include <vector>
+#include "TChain.h"
+#include "AliESDtrack.h"
+#include "AliESDEvent.h"
+#include <list>
+#include "AliRunLoader.h"
+#include "AliFemtoModelHiddenInfo.h"
+
+class AliFemtoEvent;
+
+class AliFemtoEventReaderESDKine : public AliFemtoEventReader 
+{
+ public:
+  AliFemtoEventReaderESDKine();
+  AliFemtoEventReaderESDKine(const AliFemtoEventReaderESDKine &aReader);
+  ~AliFemtoEventReaderESDKine();
+
+  AliFemtoEventReaderESDKine& operator=(const AliFemtoEventReaderESDKine& aReader);
+
+  virtual AliFemtoEvent* ReturnHbtEvent();
+  virtual AliFemtoString Report();
+  //void SetFileName(const char* fileName);
+  void SetInputFile(const char* inputFile);
+  void SetConstrained(const bool constrained);
+  bool GetConstrained() const;
+
+ protected:
+
+ private:
+  TString        fInputFile;        // name of input file with ESD filenames
+  TString        fFileName;         // name of current ESD file
+  bool           fConstrained;      // flag to set which momentum from ESD file will be use
+  int            fNumberofEvent;    // number of Events in ESD file
+  int            fCurEvent;         // number of current event
+  int            fCurRLEvent;       // Current simulated event
+  TChain*        fTree;             // ESD tree
+  AliESDEvent*   fEvent;            // ESD event
+  AliRunLoader*  fRunLoader;        // Run loader for kine reading 
+               
+  Float_t GetSigmaToVertex(const AliESDtrack* esdTrack);
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoEventReaderESDKine, 1)
+#endif
+
+    };
+  
+#endif
+
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelAllHiddenInfo.cxx b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelAllHiddenInfo.cxx
new file mode 100644 (file)
index 0000000..5f462c9
--- /dev/null
@@ -0,0 +1,319 @@
+//K//////////////////////////////////////////////////////////////////////////M//
+//K                                                                          M//
+//K AliFemtoModelAllHiddenInfo -                                             M//
+//K derived class inherits  the base class AliFemtoModelHiddenInfo           M//
+//K the hidden info for model calculations                                   M//
+//K Stores information needed for the weight generation -                    M//
+//K                                                                          M//
+//K in addition to  the base class AliFemtoModelHiddenInfo - the true        M//
+//K simulated momenta, freeze-out coordinates from model and particle PID    M//
+//K New information was added                                                M//
+//K 1. Mother ID                                                             M//
+//K 2. Mother 4-Momentum                                                     M//
+//K 3. Mother emission point 4-vector                                        M//
+//K 4. Childs IDs                                                            M//
+//K 5. Childs 4-Momentum                                                     M//
+//K--------------------------------------------------------------------------M//                                                                            //
+//K APR2008  Konstantin Mikhailov Konstantin.Mikhailov@itep.ru               M//
+//K                                                                          M//
+//K//////////////////////////////////////////////////////////////////////////M//
+#include "AliFemtoModelAllHiddenInfo.h"
+
+//_____________________________________________
+AliFemtoModelAllHiddenInfo::AliFemtoModelAllHiddenInfo() :
+  fTrueMomentumMother(0),
+  fEmissionPointMother(0),
+  fPDGPidMother(0),
+  fTrueMomentumChild1(0),
+  fTrueMomentumChild2(0),
+  fPDGPidChild1(0),
+  fPDGPidChild2(0)
+{
+  // Default constructor
+}
+//_____________________________________________
+AliFemtoModelAllHiddenInfo::AliFemtoModelAllHiddenInfo(const AliFemtoModelAllHiddenInfo &aInfo) :
+  AliFemtoModelHiddenInfo(aInfo),
+  fTrueMomentumMother(new AliFemtoLorentzVector(*(aInfo.fTrueMomentumMother))),
+  fEmissionPointMother(new AliFemtoLorentzVector(*(aInfo.fEmissionPointMother))),
+  fPDGPidMother(aInfo.fPDGPidMother),
+  fTrueMomentumChild1(new AliFemtoLorentzVector(*(aInfo.fTrueMomentumChild1))),
+  fTrueMomentumChild2(new AliFemtoLorentzVector(*(aInfo.fTrueMomentumChild2))),
+  fPDGPidChild1(aInfo.fPDGPidChild1),
+  fPDGPidChild2(aInfo.fPDGPidChild2)
+{
+  //
+  // Copy constructor
+  //
+}
+//_____________________________________________
+AliFemtoModelAllHiddenInfo::~AliFemtoModelAllHiddenInfo()
+{
+  // Destructor
+  delete fTrueMomentumMother;
+  delete fEmissionPointMother;
+  delete fTrueMomentumChild1;
+  delete fTrueMomentumChild2;
+}
+//_____________________________________________
+AliFemtoModelAllHiddenInfo& AliFemtoModelAllHiddenInfo::operator=(const AliFemtoModelAllHiddenInfo& aInfo)
+{
+  //
+  // assignment operator
+  //
+  if (this != &aInfo) {
+    AliFemtoModelHiddenInfo::operator=(aInfo);
+    delete fTrueMomentumMother;
+    fTrueMomentumMother = new AliFemtoLorentzVector(*(aInfo.fTrueMomentumMother));
+    delete fEmissionPointMother;
+    fEmissionPointMother = new AliFemtoLorentzVector(*(aInfo.fEmissionPointMother));
+    fPDGPidMother = aInfo.fPDGPidMother;
+    delete fTrueMomentumChild1;
+    fTrueMomentumChild1 = new AliFemtoLorentzVector(*(aInfo.fTrueMomentumChild1));
+    delete fTrueMomentumChild2;
+    fTrueMomentumChild2 = new AliFemtoLorentzVector(*(aInfo.fTrueMomentumChild2));
+    fPDGPidChild1 = aInfo.fPDGPidChild1;      
+    fPDGPidChild2 = aInfo.fPDGPidChild2;   
+  }
+  return *this;
+}
+//
+//   GET
+//
+//_____________________________________________
+AliFemtoLorentzVector *AliFemtoModelAllHiddenInfo::GetTrueMomentumMother() const
+{
+return fTrueMomentumMother;
+}
+//_____________________________________________
+AliFemtoLorentzVector *AliFemtoModelAllHiddenInfo::GetEmissionPointMother() const
+{
+  return fEmissionPoint;
+}
+//_____________________________________________
+  Int_t                AliFemtoModelAllHiddenInfo::GetPDGPidMother() const
+{
+  return fPDGPidMother;
+}
+//_____________________________________________
+AliFemtoLorentzVector *AliFemtoModelAllHiddenInfo::GetTrueMomentumChild1() const
+{
+return fTrueMomentumChild1;
+}
+//_____________________________________________
+AliFemtoLorentzVector *AliFemtoModelAllHiddenInfo::GetTrueMomentumChild2() const
+{
+return fTrueMomentumChild2;
+}
+//_____________________________________________
+  Int_t                AliFemtoModelAllHiddenInfo::GetPDGPidChild1() const
+{
+  return fPDGPidChild1;
+}
+//_____________________________________________
+  Int_t                AliFemtoModelAllHiddenInfo::GetPDGPidChild2() const
+{
+  return fPDGPidChild2;
+}
+//
+//   SET
+//
+//_____________________________________________
+//  Mother momentum
+//_____________________________________________
+void AliFemtoModelAllHiddenInfo::SetTrueMomentumMother(AliFemtoLorentzVector *aMomMother)
+{
+  // Set momentum from vector
+  if (fTrueMomentumMother) {
+    fTrueMomentumMother->SetX(aMomMother->px());
+    fTrueMomentumMother->SetY(aMomMother->py());
+    fTrueMomentumMother->SetZ(aMomMother->pz());
+    fTrueMomentumMother->SetT(aMomMother->e());
+  }
+  else {
+    fTrueMomentumMother = new AliFemtoLorentzVector(*aMomMother);
+  }
+}
+//_____________________________________________
+void AliFemtoModelAllHiddenInfo::SetTrueMomentumMother(const AliFemtoLorentzVector& aMomMother)
+{
+  // Set momentum from vector and energy
+  if (fTrueMomentumMother) {
+    fTrueMomentumMother->SetX(aMomMother.px());
+    fTrueMomentumMother->SetY(aMomMother.py());
+    fTrueMomentumMother->SetZ(aMomMother.pz());
+    fTrueMomentumMother->SetT(aMomMother.e());
+  }
+  else {
+    fTrueMomentumMother = new AliFemtoLorentzVector();
+    *fTrueMomentumMother = aMomMother;
+  }
+}
+//_____________________________________________
+void AliFemtoModelAllHiddenInfo::SetTrueMomentumMother(Double_t aMotherPx, Double_t aMotherPy, Double_t aMotherPz, Double_t aMotherE)
+{
+  // Set momentum from components and energy
+  if (!fTrueMomentumMother) fTrueMomentumMother = new AliFemtoLorentzVector();
+    fTrueMomentumMother->SetX(aMotherPx);
+    fTrueMomentumMother->SetY(aMotherPy);
+    fTrueMomentumMother->SetZ(aMotherPz);
+    fTrueMomentumMother->SetT(aMotherE);
+}
+//_____________________________________________
+//   Mother Emissin Point
+//_____________________________________________
+void                   AliFemtoModelAllHiddenInfo::SetEmissionPointMother(AliFemtoLorentzVector *aPos)
+{
+  // Set position from vector
+  if (fEmissionPointMother) {
+    fEmissionPointMother->SetX(aPos->px());
+    fEmissionPointMother->SetY(aPos->py());
+    fEmissionPointMother->SetZ(aPos->pz());
+    fEmissionPointMother->SetT(aPos->e());
+  }
+  else {
+    fEmissionPointMother = new AliFemtoLorentzVector(*aPos);
+  }
+}
+//_____________________________________________
+void                   AliFemtoModelAllHiddenInfo::SetEmissionPointMother(const AliFemtoLorentzVector& aPos)
+{
+  // Set position from vector
+  if (fEmissionPointMother) {
+    fEmissionPointMother->SetX(aPos.px());
+    fEmissionPointMother->SetY(aPos.py());
+    fEmissionPointMother->SetZ(aPos.pz());
+    fEmissionPointMother->SetT(aPos.e());
+  }
+  else {
+    fEmissionPointMother = new AliFemtoLorentzVector();
+    *fEmissionPointMother = aPos;
+  }
+}
+//_____________________________________________
+void                   AliFemtoModelAllHiddenInfo::SetEmissionPointMother(Double_t aRx, Double_t aRy, Double_t aRz, Double_t aT)
+{
+  // Set position from components
+  if (fEmissionPointMother) {
+    fEmissionPointMother->SetX(aRx);
+    fEmissionPointMother->SetY(aRy);
+    fEmissionPointMother->SetZ(aRz);
+    fEmissionPointMother->SetT(aT);
+  }
+  else {
+    fEmissionPointMother = new AliFemtoLorentzVector(aRx, aRy, aRz, aT); 
+  }
+}
+//_____________________________________________
+//  Mother PID
+//_____________________________________________
+void                   AliFemtoModelAllHiddenInfo::SetPDGPidMother(Int_t aPidMother)
+{
+  fPDGPidMother = aPidMother;
+}
+//_____________________________________________
+//  Child1 momentum
+//_____________________________________________
+void AliFemtoModelAllHiddenInfo::SetTrueMomentumChild1(AliFemtoLorentzVector *aMomChild1)
+{
+  // Set momentum from vector
+  if (fTrueMomentumChild1) {
+    fTrueMomentumChild1->SetX(aMomChild1->px());
+    fTrueMomentumChild1->SetY(aMomChild1->py());
+    fTrueMomentumChild1->SetZ(aMomChild1->pz());
+    fTrueMomentumChild1->SetT(aMomChild1->e());
+  }
+  else {
+    fTrueMomentumChild1 = new AliFemtoLorentzVector(*aMomChild1);
+  }
+}
+//_____________________________________________
+void AliFemtoModelAllHiddenInfo::SetTrueMomentumChild1(const AliFemtoLorentzVector& aMomChild1)
+{
+  // Set momentum from vector and energy
+  if (fTrueMomentumChild1) {
+    fTrueMomentumChild1->SetX(aMomChild1.px());
+    fTrueMomentumChild1->SetY(aMomChild1.py());
+    fTrueMomentumChild1->SetZ(aMomChild1.pz());
+    fTrueMomentumChild1->SetT(aMomChild1.e());
+  }
+  else {
+    fTrueMomentumChild1 = new AliFemtoLorentzVector();
+    *fTrueMomentumChild1 = aMomChild1;
+  }
+}
+//_____________________________________________
+void AliFemtoModelAllHiddenInfo::SetTrueMomentumChild1(Double_t aChild1Px, Double_t aChild1Py, Double_t aChild1Pz, Double_t aChild1E)
+{
+  // Set momentum from components and energy
+  if (!fTrueMomentumChild1) fTrueMomentumChild1 = new AliFemtoLorentzVector();
+    fTrueMomentumChild1->SetX(aChild1Px);
+    fTrueMomentumChild1->SetY(aChild1Py);
+    fTrueMomentumChild1->SetZ(aChild1Pz);
+    fTrueMomentumChild1->SetT(aChild1E);
+}
+//_____________________________________________
+//  Child2 momentum
+//_____________________________________________
+void AliFemtoModelAllHiddenInfo::SetTrueMomentumChild2(AliFemtoLorentzVector *aMomChild2)
+{
+  // Set momentum from vector
+  if (fTrueMomentumChild2) {
+    fTrueMomentumChild2->SetX(aMomChild2->px());
+    fTrueMomentumChild2->SetY(aMomChild2->py());
+    fTrueMomentumChild2->SetZ(aMomChild2->pz());
+    fTrueMomentumChild2->SetT(aMomChild2->e());
+  }
+  else {
+    fTrueMomentumChild2 = new AliFemtoLorentzVector(*aMomChild2);
+  }
+}
+//_____________________________________________
+void AliFemtoModelAllHiddenInfo::SetTrueMomentumChild2(const AliFemtoLorentzVector& aMomChild2)
+{
+  // Set momentum from vector and energy
+  if (fTrueMomentumChild2) {
+    fTrueMomentumChild2->SetX(aMomChild2.px());
+    fTrueMomentumChild2->SetY(aMomChild2.py());
+    fTrueMomentumChild2->SetZ(aMomChild2.pz());
+    fTrueMomentumChild2->SetT(aMomChild2.e());
+  }
+  else {
+    fTrueMomentumChild2 = new AliFemtoLorentzVector();
+    *fTrueMomentumChild2 = aMomChild2;
+  }
+}
+//_____________________________________________
+void AliFemtoModelAllHiddenInfo::SetTrueMomentumChild2(Double_t aChild2Px, Double_t aChild2Py, Double_t aChild2Pz, Double_t aChild2E)
+{
+  // Set momentum from components and energy
+  if (!fTrueMomentumChild2) fTrueMomentumChild2 = new AliFemtoLorentzVector();
+    fTrueMomentumChild2->SetX(aChild2Px);
+    fTrueMomentumChild2->SetY(aChild2Py);
+    fTrueMomentumChild2->SetZ(aChild2Pz);
+    fTrueMomentumChild2->SetT(aChild2E);
+}
+//_____________________________________________
+//  Child1 PID
+//_____________________________________________
+void                   AliFemtoModelAllHiddenInfo::SetPDGPidChild1(Int_t aPidChild1)
+{
+  fPDGPidMother = aPidChild1;
+}
+//_____________________________________________
+//  Child2 PID
+//_____________________________________________
+void                   AliFemtoModelAllHiddenInfo::SetPDGPidChild2(Int_t aPidChild2)
+{
+  fPDGPidMother = aPidChild2;
+}
+//
+//  RETURN COPY
+//
+//_____________________________________________
+ AliFemtoModelHiddenInfo* AliFemtoModelAllHiddenInfo::GetParticleHiddenInfo() const
+{
+  // return copy of this hidden info
+  AliFemtoModelAllHiddenInfo* tBuf = new AliFemtoModelAllHiddenInfo(*this);
+  return tBuf;
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelAllHiddenInfo.h b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelAllHiddenInfo.h
new file mode 100644 (file)
index 0000000..cbe55da
--- /dev/null
@@ -0,0 +1,83 @@
+//K//////////////////////////////////////////////////////////////////////////M//
+//K                                                                          M//
+//K AliFemtoModelAllHiddenInfo -                                             M//
+//K derived class inherits  the base class AliFemtoModelHiddenInfo           M//
+//K the hidden info for model calculations                                   M//
+//K Stores information needed for the weight generation -                    M//
+//K                                                                          M//
+//K in addition to  the base class AliFemtoModelHiddenInfo - the true        M//
+//K simulated momenta, freeze-out coordinates from model and particle PID    M//
+//K New information was added                                                M//
+//K 1. Mother ID                                                             M//
+//K 2. Mother 4-Momentum                                                     M//
+//K 3. Mother emission point 4-vector                                        M//
+//K 4. Childs IDs                                                            M//
+//K 5. Childs 4-Momentum                                                     M//
+//K                                                                          M//
+//K//////////////////////////////////////////////////////////////////////////M//
+#ifndef ALIFEMTOMODELALLHIDDENINFO_H
+#define ALIFEMTOMODELALLHIDDENINFO_H
+
+#include <TH1D.h>
+#include "AliFemtoTypes.h"
+#include "AliFemtoThreeVector.h"
+#include "AliFemtoLorentzVector.h"
+#include "AliFemtoHiddenInfo.h"
+#include "AliFemtoModelHiddenInfo.h"
+
+class AliFemtoModelAllHiddenInfo : public AliFemtoModelHiddenInfo{
+
+public:
+  AliFemtoModelAllHiddenInfo();
+  AliFemtoModelAllHiddenInfo(const AliFemtoModelAllHiddenInfo &aInfo);
+  virtual ~AliFemtoModelAllHiddenInfo();
+
+  AliFemtoModelAllHiddenInfo& operator=(const AliFemtoModelAllHiddenInfo& aInfo);
+
+  AliFemtoLorentzVector *GetTrueMomentumMother() const;
+  AliFemtoLorentzVector *GetEmissionPointMother() const;
+  Int_t                  GetPDGPidMother() const;
+  AliFemtoLorentzVector *GetTrueMomentumChild1() const;
+  AliFemtoLorentzVector *GetTrueMomentumChild2() const;
+  Int_t                  GetPDGPidChild1() const;
+  Int_t                  GetPDGPidChild2() const;
+
+  void                   SetTrueMomentumMother(AliFemtoLorentzVector *aMomMother);
+  void                   SetTrueMomentumMother(const AliFemtoLorentzVector& aMomMother);
+  void                   SetTrueMomentumMother(Double_t aMotherPx, Double_t aMotherPy, Double_t aMotherPz, Double_t aMotherE);
+  void                   SetEmissionPointMother(AliFemtoLorentzVector *aPos);
+  void                   SetEmissionPointMother(const AliFemtoLorentzVector& aPos);
+  void                   SetEmissionPointMother(Double_t aRx, Double_t aRy, Double_t aRz, Double_t aT);
+  void                   SetPDGPidMother(Int_t aPidMother);
+  void                   SetTrueMomentumChild1(AliFemtoLorentzVector *aMomChild1);
+  void                   SetTrueMomentumChild1(const AliFemtoLorentzVector& aMomChild1);
+  void                   SetTrueMomentumChild1(Double_t aChild1Px, Double_t aChild1Py, Double_t aChild1Pz, Double_t aChild1E);
+  void                   SetTrueMomentumChild2(AliFemtoLorentzVector *aMomChild2);
+  void                   SetTrueMomentumChild2(const AliFemtoLorentzVector& aMomChild2);
+  void                   SetTrueMomentumChild2(Double_t aChild2Px, Double_t aChild2Py, Double_t aChild2Pz, Double_t aChild2E);
+  void                   SetPDGPidChild1(Int_t aPidChild1);
+  void                   SetPDGPidChild2(Int_t aPidChild2);
+
+
+// !!! MANDATORY !!!
+// --- Copy the hidden info from AliFemtoTrack to AliFemtoParticle
+  virtual AliFemtoModelHiddenInfo* Clone() const;
+ protected:
+  virtual AliFemtoModelHiddenInfo* GetParticleHiddenInfo() const;
+
+  AliFemtoLorentzVector *fTrueMomentumMother;  // True (simulated) momentum of Mother (100.,100.,100.,100. if Mother -1)
+  AliFemtoLorentzVector *fEmissionPointMother; // Emission point coordinates Mother;
+  Int_t                  fPDGPidMother;        // True PID of the particle mother
+  AliFemtoLorentzVector *fTrueMomentumChild1;  // True (simulated) momentum of Child1  (200.,200.,200.,200. if Child1 -1)
+  AliFemtoLorentzVector *fTrueMomentumChild2;  // True (simulated) momentum of Child2  (200.,200.,200.,200. if Child2 -1)
+  Int_t                  fPDGPidChild1;        // True PID of the particle child1 (-1 if is not)
+  Int_t                  fPDGPidChild2;        // True PID of the particle child2 (-1 if is not)
+
+};
+//_______________________________________
+inline AliFemtoModelHiddenInfo* AliFemtoModelAllHiddenInfo::Clone() const{
+  // return exact copy of this hidden info
+  return GetParticleHiddenInfo();
+}
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelBPLCMSCorrFctn.cxx b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelBPLCMSCorrFctn.cxx
new file mode 100644 (file)
index 0000000..d086e5f
--- /dev/null
@@ -0,0 +1,246 @@
+////////////////////////////////////////////////////////////////////////////////
+///                                                                          ///
+/// AliFemtoModelBPLCMSCorrFctn - the class for correlation function which   ///
+/// uses the model framework and weight generation and calculated the 3D     ///
+/// correlation function in the Bertsh-Pratt LCMS system                     ///
+/// Authors: Adam Kisiel, kisiel@mps.ohio-state.edu                          ///
+///                                                                          ///
+////////////////////////////////////////////////////////////////////////////////
+#include "AliFemtoModelBPLCMSCorrFctn.h"
+#include "AliFemtoPair.h"
+#include "AliFemtoModelManager.h"
+#include "AliFemtoKTPairCut.h"
+#include "AliFemtoAnalysisReactionPlane.h"
+#include <cstdio>
+
+#ifdef __ROOT__ 
+ClassImp(AliFemtoModelBPLCMSCorrFctn)
+#endif
+
+//____________________________
+AliFemtoModelBPLCMSCorrFctn::AliFemtoModelBPLCMSCorrFctn(char* title, const int& nbins, const float& QLo, const float& QHi)
+  :
+  AliFemtoModelCorrFctn(title, nbins, QLo, QHi),
+  fNumerator3DTrue(0),
+  fNumerator3DFake(0),
+  fDenominator3D(0),
+  fQinvHisto(0),
+  fPairCut(0),
+  fUseRPSelection(0)
+{
+  // set up true numerator
+  char tTitNumT[101] = "Num3DTrue";
+  strncat(tTitNumT,title, 100);
+  fNumerator3DTrue = new TH3D(tTitNumT,title,nbins,QLo,QHi,nbins,QLo,QHi,nbins,QLo,QHi);
+  // set up fake numerator
+  char tTitNumF[101] = "Num3DFake";
+  strncat(tTitNumF,title, 100);
+  fNumerator3DFake = new TH3D(tTitNumF,title,nbins,QLo,QHi,nbins,QLo,QHi,nbins,QLo,QHi);
+  // set up denominator
+  char tTitDen[101] = "Den3D";
+  strncat(tTitDen,title, 100);
+  fDenominator3D = new TH3D(tTitDen,title,nbins,QLo,QHi,nbins,QLo,QHi,nbins,QLo,QHi);
+  // set up ave qInv
+  char tTitQinv[101] = "Qinv";
+  strncat(tTitQinv,title, 100);
+  fQinvHisto = new TH3D(tTitQinv,title,nbins,QLo,QHi,nbins,QLo,QHi,nbins,QLo,QHi);
+
+  // to enable error bar calculation...
+  fNumerator3DTrue->Sumw2();
+  fNumerator3DFake->Sumw2();
+  fDenominator3D->Sumw2();
+}
+
+AliFemtoModelBPLCMSCorrFctn::AliFemtoModelBPLCMSCorrFctn(const AliFemtoModelBPLCMSCorrFctn& aCorrFctn) :
+  AliFemtoModelCorrFctn(aCorrFctn),
+  fNumerator3DTrue(0),
+  fNumerator3DFake(0),
+  fDenominator3D(0),
+  fQinvHisto(0),
+  fPairCut(0),
+  fUseRPSelection(0)
+{
+  // Copy constructor
+  fNumerator3DTrue = new TH3D(*aCorrFctn.fNumerator3DTrue);
+  fNumerator3DFake = new TH3D(*aCorrFctn.fNumerator3DFake);
+  fDenominator3D   = new TH3D(*aCorrFctn.fDenominator3D);
+  fQinvHisto       = new TH3D(*aCorrFctn.fQinvHisto);
+  fPairCut         = aCorrFctn.fPairCut->Clone();
+}
+//____________________________
+AliFemtoModelBPLCMSCorrFctn::~AliFemtoModelBPLCMSCorrFctn()
+{
+  // destructor
+  if (fNumeratorTrue) delete fNumeratorTrue;
+  if (fNumeratorFake) delete fNumeratorFake;
+  if (fDenominator) delete fDenominator;
+  delete fNumerator3DTrue;
+  delete fNumerator3DFake;
+  delete fDenominator3D;
+  delete fQinvHisto;
+  if (fPairCut) delete fPairCut;
+}
+//_________________________
+AliFemtoModelBPLCMSCorrFctn& AliFemtoModelBPLCMSCorrFctn::operator=(const AliFemtoModelBPLCMSCorrFctn& aCorrFctn)
+{
+  // Assignment operator
+  if (this == &aCorrFctn)
+    return *this;
+  if (fNumerator3DTrue) delete fNumerator3DTrue;
+  fNumerator3DTrue = new TH3D(*aCorrFctn.fNumerator3DTrue);
+  if (fNumerator3DFake) delete fNumerator3DFake;
+  fNumerator3DFake = new TH3D(*aCorrFctn.fNumerator3DFake);
+  if (fDenominator3D) delete fDenominator3D;
+  fDenominator3D = new TH3D(*aCorrFctn.fDenominator3D);
+  if (fQinvHisto) delete fQinvHisto;
+  fQinvHisto = new TH3D(*aCorrFctn.fQinvHisto);
+  fPairCut = aCorrFctn.fPairCut->Clone();
+
+  return *this;
+}
+
+//_________________________
+void AliFemtoModelBPLCMSCorrFctn::Write(){
+  // Write out data histograms
+  AliFemtoModelCorrFctn::Write();
+  fNumerator3DTrue->Write();
+  fNumerator3DFake->Write();
+  fDenominator3D->Write();
+  fQinvHisto->Write();
+}
+//________________________
+TList* AliFemtoModelBPLCMSCorrFctn::GetOutputList()
+{
+  // Prepare the list of objects to be written to the output
+  TList *tOutputList = AliFemtoModelCorrFctn::GetOutputList();
+
+  tOutputList->Add(fNumerator3DTrue); 
+  tOutputList->Add(fNumerator3DFake);  
+  tOutputList->Add(fDenominator3D);  
+  tOutputList->Add(fQinvHisto);  
+
+  return tOutputList;
+}
+
+//_________________________
+void AliFemtoModelBPLCMSCorrFctn::Finish(){
+  fQinvHisto->Divide(fDenominator);
+}
+
+//____________________________
+AliFemtoString AliFemtoModelBPLCMSCorrFctn::Report(){
+  // Prepare a report from the execution
+  string stemp = "LCMS Frame Bertsch-Pratt 3D Model Correlation Function Report:\n";
+  char ctemp[100];
+  snprintf(ctemp , 100, "Number of entries in numerator:\t%E\n",fNumeratorTrue->GetEntries());
+  stemp += ctemp;
+  snprintf(ctemp , 100, "Number of entries in denominator:\t%E\n",fDenominator->GetEntries());
+  stemp += ctemp;
+  /*  if (fCorrection)
+      {
+      float radius = fCorrection->GetRadius();
+      snprintf(ctemp , 100, "Coulomb correction used radius of\t%E\n",radius);
+      }
+      else
+      {
+      snprintf(ctemp , 100, "No Coulomb Correction applied to this CorrFctn\n");
+      }
+      stemp += ctemp;
+  */
+
+  //  
+  AliFemtoString returnThis = stemp;
+  return returnThis;
+}
+//____________________________
+void AliFemtoModelBPLCMSCorrFctn::AddRealPair( AliFemtoPair* pair)
+{
+  // Store a real pair in numerator
+  if (fPairCut){
+    if (fUseRPSelection) {
+      AliFemtoKTPairCut *ktc = dynamic_cast<AliFemtoKTPairCut *>(fPairCut);
+      if (!ktc) { 
+       cout << "RP aware cut requested, but not connected to the CF" << endl;
+       if (!(fPairCut->Pass(pair))) return;
+      }
+      else {
+       AliFemtoAnalysisReactionPlane *arp = dynamic_cast<AliFemtoAnalysisReactionPlane *> (HbtAnalysis());
+       if (!arp) {
+         cout << "RP aware cut requested, but not connected to the CF" << endl;
+         if (!(fPairCut->Pass(pair))) return;
+       }
+       else if (!(ktc->Pass(pair, arp->GetCurrentReactionPlane()))) return;
+      }
+    }
+    else
+      if (!(fPairCut->Pass(pair))) return;
+  }
+//   if (fPairCut){
+//     if (!(fPairCut->Pass(pair))) return;
+//   }
+  
+  Double_t weight = fManager->GetWeight(pair);
+
+  double qOut = (pair->QOutCMS());
+  double qSide = (pair->QSideCMS());
+  double qLong = (pair->QLongCMS());
+
+  fNumerator3DTrue->Fill(qOut, qSide, qLong, weight);
+  fNumeratorTrue->Fill(pair->QInv(), weight);
+}
+//____________________________
+void AliFemtoModelBPLCMSCorrFctn::AddMixedPair( AliFemtoPair* pair){
+  // store mixed pair in denominator
+  if (fPairCut){
+    if (fUseRPSelection) {
+      AliFemtoKTPairCut *ktc = dynamic_cast<AliFemtoKTPairCut *>(fPairCut);
+      if (!ktc) { 
+       cout << "RP aware cut requested, but not connected to the CF" << endl;
+       if (!(fPairCut->Pass(pair))) return;
+      }
+      else {
+       AliFemtoAnalysisReactionPlane *arp = dynamic_cast<AliFemtoAnalysisReactionPlane *> (HbtAnalysis());
+       if (!arp) {
+         cout << "RP aware cut requested, but not connected to the CF" << endl;
+         if (!(fPairCut->Pass(pair))) return;
+       }
+       else if (!(ktc->Pass(pair, arp->GetCurrentReactionPlane()))) return;
+      }
+    }
+    else
+      if (!(fPairCut->Pass(pair))) return;
+  }
+//   if (fPairCut){
+//     if (!(fPairCut->Pass(pair))) return;
+//   }
+
+  Double_t weight = fManager->GetWeight(pair);
+
+  double qOut = (pair->QOutCMS());
+  double qSide = (pair->QSideCMS());
+  double qLong = (pair->QLongCMS());
+
+  fNumerator3DFake->Fill(qOut, qSide, qLong, weight);
+  fDenominator3D->Fill(qOut, qSide, qLong, 1.0);
+  fNumeratorFake->Fill(pair->QInv(), weight);
+  fDenominator->Fill(pair->QInv(), 1.0);
+
+}
+//_______________________
+AliFemtoModelCorrFctn* AliFemtoModelBPLCMSCorrFctn::Clone()
+{
+  // Clone the correlation function
+  AliFemtoModelBPLCMSCorrFctn *tCopy = new AliFemtoModelBPLCMSCorrFctn(*this);
+  
+  return tCopy;
+}
+
+void AliFemtoModelBPLCMSCorrFctn::SetSpecificPairCut(AliFemtoPairCut* aCut)
+{
+  fPairCut = aCut;
+}
+
+void AliFemtoModelBPLCMSCorrFctn::SetUseRPSelection(unsigned short aRPSel)
+{
+  fUseRPSelection = aRPSel;
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelBPLCMSCorrFctn.h b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelBPLCMSCorrFctn.h
new file mode 100644 (file)
index 0000000..ca92456
--- /dev/null
@@ -0,0 +1,63 @@
+////////////////////////////////////////////////////////////////////////////////
+///                                                                          ///
+/// AliFemtoModelBPLCMSCorrFctn - the class for correlation function which   ///
+/// uses the model framework and weight generation and calculated the 3D     ///
+/// correlation function in the Bertsh-Pratt LCMS system                     ///
+/// Authors: Adam Kisiel, kisiel@mps.ohio-state.edu                          ///
+///                                                                          ///
+////////////////////////////////////////////////////////////////////////////////
+#ifndef ALIFEMTOMODELBPLCMSCORRFCTN_H
+#define ALIFEMTOMODELBPLCMSCORRFCTN_H
+
+#include "AliFemtoCorrFctn.h"
+#include "AliFemtoModelCorrFctn.h"
+#include "AliFemtoPairCut.h"
+#include "TH3D.h"
+
+class AliFemtoModelBPLCMSCorrFctn : public AliFemtoModelCorrFctn {
+ public:
+  AliFemtoModelBPLCMSCorrFctn()  :
+    AliFemtoModelCorrFctn(),
+    fNumerator3DTrue(0),
+    fNumerator3DFake(0),
+    fDenominator3D(0),
+    fQinvHisto(0),
+    fPairCut(0),
+    fUseRPSelection(0){}
+  AliFemtoModelBPLCMSCorrFctn(char* title, const int& nbins, const float& QLo, const float& QHi);
+  AliFemtoModelBPLCMSCorrFctn(const AliFemtoModelBPLCMSCorrFctn& aCorrFctn);
+  virtual ~AliFemtoModelBPLCMSCorrFctn();
+
+  AliFemtoModelBPLCMSCorrFctn& operator=(const AliFemtoModelBPLCMSCorrFctn& aCorrFctn);
+
+  virtual AliFemtoString Report();
+  virtual void AddRealPair(AliFemtoPair* pair);
+  virtual void AddMixedPair(AliFemtoPair* pair);
+
+  virtual void Finish();
+
+  virtual void Write();
+  virtual TList* GetOutputList();
+
+  void SetSpecificPairCut(AliFemtoPairCut* aCut);
+  void SetUseRPSelection(unsigned short aRPSel);
+
+  virtual AliFemtoModelCorrFctn* Clone();
+
+protected:
+  TH3D* fNumerator3DTrue;            // 3D Numerator with pairs from same event only
+  TH3D* fNumerator3DFake;            // 3D Numerator with pairs from mixed events
+  TH3D* fDenominator3D;              // 3D Denominator with the weight of 1.0
+
+  TH3D* fQinvHisto;                  // Averag qinv histogram
+
+  AliFemtoPairCut* fPairCut;    //! this is a PairCut specific to THIS CorrFctn, not the Analysis
+
+  unsigned short fUseRPSelection;  // The pair cut uses RP selection
+#ifdef __ROOT__
+  ClassDef(AliFemtoModelBPLCMSCorrFctn, 1)
+#endif
+};
+
+#endif
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctn3DLCMSSpherical.cxx b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctn3DLCMSSpherical.cxx
new file mode 100644 (file)
index 0000000..775d95a
--- /dev/null
@@ -0,0 +1,179 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFemtoModelCorrFctn3DLCMSSpherical: a class to calculate 3D correlation //
+// for pairs of identical particles, binned in spherical coordinates.    //
+// In analysis the function should be first created in a macro, then     //
+// added to the analysis, and at the end of the macro the procedure to   //
+// write out histograms should be called.                                //
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+
+#include "AliFemtoModelCorrFctn3DLCMSSpherical.h"
+#include "AliFemtoModelManager.h"
+#include <TMath.h>
+#include <cstdio>
+
+#ifdef __ROOT__ 
+ClassImp(AliFemtoModelCorrFctn3DLCMSSpherical)
+#endif
+
+//____________________________
+  AliFemtoModelCorrFctn3DLCMSSpherical::AliFemtoModelCorrFctn3DLCMSSpherical(char* title, const int& nqbins, const float& QLo, const float& QHi, const int& nphibins, const int& ncthetabins):
+  fTrueNumeratorSph(0),
+  fFakeNumeratorSph(0),
+  fDenominatorSph(0),
+  fPairCut(0x0)
+{
+  // set up numerator
+  char tTitNum[101] = "NumTrue";
+  strncat(tTitNum,title, 100);
+  fTrueNumeratorSph = new TH3D(tTitNum,title,nqbins,QLo,QHi,nphibins,-TMath::Pi(),TMath::Pi(),ncthetabins,-1.0,1.0);
+  // set up numerator
+  char tTitNumF[101] = "NumFake";
+  strncat(tTitNumF,title, 100);
+  fFakeNumeratorSph = new TH3D(tTitNumF,title,nqbins,QLo,QHi,nphibins,-TMath::Pi(),TMath::Pi(),ncthetabins,-1.0,1.0);
+  // set up denominator
+  char tTitDen[101] = "Den";
+  strncat(tTitDen,title, 100);
+  fDenominatorSph = new TH3D(tTitDen,title,nqbins,QLo,QHi,nphibins,-TMath::Pi(),TMath::Pi(),ncthetabins,-1.0,1.0);
+
+  // to enable error bar calculation...
+  fTrueNumeratorSph->Sumw2();
+  fFakeNumeratorSph->Sumw2();
+  fDenominatorSph->Sumw2();
+}
+
+AliFemtoModelCorrFctn3DLCMSSpherical::AliFemtoModelCorrFctn3DLCMSSpherical(const AliFemtoModelCorrFctn3DLCMSSpherical& aCorrFctn) :
+  AliFemtoModelCorrFctn(),
+  fTrueNumeratorSph(0),
+  fFakeNumeratorSph(0),
+  fDenominatorSph(0),
+  fPairCut(0x0)
+{
+  // Copy constructor
+  fTrueNumeratorSph = new TH3D(*aCorrFctn.fTrueNumeratorSph);
+  fFakeNumeratorSph = new TH3D(*aCorrFctn.fFakeNumeratorSph);
+  fDenominatorSph = new TH3D(*aCorrFctn.fDenominatorSph);
+  fPairCut = aCorrFctn.fPairCut;
+}
+//____________________________
+AliFemtoModelCorrFctn3DLCMSSpherical::~AliFemtoModelCorrFctn3DLCMSSpherical(){
+  // Destructor
+  delete fTrueNumeratorSph;
+  delete fFakeNumeratorSph;
+  delete fDenominatorSph;
+}
+//_________________________
+AliFemtoModelCorrFctn3DLCMSSpherical& AliFemtoModelCorrFctn3DLCMSSpherical::operator=(const AliFemtoModelCorrFctn3DLCMSSpherical& aCorrFctn)
+{
+  // assignment operator
+  if (this == &aCorrFctn)
+    return *this;
+
+  if (fTrueNumeratorSph) delete fTrueNumeratorSph;
+  fTrueNumeratorSph = new TH3D(*aCorrFctn.fTrueNumeratorSph);
+  if (fFakeNumeratorSph) delete fFakeNumeratorSph;
+  fFakeNumeratorSph = new TH3D(*aCorrFctn.fFakeNumeratorSph);
+  if (fDenominatorSph) delete fDenominatorSph;
+  fDenominatorSph = new TH3D(*aCorrFctn.fDenominatorSph);
+  
+  fPairCut = aCorrFctn.fPairCut;
+  
+  return *this;
+}
+
+//_________________________
+void AliFemtoModelCorrFctn3DLCMSSpherical::WriteOutHistos(){
+  // Write out all histograms to file
+  fTrueNumeratorSph->Write();
+  fFakeNumeratorSph->Write();
+  fDenominatorSph->Write();
+}
+//______________________________
+TList* AliFemtoModelCorrFctn3DLCMSSpherical::GetOutputList()
+{
+  // Prepare the list of objects to be written to the output
+  TList *tOutputList = new TList();
+
+  tOutputList->Add(fTrueNumeratorSph); 
+  tOutputList->Add(fFakeNumeratorSph); 
+  tOutputList->Add(fDenominatorSph);  
+
+  return tOutputList;
+}
+
+//_________________________
+void AliFemtoModelCorrFctn3DLCMSSpherical::Finish(){
+  // here is where we should normalize, fit, etc...
+}
+
+//____________________________
+AliFemtoString AliFemtoModelCorrFctn3DLCMSSpherical::Report(){
+  // Construct the report
+  string stemp = "LCMS Frame Spherical 3D Model Correlation Function Report:\n";
+  char ctemp[100];
+  snprintf(ctemp , 100, "Number of entries in numerator:\t%E\n",fTrueNumeratorSph->GetEntries());
+  stemp += ctemp;
+  snprintf(ctemp , 100, "Number of entries in denominator:\t%E\n",fDenominatorSph->GetEntries());
+  stemp += ctemp;
+
+  if (fPairCut){
+    snprintf(ctemp , 100, "Here is the PairCut specific to this CorrFctn\n");
+    stemp += ctemp;
+    stemp += fPairCut->Report();
+  }
+  else{
+    snprintf(ctemp , 100, "No PairCut specific to this CorrFctn\n");
+    stemp += ctemp;
+  }
+
+  //  
+  AliFemtoString returnThis = stemp;
+  return returnThis;
+}
+//____________________________
+void AliFemtoModelCorrFctn3DLCMSSpherical::AddRealPair( AliFemtoPair* pair){
+  // perform operations on real pairs
+  if (fPairCut){
+    if (!(fPairCut->Pass(pair))) return;
+  }
+
+  Double_t weight = fManager->GetWeight(pair);
+
+
+  double tKO = (pair->QOutCMS());
+  double tKS = (pair->QSideCMS());
+  double tKL = (pair->QLongCMS());
+
+  double tKR = sqrt(tKO*tKO + tKS*tKS + tKL*tKL);
+  double tKC;
+  if ( fabs(tKR) < 1e-10 ) tKC = 0.0;
+  else tKC=tKL/tKR;
+  double tKP=atan2(tKS,tKO);
+
+  fTrueNumeratorSph->Fill(tKR,tKP,tKC,weight);
+}
+//____________________________
+void AliFemtoModelCorrFctn3DLCMSSpherical::AddMixedPair( AliFemtoPair* pair){
+  // perform operations on mixed pairs
+  if (fPairCut){
+    if (!(fPairCut->Pass(pair))) return;
+  }
+
+  Double_t weight = fManager->GetWeight(pair);
+
+  double tKO = (pair->QOutCMS());
+  double tKS = (pair->QSideCMS());
+  double tKL = (pair->QLongCMS());
+
+  double tKR = sqrt(tKO*tKO + tKS*tKS + tKL*tKL);
+  double tKC;
+  if ( fabs(tKR) < 1e-10 ) tKC = 0.0;
+  else tKC=tKL/tKR;
+  double tKP=atan2(tKS,tKO);
+
+  fFakeNumeratorSph->Fill(tKR,tKP,tKC,weight);
+  fDenominatorSph->Fill(tKR,tKP,tKC);
+}
+
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctn3DLCMSSpherical.h b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctn3DLCMSSpherical.h
new file mode 100644 (file)
index 0000000..f3814f4
--- /dev/null
@@ -0,0 +1,53 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFemtoModelCorrFctn3DSpherical: a class to calculate 3D correlation //
+// for pairs of identical particles, binned in spherical coordinates     //
+// (q_inv, phi, cos(theta))                                              //
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+
+#ifndef ALIFEMTOMODELCORRFCTN3DLCMSSPHERICAL_H
+#define ALIFEMTOMODELCORRFCTN3DLCMSSPHERICAL_H
+
+#include "AliFemtoModelCorrFctn.h"
+#include "AliFemtoPairCut.h"
+#include "TH3D.h"
+
+class AliFemtoModelCorrFctn3DLCMSSpherical : public AliFemtoModelCorrFctn {
+public:
+  AliFemtoModelCorrFctn3DLCMSSpherical(char* title, 
+                             const int& nqbins, const float& QLo, const float& QHi,
+                             const int& nphibins, const int& ncthetabins);
+  AliFemtoModelCorrFctn3DLCMSSpherical(const AliFemtoModelCorrFctn3DLCMSSpherical& aCorrFctn);
+  virtual ~AliFemtoModelCorrFctn3DLCMSSpherical();
+
+  AliFemtoModelCorrFctn3DLCMSSpherical& operator=(const AliFemtoModelCorrFctn3DLCMSSpherical& aCorrFctn);
+
+  virtual AliFemtoString Report();
+  virtual void AddRealPair( AliFemtoPair* aPair);
+  virtual void AddMixedPair( AliFemtoPair* aPair);
+
+  virtual void Finish();
+
+  void WriteOutHistos();
+  virtual TList* GetOutputList();
+
+  void SetSpecificPairCut(AliFemtoPairCut* aCut);
+
+private:
+  // here are a whole bunch of histos that get filled if we do resolution correction
+  TH3D* fTrueNumeratorSph;         // numerator
+  TH3D* fFakeNumeratorSph;         // numerator
+  TH3D* fDenominatorSph;       // denominator
+
+  AliFemtoPairCut* fPairCut;    //! this is a PairCut specific to THIS CorrFctn, not the Analysis
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoModelCorrFctn3DLCMSSpherical, 1)
+#endif
+};
+
+inline  void AliFemtoModelCorrFctn3DLCMSSpherical::SetSpecificPairCut(AliFemtoPairCut* pc){fPairCut=pc;}
+
+#endif
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctn3DSpherical.cxx b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctn3DSpherical.cxx
new file mode 100644 (file)
index 0000000..79c0578
--- /dev/null
@@ -0,0 +1,180 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFemtoModelCorrFctn3DSpherical: a class to calculate 3D correlation //
+// for pairs of identical particles, binned in spherical coordinates.    //
+// In analysis the function should be first created in a macro, then     //
+// added to the analysis, and at the end of the macro the procedure to   //
+// write out histograms should be called.                                //
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+
+#include "AliFemtoModelCorrFctn3DSpherical.h"
+#include "AliFemtoModelManager.h"
+#include <TMath.h>
+#include <cstdio>
+//#include <Math/SpecFunc.h>
+
+#ifdef __ROOT__ 
+ClassImp(AliFemtoModelCorrFctn3DSpherical)
+#endif
+
+//____________________________
+AliFemtoModelCorrFctn3DSpherical::AliFemtoModelCorrFctn3DSpherical(char* title, const int& nqbins, const float& QLo, const float& QHi, const int& nphibins, const int& ncthetabins):
+  AliFemtoModelCorrFctn(),
+  fTrueNumeratorSph(0),
+  fFakeNumeratorSph(0),
+  fDenominatorSph(0),
+  fPairCut(0x0)
+{
+  // set up numerator
+  char tTitNum[101] = "NumTrue";
+  strncat(tTitNum,title, 100);
+  fTrueNumeratorSph = new TH3D(tTitNum,title,nqbins,QLo,QHi,nphibins,-TMath::Pi(),TMath::Pi(),ncthetabins,-1.0,1.0);
+  // set up numerator
+  char tTitNumF[101] = "NumFake";
+  strncat(tTitNumF,title, 100);
+  fFakeNumeratorSph = new TH3D(tTitNumF,title,nqbins,QLo,QHi,nphibins,-TMath::Pi(),TMath::Pi(),ncthetabins,-1.0,1.0);
+  // set up denominator
+  char tTitDen[101] = "Den";
+  strncat(tTitDen,title, 100);
+  fDenominatorSph = new TH3D(tTitDen,title,nqbins,QLo,QHi,nphibins,-TMath::Pi(),TMath::Pi(),ncthetabins,-1.0,1.0);
+
+  // to enable error bar calculation...
+  fTrueNumeratorSph->Sumw2();
+  fFakeNumeratorSph->Sumw2();
+  fDenominatorSph->Sumw2();
+}
+
+AliFemtoModelCorrFctn3DSpherical::AliFemtoModelCorrFctn3DSpherical(const AliFemtoModelCorrFctn3DSpherical& aCorrFctn) :
+  AliFemtoModelCorrFctn(aCorrFctn),
+  fTrueNumeratorSph(0),
+  fFakeNumeratorSph(0),
+  fDenominatorSph(0),
+  fPairCut(0x0)
+{
+  // Copy constructor
+  fTrueNumeratorSph = new TH3D(*aCorrFctn.fTrueNumeratorSph);
+  fFakeNumeratorSph = new TH3D(*aCorrFctn.fFakeNumeratorSph);
+  fDenominatorSph = new TH3D(*aCorrFctn.fDenominatorSph);
+  fPairCut = aCorrFctn.fPairCut;
+}
+//____________________________
+AliFemtoModelCorrFctn3DSpherical::~AliFemtoModelCorrFctn3DSpherical(){
+  // Destructor
+  delete fTrueNumeratorSph;
+  delete fFakeNumeratorSph;
+  delete fDenominatorSph;
+}
+//_________________________
+AliFemtoModelCorrFctn3DSpherical& AliFemtoModelCorrFctn3DSpherical::operator=(const AliFemtoModelCorrFctn3DSpherical& aCorrFctn)
+{
+  // assignment operator
+  if (this == &aCorrFctn)
+    return *this;
+
+  if (fTrueNumeratorSph) delete fTrueNumeratorSph;
+  fTrueNumeratorSph = new TH3D(*aCorrFctn.fTrueNumeratorSph);
+  if (fFakeNumeratorSph) delete fFakeNumeratorSph;
+  fFakeNumeratorSph = new TH3D(*aCorrFctn.fFakeNumeratorSph);
+  if (fDenominatorSph) delete fDenominatorSph;
+  fDenominatorSph = new TH3D(*aCorrFctn.fDenominatorSph);
+  
+  fPairCut = aCorrFctn.fPairCut;
+  
+  return *this;
+}
+
+//_________________________
+void AliFemtoModelCorrFctn3DSpherical::WriteOutHistos(){
+  // Write out all histograms to file
+  fTrueNumeratorSph->Write();
+  fFakeNumeratorSph->Write();
+  fDenominatorSph->Write();
+}
+//______________________________
+TList* AliFemtoModelCorrFctn3DSpherical::GetOutputList()
+{
+  // Prepare the list of objects to be written to the output
+  TList *tOutputList = new TList();
+
+  tOutputList->Add(fTrueNumeratorSph); 
+  tOutputList->Add(fFakeNumeratorSph); 
+  tOutputList->Add(fDenominatorSph);  
+
+  return tOutputList;
+}
+
+//_________________________
+void AliFemtoModelCorrFctn3DSpherical::Finish(){
+  // here is where we should normalize, fit, etc...
+}
+
+//____________________________
+AliFemtoString AliFemtoModelCorrFctn3DSpherical::Report(){
+  // Construct the report
+  string stemp = "PRF Frame Spherical 3D Model Correlation Function Report:\n";
+  char ctemp[100];
+  snprintf(ctemp , 100, "Number of entries in numerator:\t%E\n",fTrueNumeratorSph->GetEntries());
+  stemp += ctemp;
+  snprintf(ctemp , 100, "Number of entries in denominator:\t%E\n",fDenominatorSph->GetEntries());
+  stemp += ctemp;
+
+  if (fPairCut){
+    snprintf(ctemp , 100, "Here is the PairCut specific to this CorrFctn\n");
+    stemp += ctemp;
+    stemp += fPairCut->Report();
+  }
+  else{
+    snprintf(ctemp , 100, "No PairCut specific to this CorrFctn\n");
+    stemp += ctemp;
+  }
+
+  //  
+  AliFemtoString returnThis = stemp;
+  return returnThis;
+}
+//____________________________
+void AliFemtoModelCorrFctn3DSpherical::AddRealPair( AliFemtoPair* pair){
+  // perform operations on real pairs
+  if (fPairCut){
+    if (!(fPairCut->Pass(pair))) return;
+  }
+
+  Double_t weight = fManager->GetWeight(pair);
+
+  double tKO = pair->KOut();
+  double tKS = pair->KSide();
+  double tKL = pair->KLong();
+
+  double tKR = sqrt(tKO*tKO + tKS*tKS + tKL*tKL);
+  double tKC;
+  if ( fabs(tKR) < 1e-10 ) tKC = 0.0;
+  else tKC=tKL/tKR;
+  double tKP=atan2(tKS,tKO);
+
+  fTrueNumeratorSph->Fill(tKR,tKP,tKC,weight);
+}
+//____________________________
+void AliFemtoModelCorrFctn3DSpherical::AddMixedPair( AliFemtoPair* pair){
+  // perform operations on mixed pairs
+  if (fPairCut){
+    if (!(fPairCut->Pass(pair))) return;
+  }
+
+  Double_t weight = fManager->GetWeight(pair);
+
+  double tKO = pair->KOut();
+  double tKS = pair->KSide();
+  double tKL = pair->KLong();
+
+  double tKR = sqrt(tKO*tKO + tKS*tKS + tKL*tKL);
+  double tKC;
+  if ( fabs(tKR) < 1e-10 ) tKC = 0.0;
+  else tKC=tKL/tKR;
+  double tKP=atan2(tKS,tKO);
+
+  fFakeNumeratorSph->Fill(tKR,tKP,tKC,weight);
+  fDenominatorSph->Fill(tKR,tKP,tKC);
+}
+
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctn3DSpherical.h b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctn3DSpherical.h
new file mode 100644 (file)
index 0000000..9819288
--- /dev/null
@@ -0,0 +1,53 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFemtoModelCorrFctn3DSpherical: a class to calculate 3D correlation //
+// for pairs of identical particles, binned in spherical coordinates     //
+// (q_inv, phi, cos(theta))                                              //
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+
+#ifndef ALIFEMTOMODELCORRFCTN3DSPHERICAL_H
+#define ALIFEMTOMODELCORRFCTN3DSPHERICAL_H
+
+#include "AliFemtoModelCorrFctn.h"
+#include "AliFemtoPairCut.h"
+#include "TH3D.h"
+
+class AliFemtoModelCorrFctn3DSpherical : public AliFemtoModelCorrFctn {
+public:
+  AliFemtoModelCorrFctn3DSpherical(char* title, 
+                             const int& nqbins, const float& QLo, const float& QHi,
+                             const int& nphibins, const int& ncthetabins);
+  AliFemtoModelCorrFctn3DSpherical(const AliFemtoModelCorrFctn3DSpherical& aCorrFctn);
+  virtual ~AliFemtoModelCorrFctn3DSpherical();
+
+  AliFemtoModelCorrFctn3DSpherical& operator=(const AliFemtoModelCorrFctn3DSpherical& aCorrFctn);
+
+  virtual AliFemtoString Report();
+  virtual void AddRealPair( AliFemtoPair* aPair);
+  virtual void AddMixedPair( AliFemtoPair* aPair);
+
+  virtual void Finish();
+
+  void WriteOutHistos();
+  virtual TList* GetOutputList();
+
+  void SetSpecificPairCut(AliFemtoPairCut* aCut);
+
+private:
+  // here are a whole bunch of histos that get filled if we do resolution correction
+  TH3D* fTrueNumeratorSph;         // numerator
+  TH3D* fFakeNumeratorSph;         // numerator
+  TH3D* fDenominatorSph;       // denominator
+
+  AliFemtoPairCut* fPairCut;    //! this is a PairCut specific to THIS CorrFctn, not the Analysis
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoModelCorrFctn3DSpherical, 1)
+#endif
+};
+
+inline  void AliFemtoModelCorrFctn3DSpherical::SetSpecificPairCut(AliFemtoPairCut* pc){fPairCut=pc;}
+
+#endif
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctnDEtaDPhi.cxx b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctnDEtaDPhi.cxx
new file mode 100644 (file)
index 0000000..5e97932
--- /dev/null
@@ -0,0 +1,496 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoModelCorrFctnDEtaDPhi - A correlation function that analyzes            //
+// two particle correlations with respect to the azimuthal angle (phi)        //
+// and pseudorapidity (eta) difference                                        //
+//                                                                            //
+// Authors: Adam Kisiel Adam.Kisiel@cern.ch                                   //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+
+#include "AliFemtoModelCorrFctnDEtaDPhi.h"
+//#include "AliFemtoHisto.hh"
+#include <cstdio>
+#include <TMath.h>
+
+#ifdef __ROOT__ 
+ClassImp(AliFemtoModelCorrFctnDEtaDPhi)
+#endif
+
+/*And some Model libraries..*/
+//1
+//#include "AliFemtoModelGausLCMSFreezeOutGenerator.h"
+//#include "AliFemtoModelHiddenInfo.h"
+//2
+#include "AliFemtoModelGausLCMSFreezeOutGenerator.h"
+#include "AliFemtoModelHiddenInfo.h"
+#include "AliFemtoPair.h"
+#include "AliFemtoModelManager.h"
+//
+
+//____________________________
+AliFemtoModelCorrFctnDEtaDPhi::AliFemtoModelCorrFctnDEtaDPhi(char* title, const int& aPhiBins=20, const int& aEtaBins=20):
+  AliFemtoModelCorrFctn(),
+  fDPhiDEtaNumeratorTrue(0),
+  fDPhiDEtaNumeratorFake(0),
+  fDPhiDEtaDenominator(0),
+  fDPhiDEtaColNumerator(0),
+  fDPhiDEtaColDenominator(0),
+  fDPhiNumeratorTrue(0),
+  fDPhiNumeratorFake(0),
+  fDPhiDenominator(0),
+  fDCosNumeratorTrue(0),
+  fDCosNumeratorFake(0),
+  fDCosDenominator(0),
+  fDPhiPtNumerator(0),
+  fDPhiPtDenominator(0),
+  fDCosPtNumerator(0),
+  fDCosPtDenominator(0)
+{
+  // set up numerator
+  char tTitNumDT[101] = "NumDPhiDEtaTrue";
+  strncat(tTitNumDT,title, 100);
+  fDPhiDEtaNumeratorTrue = new TH2D(tTitNumDT,title,aPhiBins,-0.5*TMath::Pi(),1.5*TMath::Pi(),aEtaBins,-2.0,2.0);
+
+  char tTitNumDF[101] = "NumDPhiDEtaFake";
+  strncat(tTitNumDF,title, 100);
+  fDPhiDEtaNumeratorFake = new TH2D(tTitNumDF,title,aPhiBins,-0.5*TMath::Pi(),1.5*TMath::Pi(),aEtaBins,-2.0,2.0);
+
+
+  // set up denominator
+  char tTitDenD[101] = "DenDPhiDEta";
+  strncat(tTitDenD,title, 100);
+  fDPhiDEtaDenominator = new TH2D(tTitDenD,title,aPhiBins,-0.5*TMath::Pi(),1.5*TMath::Pi(),aEtaBins,-2.0,2.0);
+
+  // set up numerator
+  char tTitNumR[101] = "NumDPhiDEtaCol";
+  strncat(tTitNumR,title, 100);
+  fDPhiDEtaColNumerator = new TH2D(tTitNumR,title,aPhiBins,-0.5*TMath::Pi(),1.5*TMath::Pi(),aEtaBins,-2.0,2.0);
+  // set up denominator
+  char tTitDenR[101] = "DenDPhiDEtaCol";
+  strncat(tTitDenR,title, 100);
+  fDPhiDEtaColDenominator = new TH2D(tTitDenR,title,aPhiBins,-0.5*TMath::Pi(),1.5*TMath::Pi(),aEtaBins,-2.0,2.0);
+
+  // set up numerator
+  char tTitNumDPhiT[101] = "NumDPhiTrue";
+  strncat(tTitNumDPhiT,title, 100);
+  fDPhiNumeratorTrue = new TH1D(tTitNumDPhiT,title,aPhiBins*2,-0.5*TMath::Pi(),1.5*TMath::Pi());
+  // set up numerator
+  char tTitNumDPhiF[101] = "NumDPhiFake";
+  strncat(tTitNumDPhiF,title, 100);
+  fDPhiNumeratorFake = new TH1D(tTitNumDPhiF,title,aPhiBins*2,-0.5*TMath::Pi(),1.5*TMath::Pi());
+
+  // set up denominator
+  char tTitDenDPhi[101] = "DenDPhi";
+  strncat(tTitDenDPhi,title, 100);
+  fDPhiDenominator = new TH1D(tTitDenDPhi,title,aPhiBins*2,-0.5*TMath::Pi(),1.5*TMath::Pi());
+
+  // set up numerator
+  char tTitNumDCosT[101] = "NumDCosTrue";
+  strncat(tTitNumDCosT,title, 100);
+  fDCosNumeratorTrue = new TH1D(tTitNumDCosT,title,aPhiBins*2,-1.0,1.0);
+  // set up numerator
+  char tTitNumDCosF[101] = "NumDCosFake";
+  strncat(tTitNumDCosF,title, 100);
+  fDCosNumeratorFake = new TH1D(tTitNumDCosF,title,aPhiBins*2,-1.0,1.0);
+
+  // set up denominator
+  char tTitDenDCos[101] = "DenDCos";
+  strncat(tTitDenDCos,title, 100);
+  fDCosDenominator = new TH1D(tTitDenDCos,title,aPhiBins*2,-1.0,1.0);
+
+  // set up numerator
+  char tTitNumDPhiPt[101] = "NumDPhiPt";
+  strncat(tTitNumDPhiPt,title, 100);
+  fDPhiPtNumerator = new TH2D(tTitNumDPhiPt,title,aPhiBins*2,-0.5*TMath::Pi(),1.5*TMath::Pi(), 30, 0.0, 3.0);
+  // set up denominator
+  char tTitDenDPhiPt[101] = "DenDPhiPt";
+  strncat(tTitDenDPhiPt,title, 100);
+  fDPhiPtDenominator = new TH2D(tTitDenDPhiPt,title,aPhiBins*2,-0.5*TMath::Pi(),1.5*TMath::Pi(), 30, 0.0, 3.0);
+
+  // set up numerator
+  char tTitNumDCosPt[101] = "NumDCosPt";
+  strncat(tTitNumDCosPt,title, 100);
+  fDCosPtNumerator = new TH2D(tTitNumDCosPt,title,aPhiBins*2,-1.0,1.0, 30, 0.0, 3.0);
+  // set up denominator
+  char tTitDenDCosPt[101] = "DenDCosPt";
+  strncat(tTitDenDCosPt,title, 100);
+  fDCosPtDenominator = new TH2D(tTitDenDCosPt,title,aPhiBins*2,-1.0,1.0, 30, 0.0, 3.0);
+
+  // to enable error bar calculation...
+  fDPhiDEtaNumeratorTrue->Sumw2();
+  fDPhiDEtaNumeratorFake->Sumw2();
+  fDPhiDEtaDenominator->Sumw2();
+  fDPhiDEtaColNumerator->Sumw2();
+  fDPhiDEtaColDenominator->Sumw2();
+  fDPhiNumeratorTrue->Sumw2();
+  fDPhiNumeratorFake->Sumw2();
+  fDPhiDenominator->Sumw2();
+  fDCosNumeratorTrue->Sumw2();
+  fDCosNumeratorFake->Sumw2();
+  fDCosDenominator->Sumw2();
+  fDPhiPtNumerator->Sumw2();
+  fDPhiPtDenominator->Sumw2();
+  fDCosPtNumerator->Sumw2();
+  fDCosPtDenominator->Sumw2();
+
+}
+
+//____________________________
+AliFemtoModelCorrFctnDEtaDPhi::AliFemtoModelCorrFctnDEtaDPhi(const AliFemtoModelCorrFctnDEtaDPhi& aCorrFctn) :
+  AliFemtoModelCorrFctn(),
+  fDPhiDEtaNumeratorTrue(0),
+  fDPhiDEtaNumeratorFake(0),
+  fDPhiDEtaDenominator(0),
+  fDPhiDEtaColNumerator(0),
+  fDPhiDEtaColDenominator(0),
+  fDPhiNumeratorTrue(0),
+  fDPhiNumeratorFake(0),
+  fDPhiDenominator(0),
+  fDCosNumeratorTrue(0),
+  fDCosNumeratorFake(0),
+  fDCosDenominator(0),
+  fDPhiPtNumerator(0),
+  fDPhiPtDenominator(0),
+  fDCosPtNumerator(0),
+  fDCosPtDenominator(0)
+{
+  // copy constructor
+  if (aCorrFctn.fDPhiDEtaNumeratorTrue)
+    fDPhiDEtaNumeratorTrue = new TH2D(*aCorrFctn.fDPhiDEtaNumeratorTrue);
+  else
+    fDPhiDEtaNumeratorTrue = 0;
+  if (aCorrFctn.fDPhiDEtaNumeratorFake)
+    fDPhiDEtaNumeratorFake = new TH2D(*aCorrFctn.fDPhiDEtaNumeratorFake);
+  else
+    fDPhiDEtaNumeratorFake = 0;
+
+  if (aCorrFctn.fDPhiDEtaDenominator)
+    fDPhiDEtaDenominator = new TH2D(*aCorrFctn.fDPhiDEtaDenominator);
+  else
+    fDPhiDEtaDenominator = 0;
+
+  if (aCorrFctn.fDPhiDEtaColNumerator)
+    fDPhiDEtaColNumerator = new TH2D(*aCorrFctn.fDPhiDEtaColNumerator);
+  else
+    fDPhiDEtaColNumerator = 0;
+  if (aCorrFctn.fDPhiDEtaColDenominator)
+    fDPhiDEtaColDenominator = new TH2D(*aCorrFctn.fDPhiDEtaColDenominator);
+  else
+    fDPhiDEtaColDenominator = 0;
+
+  if (aCorrFctn.fDPhiNumeratorTrue)
+    fDPhiNumeratorTrue = new TH1D(*aCorrFctn.fDPhiNumeratorTrue);
+  else
+    fDPhiNumeratorTrue = 0;
+
+  if (aCorrFctn.fDPhiNumeratorFake)
+    fDPhiNumeratorFake = new TH1D(*aCorrFctn.fDPhiNumeratorFake);
+  else
+    fDPhiNumeratorFake = 0;
+
+  if (aCorrFctn.fDPhiDenominator)
+    fDPhiDenominator = new TH1D(*aCorrFctn.fDPhiDenominator);
+  else
+    fDPhiDenominator = 0;
+
+  if (aCorrFctn.fDCosNumeratorTrue)
+    fDCosNumeratorTrue = new TH1D(*aCorrFctn.fDCosNumeratorTrue);
+  else
+    fDCosNumeratorTrue = 0;
+  if (aCorrFctn.fDCosNumeratorFake)
+    fDCosNumeratorFake = new TH1D(*aCorrFctn.fDCosNumeratorFake);
+  else
+    fDCosNumeratorFake = 0;
+
+  if (aCorrFctn.fDCosDenominator)
+    fDCosDenominator = new TH1D(*aCorrFctn.fDCosDenominator);
+  else
+    fDCosDenominator = 0;
+
+  if (aCorrFctn.fDPhiPtNumerator)
+    fDPhiPtNumerator = new TH2D(*aCorrFctn.fDPhiPtNumerator);
+  else
+    fDPhiPtNumerator = 0;
+  if (aCorrFctn.fDPhiPtDenominator)
+    fDPhiPtDenominator = new TH2D(*aCorrFctn.fDPhiPtDenominator);
+  else
+    fDPhiPtDenominator = 0;
+
+  if (aCorrFctn.fDCosPtNumerator)
+    fDCosPtNumerator = new TH2D(*aCorrFctn.fDCosPtNumerator);
+  else
+    fDCosPtNumerator = 0;
+  if (aCorrFctn.fDCosPtDenominator)
+    fDCosPtDenominator = new TH2D(*aCorrFctn.fDCosPtDenominator);
+  else
+    fDCosPtDenominator = 0;
+}
+//____________________________
+AliFemtoModelCorrFctnDEtaDPhi::~AliFemtoModelCorrFctnDEtaDPhi(){
+  // destructor
+  if(fDPhiDEtaNumeratorTrue)      delete fDPhiDEtaNumeratorTrue;
+  if(fDPhiDEtaNumeratorFake)      delete fDPhiDEtaNumeratorFake;
+  if(fDPhiDEtaDenominator)    delete fDPhiDEtaDenominator;
+  if(fDPhiDEtaColNumerator)   delete fDPhiDEtaColNumerator;
+  if(fDPhiDEtaColDenominator) delete fDPhiDEtaColDenominator;
+  if(fDPhiNumeratorTrue)       delete fDPhiNumeratorTrue;
+  if(fDPhiNumeratorFake)       delete fDPhiNumeratorFake;
+  if(fDPhiDenominator)     delete fDPhiDenominator;
+  if(fDCosNumeratorTrue)       delete fDCosNumeratorTrue;
+  if(fDCosNumeratorFake)       delete fDCosNumeratorFake;
+  if(fDCosDenominator)     delete fDCosDenominator;
+  if(fDPhiPtNumerator)     delete fDPhiPtNumerator;
+  if(fDPhiPtDenominator)   delete fDPhiPtDenominator;
+  if(fDCosPtNumerator)     delete fDCosPtNumerator;
+  if(fDCosPtDenominator)   delete fDCosPtDenominator;
+}
+//_________________________
+AliFemtoModelCorrFctnDEtaDPhi& AliFemtoModelCorrFctnDEtaDPhi::operator=(const AliFemtoModelCorrFctnDEtaDPhi& aCorrFctn)
+{
+  // assignment operator
+  if (this == &aCorrFctn)
+    return *this;
+
+  if (aCorrFctn.fDPhiDEtaNumeratorTrue)
+    fDPhiDEtaNumeratorTrue = new TH2D(*aCorrFctn.fDPhiDEtaNumeratorTrue);
+  else
+    fDPhiDEtaNumeratorTrue = 0;
+
+  if (aCorrFctn.fDPhiDEtaNumeratorFake)
+    fDPhiDEtaNumeratorFake = new TH2D(*aCorrFctn.fDPhiDEtaNumeratorFake);
+  else
+    fDPhiDEtaNumeratorFake = 0;
+
+  if (aCorrFctn.fDPhiDEtaDenominator)
+    fDPhiDEtaDenominator = new TH2D(*aCorrFctn.fDPhiDEtaDenominator);
+  else
+    fDPhiDEtaDenominator = 0;
+
+  if (aCorrFctn.fDPhiDEtaColNumerator)
+    fDPhiDEtaColNumerator = new TH2D(*aCorrFctn.fDPhiDEtaColNumerator);
+  else
+    fDPhiDEtaColNumerator = 0;
+  if (aCorrFctn.fDPhiDEtaColDenominator)
+    fDPhiDEtaColDenominator = new TH2D(*aCorrFctn.fDPhiDEtaColDenominator);
+  else
+    fDPhiDEtaColDenominator = 0;
+
+  if (aCorrFctn.fDPhiNumeratorTrue)
+    fDPhiNumeratorTrue = new TH1D(*aCorrFctn.fDPhiNumeratorTrue);
+  else
+    fDPhiNumeratorTrue = 0;
+  if (aCorrFctn.fDPhiNumeratorFake)
+    fDPhiNumeratorFake = new TH1D(*aCorrFctn.fDPhiNumeratorFake);
+  else
+    fDPhiNumeratorFake = 0;
+
+  if (aCorrFctn.fDPhiDenominator)
+    fDPhiDenominator = new TH1D(*aCorrFctn.fDPhiDenominator);
+  else
+    fDPhiDenominator = 0;
+
+  if (aCorrFctn.fDCosNumeratorTrue)
+    fDCosNumeratorTrue = new TH1D(*aCorrFctn.fDCosNumeratorTrue);
+  else
+    fDCosNumeratorTrue = 0;
+  if (aCorrFctn.fDCosNumeratorFake)
+    fDCosNumeratorFake = new TH1D(*aCorrFctn.fDCosNumeratorFake);
+  else
+    fDCosNumeratorFake = 0;
+
+  if (aCorrFctn.fDCosDenominator)
+    fDCosDenominator = new TH1D(*aCorrFctn.fDCosDenominator);
+  else
+    fDCosDenominator = 0;
+
+  if (aCorrFctn.fDPhiPtNumerator)
+    fDPhiPtNumerator = new TH2D(*aCorrFctn.fDPhiPtNumerator);
+  else
+    fDPhiPtNumerator = 0;
+  if (aCorrFctn.fDPhiPtDenominator)
+    fDPhiPtDenominator = new TH2D(*aCorrFctn.fDPhiPtDenominator);
+  else
+    fDPhiPtDenominator = 0;
+
+  if (aCorrFctn.fDCosPtNumerator)
+    fDCosPtNumerator = new TH2D(*aCorrFctn.fDCosPtNumerator);
+  else
+    fDCosPtNumerator = 0;
+  if (aCorrFctn.fDCosPtDenominator)
+    fDCosPtDenominator = new TH2D(*aCorrFctn.fDCosPtDenominator);
+  else
+    fDCosPtDenominator = 0;
+
+  return *this;
+}
+//_________________________
+void AliFemtoModelCorrFctnDEtaDPhi::Finish(){
+  // here is where we should normalize, fit, etc...
+  // we should NOT Draw() the histos (as I had done it below),
+  // since we want to insulate ourselves from root at this level
+  // of the code.  Do it instead at root command line with browser.
+  //  mShareNumerator->Draw();
+  //mShareDenominator->Draw();
+  //mRatio->Draw();
+
+}
+
+//____________________________
+AliFemtoString AliFemtoModelCorrFctnDEtaDPhi::Report(){
+  // create report
+  string stemp = "TPC Ncls Correlation Function Report:\n";
+  char ctemp[100];
+  snprintf(ctemp,100,"Number of entries in numerator true:\t%E\n",fDPhiDEtaNumeratorTrue->GetEntries());
+  snprintf(ctemp,100,"Number of entries in numerator fake:\t%E\n",fDPhiDEtaNumeratorFake->GetEntries());
+  stemp += ctemp;
+  snprintf(ctemp,100,"Number of entries in denominator:\t%E\n",fDPhiDEtaDenominator->GetEntries());
+  stemp += ctemp;
+  //  stemp += mCoulombWeight->Report();
+  AliFemtoString returnThis = stemp;
+  return returnThis;
+}
+//____________________________
+void AliFemtoModelCorrFctnDEtaDPhi::AddRealPair( AliFemtoPair* pair){
+  // add real (effect) pair
+  double phi1 = pair->Track1()->Track()->P().Phi();
+  double phi2 = pair->Track2()->Track()->P().Phi();
+  double eta1 = pair->Track1()->Track()->P().PseudoRapidity();
+  double eta2 = pair->Track2()->Track()->P().PseudoRapidity();
+
+  double dphi = phi1 - phi2;
+  while (dphi<-TMath::Pi()/2) dphi+=TMath::Pi()*2;
+  while (dphi>3*TMath::Pi()/2) dphi-=TMath::Pi()*2;
+
+  double deta = eta1 - eta2;
+
+  double px1 = pair->Track1()->Track()->P().x();
+  double py1 = pair->Track1()->Track()->P().y();
+  double pz1 = pair->Track1()->Track()->P().z();
+
+  double px2 = pair->Track2()->Track()->P().x();
+  double py2 = pair->Track2()->Track()->P().y();
+  double pz2 = pair->Track2()->Track()->P().z();
+
+  double pt1 = TMath::Hypot(px1, py1);
+  double pt2 = TMath::Hypot(px2, py2);
+  double ptmin = pt1>pt2 ? pt2 : pt1;
+
+  double cosphi = (px1*px2 + py1*py2 + pz1*pz2)/
+    sqrt((px1*px1 + py1*py1 + pz1*pz1)*(px2*px2 + py2*py2 + pz2*pz2));
+
+/*weights*/
+  Double_t weight = fManager->GetWeight(pair);
+  fDPhiDEtaNumeratorTrue->Fill(dphi, deta,weight);
+
+  if (cosphi > 0) {
+    fDPhiDEtaColNumerator->Fill(dphi, deta);
+  }
+  else {
+    fDPhiDEtaColNumerator->Fill(dphi, -eta1-eta2);
+  }
+
+  fDPhiNumeratorTrue->Fill(dphi,weight);
+  fDCosNumeratorTrue->Fill(cosphi,weight);
+
+  fDPhiPtNumerator->Fill(dphi, ptmin);
+  fDCosPtNumerator->Fill(cosphi, ptmin);
+
+}
+//____________________________
+void AliFemtoModelCorrFctnDEtaDPhi::AddMixedPair( AliFemtoPair* pair){
+  // add mixed (background) pair
+  double phi1 = pair->Track1()->Track()->P().Phi();
+  double phi2 = pair->Track2()->Track()->P().Phi();
+  double eta1 = pair->Track1()->Track()->P().PseudoRapidity();
+  double eta2 = pair->Track2()->Track()->P().PseudoRapidity();
+
+  double dphi = phi1 - phi2;
+  while (dphi<-TMath::Pi()/2) dphi+=TMath::Pi()*2;
+  while (dphi>3*TMath::Pi()/2) dphi-=TMath::Pi()*2;
+
+  double deta = eta1 - eta2;
+
+  double px1 = pair->Track1()->Track()->P().x();
+  double py1 = pair->Track1()->Track()->P().y();
+  double pz1 = pair->Track1()->Track()->P().z();
+
+  double px2 = pair->Track2()->Track()->P().x();
+  double py2 = pair->Track2()->Track()->P().y();
+  double pz2 = pair->Track2()->Track()->P().z();
+
+  double pt1 = TMath::Hypot(px1, py1);
+  double pt2 = TMath::Hypot(px2, py2);
+  double ptmin = pt1>pt2 ? pt2 : pt1;
+
+  double cosphi = (px1*px2 + py1*py2 + pz1*pz2)/
+    sqrt((px1*px1 + py1*py1 + pz1*pz1)*(px2*px2 + py2*py2 + pz2*pz2));
+
+
+  Double_t weight = fManager->GetWeight(pair);
+  fDPhiDEtaNumeratorFake->Fill(dphi, deta,weight);
+
+  fDPhiDEtaDenominator->Fill(dphi, deta,1.0);
+
+  if (cosphi > 0) {
+    fDPhiDEtaColDenominator->Fill(dphi, deta);
+  }
+  else {
+    fDPhiDEtaColDenominator->Fill(dphi, -eta1-eta2);
+  }
+
+  fDPhiNumeratorFake->Fill(dphi,weight);
+  fDCosNumeratorFake->Fill(cosphi,weight);
+
+  fDPhiDenominator->Fill(dphi,1.0);
+  fDCosDenominator->Fill(cosphi,1.0);
+
+  fDPhiPtDenominator->Fill(dphi, ptmin);
+  fDCosPtDenominator->Fill(cosphi, ptmin);
+}
+
+
+void AliFemtoModelCorrFctnDEtaDPhi::WriteHistos()
+{
+  // Write out result histograms
+  fDPhiDEtaNumeratorTrue->Write();
+  fDPhiDEtaNumeratorFake->Write();
+  fDPhiDEtaDenominator->Write();
+  fDPhiDEtaColNumerator->Write();
+  fDPhiDEtaColDenominator->Write();
+  fDPhiNumeratorTrue->Write();
+  fDPhiNumeratorFake->Write();
+  fDPhiDenominator->Write();
+  fDCosNumeratorTrue->Write();
+  fDCosNumeratorFake->Write();
+  fDCosDenominator->Write();
+  fDPhiPtNumerator->Write();
+  fDPhiPtDenominator->Write();
+  fDCosPtNumerator->Write();
+  fDCosPtDenominator->Write();
+}
+
+TList* AliFemtoModelCorrFctnDEtaDPhi::GetOutputList()
+{
+  // Prepare the list of objects to be written to the output
+  TList *tOutputList = new TList();
+
+  tOutputList->Add(fDPhiDEtaNumeratorTrue);
+  tOutputList->Add(fDPhiDEtaNumeratorFake);
+  tOutputList->Add(fDPhiDEtaDenominator);
+  tOutputList->Add(fDPhiDEtaColNumerator);
+  tOutputList->Add(fDPhiDEtaColDenominator);
+  tOutputList->Add(fDPhiNumeratorTrue);
+  tOutputList->Add(fDPhiNumeratorFake);
+  tOutputList->Add(fDPhiDenominator);
+  tOutputList->Add(fDCosNumeratorTrue);
+  tOutputList->Add(fDCosNumeratorFake);
+  tOutputList->Add(fDCosDenominator);
+  tOutputList->Add(fDPhiPtNumerator);
+  tOutputList->Add(fDPhiPtDenominator);
+  tOutputList->Add(fDCosPtNumerator);
+  tOutputList->Add(fDCosPtDenominator);
+
+  return tOutputList;
+
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctnDEtaDPhi.h b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctnDEtaDPhi.h
new file mode 100644 (file)
index 0000000..6e2a880
--- /dev/null
@@ -0,0 +1,67 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoCorrFctnDEtaDPhi - A correlation function that analyzes            //
+// two particle correlations with respect to the azimuthal angle (phi)        //
+// and pseudorapidity (eta) difference                                        //
+//                                                                            //
+// Authors: Adam Kisiel Adam.Kisiel@cern.ch                                   //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+
+#ifndef ALIFEMTOMODELCORRFCTNDETADPHI_H
+#define ALIFEMTOMODELCORRFCTNDETADPHI_H
+
+#include "TH1D.h"
+#include "TH2D.h"
+#include "AliFemtoCorrFctn.h"
+#include "AliFemtoPair.h"
+#include "AliFemtoModelManager.h"
+#include "AliFemtoModelCorrFctn.h"
+
+class AliFemtoModelCorrFctnDEtaDPhi : public AliFemtoModelCorrFctn {
+public:
+  AliFemtoModelCorrFctnDEtaDPhi(char* title, const int& aPhiBins, const int& aEtaBins);
+  AliFemtoModelCorrFctnDEtaDPhi(const AliFemtoModelCorrFctnDEtaDPhi& aCorrFctn);
+  virtual ~AliFemtoModelCorrFctnDEtaDPhi();
+
+  AliFemtoModelCorrFctnDEtaDPhi& operator=(const AliFemtoModelCorrFctnDEtaDPhi& aCorrFctn);
+
+  virtual AliFemtoString Report();
+  virtual void AddRealPair(AliFemtoPair* aPair);
+  virtual void AddMixedPair(AliFemtoPair* aPair);
+
+  virtual void Finish();
+
+  void WriteHistos();
+  virtual TList* GetOutputList();
+private:
+  
+  TH2D *fDPhiDEtaNumeratorTrue;      // Numerator of dEta dPhi true function
+  TH2D *fDPhiDEtaNumeratorFake;      // Numerator of dEta dPhi fake function
+  TH2D *fDPhiDEtaDenominator;        // Denominator of dEta dPhi function
+
+  TH2D *fDPhiDEtaColNumerator;       // Numerator of colinear dEta dPhi function 
+  TH2D *fDPhiDEtaColDenominator;     // Denominator of colinear dEta dPhi function
+
+  TH1D *fDPhiNumeratorTrue;          // Numerator of dPhi true correlation
+  TH1D *fDPhiNumeratorFake;          // Numerator of dPhi fake correlation
+  TH1D *fDPhiDenominator;            // Denominator of dPhi correlation
+
+  TH1D *fDCosNumeratorTrue;           // Numerator of colinearity true correlation
+  TH1D *fDCosNumeratorFake;           // Numerator of colinearity fake correlation
+  TH1D *fDCosDenominator;            // Denominator of colinearity correlation
+
+  TH2D *fDPhiPtNumerator;            // Numerator of dPhi correlation vs. Pt min
+  TH2D *fDPhiPtDenominator;          // Denominator of dPhi correlation vs. Pt min
+
+  TH2D *fDCosPtNumerator;            // Numerator of colinearity correlation vs. Pt min
+  TH2D *fDCosPtDenominator;          // Denominator of colinearity correlation vs. Pt min
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoModelCorrFctnDEtaDPhi, 1)
+#endif
+};
+
+
+#endif
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctnDirectYlm.cxx b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctnDirectYlm.cxx
new file mode 100644 (file)
index 0000000..bed5a28
--- /dev/null
@@ -0,0 +1,209 @@
+////////////////////////////////////////////////////////////////////////////////
+///                                                                          ///
+/// AliFemtoModelCorrFctnDirectYlm - the class for correlation function which   ///
+/// uses the model framework and weight generation and saves the generated   ///
+/// emission source                                                          ///
+/// Authors: Adam Kisiel, kisiel@mps.ohio-state.edu                          ///
+///                                                                          ///
+////////////////////////////////////////////////////////////////////////////////
+#ifdef __ROOT__
+  ClassImp(AliFemtoModelCorrFctnDirectYlm, 1)
+#endif
+
+#include "AliFemtoModelGausLCMSFreezeOutGenerator.h"
+#include "AliFemtoModelHiddenInfo.h"
+#include "AliFemtoModelCorrFctnDirectYlm.h"
+    
+//_______________________
+AliFemtoModelCorrFctnDirectYlm::AliFemtoModelCorrFctnDirectYlm(): 
+  AliFemtoModelCorrFctn(),
+  fCYlmTrue(0),
+  fCYlmFake(0),
+  fUseLCMS(0)
+{
+  // default constructor
+
+  fCYlmTrue = new AliFemtoCorrFctnDirectYlm();
+  fCYlmFake = new AliFemtoCorrFctnDirectYlm();
+  fCYlmTrue->SetUseLCMS(fUseLCMS);
+  fCYlmFake->SetUseLCMS(fUseLCMS);
+}
+//_______________________
+AliFemtoModelCorrFctnDirectYlm::AliFemtoModelCorrFctnDirectYlm(const char *title, Int_t aMaxL, Int_t aNbins, Double_t aQinvLo, Double_t aQinvHi, int aUseLCMS=0):
+  AliFemtoModelCorrFctn(title, aNbins, aQinvLo, aQinvHi),
+  fCYlmTrue(0),
+  fCYlmFake(0),
+  fUseLCMS(aUseLCMS)
+{
+  // basic constructor
+  char fname[1000];
+  snprintf(fname, 1000, "%s%s", title, "True");
+  fCYlmTrue = new AliFemtoCorrFctnDirectYlm(fname, aMaxL, aNbins, aQinvLo, aQinvHi, fUseLCMS);
+  snprintf(fname, 1000, "%s%s", title, "Fake");
+  fCYlmFake = new AliFemtoCorrFctnDirectYlm(fname, aMaxL, aNbins, aQinvLo, aQinvHi, fUseLCMS);
+}
+//_______________________
+AliFemtoModelCorrFctnDirectYlm::AliFemtoModelCorrFctnDirectYlm(const AliFemtoModelCorrFctnDirectYlm& aCorrFctn):
+  AliFemtoModelCorrFctn(aCorrFctn),
+  fCYlmTrue(new AliFemtoCorrFctnDirectYlm(*(aCorrFctn.fCYlmTrue))),
+  fCYlmFake(new AliFemtoCorrFctnDirectYlm(*(aCorrFctn.fCYlmFake))),
+  fUseLCMS(0)
+{
+  // copy constructor
+  fUseLCMS = aCorrFctn.fUseLCMS;
+//   fCYlmTrue = dynamic_cast<AliFemtoCorrFctnDirectYlm*>(aCorrFctn.fCYlmTrue->Clone());
+//   fCYlmFake = dynamic_cast<AliFemtoCorrFctnDirectYlm*>(aCorrFctn.fCYlmFake->Clone());
+}
+//_______________________
+AliFemtoModelCorrFctnDirectYlm::~AliFemtoModelCorrFctnDirectYlm()
+{
+  // destructor
+  if (fCYlmTrue) delete fCYlmTrue;
+  if (fCYlmFake) delete fCYlmFake;
+  if (fNumeratorTrue) delete fNumeratorTrue;
+  if (fNumeratorFake) delete fNumeratorFake;
+  if (fDenominator) delete fDenominator;
+}
+
+//_______________________
+AliFemtoModelCorrFctnDirectYlm& AliFemtoModelCorrFctnDirectYlm::operator=(const AliFemtoModelCorrFctnDirectYlm& aCorrFctn)
+{
+  // assignment operator
+  if (this != &aCorrFctn) {
+
+    fUseLCMS = aCorrFctn.fUseLCMS;
+    
+    if (fCYlmTrue) delete fCYlmTrue;
+    if (aCorrFctn.fCYlmTrue)
+      fCYlmTrue = new AliFemtoCorrFctnDirectYlm(*aCorrFctn.fCYlmTrue);
+    else fCYlmTrue = 0;
+    
+    if (fCYlmFake) delete fCYlmFake;
+    if (aCorrFctn.fCYlmFake)
+      fCYlmFake = new AliFemtoCorrFctnDirectYlm(*aCorrFctn.fCYlmFake);
+    else fCYlmFake = 0;
+    
+    if (fNumeratorTrue) delete fNumeratorTrue;
+    if (aCorrFctn.fNumeratorTrue)
+      fNumeratorTrue = new TH1D(*aCorrFctn.fNumeratorTrue);
+    else
+      fNumeratorTrue = 0;
+    
+    if (fNumeratorFake) delete fNumeratorFake;
+    if (aCorrFctn.fNumeratorFake)
+      fNumeratorFake = new TH1D(*aCorrFctn.fNumeratorFake);
+    else
+      fNumeratorFake = 0;
+    
+    if (fDenominator) delete fDenominator;
+    if (aCorrFctn.fDenominator)
+      fDenominator = new TH1D(*aCorrFctn.fDenominator);
+    else
+      fDenominator = 0;
+  }
+
+  return *this;
+}
+//_______________________
+AliFemtoString AliFemtoModelCorrFctnDirectYlm::Report()
+{
+  // construct report
+  AliFemtoString tStr = "AliFemtoModelCorrFctnDirectYlm report";
+
+  return tStr;
+}
+
+//_______________________
+void AliFemtoModelCorrFctnDirectYlm::AddRealPair(AliFemtoPair* aPair)
+{
+  // add real (effect) pair
+  if (fPairCut)
+    if (!(fPairCut->Pass(aPair))) return;
+
+  Double_t weight = fManager->GetWeight(aPair);
+  
+  if (fUseLCMS)
+    fCYlmTrue->AddRealPair(aPair->QOutCMS(), aPair->QSideCMS(), aPair->QLongCMS(), weight);
+  else
+    fCYlmTrue->AddRealPair(aPair->KOut(), aPair->KSide(), aPair->KLong(), weight);
+}
+//_______________________
+void AliFemtoModelCorrFctnDirectYlm::AddMixedPair(AliFemtoPair* aPair)
+{
+  // add mixed (background) pair
+  if (fPairCut)
+    if (!(fPairCut->Pass(aPair))) return;
+
+  Double_t weight = fManager->GetWeight(aPair);
+
+  if (fUseLCMS) {
+    fCYlmTrue->AddMixedPair(aPair->QOutCMS(), aPair->QSideCMS(), aPair->QLongCMS(), 1.0);
+    fCYlmFake->AddRealPair(aPair->QOutCMS(), aPair->QSideCMS(), aPair->QLongCMS(), weight);
+    fCYlmFake->AddMixedPair(aPair->QOutCMS(), aPair->QSideCMS(), aPair->QLongCMS(), 1.0);
+  }
+  else {
+    fCYlmTrue->AddMixedPair(aPair->KOut(), aPair->KSide(), aPair->KLong(), 1.0);
+    fCYlmFake->AddRealPair(aPair->KOut(), aPair->KSide(), aPair->KLong(), weight);
+    fCYlmFake->AddMixedPair(aPair->KOut(), aPair->KSide(), aPair->KLong(), 1.0);
+  }
+}
+//_______________________
+void AliFemtoModelCorrFctnDirectYlm::Write()
+{
+  // write out all the histograms
+  
+  fCYlmTrue->Write();
+  fCYlmFake->Write();
+}
+//_______________________
+TList* AliFemtoModelCorrFctnDirectYlm::GetOutputList()
+{
+  // Prepare the list of objects to be written to the output
+  TList *tOutputList = AliFemtoModelCorrFctn::GetOutputList();
+  tOutputList->Clear();
+
+  TList *tListCfTrue = fCYlmTrue->GetOutputList();
+    
+  TIter nextListCfTrue(tListCfTrue);
+  while (TObject *obj = nextListCfTrue()) {
+    tOutputList->Add(obj);
+  }
+
+  TList *tListCfFake = fCYlmFake->GetOutputList();
+    
+  TIter nextListCfFake(tListCfFake);
+  while (TObject *obj = nextListCfFake()) {
+    tOutputList->Add(obj);
+  }
+//   tOutputList->Add(fCYlmTrue->GetOutputList());
+//   tOutputList->Add(fCYlmFake->GetOutputList());
+
+  return tOutputList;
+}
+//_______________________
+AliFemtoModelCorrFctn* AliFemtoModelCorrFctnDirectYlm::Clone()
+{
+  // Clone the correlation function
+  AliFemtoModelCorrFctnDirectYlm *tCopy = new AliFemtoModelCorrFctnDirectYlm(*this);
+  
+  return tCopy;
+}
+//_______________________
+void AliFemtoModelCorrFctnDirectYlm::Finish()
+{
+  fCYlmTrue->Finish();
+  fCYlmFake->Finish();
+}
+//_______________________
+void AliFemtoModelCorrFctnDirectYlm::SetUseLCMS(int aUseLCMS)
+{
+  fUseLCMS = aUseLCMS;
+  fCYlmTrue->SetUseLCMS(fUseLCMS);
+  fCYlmFake->SetUseLCMS(fUseLCMS);
+}
+//_______________________
+int  AliFemtoModelCorrFctnDirectYlm::GetUseLCMS()
+{
+  return fUseLCMS;
+}
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctnDirectYlm.h b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctnDirectYlm.h
new file mode 100644 (file)
index 0000000..ee07e89
--- /dev/null
@@ -0,0 +1,56 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoModelCorrFctnDirectYlm - the class for correlation function which  //
+// uses the model framework and weight generation and saves the correlation   //
+// function directly in spherical harmonics                                   //
+// Authors: Adam Kisiel, kisiel@mps.ohio-state.edu                            //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+#ifndef ALIFEMTOMODELCORRFCTNDIRECTYLM_H
+#define ALIFEMTOMODELCORRFCTNDIRECTYLM_H
+
+#include "AliFemtoCorrFctn.h"
+#include "AliFemtoPair.h"
+#include "AliFemtoModelManager.h"
+#include "AliFemtoModelCorrFctn.h"
+#include "AliFemtoCorrFctnDirectYlm.h"
+
+class AliFemtoModelCorrFctnDirectYlm: public AliFemtoModelCorrFctn {
+
+public:
+  AliFemtoModelCorrFctnDirectYlm();
+  AliFemtoModelCorrFctnDirectYlm(const char *title, Int_t aMaxL, Int_t aNbins, Double_t aQinvLo, Double_t aQinvHi, int aUseLCMS);
+  AliFemtoModelCorrFctnDirectYlm(const AliFemtoModelCorrFctnDirectYlm& aCorrFctn);
+  virtual ~AliFemtoModelCorrFctnDirectYlm();
+  
+  AliFemtoModelCorrFctnDirectYlm& operator=(const AliFemtoModelCorrFctnDirectYlm& aCorrFctn);
+
+  virtual AliFemtoString Report();
+
+  virtual void AddRealPair(AliFemtoPair* aPair);
+  virtual void AddMixedPair(AliFemtoPair* aPir);
+
+  virtual void Finish();
+  virtual void Write();
+  virtual TList* GetOutputList();
+
+  virtual AliFemtoModelCorrFctn* Clone();
+
+  void SetUseLCMS(int aUseLCMS);
+  int  GetUseLCMS();
+
+protected:
+
+  AliFemtoCorrFctnDirectYlm* fCYlmTrue;     // True Correlation function in spherical harmonics
+  AliFemtoCorrFctnDirectYlm* fCYlmFake;     // Fake Correlation function in spherical harmonics
+
+  int fUseLCMS;                             // 0 - Use k* in PRF, 1 - use q in LCMS
+  
+private:
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoModelCorrFctnDirectYlm, 1)
+#endif
+};
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctnNonIdDR.cxx b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctnNonIdDR.cxx
new file mode 100644 (file)
index 0000000..bfae8e0
--- /dev/null
@@ -0,0 +1,382 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoModelCorrFctnNonIdDR - correlation function for non-identical      //
+// particles which uses k* as a function variable. Stores the correlation     //
+// function separately for positive and negative signs of k* projections into //
+// out, side and long directions, enabling the calculations of double ratios  //
+// Uses pair weight to simulate the model correlation function.               //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+
+#include "AliFemtoModelCorrFctnNonIdDR.h"
+#include "AliFemtoModelManager.h"
+//#include "AliFemtoHisto.h"
+#include <cstdio>
+
+#ifdef __ROOT__ 
+ClassImp(AliFemtoModelCorrFctnNonIdDR)
+#endif
+
+//____________________________
+AliFemtoModelCorrFctnNonIdDR::AliFemtoModelCorrFctnNonIdDR(char* title, const int& nbins, const float& QinvLo, const float& QinvHi):
+  AliFemtoModelCorrFctn(title, nbins, QinvLo, QinvHi),
+  fNumTOutP(0), 
+  fNumTOutN(0),  
+  fNumTSideP(0), 
+  fNumTSideN(0), 
+  fNumTLongP(0), 
+  fNumTLongN(0), 
+  fNumFOutP(0), 
+  fNumFOutN(0),  
+  fNumFSideP(0), 
+  fNumFSideN(0), 
+  fNumFLongP(0), 
+  fNumFLongN(0), 
+  fDenOutP(0),  
+  fDenOutN(0),  
+  fDenSideP(0), 
+  fDenSideN(0), 
+  fDenLongP(0), 
+  fDenLongN(0)
+{
+  // Default constructor
+  char bufname[200];
+
+  // set up true numerators
+  snprintf(bufname, 200, "NumTOutP%s", title);
+  fNumTOutP = new TH1D(bufname,title,nbins,QinvLo,QinvHi);
+  snprintf(bufname, 200, "NumTOutN%s", title);
+  fNumTOutN = new TH1D(bufname,title,nbins,QinvLo,QinvHi);
+  snprintf(bufname, 200, "NumTSideP%s", title);
+  fNumTSideP = new TH1D(bufname,title,nbins,QinvLo,QinvHi);
+  snprintf(bufname, 200, "NumTSideN%s", title);
+  fNumTSideN = new TH1D(bufname,title,nbins,QinvLo,QinvHi);
+  snprintf(bufname, 200, "NumTLongP%s", title);
+  fNumTLongP = new TH1D(bufname,title,nbins,QinvLo,QinvHi);
+  snprintf(bufname, 200, "NumTLongN%s", title);
+  fNumTLongN = new TH1D(bufname,title,nbins,QinvLo,QinvHi);
+
+  // set up fake numerators
+  snprintf(bufname, 200, "NumFOutP%s", title);
+  fNumFOutP = new TH1D(bufname,title,nbins,QinvLo,QinvHi);
+  snprintf(bufname, 200, "NumFOutN%s", title);
+  fNumFOutN = new TH1D(bufname,title,nbins,QinvLo,QinvHi);
+  snprintf(bufname, 200, "NumFSideP%s", title);
+  fNumFSideP = new TH1D(bufname,title,nbins,QinvLo,QinvHi);
+  snprintf(bufname, 200, "NumFSideN%s", title);
+  fNumFSideN = new TH1D(bufname,title,nbins,QinvLo,QinvHi);
+  snprintf(bufname, 200, "NumFLongP%s", title);
+  fNumFLongP = new TH1D(bufname,title,nbins,QinvLo,QinvHi);
+  snprintf(bufname, 200, "NumFLongN%s", title);
+  fNumFLongN = new TH1D(bufname,title,nbins,QinvLo,QinvHi);
+
+  // set up denominators
+  snprintf(bufname, 200, "DenOutP%s", title);
+  fDenOutP = new TH1D(bufname,title,nbins,QinvLo,QinvHi);
+  snprintf(bufname, 200, "DenOutN%s", title);
+  fDenOutN = new TH1D(bufname,title,nbins,QinvLo,QinvHi);
+  snprintf(bufname, 200, "DenSideP%s", title);
+  fDenSideP = new TH1D(bufname,title,nbins,QinvLo,QinvHi);
+  snprintf(bufname, 200, "DenSideN%s", title);
+  fDenSideN = new TH1D(bufname,title,nbins,QinvLo,QinvHi);
+  snprintf(bufname, 200, "DenLongP%s", title);
+  fDenLongP = new TH1D(bufname,title,nbins,QinvLo,QinvHi);
+  snprintf(bufname, 200, "DenLongN%s", title);
+  fDenLongN = new TH1D(bufname,title,nbins,QinvLo,QinvHi);
+
+  // to enable error bar calculation...
+  fNumTOutP->Sumw2(); 
+  fNumTOutN->Sumw2();  
+  fNumTSideP->Sumw2(); 
+  fNumTSideN->Sumw2(); 
+  fNumTLongP->Sumw2(); 
+  fNumTLongN->Sumw2(); 
+  fNumFOutP->Sumw2(); 
+  fNumFOutN->Sumw2();  
+  fNumFSideP->Sumw2(); 
+  fNumFSideN->Sumw2(); 
+  fNumFLongP->Sumw2(); 
+  fNumFLongN->Sumw2(); 
+  fDenOutP->Sumw2();  
+  fDenOutN->Sumw2();  
+  fDenSideP->Sumw2(); 
+  fDenSideN->Sumw2(); 
+  fDenLongP->Sumw2(); 
+  fDenLongN->Sumw2();
+}
+
+//____________________________
+AliFemtoModelCorrFctnNonIdDR::AliFemtoModelCorrFctnNonIdDR(const AliFemtoModelCorrFctnNonIdDR& aCorrFctn) :
+  AliFemtoModelCorrFctn(),
+  fNumTOutP(0), 
+  fNumTOutN(0),  
+  fNumTSideP(0), 
+  fNumTSideN(0), 
+  fNumTLongP(0), 
+  fNumTLongN(0), 
+  fNumFOutP(0), 
+  fNumFOutN(0),  
+  fNumFSideP(0), 
+  fNumFSideN(0), 
+  fNumFLongP(0), 
+  fNumFLongN(0), 
+  fDenOutP(0),  
+  fDenOutN(0),  
+  fDenSideP(0), 
+  fDenSideN(0), 
+  fDenLongP(0), 
+  fDenLongN(0)
+{
+  // copy constructor
+  if (aCorrFctn.fNumTOutP)
+    fNumTOutP = new TH1D(*aCorrFctn.fNumTOutP);
+  if (aCorrFctn.fNumTOutN)
+    fNumTOutN = new TH1D(*aCorrFctn.fNumTOutN);
+  if (aCorrFctn.fNumTSideP)
+    fNumTSideP = new TH1D(*aCorrFctn.fNumTSideP);
+  if (aCorrFctn.fNumTSideN)
+    fNumTSideN = new TH1D(*aCorrFctn.fNumTSideN);
+  if (aCorrFctn.fNumTLongP)
+    fNumTLongP = new TH1D(*aCorrFctn.fNumTLongP);
+  if (aCorrFctn.fNumTLongN)
+    fNumTLongN = new TH1D(*aCorrFctn.fNumTLongN);
+
+  if (aCorrFctn.fNumFOutP)
+    fNumFOutP = new TH1D(*aCorrFctn.fNumFOutP);
+  if (aCorrFctn.fNumFOutN)
+    fNumFOutN = new TH1D(*aCorrFctn.fNumFOutN);
+  if (aCorrFctn.fNumFSideP)
+    fNumFSideP = new TH1D(*aCorrFctn.fNumFSideP);
+  if (aCorrFctn.fNumFSideN)
+    fNumFSideN = new TH1D(*aCorrFctn.fNumFSideN);
+  if (aCorrFctn.fNumFLongP)
+    fNumFLongP = new TH1D(*aCorrFctn.fNumFLongP);
+  if (aCorrFctn.fNumFLongN)
+    fNumFLongN = new TH1D(*aCorrFctn.fNumFLongN);
+
+  if (aCorrFctn.fDenOutP)
+    fDenOutP = new TH1D(*aCorrFctn.fDenOutP);
+  if (aCorrFctn.fDenOutN)
+    fDenOutN = new TH1D(*aCorrFctn.fDenOutN);
+  if (aCorrFctn.fDenSideP)
+    fDenSideP = new TH1D(*aCorrFctn.fDenSideP);
+  if (aCorrFctn.fDenSideN)
+    fDenSideN = new TH1D(*aCorrFctn.fDenSideN);
+  if (aCorrFctn.fDenLongP)
+    fDenLongP = new TH1D(*aCorrFctn.fDenLongP);
+  if (aCorrFctn.fDenLongN)
+    fDenLongN = new TH1D(*aCorrFctn.fDenLongN);
+}
+//____________________________
+AliFemtoModelCorrFctnNonIdDR::~AliFemtoModelCorrFctnNonIdDR(){
+  // Destructor
+  delete fNumTOutP; 
+  delete fNumTOutN;  
+  delete fNumTSideP; 
+  delete fNumTSideN; 
+  delete fNumTLongP; 
+  delete fNumTLongN; 
+  delete fNumFOutP; 
+  delete fNumFOutN;  
+  delete fNumFSideP; 
+  delete fNumFSideN; 
+  delete fNumFLongP; 
+  delete fNumFLongN; 
+  delete fDenOutP;  
+  delete fDenOutN;  
+  delete fDenSideP; 
+  delete fDenSideN; 
+  delete fDenLongP; 
+  delete fDenLongN;
+}
+//_________________________
+AliFemtoModelCorrFctnNonIdDR& AliFemtoModelCorrFctnNonIdDR::operator=(const AliFemtoModelCorrFctnNonIdDR& aCorrFctn)
+{
+  // assignment operator
+  if (this == &aCorrFctn)
+    return *this;
+
+  if (aCorrFctn.fNumTOutP)
+    fNumTOutP = new TH1D(*aCorrFctn.fNumTOutP);
+  if (aCorrFctn.fNumTOutN)
+    fNumTOutN = new TH1D(*aCorrFctn.fNumTOutN);
+  if (aCorrFctn.fNumTSideP)
+    fNumTSideP = new TH1D(*aCorrFctn.fNumTSideP);
+  if (aCorrFctn.fNumTSideN)
+    fNumTSideN = new TH1D(*aCorrFctn.fNumTSideN);
+  if (aCorrFctn.fNumTLongP)
+    fNumTLongP = new TH1D(*aCorrFctn.fNumTLongP);
+  if (aCorrFctn.fNumTLongN)
+    fNumTLongN = new TH1D(*aCorrFctn.fNumTLongN);
+
+  if (aCorrFctn.fNumFOutP)
+    fNumFOutP = new TH1D(*aCorrFctn.fNumFOutP);
+  if (aCorrFctn.fNumFOutN)
+    fNumFOutN = new TH1D(*aCorrFctn.fNumFOutN);
+  if (aCorrFctn.fNumFSideP)
+    fNumFSideP = new TH1D(*aCorrFctn.fNumFSideP);
+  if (aCorrFctn.fNumFSideN)
+    fNumFSideN = new TH1D(*aCorrFctn.fNumFSideN);
+  if (aCorrFctn.fNumFLongP)
+    fNumFLongP = new TH1D(*aCorrFctn.fNumFLongP);
+  if (aCorrFctn.fNumFLongN)
+    fNumFLongN = new TH1D(*aCorrFctn.fNumFLongN);
+
+  if (aCorrFctn.fDenOutP)
+    fDenOutP = new TH1D(*aCorrFctn.fDenOutP);
+  if (aCorrFctn.fDenOutN)
+    fDenOutN = new TH1D(*aCorrFctn.fDenOutN);
+  if (aCorrFctn.fDenSideP)
+    fDenSideP = new TH1D(*aCorrFctn.fDenSideP);
+  if (aCorrFctn.fDenSideN)
+    fDenSideN = new TH1D(*aCorrFctn.fDenSideN);
+  if (aCorrFctn.fDenLongP)
+    fDenLongP = new TH1D(*aCorrFctn.fDenLongP);
+  if (aCorrFctn.fDenLongN)
+    fDenLongN = new TH1D(*aCorrFctn.fDenLongN);
+
+  return *this;
+}
+
+//_________________________
+void AliFemtoModelCorrFctnNonIdDR::Finish(){
+  // here is where we should normalize, fit, etc...
+  // we should NOT Draw() the histos (as I had done it below),
+  // since we want to insulate ourselves from root at this level
+  // of the code.  Do it instead at root command line with browser.
+  //  fNumerator->Draw();
+  //fDenominator->Draw();
+  //fRatio->Draw();
+  //  fRatio->Divide(fNumerator,fDenominator,1.0,1.0);
+
+}
+
+//____________________________
+AliFemtoString AliFemtoModelCorrFctnNonIdDR::Report(){
+  // construct report
+  string stemp = "Non-identical particles Model Correlation Function Report:\n";
+  char ctemp[100];
+  snprintf(ctemp , 100, "Number of entries in numerators:\t%E\n",fNumTOutP->GetEntries()+fNumTOutN->GetEntries());
+  stemp += ctemp;
+  snprintf(ctemp , 100, "Number of entries in denominators:\t%E\n",fDenOutP->GetEntries()+fDenOutN->GetEntries());
+  stemp += ctemp;
+  //  stemp += mCoulombWeight->Report();
+  AliFemtoString returnThis = stemp;
+  return returnThis;
+}
+//____________________________
+void AliFemtoModelCorrFctnNonIdDR::AddRealPair(AliFemtoPair* pair){
+  // add true pair
+  double tKStar = pair->KStar();
+  Double_t weight = fManager->GetWeight(pair);
+
+  if (pair->KOut()>0.0)
+    fNumTOutP->Fill(tKStar, weight);
+  else
+    fNumTOutN->Fill(tKStar, weight);
+
+  if (pair->KSide()>0.0)
+    fNumTSideP->Fill(tKStar, weight);
+  else
+    fNumTSideN->Fill(tKStar, weight);
+
+  if (pair->KLong()>0.0)
+    fNumTLongP->Fill(tKStar, weight);
+  else
+    fNumTLongN->Fill(tKStar, weight);
+
+}
+//____________________________
+void AliFemtoModelCorrFctnNonIdDR::AddMixedPair(AliFemtoPair* pair){
+  // add mixed (background) pair
+  double tKStar = pair->KStar();
+  Double_t weight = fManager->GetWeight(pair);
+
+  if (pair->KOut()>0.0)
+    fNumFOutP->Fill(tKStar, weight);
+  else
+    fNumFOutN->Fill(tKStar, weight);
+
+  if (pair->KSide()>0.0)
+    fNumFSideP->Fill(tKStar, weight);
+  else
+    fNumFSideN->Fill(tKStar, weight);
+
+  if (pair->KLong()>0.0)
+    fNumFLongP->Fill(tKStar, weight);
+  else
+    fNumFLongN->Fill(tKStar, weight);
+
+  if (pair->KOut()>0.0)
+    fDenOutP->Fill(tKStar);
+  else
+    fDenOutN->Fill(tKStar);
+
+  if (pair->KSide()>0.0)
+    fDenSideP->Fill(tKStar);
+  else
+    fDenSideN->Fill(tKStar);
+
+  if (pair->KLong()>0.0)
+    fDenLongP->Fill(tKStar);
+  else
+    fDenLongN->Fill(tKStar);
+}
+//____________________________
+void AliFemtoModelCorrFctnNonIdDR::Write(){
+  // Write out histos
+  fNumTOutP->Write(); 
+  fNumTOutN->Write();  
+  fNumTSideP->Write(); 
+  fNumTSideN->Write(); 
+  fNumTLongP->Write(); 
+  fNumTLongN->Write(); 
+  fNumFOutP->Write(); 
+  fNumFOutN->Write();  
+  fNumFSideP->Write(); 
+  fNumFSideN->Write(); 
+  fNumFLongP->Write(); 
+  fNumFLongN->Write(); 
+  fDenOutP->Write();  
+  fDenOutN->Write();  
+  fDenSideP->Write(); 
+  fDenSideN->Write(); 
+  fDenLongP->Write(); 
+  fDenLongN->Write();
+}
+
+TList* AliFemtoModelCorrFctnNonIdDR::GetOutputList()
+{
+  // Prepare the list of objects to be written to the output
+  TList *tOutputList = new TList();
+
+  tOutputList->Add(fNumTOutP); 
+  tOutputList->Add(fNumTOutN);  
+  tOutputList->Add(fNumTSideP); 
+  tOutputList->Add(fNumTSideN); 
+  tOutputList->Add(fNumTLongP); 
+  tOutputList->Add(fNumTLongN); 
+  tOutputList->Add(fNumFOutP); 
+  tOutputList->Add(fNumFOutN);  
+  tOutputList->Add(fNumFSideP); 
+  tOutputList->Add(fNumFSideN); 
+  tOutputList->Add(fNumFLongP); 
+  tOutputList->Add(fNumFLongN); 
+  tOutputList->Add(fDenOutP);  
+  tOutputList->Add(fDenOutN);  
+  tOutputList->Add(fDenSideP); 
+  tOutputList->Add(fDenSideN); 
+  tOutputList->Add(fDenLongP); 
+  tOutputList->Add(fDenLongN);
+
+  return tOutputList;
+}
+
+//_______________________
+AliFemtoModelCorrFctn* AliFemtoModelCorrFctnNonIdDR::Clone()
+{
+  // Create clone
+  AliFemtoModelCorrFctnNonIdDR *tCopy = new AliFemtoModelCorrFctnNonIdDR(*this);
+  
+  return tCopy;
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctnNonIdDR.h b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctnNonIdDR.h
new file mode 100644 (file)
index 0000000..c7a9149
--- /dev/null
@@ -0,0 +1,64 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoModelCorrFctnNonIdDR - correlation function for non-identical      //
+// particles which uses k* as a function variable. Stores the correlation     //
+// function separately for positive and negative signs of k* projections into //
+// out, side and long directions, enabling the calculations of double ratios  //
+// Uses pair weight to simulate the model correlation function.               //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+#ifndef ALIFEMTOMODELCORRFCTNNONIDDR_H
+#define ALIFEMTOMODELCORRFCTNNONIDDR_H
+
+#include "TH1D.h"
+#include "AliFemtoModelCorrFctn.h"
+
+class AliFemtoModelCorrFctnNonIdDR : public AliFemtoModelCorrFctn {
+public:
+  AliFemtoModelCorrFctnNonIdDR(char* title, const int& nbins, const float& QinvLo, const float& QinvHi);
+  AliFemtoModelCorrFctnNonIdDR(const AliFemtoModelCorrFctnNonIdDR& aCorrFctn);
+  virtual ~AliFemtoModelCorrFctnNonIdDR();
+
+  AliFemtoModelCorrFctnNonIdDR& operator=(const AliFemtoModelCorrFctnNonIdDR& aCorrFctn);
+
+  virtual AliFemtoString Report();
+  virtual void AddRealPair(AliFemtoPair* aPair);
+  virtual void AddMixedPair(AliFemtoPair* aPair);
+
+  virtual void Finish();
+
+  virtual AliFemtoModelCorrFctn* Clone();
+
+  virtual TList* GetOutputList();
+  void Write();
+
+private:
+  TH1D *fNumTOutP;     // True numerator for pair with positive k*out
+  TH1D *fNumTOutN;     // True numerator for pair with negative k*out
+  TH1D *fNumTSideP;    // True numerator for pair with positive k*side
+  TH1D *fNumTSideN;    // True numerator for pair with negative k*side
+  TH1D *fNumTLongP;    // True numerator for pair with positive k*long
+  TH1D *fNumTLongN;    // True numerator for pair with negative k*long
+
+  TH1D *fNumFOutP;     // Fake numerator for pair with positive k*out
+  TH1D *fNumFOutN;     // Fake numerator for pair with negative k*out
+  TH1D *fNumFSideP;    // Fake numerator for pair with positive k*side
+  TH1D *fNumFSideN;    // Fake numerator for pair with negative k*side
+  TH1D *fNumFLongP;    // Fake numerator for pair with positive k*long
+  TH1D *fNumFLongN;    // Fake numerator for pair with negative k*long
+
+  TH1D *fDenOutP;     // Denominator for pair with positive k*out
+  TH1D *fDenOutN;     // Denominator for pair with negative k*out
+  TH1D *fDenSideP;    // Denominator for pair with positive k*side
+  TH1D *fDenSideN;    // Denominator for pair with negative k*side
+  TH1D *fDenLongP;    // Denominator for pair with positive k*long
+  TH1D *fDenLongN;    // Denominator for pair with negative k*long
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoModelCorrFctnNonIdDR, 1)
+#endif
+};
+
+
+#endif
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctnSource.cxx b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctnSource.cxx
new file mode 100644 (file)
index 0000000..d40aa3f
--- /dev/null
@@ -0,0 +1,285 @@
+////////////////////////////////////////////////////////////////////////////////
+///                                                                          ///
+/// alifemtomodelcorrfctnsource - the class for correlation function which   ///
+/// uses the model framework and weight generation and saves the generated   ///
+/// emission source                                                          ///
+/// Authors: Adam Kisiel, kisiel@mps.ohio-state.edu                          ///
+///                                                                          ///
+////////////////////////////////////////////////////////////////////////////////
+#ifdef __ROOT__
+  ClassImp(AliFemtoModelCorrFctnSource, 1)
+#endif
+
+#include "AliFemtoModelGausLCMSFreezeOutGenerator.h"
+#include "AliFemtoModelHiddenInfo.h"
+#include "AliFemtoModelCorrFctnSource.h"
+#include "AliFemtoKTPairCut.h"
+#include "AliFemtoAnalysisReactionPlane.h"
+    
+//_______________________
+AliFemtoModelCorrFctnSource::AliFemtoModelCorrFctnSource(): 
+  AliFemtoModelCorrFctn(),
+  fHistROut(0),
+  fHistRSide(0),
+  fHistRLong(0),
+  fHistRStar(0),
+  fHistdNdR(0),
+  fHistNumWS(0),
+  fHistDenWS(0),
+  fUseRPSelection(0)
+{
+  // default constructor
+  char buf[100];
+  char title[100] = "CFSource";
+  snprintf(buf , 100,  "%sOut", title);
+  fHistROut = new TH1D(buf,buf,100,-50.0,50.0);
+  snprintf(buf , 100,  "%sSide", title);
+  fHistRSide = new TH1D(buf,buf,100,-50.0,50.0);
+  snprintf(buf , 100,  "%sLong", title);
+  fHistRLong = new TH1D(buf,buf,100,-50.0,50.0);
+  snprintf(buf , 100,  "%sInv", title);
+  fHistRStar = new TH1D(buf,buf,100,-50.0,50.0);
+  snprintf(buf , 100,  "%sdNdR", title);
+  fHistdNdR = new TH1D(buf,buf,100,-50.0,50.0);
+
+  snprintf(buf , 100,  "%sNWS", title);
+  fHistNumWS = new TH2D(buf,buf,50,0.0,0.5,100,0.0,2.0);
+  snprintf(buf , 100,  "%sDWS", title);
+  fHistDenWS = new TH2D(buf,buf,50,0.0,0.5,100,0.0,2.0);
+
+  fHistROut->Sumw2();
+  fHistRSide->Sumw2();
+  fHistRLong->Sumw2();
+  fHistRStar->Sumw2();
+  fHistdNdR->Sumw2();
+}
+//_______________________
+AliFemtoModelCorrFctnSource::AliFemtoModelCorrFctnSource(const char *title, Int_t aNbins, Double_t aQinvLo, Double_t aQinvHi):
+  AliFemtoModelCorrFctn(title, aNbins, aQinvLo, aQinvHi),
+  fHistROut(0),
+  fHistRSide(0),
+  fHistRLong(0),
+  fHistRStar(0),
+  fHistdNdR(0),
+  fHistNumWS(0),
+  fHistDenWS(0),
+  fUseRPSelection(0)
+{
+  // basic constructor
+  char buf[100];
+  snprintf(buf , 100,  "%sOut", title);
+  fHistROut = new TH1D(buf,buf,100,-50.0,50.0);
+  snprintf(buf , 100,  "%sSide", title);
+  fHistRSide = new TH1D(buf,buf,100,-50.0,50.0);
+  snprintf(buf , 100,  "%sLong", title);
+  fHistRLong = new TH1D(buf,buf,100,-50.0,50.0);
+  snprintf(buf , 100,  "%sInv", title);
+  fHistRStar = new TH1D(buf,buf,100,-50.0,50.0);
+  snprintf(buf , 100,  "%sdNdR", title);
+  fHistdNdR = new TH1D(buf,buf,100,-50.0,50.0);
+
+  snprintf(buf , 100,  "%sNWS", title);
+  fHistNumWS = new TH2D(buf,buf,50,0.0,0.5,100,0.0,2.0);
+  snprintf(buf , 100,  "%sDWS", title);
+  fHistDenWS = new TH2D(buf,buf,50,0.0,0.5,100,0.0,2.0);
+
+  fHistROut->Sumw2();
+  fHistRSide->Sumw2();
+  fHistRLong->Sumw2();
+  fHistRStar->Sumw2();
+  fHistdNdR->Sumw2();
+}
+//_______________________
+AliFemtoModelCorrFctnSource::AliFemtoModelCorrFctnSource(const AliFemtoModelCorrFctnSource& aCorrFctn):
+  AliFemtoModelCorrFctn(aCorrFctn),
+  fHistROut(0),
+  fHistRSide(0),
+  fHistRLong(0),
+  fHistRStar(0),
+  fHistdNdR(0),
+  fHistNumWS(0),
+  fHistDenWS(0),
+  fUseRPSelection(0)
+{
+  // copy constructor
+  fHistROut = new TH1D (*aCorrFctn.fHistROut);
+  fHistRSide = new TH1D(*aCorrFctn.fHistRSide);
+  fHistRLong = new TH1D(*aCorrFctn.fHistRLong);
+  fHistRStar = new TH1D(*aCorrFctn.fHistRStar);
+  fHistdNdR = new TH1D(*aCorrFctn.fHistdNdR);
+  fHistNumWS = new TH2D(*aCorrFctn.fHistNumWS);
+  fHistDenWS = new TH2D(*aCorrFctn.fHistDenWS);
+
+  fUseRPSelection = aCorrFctn.fUseRPSelection;
+}
+//_______________________
+AliFemtoModelCorrFctnSource::~AliFemtoModelCorrFctnSource()
+{
+  // destructor
+  if (fHistROut) delete fHistROut;
+  if (fHistRSide) delete fHistRSide;
+  if (fHistRLong) delete fHistRLong;
+  if (fHistRStar) delete fHistRStar;
+  if (fHistdNdR) delete fHistdNdR;
+  if (fHistNumWS) delete fHistNumWS;
+  if (fHistDenWS) delete fHistDenWS;
+  if (fNumeratorTrue) delete fNumeratorTrue;
+  if (fNumeratorFake) delete fNumeratorFake;
+  if (fDenominator) delete fDenominator;
+}
+
+//_______________________
+AliFemtoModelCorrFctnSource& AliFemtoModelCorrFctnSource::operator=(const AliFemtoModelCorrFctnSource& aCorrFctn)
+{
+  // assignment operator
+  if (this == &aCorrFctn) 
+    return *this;
+  if (aCorrFctn.fHistROut)
+    fHistROut = new TH1D (*aCorrFctn.fHistROut);
+  else fHistROut = 0;
+  if (aCorrFctn.fHistRSide)
+    fHistRSide = new TH1D(*aCorrFctn.fHistRSide);
+  else fHistRSide = 0;
+  if (aCorrFctn.fHistRLong)
+    fHistRLong = new TH1D(*aCorrFctn.fHistRLong);
+  else fHistRLong = 0;
+  if (aCorrFctn.fHistRStar)
+    fHistRStar = new TH1D(*aCorrFctn.fHistRStar);
+  fHistRStar = 0;
+  if (aCorrFctn.fHistdNdR)
+    fHistdNdR = new TH1D(*aCorrFctn.fHistdNdR);
+  else fHistdNdR = 0;
+  if (aCorrFctn.fHistNumWS)
+    fHistNumWS = new TH2D(*aCorrFctn.fHistNumWS);
+  else fHistNumWS = 0;
+  if (aCorrFctn.fHistDenWS)
+    fHistDenWS = new TH2D(*aCorrFctn.fHistDenWS);
+  else fHistDenWS = 0;
+
+  fUseRPSelection = aCorrFctn.fUseRPSelection;
+
+  return *this;
+}
+//_______________________
+AliFemtoString AliFemtoModelCorrFctnSource::Report()
+{
+  // construct report
+  AliFemtoString tStr = "AliFemtoModelCorrFctnSource report";
+
+  return tStr;
+}
+
+//_______________________
+void AliFemtoModelCorrFctnSource::AddRealPair(AliFemtoPair* aPair)
+{
+  // add real (effect) pair
+//   if (fPairCut){
+//     if (!(fPairCut->Pass(aPair))) return;
+//   }
+  if (fPairCut){
+    if (fUseRPSelection) {
+      AliFemtoKTPairCut *ktc = dynamic_cast<AliFemtoKTPairCut *>(fPairCut);
+      if (!ktc) { 
+       cout << "RP aware cut requested, but not connected to the CF" << endl;
+       if (!(fPairCut->Pass(aPair))) return;
+      }
+      else {
+       AliFemtoAnalysisReactionPlane *arp = dynamic_cast<AliFemtoAnalysisReactionPlane *> (HbtAnalysis());
+       if (!arp) {
+         cout << "RP aware cut requested, but not connected to the CF" << endl;
+         if (!(fPairCut->Pass(aPair))) return;
+       }
+       else if (!(ktc->Pass(aPair, arp->GetCurrentReactionPlane()))) return;
+      }
+    }
+    else
+      if (!(fPairCut->Pass(aPair))) return;
+  }
+  
+  AliFemtoModelCorrFctn::AddRealPair(aPair);
+
+}
+//_______________________
+void AliFemtoModelCorrFctnSource::AddMixedPair(AliFemtoPair* aPair)
+{
+  // add mixed (background) pair
+//   if (fPairCut){
+//     if (!(fPairCut->Pass(aPair))) return;
+//   }
+  if (fPairCut){
+    if (fUseRPSelection) {
+      AliFemtoKTPairCut *ktc = dynamic_cast<AliFemtoKTPairCut *>(fPairCut);
+      if (!ktc) { 
+       cout << "RP aware cut requested, but not connected to the CF" << endl;
+       if (!(fPairCut->Pass(aPair))) return;
+      }
+      else {
+       AliFemtoAnalysisReactionPlane *arp = dynamic_cast<AliFemtoAnalysisReactionPlane *> (HbtAnalysis());
+       if (!arp) {
+         cout << "RP aware cut requested, but not connected to the CF" << endl;
+         if (!(fPairCut->Pass(aPair))) return;
+       }
+       else if (!(ktc->Pass(aPair, arp->GetCurrentReactionPlane()))) return;
+      }
+    }
+    else
+      if (!(fPairCut->Pass(aPair))) return;
+  }
+  
+  AliFemtoModelCorrFctn::AddMixedPair(aPair);
+  // save the generated positions
+  if (aPair->KStar() < 0.2) {
+    fHistROut->Fill (fManager->GetWeightGenerator()->GetRStarOut());
+    fHistRSide->Fill(fManager->GetWeightGenerator()->GetRStarSide());
+    fHistRLong->Fill(fManager->GetWeightGenerator()->GetRStarLong());
+    fHistRStar->Fill(fManager->GetWeightGenerator()->GetRStar());
+    fHistdNdR->Fill (fManager->GetWeightGenerator()->GetRStar(),1.0/(fManager->GetWeightGenerator()->GetRStar()*fManager->GetWeightGenerator()->GetRStar()));
+  }
+
+  fHistDenWS->Fill(aPair->QInv(), 1.0);
+  Double_t weight = fManager->GetWeight(aPair);
+  fHistNumWS->Fill(aPair->QInv(), weight);
+}
+//_______________________
+void AliFemtoModelCorrFctnSource::Write()
+{
+  // write out all the histograms
+  fHistROut->Write();
+  fHistRSide->Write();
+  fHistRLong->Write();
+  fHistRStar->Write();
+  fHistdNdR->Write();
+  fHistNumWS->Write();
+  fHistDenWS->Write();
+
+  AliFemtoModelCorrFctn::Write();
+}
+//________________________
+TList* AliFemtoModelCorrFctnSource::GetOutputList()
+{
+  // Prepare the list of objects to be written to the output
+  TList *tOutputList = AliFemtoModelCorrFctn::GetOutputList();
+
+  tOutputList->Add(fHistROut); 
+  tOutputList->Add(fHistRSide);  
+  tOutputList->Add(fHistRLong);  
+  tOutputList->Add(fHistRStar);  
+  tOutputList->Add(fHistdNdR);  
+  tOutputList->Add(fHistDenWS);
+  tOutputList->Add(fHistNumWS);
+
+  return tOutputList;
+}
+//_______________________
+AliFemtoModelCorrFctn* AliFemtoModelCorrFctnSource::Clone()
+{
+  // Clone the correlation function
+  AliFemtoModelCorrFctnSource *tCopy = new AliFemtoModelCorrFctnSource(*this);
+  
+  return tCopy;
+}
+
+void AliFemtoModelCorrFctnSource::SetUseRPSelection(unsigned short aRPSel)
+{
+  fUseRPSelection = aRPSel;
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctnSource.h b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctnSource.h
new file mode 100644 (file)
index 0000000..f5ecc71
--- /dev/null
@@ -0,0 +1,58 @@
+////////////////////////////////////////////////////////////////////////////////
+///                                                                          ///
+/// AliFemtoModelCorrFctnSource - the class for correlation function which   ///
+/// uses the model framework and weight generation and saves the generated   ///
+/// emission source                                                          ///
+/// Authors: Adam Kisiel, kisiel@mps.ohio-state.edu                          ///
+///                                                                          ///
+////////////////////////////////////////////////////////////////////////////////
+#ifndef ALIFEMTOMODELCORRFCTNSOURCE_H
+#define ALIFEMTOMODELCORRFCTNSOURCE_H
+
+#include "TH2D.h"
+#include "AliFemtoCorrFctn.h"
+#include "AliFemtoPair.h"
+#include "AliFemtoModelManager.h"
+#include "AliFemtoModelCorrFctn.h"
+
+class AliFemtoModelCorrFctnSource: public AliFemtoModelCorrFctn {
+
+public:
+  AliFemtoModelCorrFctnSource();
+  AliFemtoModelCorrFctnSource(const char *title, Int_t aNbins, Double_t aQinvLo, Double_t aQinvHi);
+  AliFemtoModelCorrFctnSource(const AliFemtoModelCorrFctnSource& aCorrFctn);
+  virtual ~AliFemtoModelCorrFctnSource();
+  
+  AliFemtoModelCorrFctnSource& operator=(const AliFemtoModelCorrFctnSource& aCorrFctn);
+
+  virtual AliFemtoString Report();
+
+  virtual void AddRealPair(AliFemtoPair* aPair);
+  virtual void AddMixedPair(AliFemtoPair* aPir);
+
+  virtual void Write();
+  virtual TList* GetOutputList();
+
+  virtual AliFemtoModelCorrFctn* Clone();
+
+  void SetUseRPSelection(unsigned short aRPSel);
+protected:
+
+  TH1D *fHistROut;     // Distribution of Rout
+  TH1D *fHistRSide;    // Distribution of Rside
+  TH1D *fHistRLong;    // Distribution of Rlong
+  TH1D *fHistRStar;    // Distribution of RStar
+  TH1D *fHistdNdR;     // Distribution of RStar weighted by Jacobian 
+  TH2D *fHistNumWS;    // Weight spread for numerator
+  TH2D *fHistDenWS;    // Weight spread for denominator
+
+private:
+
+  unsigned short fUseRPSelection;  // The pair cut uses RP selection
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoModelCorrFctnSource, 1)
+#endif
+};
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctnTrueQ.cxx b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctnTrueQ.cxx
new file mode 100644 (file)
index 0000000..e3d814e
--- /dev/null
@@ -0,0 +1,138 @@
+////////////////////////////////////////////////////////////////////////////////
+///                                                                          ///
+/// AliFemtoModelCorrFctnTrueQ - the class for correlation function which   ///
+/// uses the model framework and weight generation and saves the generated   ///
+/// emission source                                                          ///
+/// Authors: Adam Kisiel, kisiel@mps.ohio-state.edu                          ///
+///                                                                          ///
+////////////////////////////////////////////////////////////////////////////////
+#ifdef __ROOT__
+  ClassImp(AliFemtoModelCorrFctnTrueQ, 1)
+#endif
+
+#include "AliFemtoModelGausLCMSFreezeOutGenerator.h"
+#include "AliFemtoModelHiddenInfo.h"
+#include "AliFemtoModelCorrFctnTrueQ.h"
+    
+//_______________________
+AliFemtoModelCorrFctnTrueQ::AliFemtoModelCorrFctnTrueQ(): 
+  AliFemtoModelCorrFctn(),
+  fTrueNum(0),
+  fTrueDen(0)
+{
+  // default constructor
+  char buf[100];
+  char title[100] = "CFTrueQ";
+  snprintf(buf , 100,  "%sNum", title);
+  fTrueNum = new TH1D(buf,buf,100,0.0,0.4);
+  snprintf(buf , 100,  "%sDen", title);
+  fTrueDen = new TH1D(buf,buf,100,0.0,0.4);
+
+  fTrueNum->Sumw2();
+  fTrueDen->Sumw2();
+}
+//_______________________
+AliFemtoModelCorrFctnTrueQ::AliFemtoModelCorrFctnTrueQ(const char *title, Int_t aNbins, Double_t aQinvLo, Double_t aQinvHi):
+  AliFemtoModelCorrFctn(title, aNbins, aQinvLo, aQinvHi),
+  fTrueNum(0),
+  fTrueDen(0)
+{
+  // basic constructor
+  char buf[100];
+  snprintf(buf , 100,  "%sTrueQNum", title);
+  fTrueNum = new TH1D(buf,buf,aNbins,aQinvLo,aQinvHi);
+  snprintf(buf , 100,  "%sTrueQDen", title);
+  fTrueDen = new TH1D(buf,buf,aNbins,aQinvLo,aQinvHi);
+
+  fTrueNum->Sumw2();
+  fTrueDen->Sumw2();
+}
+//_______________________
+AliFemtoModelCorrFctnTrueQ::AliFemtoModelCorrFctnTrueQ(const AliFemtoModelCorrFctnTrueQ& aCorrFctn):
+  AliFemtoModelCorrFctn(aCorrFctn),
+  fTrueNum(0),
+  fTrueDen(0)
+{
+  // copy constructor
+  fTrueNum = new TH1D(*aCorrFctn.fTrueNum);
+  fTrueDen = new TH1D(*aCorrFctn.fTrueDen);
+}
+//_______________________
+AliFemtoModelCorrFctnTrueQ::~AliFemtoModelCorrFctnTrueQ()
+{
+  // destructor
+  if (fTrueNum) delete fTrueNum;
+  if (fTrueDen) delete fTrueDen;
+  if (fNumeratorTrue) delete fNumeratorTrue;
+  if (fNumeratorFake) delete fNumeratorFake;
+  if (fDenominator) delete fDenominator;
+}
+
+//_______________________
+AliFemtoModelCorrFctnTrueQ& AliFemtoModelCorrFctnTrueQ::operator=(const AliFemtoModelCorrFctnTrueQ& aCorrFctn)
+{
+  // assignment operator
+  if (this == &aCorrFctn) 
+    return *this;
+  if (aCorrFctn.fTrueNum)
+    fTrueNum = new TH1D (*aCorrFctn.fTrueNum);
+  else fTrueNum = 0;
+  if (aCorrFctn.fTrueDen)
+    fTrueDen = new TH1D(*aCorrFctn.fTrueDen);
+  else fTrueDen = 0;
+
+  return *this;
+}
+//_______________________
+AliFemtoString AliFemtoModelCorrFctnTrueQ::Report()
+{
+  // construct report
+  AliFemtoString tStr = "AliFemtoModelCorrFctnTrueQ report";
+
+  return tStr;
+}
+
+//_______________________
+void AliFemtoModelCorrFctnTrueQ::AddRealPair(AliFemtoPair* aPair)
+{
+  // add real (effect) pair
+  AliFemtoModelCorrFctn::AddRealPair(aPair);
+  fTrueNum->Fill(fManager->GetWeightGenerator()->GetKStar()*2);
+}
+//_______________________
+void AliFemtoModelCorrFctnTrueQ::AddMixedPair(AliFemtoPair* aPair)
+{
+  // add mixed (background) pair
+  AliFemtoModelCorrFctn::AddMixedPair(aPair);
+  // save the generated positions
+  fTrueDen->Fill(fManager->GetWeightGenerator()->GetKStar()*2);
+}
+//_______________________
+void AliFemtoModelCorrFctnTrueQ::Write()
+{
+  // write out all the histograms
+  fTrueNum->Write();
+  fTrueDen->Write();
+  
+  AliFemtoModelCorrFctn::Write();
+}
+//_______________________
+TList* AliFemtoModelCorrFctnTrueQ::GetOutputList()
+{
+  // Prepare the list of objects to be written to the output
+  TList *tOutputList = AliFemtoModelCorrFctn::GetOutputList();
+
+  tOutputList->Add(fTrueNum); 
+  tOutputList->Add(fTrueDen);  
+
+  return tOutputList;
+}
+//_______________________
+AliFemtoModelCorrFctn* AliFemtoModelCorrFctnTrueQ::Clone()
+{
+  // Clone the correlation function
+  AliFemtoModelCorrFctnTrueQ *tCopy = new AliFemtoModelCorrFctnTrueQ(*this);
+  
+  return tCopy;
+}
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctnTrueQ.h b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelCorrFctnTrueQ.h
new file mode 100644 (file)
index 0000000..e2f892d
--- /dev/null
@@ -0,0 +1,49 @@
+////////////////////////////////////////////////////////////////////////////////
+///                                                                          ///
+/// AliFemtoModelCorrFctnTrueQ - the class for correlation function which    ///
+/// uses the model framework and weight generation and saves the correlation ///
+/// function in true qinv                                                    ///
+/// Authors: Adam Kisiel, kisiel@mps.ohio-state.edu                          ///
+///                                                                          ///
+////////////////////////////////////////////////////////////////////////////////
+#ifndef ALIFEMTOMODELCORRFCTNTRUEQ_H
+#define ALIFEMTOMODELCORRFCTNTRUEQ_H
+
+#include "AliFemtoCorrFctn.h"
+#include "AliFemtoPair.h"
+#include "AliFemtoModelManager.h"
+#include "AliFemtoModelCorrFctn.h"
+
+class AliFemtoModelCorrFctnTrueQ: public AliFemtoModelCorrFctn {
+
+public:
+  AliFemtoModelCorrFctnTrueQ();
+  AliFemtoModelCorrFctnTrueQ(const char *title, Int_t aNbins, Double_t aQinvLo, Double_t aQinvHi);
+  AliFemtoModelCorrFctnTrueQ(const AliFemtoModelCorrFctnTrueQ& aCorrFctn);
+  virtual ~AliFemtoModelCorrFctnTrueQ();
+  
+  AliFemtoModelCorrFctnTrueQ& operator=(const AliFemtoModelCorrFctnTrueQ& aCorrFctn);
+
+  virtual AliFemtoString Report();
+
+  virtual void AddRealPair(AliFemtoPair* aPair);
+  virtual void AddMixedPair(AliFemtoPair* aPir);
+
+  virtual void Write();
+  virtual TList* GetOutputList();
+
+  virtual AliFemtoModelCorrFctn* Clone();
+
+protected:
+
+  TH1D *fTrueNum;           // Numerator in true q
+  TH1D *fTrueDen;           // Denominator in true q
+private:
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoModelCorrFctnTrueQ, 1)
+#endif
+};
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelGausRinvFreezeOutGenerator.cxx b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelGausRinvFreezeOutGenerator.cxx
new file mode 100644 (file)
index 0000000..3f3f3f0
--- /dev/null
@@ -0,0 +1,179 @@
+////////////////////////////////////////////////////////////////////////////////
+///                                                                          ///
+/// AliFemtoModelGausRinvFreezeOutGenerator - freeze-out                     ///
+/// coordinates generator, generating a 3D gaussian ellipsoid in LCMS        ///
+/// Authors: Adam Kisiel kisiel@mps.ohio-state.edu                           ///
+///                                                                          ///
+////////////////////////////////////////////////////////////////////////////////
+#ifdef __ROOT__
+  ClassImp(AliFemtoModelGausRinvFreezeOutGenerator, 1)
+#endif
+
+#include "math.h"
+#include "AliFemtoModelGausRinvFreezeOutGenerator.h"
+#include "AliFemtoModelHiddenInfo.h"
+#include "AliFemtoModelGlobalHiddenInfo.h"
+#include "AliFemtoLorentzVector.h"
+
+//_______________________
+AliFemtoModelGausRinvFreezeOutGenerator::AliFemtoModelGausRinvFreezeOutGenerator() :
+  fSizeInv(0),
+  fSelectPrimary(false)
+{
+  // Default constructor
+  fRandom = new TRandom2();
+}
+
+//_______________________
+AliFemtoModelGausRinvFreezeOutGenerator::AliFemtoModelGausRinvFreezeOutGenerator(const AliFemtoModelGausRinvFreezeOutGenerator &aModel):
+  AliFemtoModelFreezeOutGenerator(),
+  fSizeInv(0),
+  fSelectPrimary(false)
+{
+  // Copy constructor
+  fRandom = new TRandom2();
+  SetSizeInv(aModel.GetSizeInv());
+}
+//_______________________
+AliFemtoModelGausRinvFreezeOutGenerator::~AliFemtoModelGausRinvFreezeOutGenerator()
+{
+  if (fRandom) delete fRandom;
+}
+//_______________________
+AliFemtoModelGausRinvFreezeOutGenerator& AliFemtoModelGausRinvFreezeOutGenerator::operator=(const AliFemtoModelGausRinvFreezeOutGenerator &aModel)
+{
+  if (this != &aModel) {
+    fRandom = new TRandom2();
+    SetSizeInv(aModel.GetSizeInv());
+  }
+
+  return *this;
+
+}
+//_______________________
+void AliFemtoModelGausRinvFreezeOutGenerator::GenerateFreezeOut(AliFemtoPair *aPair)
+{
+  AliFemtoModelHiddenInfo *inf1 = (AliFemtoModelHiddenInfo *) aPair->Track1()->HiddenInfo();
+  AliFemtoModelHiddenInfo *inf2 = (AliFemtoModelHiddenInfo *) aPair->Track2()->HiddenInfo();
+
+  if ((!inf1) || (!inf2)) { cout << "Hidden info not created! "  << endl; exit(kFALSE); }
+
+  if (fSelectPrimary) {
+    const AliFemtoModelGlobalHiddenInfo *infg1 = dynamic_cast<const AliFemtoModelGlobalHiddenInfo *>(aPair->Track1()->HiddenInfo());
+    const AliFemtoModelGlobalHiddenInfo *infg2 = dynamic_cast<const AliFemtoModelGlobalHiddenInfo *>(aPair->Track2()->HiddenInfo());
+    
+    if ((infg1) && (infg2)) {
+      // assume the emission point is in [cm] and try to judge if
+      // both particles are primary
+      Double_t dist1 = infg1->GetGlobalEmissionPoint()->Perp();
+      Double_t dist2 = infg2->GetGlobalEmissionPoint()->Perp();
+
+      if ((dist1 > 0.05) && (dist2 > 0.05)) {
+       // At least one particle is non primary
+       if (!(inf1->GetEmissionPoint())) {
+         AliFemtoLorentzVector tPos(-1000,1000,-500,0);
+         inf1->SetEmissionPoint(&tPos);
+       }
+       else
+         inf1->SetEmissionPoint(-1000,1000,-500,0);
+       if (!(inf2->GetEmissionPoint())) {
+         AliFemtoLorentzVector tPos(fRandom->Gaus(0,1000.0),fRandom->Gaus(0,1000),fRandom->Gaus(0,1000),0.0);
+         inf2->SetEmissionPoint(&tPos);
+       }
+       else
+         inf2->SetEmissionPoint(fRandom->Gaus(0,1000), fRandom->Gaus(0,1000), fRandom->Gaus(0,1000), 0.0);
+       
+       return;
+      }
+    }
+  }
+
+  // Generate two particle emission points with respect
+  // to their pair momentum 
+  // The source is the 3D Gaussian ellipsoid in the LCMS frame
+
+  // Calculate sum momenta
+  Double_t tPx = inf1->GetTrueMomentum()->x() + inf2->GetTrueMomentum()->x();
+  Double_t tPy = inf1->GetTrueMomentum()->y() + inf2->GetTrueMomentum()->y();
+  Double_t tPz = inf1->GetTrueMomentum()->z() + inf2->GetTrueMomentum()->z();
+  Double_t tM1 = inf1->GetMass();
+  Double_t tM2 = inf2->GetMass();
+  Double_t tE1 = sqrt(tM1*tM1 + inf1->GetTrueMomentum()->Mag2());
+  Double_t tE2 = sqrt(tM2*tM2 + inf2->GetTrueMomentum()->Mag2());
+  Double_t tEs = tE1 + tE2;
+
+  Double_t tPt = sqrt(tPx*tPx + tPy*tPy);
+  Double_t tMt = sqrt(tEs*tEs - tPz*tPz);
+
+  // Generate positions in PRF from a Gaussian
+  Double_t tROutS =  fRandom->Gaus(0,fSizeInv); // reuse of long
+  Double_t tRSideS = fRandom->Gaus(0,fSizeInv);
+  Double_t tRLongS = fRandom->Gaus(0,fSizeInv);
+  Double_t tRTimeS = 0;
+      
+  Double_t tBetat  = tPt/tMt;
+  Double_t tGammat = 1.0/sqrt(1.0-tBetat*tBetat);
+
+  Double_t tBetaz  = tPz/tEs;
+  Double_t tGammaz = 1.0/sqrt(1.0-tBetaz*tBetaz);
+
+  Double_t tROut = tGammat * (tROutS + tBetat * tRTimeS);
+  Double_t tDtL  = tGammat * (tRTimeS + tBetat * tROutS);
+  Double_t tRSide = tRSideS;
+
+  Double_t tRLong = tGammaz * (tRLongS + tBetaz * tDtL);
+  Double_t tDt    = tGammaz * (tDtL + tBetaz * tRLongS);
+         
+  tPx /= tPt;
+  tPy /= tPt;
+         
+  Double_t tXout  = tROut*tPx-tRSide*tPy;
+  Double_t tXside = tROut*tPy+tRSide*tPx;
+  Double_t tXlong = tRLong;
+  Double_t tXtime = tDt;
+  
+  if (!(inf1->GetEmissionPoint())) {
+    AliFemtoLorentzVector tPos(0,0,0,0);
+    inf1->SetEmissionPoint(&tPos);
+  }
+  else
+    inf1->SetEmissionPoint(0,0,0,0);
+  if (!(inf2->GetEmissionPoint())) {
+    AliFemtoLorentzVector tPos(tXout,tXside,tXlong,tXtime);
+    inf2->SetEmissionPoint(&tPos);
+  }
+  else
+    inf2->SetEmissionPoint(tXout, tXside, tXlong, tXtime);
+}
+
+//_______________________
+void AliFemtoModelGausRinvFreezeOutGenerator::SetSizeInv(Double_t aSizeInv)
+{
+  fSizeInv = aSizeInv;
+}
+//_______________________
+Double_t AliFemtoModelGausRinvFreezeOutGenerator::GetSizeInv() const
+{
+  return fSizeInv;
+}
+//_______________________
+AliFemtoModelFreezeOutGenerator* AliFemtoModelGausRinvFreezeOutGenerator::Clone() const
+{ 
+  return GetGenerator(); 
+}
+//_______________________
+inline AliFemtoModelFreezeOutGenerator* AliFemtoModelGausRinvFreezeOutGenerator::GetGenerator() const 
+{ 
+  AliFemtoModelFreezeOutGenerator* tModel = new AliFemtoModelGausRinvFreezeOutGenerator(*this); 
+  return tModel; 
+}
+//_______________________
+void AliFemtoModelGausRinvFreezeOutGenerator::SetSelectPrimaryFromHidden(bool aUse)
+{
+  fSelectPrimary = aUse;
+}
+Bool_t AliFemtoModelGausRinvFreezeOutGenerator::GetSelectPrimaryFromHidden()
+{
+  return fSelectPrimary;
+}
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelGausRinvFreezeOutGenerator.h b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoModelGausRinvFreezeOutGenerator.h
new file mode 100644 (file)
index 0000000..9bcf481
--- /dev/null
@@ -0,0 +1,52 @@
+////////////////////////////////////////////////////////////////////////////////
+///                                                                          ///
+/// AliFemtoModelGausRinvFreezeOutGenerator - freeze-out                     ///
+/// coordinates generator, generating a 3D gaussian spheroid in PRF          ///
+/// Authors: Adam Kisiel kisiel@mps.ohio-state.edu                           ///
+///                                                                          ///
+////////////////////////////////////////////////////////////////////////////////
+#ifndef AliFemtoModelGausRinvFreezeOutGenerator_hh
+#define AliFemtoModelGausRinvFreezeOutGenerator_hh
+
+#include "AliFemtoModelFreezeOutGenerator.h"
+
+#include "TRandom.h"
+
+class AliFemtoModelGausRinvFreezeOutGenerator : public AliFemtoModelFreezeOutGenerator
+{
+ public:
+  AliFemtoModelGausRinvFreezeOutGenerator();
+  AliFemtoModelGausRinvFreezeOutGenerator(const AliFemtoModelGausRinvFreezeOutGenerator &aModel);
+  virtual ~AliFemtoModelGausRinvFreezeOutGenerator();
+  virtual void GenerateFreezeOut(AliFemtoPair *aPair);
+  AliFemtoModelGausRinvFreezeOutGenerator& operator=(const AliFemtoModelGausRinvFreezeOutGenerator &aModel);
+
+  void SetSelectPrimaryFromHidden(bool aUse);
+  Bool_t GetSelectPrimaryFromHidden();
+
+  void SetSizeInv(Double_t aSizeInv);
+  
+  Double_t GetSizeInv() const;
+
+  virtual AliFemtoModelFreezeOutGenerator* Clone() const;
+
+ protected:
+  Double_t fSizeInv;        // Size of the source
+  Bool_t fSelectPrimary;    // If set to true, the existing hidden info is assumed
+                            // to contain the particle creation point (in cm)
+                            // and the model will try to guess whether the particle
+                            // is primary based on that and assign creation point
+                            // only for primary particles
+
+ private:
+  AliFemtoModelFreezeOutGenerator* GetGenerator() const;
+               
+#ifdef __ROOT__
+  ClassDef(AliFemtoModelGausRinvFreezeOutGenerator, 1)
+#endif
+
+    };
+  
+#endif
+
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoPairCutAntiGamma.cxx b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoPairCutAntiGamma.cxx
new file mode 100644 (file)
index 0000000..0e31e03
--- /dev/null
@@ -0,0 +1,165 @@
+/////////////////////////////////////////////////////////////////////////////
+//                                                                         //
+// AliFemtoPairCutAntiGamma - a pair cut which checks     //
+// for some pair qualities that attempt to identify slit/doubly            //
+// reconstructed tracks and also selects pairs based on their separation   //
+// at the entrance to the TPC                                              //
+//                                                                         //
+/////////////////////////////////////////////////////////////////////////////
+/***************************************************************************
+ *
+ * $Id: AliFemtoPairCutAntiGamma.cxx,v 1.1.2.1 2007/10/19 13:35:33 akisiel Exp $
+ *
+ * Author: Adam Kisiel, Ohio State, kisiel@mps.ohio-state.edu
+ ***************************************************************************
+ *
+ * Description: part of STAR HBT Framework: AliFemtoMaker package
+ *   a cut to remove "shared" and "split" pairs
+ *
+ ***************************************************************************
+ *
+ *
+ **************************************************************************/
+
+#include "AliFemtoPairCutAntiGamma.h"
+#include <string>
+#include <cstdio>
+#include <TMath.h>
+
+#ifdef __ROOT__
+ClassImp(AliFemtoPairCutAntiGamma)
+#endif
+
+//__________________
+AliFemtoPairCutAntiGamma::AliFemtoPairCutAntiGamma():
+  AliFemtoShareQualityPairCut(),
+  fMaxEEMinv(0.0),
+  fMaxDTheta(0.0),
+  fDTPCMin(0),
+  fUseAOD(kFALSE)
+{
+}
+//__________________
+AliFemtoPairCutAntiGamma::AliFemtoPairCutAntiGamma(const AliFemtoPairCutAntiGamma& c) : 
+  AliFemtoShareQualityPairCut(c),
+  fMaxEEMinv(0.0),
+  fMaxDTheta(0.0),
+  fDTPCMin(0),
+  fUseAOD(kFALSE)
+{ 
+  fMaxEEMinv = c.fMaxEEMinv;
+  fMaxDTheta = c.fMaxDTheta;
+  fDTPCMin = c.fDTPCMin;
+  fUseAOD = c.fUseAOD;
+}
+
+AliFemtoPairCutAntiGamma& AliFemtoPairCutAntiGamma::operator=(const AliFemtoPairCutAntiGamma& c)
+{
+  if (this != &c) {
+    fMaxEEMinv = c.fMaxEEMinv;
+    fMaxDTheta = c.fMaxDTheta;
+    fDTPCMin = c.fDTPCMin;
+    fUseAOD = c.fUseAOD;
+  }
+
+  return *this;
+
+}
+//__________________
+AliFemtoPairCutAntiGamma::~AliFemtoPairCutAntiGamma(){
+  /* no-op */
+}
+//__________________
+bool AliFemtoPairCutAntiGamma::Pass(const AliFemtoPair* pair){
+  // Accept pairs based on their TPC entrance separation and
+  // quality and sharity
+  bool temp = true;
+
+  double me = 0.000511;
+
+  if ((pair->Track1()->Track()->Charge() * pair->Track2()->Track()->Charge()) < 0.0) {
+    double theta1 = pair->Track1()->Track()->P().Theta();
+    double theta2 = pair->Track2()->Track()->P().Theta();
+    double dtheta = TMath::Abs(theta1 - theta2);
+    
+    double e1 = TMath::Sqrt(me*me + pair->Track1()->Track()->P().Mag2());
+    double e2 = TMath::Sqrt(me*me + pair->Track2()->Track()->P().Mag2());
+    
+    double minv = 2*me*me + 2*(e1*e2 - 
+                              pair->Track1()->Track()->P().x()*pair->Track2()->Track()->P().x() -
+                              pair->Track1()->Track()->P().y()*pair->Track2()->Track()->P().y() -
+                              pair->Track1()->Track()->P().z()*pair->Track2()->Track()->P().z());
+    
+    if ((minv < fMaxEEMinv) && (dtheta < fMaxDTheta)) temp = false;
+  }
+
+  bool tempTPCEntrance = true;
+  if(!fUseAOD)
+    {
+      double distx = pair->Track1()->Track()->NominalTpcEntrancePoint().x() - pair->Track2()->Track()->NominalTpcEntrancePoint().x();
+      double disty = pair->Track1()->Track()->NominalTpcEntrancePoint().y() - pair->Track2()->Track()->NominalTpcEntrancePoint().y();
+      double distz = pair->Track1()->Track()->NominalTpcEntrancePoint().z() - pair->Track2()->Track()->NominalTpcEntrancePoint().z();
+      double dist = sqrt(distx*distx + disty*disty + distz*distz);
+
+      tempTPCEntrance = dist > fDTPCMin;
+    }
+
+
+  if (temp && tempTPCEntrance) {
+    temp = AliFemtoShareQualityPairCut::Pass(pair);
+    if (temp) fNPairsPassed++;
+    else fNPairsFailed++;
+    return temp;
+  }
+  else
+    {
+    fNPairsFailed++;
+    return false;
+    }
+
+}
+//__________________
+AliFemtoString AliFemtoPairCutAntiGamma::Report(){
+  // Prepare a report from the execution
+  string stemp = "AliFemtoPairCutAntiGamma Pair Cut - remove pairs possibly coming from Gamma conversions\n";  
+  char ctemp[100];
+  stemp += ctemp;
+  snprintf(ctemp , 100, "Number of pairs which passed:\t%ld  Number which failed:\t%ld\n",fNPairsPassed,fNPairsFailed);
+  stemp += ctemp;
+  AliFemtoString returnThis = stemp;
+  return returnThis;}
+//__________________
+
+TList *AliFemtoPairCutAntiGamma::ListSettings()
+{
+  // return a list of settings in a writable form
+  TList *tListSetttings =  AliFemtoShareQualityPairCut::ListSettings();
+  char buf[200];
+  snprintf(buf, 200, "AliFemtoPairCutAntiGamma.maxeeminv=%f", fMaxEEMinv);
+  snprintf(buf, 200, "AliFemtoPairCutAntiGamma.maxdtheta=%f", fMaxDTheta);
+  tListSetttings->AddLast(new TObjString(buf));
+
+  return tListSetttings;
+}
+
+void AliFemtoPairCutAntiGamma::SetMaxEEMinv(Double_t maxeeminv)
+{
+  fMaxEEMinv = maxeeminv;
+}
+
+void AliFemtoPairCutAntiGamma::SetMaxThetaDiff(Double_t maxdtheta)
+{
+  fMaxDTheta = maxdtheta;
+}
+
+void AliFemtoPairCutAntiGamma::SetTPCEntranceSepMinimum(double dtpc)
+{
+  fDTPCMin = dtpc;
+}
+
+void AliFemtoPairCutAntiGamma::SetUseAOD(Bool_t UseAOD)
+{
+  fUseAOD = UseAOD;
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoPairCutAntiGamma.h b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoPairCutAntiGamma.h
new file mode 100644 (file)
index 0000000..9114e50
--- /dev/null
@@ -0,0 +1,61 @@
+/////////////////////////////////////////////////////////////////////////////
+//                                                                         //
+// AliFemtoPairCutAntiGamma - a pair cut which checks     //
+// for some pair qualities that attempt to identify slit/doubly            //
+// reconstructed tracks and also selects pairs based on their separation   //
+// at the entrance to the TPC                                              //
+//                                                                         //
+/////////////////////////////////////////////////////////////////////////////
+/***************************************************************************
+ *
+ * $Id: AliFemtoPairCutAntiGamma.h,v 1.1.2.1 2007/10/19 13:35:33 akisiel Exp $
+ *
+ * Author: Adam Kisiel, Ohio State University, kisiel@mps.ohio-state.edu
+ ***************************************************************************
+ *
+ * Description: part of STAR HBT Framework: AliFemtoMaker package
+ *   a cut to remove "shared" and "split" pairs
+ *
+ ***************************************************************************
+ *
+ *
+ **************************************************************************/
+
+
+#ifndef ALIFEMTOPAIRCUTANTIGAMMA_H
+#define ALIFEMTOPAIRCUTANTIGAMMA_H
+
+#include "AliFemtoPairCut.h"
+#include "AliFemtoShareQualityPairCut.h"
+
+class AliFemtoPairCutAntiGamma : public AliFemtoShareQualityPairCut{
+public:
+  AliFemtoPairCutAntiGamma();
+  AliFemtoPairCutAntiGamma(const AliFemtoPairCutAntiGamma& c);
+  virtual ~AliFemtoPairCutAntiGamma();
+  AliFemtoPairCutAntiGamma& operator=(const AliFemtoPairCutAntiGamma& c);
+
+  virtual bool Pass(const AliFemtoPair* pair);
+  virtual AliFemtoString Report();
+  virtual TList *ListSettings();
+  virtual AliFemtoPairCut* Clone();
+  void SetMaxEEMinv(Double_t maxeeminv);
+  void SetMaxThetaDiff(Double_t maxdtheta);
+  void SetTPCEntranceSepMinimum(double dtpc);
+  void SetUseAOD(Bool_t UseAOD);
+  
+ protected:
+  Double_t fMaxEEMinv; // Maximum allowed ee Minv
+  Double_t fMaxDTheta; // Maximum polar angle difference
+  Double_t fDTPCMin;          // Minimum allowed pair nominal separation at the entrance to the TPC
+  Bool_t fUseAOD; // Use AODs
+
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoPairCutAntiGamma, 0)
+#endif
+};
+
+inline AliFemtoPairCut* AliFemtoPairCutAntiGamma::Clone() { AliFemtoPairCutAntiGamma* c = new AliFemtoPairCutAntiGamma(*this); return c;}
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoPairCutPt.cxx b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoPairCutPt.cxx
new file mode 100644 (file)
index 0000000..0bb57c2
--- /dev/null
@@ -0,0 +1,123 @@
+/////////////////////////////////////////////////////////////////////////////////////
+//                                                                                 //
+// AliFemtoPairCutPt - a pair cut which checks if the sum of the transverse        //
+// momenta of two particles fit within given range                                //
+// Authors: Malgorzata Janik, Warsaw University of Technology, majanik@cern.ch     //
+//          Lukasz Graczykowski, Warsaw University of Technology, lgraczyk@cern.ch //
+//                                                                                //
+/////////////////////////////////////////////////////////////////////////////////////
+
+#include "AliFemtoPairCutPt.h"
+#include <string>
+#include <cstdio>
+#include <TMath.h>
+
+#ifdef __ROOT__
+ClassImp(AliFemtoPairCutPt)
+#endif
+
+//__________________
+AliFemtoPairCutPt::AliFemtoPairCutPt():
+  AliFemtoPairCut(),
+  fSumPtMin(0),
+  fSumPtMax(10000),
+  fNPairsFailed(0),
+  fNPairsPassed(0)
+{
+
+}
+//__________________
+AliFemtoPairCutPt::AliFemtoPairCutPt(double lo, double hi):
+  AliFemtoPairCut(),
+  fSumPtMin(lo),
+  fSumPtMax(hi),
+  fNPairsFailed(0),
+  fNPairsPassed(0)
+{
+  fSumPtMin=lo;
+  fSumPtMax=hi;
+}
+//__________________
+AliFemtoPairCutPt::AliFemtoPairCutPt(const AliFemtoPairCutPt& c) : 
+  AliFemtoPairCut(c),
+  fSumPtMin(0),
+  fSumPtMax(0),
+  fNPairsFailed(0),
+  fNPairsPassed(0)
+{ 
+  fSumPtMin = c.fSumPtMin;
+  fSumPtMax = c.fSumPtMax;
+}
+AliFemtoPairCutPt& AliFemtoPairCutPt::operator=(const AliFemtoPairCutPt& c)
+{
+  if (this != &c) {
+    fSumPtMin = c.fSumPtMin;
+    fSumPtMax = c.fSumPtMax;
+  }
+
+  return *this;
+
+}
+
+//__________________
+AliFemtoPairCutPt::~AliFemtoPairCutPt(){
+  /* no-op */
+}
+//__________________
+bool AliFemtoPairCutPt::Pass(const AliFemtoPair* pair){
+
+  bool temp = true;
+
+  double pt1 = pair->Track1()->Track()->Pt();
+  double pt2 = pair->Track2()->Track()->Pt();
+
+  double pt_sum = pt1 + pt2;
+
+  if(pt_sum >= fSumPtMin && pt_sum <= fSumPtMax)
+    temp = true;
+  else
+    temp = false;
+
+  if(temp) 
+    fNPairsPassed++;
+  else fNPairsFailed++;
+
+
+  return temp;
+  
+}
+//__________________
+AliFemtoString AliFemtoPairCutPt::Report(){
+  // Prepare a report from the execution
+  string stemp = "AliFemtoPairCutPt Pair Cut\n";  
+  char ctemp[100];
+  stemp += ctemp;
+  snprintf(ctemp,100,"Number of pairs which passed:\t%ld  Number which failed:\t%ld\n",(long int) fNPairsPassed,(long int) fNPairsFailed);
+  stemp += ctemp;
+  AliFemtoString returnThis = stemp;
+  return returnThis;}
+//__________________
+
+TList *AliFemtoPairCutPt::ListSettings()
+{
+  // return a list of settings in a writable form
+  TList *tListSetttings = new TList();
+  char buf[200];
+  snprintf(buf, 200, "AliFemtoPairCutPt.sumptmin=%f", fSumPtMin);
+  snprintf(buf, 200, "AliFemtoPairCutPr.sumptmax=%f", fSumPtMax);
+  tListSetttings->AddLast(new TObjString(buf));
+
+  return tListSetttings;
+}
+
+void AliFemtoPairCutPt::SetMinSumPt(Double_t sumptmin)
+{
+  fSumPtMin = sumptmin;
+}
+
+void AliFemtoPairCutPt::SetMaxSumPt(Double_t sumptmax)
+{
+  fSumPtMax = sumptmax;
+}
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoPairCutPt.h b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoPairCutPt.h
new file mode 100644 (file)
index 0000000..7048413
--- /dev/null
@@ -0,0 +1,44 @@
+/////////////////////////////////////////////////////////////////////////////////////
+//                                                                                 //
+// AliFemtoPairCutPt - a pair cut which checks if the sum of the transverse        //
+// momenta of two particles fit within given range                                //
+// Authors: Malgorzata Janik, Warsaw University of Technology, majanik@cern.ch     //
+//          Lukasz Graczykowski, Warsaw University of Technology, lgraczyk@cern.ch //
+//                                                                                //
+/////////////////////////////////////////////////////////////////////////////////////
+
+
+#ifndef ALIFEMTOPAIRCUTPT_H
+#define ALIFEMTOPAIRCUTPT_H
+
+#include "AliFemtoPairCut.h"
+
+class AliFemtoPairCutPt : public AliFemtoPairCut{
+public:
+  AliFemtoPairCutPt();
+  AliFemtoPairCutPt(double lo, double hi);
+  AliFemtoPairCutPt(const AliFemtoPairCutPt& c);
+  virtual ~AliFemtoPairCutPt();
+  AliFemtoPairCutPt& operator=(const AliFemtoPairCutPt& c);
+
+  virtual bool Pass(const AliFemtoPair* pair);
+  virtual AliFemtoString Report();
+  virtual TList *ListSettings();
+  AliFemtoPairCut* Clone();
+  void SetMinSumPt(Double_t sumptmin);
+  void SetMaxSumPt(Double_t sumptmax);
+  
+ protected:
+  Double_t fSumPtMin;
+  Double_t fSumPtMax;
+  Double_t fNPairsFailed;
+  Double_t fNPairsPassed;
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoPairCutPt, 0)
+#endif
+};
+
+inline AliFemtoPairCut* AliFemtoPairCutPt::Clone() { AliFemtoPairCutPt* c = new AliFemtoPairCutPt(*this); return c;}
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoPairCutRadialDistance.cxx b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoPairCutRadialDistance.cxx
new file mode 100644 (file)
index 0000000..d17db09
--- /dev/null
@@ -0,0 +1,151 @@
+/////////////////////////////////////////////////////////////////////////////////
+//                                                                             //
+// AliFemtoPairCutRadialDistance - a pair cut which checks                     //
+// for some pair qualities that attempt to identify slit/doubly                //
+// reconstructed tracks and also selects pairs based on their separation       //
+// at the entrance to the TPC                                                  //
+//                                                                             //
+/////////////////////////////////////////////////////////////////////////////////
+/********************************************************************************
+ *
+ * Author: Johanna Gramling, University of Heidelberg, jgramlin@cern.ch
+ *         Malgorzata Janik, Warsaw University of Technology, majanik@cern.ch
+ *         Lukasz Graczykowski, Warsaw University of Technology, lgraczyk@cern.ch
+ *
+ ********************************************************************************/
+
+#include "AliFemtoPairCutRadialDistance.h"
+#include <string>
+#include <cstdio>
+
+#ifdef __ROOT__
+ClassImp(AliFemtoPairCutRadialDistance)
+#endif
+
+//__________________
+AliFemtoPairCutRadialDistance::AliFemtoPairCutRadialDistance():
+  AliFemtoPairCutAntiGamma(),
+  fDPhiStarMin(0),
+  fEtaMin(0),
+  fMinRad(0.8),
+  fMagSign(1)
+{
+}
+//__________________
+AliFemtoPairCutRadialDistance::AliFemtoPairCutRadialDistance(const AliFemtoPairCutRadialDistance& c) : 
+  AliFemtoPairCutAntiGamma(c),
+  fDPhiStarMin(0), 
+  fEtaMin(0),
+  fMinRad(0.8),
+  fMagSign(1)
+{ 
+  fDPhiStarMin = c.fDPhiStarMin;
+  fEtaMin = c.fEtaMin;
+  fMinRad = c.fMinRad;
+  fMagSign = c.fMagSign;
+}
+
+//__________________
+AliFemtoPairCutRadialDistance::~AliFemtoPairCutRadialDistance(){
+  /* no-op */
+}
+AliFemtoPairCutRadialDistance& AliFemtoPairCutRadialDistance::operator=(const AliFemtoPairCutRadialDistance& c)
+{
+  if (this != &c) {
+    fDPhiStarMin = c.fDPhiStarMin;
+    fEtaMin = c.fEtaMin;
+    fMinRad = c.fMinRad;
+    fMagSign = c.fMagSign;
+  }
+
+  return *this;
+}
+//__________________
+bool AliFemtoPairCutRadialDistance::Pass(const AliFemtoPair* pair){
+  // Accept pairs based on their TPC entrance separation and
+  // quality and sharity
+  //  bool temp = true;
+  
+//    double pih = 3.14159265358979312;
+//    double pit = 6.28318530717958623;
+
+  
+  double phi1 = pair->Track1()->Track()->P().Phi();
+  double phi2 = pair->Track2()->Track()->P().Phi();
+  double chg1 = pair->Track1()->Track()->Charge();
+  double chg2 = pair->Track2()->Track()->Charge();
+  double ptv1 = pair->Track1()->Track()->Pt();
+  double ptv2 = pair->Track2()->Track()->Pt();
+  double eta1 = pair->Track1()->Track()->P().PseudoRapidity();
+  double eta2 = pair->Track2()->Track()->P().PseudoRapidity();
+
+
+  Double_t rad;
+  Bool_t pass5 = kTRUE;
+
+    rad = fMinRad;
+    for (Double_t iter=fMinRad*10; iter<251; iter+=1.0) {
+      Double_t dps = (phi1-phi2+(TMath::ASin(-0.075*chg1*fMagSign*rad/ptv1))-(TMath::ASin(-0.075*chg2*fMagSign*rad/ptv2)));
+      double etad = eta2 - eta1;
+      if (fabs(etad)<fEtaMin && fabs(dps)<fDPhiStarMin) {
+       //       cout << "5% cut is not passed - returning" << endl;
+       pass5 = kFALSE;
+       break;
+      }
+      rad+=0.01;
+    }
+  
+
+  if (pass5) {
+    pass5 = AliFemtoPairCutAntiGamma::Pass(pair);
+  }
+  else
+    fNPairsFailed++;
+
+  return pass5;
+}
+//__________________
+AliFemtoString AliFemtoPairCutRadialDistance::Report(){
+  // Prepare a report from the execution
+  string stemp = "AliFemtoRadialDistance Pair Cut - remove shared and split pairs and pairs with small separation at the specified radius\n";  char ctemp[100];
+  snprintf(ctemp , 100, "Accept pair with separation more that %f",fDPhiStarMin);
+  stemp += ctemp;
+  snprintf(ctemp , 100, "Number of pairs which passed:\t%ld  Number which failed:\t%ld\n",fNPairsPassed,fNPairsFailed);
+  stemp += ctemp;
+  AliFemtoString returnThis = stemp;
+  return returnThis;}
+//__________________
+
+TList *AliFemtoPairCutRadialDistance::ListSettings()
+{
+  // return a list of settings in a writable form
+  TList *tListSetttings =  AliFemtoPairCutAntiGamma::ListSettings();
+  char buf[200];
+  snprintf(buf, 200, "AliFemtoPairCutRadialDistance.phistarsepmin=%f", fDPhiStarMin);
+  tListSetttings->AddLast(new TObjString(buf));
+
+  return tListSetttings;
+}
+
+void AliFemtoPairCutRadialDistance::SetPhiStarDifferenceMinimum(double dtpc)
+{
+  fDPhiStarMin = dtpc;
+}
+
+void AliFemtoPairCutRadialDistance::SetEtaDifferenceMinimum(double etpc) 
+{
+  fEtaMin = etpc;
+}
+
+
+void AliFemtoPairCutRadialDistance::SetMinimumRadius(double minrad) 
+{
+  fMinRad = minrad;
+}
+
+void AliFemtoPairCutRadialDistance::SetMagneticFieldSign(int magsign)
+{
+  if(magsign>1) fMagSign = 1;
+  else if(magsign<1) fMagSign = -1;
+  else fMagSign = magsign;
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoPairCutRadialDistance.h b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoPairCutRadialDistance.h
new file mode 100644 (file)
index 0000000..d725f46
--- /dev/null
@@ -0,0 +1,62 @@
+/////////////////////////////////////////////////////////////////////////////////
+//                                                                             //
+// AliFemtoPairCutRadialDistance - a pair cut which checks                     //
+// for some pair qualities that attempt to identify slit/doubly                //
+// reconstructed tracks and also selects pairs based on their separation       //
+// at the entrance to the TPC                                                  //
+//                                                                             //
+/////////////////////////////////////////////////////////////////////////////////
+/********************************************************************************
+ *
+ * Authors: Johanna Gramling, University of Heidelberg, jgramlin@cern.ch
+ *          Malgorzata Janik, Warsaw University of Technology, majanik@cern.ch
+ *          Lukasz Graczykowski, Warsaw University of Technology, lgraczyk@cern.ch
+ *
+ ********************************************************************************/
+
+
+
+#ifndef ALIFEMTOPAIRCUTRADIALDISTANCE_H
+#define ALIFEMTOPAIRCUTRADIALDISTANCE_H
+
+// do I need these lines ?
+//#ifndef StMaker_H
+//#include "StMaker.h"
+//#endif
+
+#include "AliFemtoPairCut.h"
+#include "AliFemtoShareQualityPairCut.h"
+#include "AliFemtoPairCutAntiGamma.h"
+
+class AliFemtoPairCutRadialDistance : public AliFemtoPairCutAntiGamma {
+public:
+  AliFemtoPairCutRadialDistance();
+  AliFemtoPairCutRadialDistance(const AliFemtoPairCutRadialDistance& c);
+  virtual ~AliFemtoPairCutRadialDistance();
+  AliFemtoPairCutRadialDistance& operator=(const AliFemtoPairCutRadialDistance& c);
+
+  virtual bool Pass(const AliFemtoPair* pair);
+  virtual AliFemtoString Report();
+  virtual TList *ListSettings();
+  virtual AliFemtoPairCut* Clone();
+  void SetPhiStarDifferenceMinimum(double dtpc);
+  void SetEtaDifferenceMinimum(double etpc);
+  void SetMinimumRadius(double minrad);
+  void SetMagneticFieldSign(int magsign);
+
+
+ protected:
+  Double_t fDPhiStarMin;          // Minimum allowed pair separation //at the specified radius
+  //Double_t fRadius;           // Radius at which the separation is calculated
+  Double_t fEtaMin;           // Minimum allowed pair separation in eta
+  Double_t fMinRad;
+  Int_t fMagSign;
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoPairCutRadialDistance, 0)
+#endif
+};
+
+inline AliFemtoPairCut* AliFemtoPairCutRadialDistance::Clone() { AliFemtoPairCutRadialDistance* c = new AliFemtoPairCutRadialDistance(*this); return c;}
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoQAEventCut.cxx b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoQAEventCut.cxx
new file mode 100755 (executable)
index 0000000..1b36f0d
--- /dev/null
@@ -0,0 +1,132 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoQAEventCut - the basic cut to check QA for event cuts.             //
+// Only cuts on event multiplicity and z-vertex position                      //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+
+#include "AliFemtoQAEventCut.h"
+//#include <cstdio>
+
+#ifdef __ROOT__
+ClassImp(AliFemtoQAEventCut)
+#endif
+
+AliFemtoQAEventCut::AliFemtoQAEventCut() :
+  AliFemtoEventCut(),
+  fEventMult(),
+  fVertZPos(),
+  fAcceptBadVertex(false), 
+  fNEventsPassed(0), 
+  fNEventsFailed(0),
+  fHighOrLowSwitch(0), 
+  fEventMultQASwitch(kFALSE), 
+  fEventZPosQASwitch(kFALSE)
+{
+  // Default constructor
+  fEventMult[0] = 0;
+  fEventMult[1] = 100000;
+  fVertZPos[0] = -100.0;
+  fVertZPos[1] = 100.0;
+  
+  fHighOrLowSwitch = 1;
+  fEventMultQASwitch = false;
+  fEventZPosQASwitch = false;
+  fEventMultQAExclusionZone[0] = 0;
+  fEventMultQAExclusionZone[1] = 100000;
+  fEventZPosQAExclusionZone[0] = -100.0;
+  fEventZPosQAExclusionZone[1] = 100.0;
+
+} 
+//------------------------------
+AliFemtoQAEventCut::~AliFemtoQAEventCut(){
+  // Default destructor
+}
+//------------------------------
+AliFemtoQAEventCut& AliFemtoQAEventCut::operator=(AliFemtoQAEventCut& c)
+{
+  if (this != &c) {
+    fEventMult[0] = c.fEventMult[0];
+    fEventMult[1] = c.fEventMult[1];
+    fVertZPos[0] = c.fVertZPos[0];
+    fVertZPos[1] = c.fVertZPos[1];
+    
+    fHighOrLowSwitch = c.fHighOrLowSwitch;
+    fEventMultQASwitch = c.fEventMultQASwitch;
+    fEventZPosQASwitch = c.fEventZPosQASwitch;
+    fEventMultQAExclusionZone[0] = c.fEventMultQAExclusionZone[0];
+    fEventMultQAExclusionZone[1] = c.fEventMultQAExclusionZone[1];
+    fEventZPosQAExclusionZone[0] = c.fEventZPosQAExclusionZone[0];
+    fEventZPosQAExclusionZone[1] = c.fEventZPosQAExclusionZone[1];
+  }
+
+  return *this;
+}
+//------------------------------
+bool AliFemtoQAEventCut::Pass(const AliFemtoEvent* event){
+  // Pass events if they fall within the multiplicity and z-vertex
+  // position range. If QA cutting on quantity, pass if outside 
+  // exclusion zone between low and high cut values. Fail otherwise.
+  int mult =  event->NumberOfTracks();
+  double vertexZPos = event->PrimVertPos().z();
+  cout << "AliFemtoQAEventCut:: mult:       " << fEventMult[0] << " < " << mult << " < " << fEventMult[1] << endl;
+  cout << "AliFemtoQAEventCut:: VertexZPos: " << fVertZPos[0] << " < " << vertexZPos << " < " << fVertZPos[1] << endl;
+  
+  bool goodEvent;
+  
+  if (fEventMultQASwitch) {
+    goodEvent =
+      ( (((mult < fEventMultQAExclusionZone[0]) && (fHighOrLowSwitch > 0))  ||
+        ((mult > fEventMultQAExclusionZone[1]) && (fHighOrLowSwitch < 0))) &&
+      (mult > fEventMult[0]) && 
+      (mult < fEventMult[1]) && 
+      (vertexZPos > fVertZPos[0]) &&
+      (vertexZPos < fVertZPos[1]) &&
+      (fAcceptBadVertex || (event->PrimVertCov()[4] > -1000.0)));
+  }
+  else if (fEventZPosQASwitch) {
+    goodEvent =
+      ((((vertexZPos < fEventZPosQAExclusionZone[0]) && (fHighOrLowSwitch > 0))  ||
+       ((vertexZPos > fEventZPosQAExclusionZone[1]) && (fHighOrLowSwitch < 0))) &&
+      (mult > fEventMult[0]) && 
+      (mult < fEventMult[1]) && 
+      (vertexZPos > fVertZPos[0]) &&
+      (vertexZPos < fVertZPos[1]) &&
+      (fAcceptBadVertex || (event->PrimVertCov()[4] > -1000.0)));
+  }
+  else {
+  goodEvent =
+    ((mult > fEventMult[0]) && 
+     (mult < fEventMult[1]) && 
+     (vertexZPos > fVertZPos[0]) &&
+     (vertexZPos < fVertZPos[1]) &&
+     (fAcceptBadVertex || (event->PrimVertCov()[4] > -1000.0)));
+  }
+  
+  if (goodEvent) fHighOrLowSwitch *= -1;
+  goodEvent ? fNEventsPassed++ : fNEventsFailed++ ;
+  //cout << "AliFemtoQAEventCut:: return : " << goodEvent << endl;
+  return (goodEvent);
+}
+//------------------------------
+AliFemtoString AliFemtoQAEventCut::Report(){
+  // Prepare report
+  string stemp;
+  char ctemp[100];
+  snprintf(ctemp , 100, "\nMultiplicity:\t %d-%d",fEventMult[0],fEventMult[1]);
+  stemp = ctemp;
+  snprintf(ctemp , 100, "\nVertex Z-position:\t %E-%E",fVertZPos[0],fVertZPos[1]);
+  stemp += ctemp;
+  snprintf(ctemp , 100, "\nNumber of events which passed:\t%ld  Number which failed:\t%ld",fNEventsPassed,fNEventsFailed);
+  stemp += ctemp;
+  AliFemtoString returnThis = stemp;
+  return returnThis;
+}
+void AliFemtoQAEventCut::SetAcceptBadVertex(bool b)
+{
+  fAcceptBadVertex = b;
+}
+bool AliFemtoQAEventCut::GetAcceptBadVertex()
+{
+  return fAcceptBadVertex;
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoQAEventCut.h b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoQAEventCut.h
new file mode 100755 (executable)
index 0000000..5c2f9e3
--- /dev/null
@@ -0,0 +1,89 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoQAEventCut - the basic cut to check QA for event cuts.             //
+// Only cuts on event multiplicity and z-vertex position                      //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+
+#ifndef ALIFEMTOQAEVENTCUT_H
+#define ALIFEMTOQAEVENTCUT_H
+
+// do I need these lines ?
+//#ifndef StMaker_H
+//#include "StMaker.h"
+//#endif
+
+#include "AliFemtoEventCut.h"
+
+class AliFemtoQAEventCut : public AliFemtoEventCut {
+
+public:
+
+  AliFemtoQAEventCut();
+  AliFemtoQAEventCut(AliFemtoQAEventCut& c);
+  virtual ~AliFemtoQAEventCut();
+  AliFemtoQAEventCut& operator=(AliFemtoQAEventCut& c);
+
+
+  void SetEventMult(const int& lo,const int& hi);
+  void SetEventMultQASwitch(const bool Switch);
+  void SetEventMultQAExclusionZone(const int& lo, const int& hi);
+  void SetVertZPos(const float& lo, const float& hi);
+  void SetEventZPosQASwitch(const bool Switch);
+  void SetEventZPosQAExclusionZone(const float& lo, const float& hi);
+  void SetAcceptBadVertex(bool b);
+  int NEventsPassed() const;
+  int NEventsFailed() const;
+  bool GetAcceptBadVertex();
+
+  virtual AliFemtoString Report();
+  virtual bool Pass(const AliFemtoEvent* event);
+
+  AliFemtoQAEventCut* Clone();
+
+private:   // here are the quantities I want to cut on...
+
+  int   fEventMult[2];     // range of multiplicity
+  float fVertZPos[2];      // range of z-position of vertex
+  bool  fAcceptBadVertex;  // Set to true to accept events with bad vertex
+  long  fNEventsPassed;    // Number of events checked by this cut that passed
+  long  fNEventsFailed;    // Number of events checked by this cut that failed
+  
+  int   fHighOrLowSwitch;             // if 1, then previous hbtEvent was high; if -1, then previous event was low.
+  bool  fEventMultQASwitch;           // Turn on multiplicity exclusion zone (true=on)
+  int   fEventMultQAExclusionZone[2]; // Set limits of the multiplicity exclusion zone
+  bool  fEventZPosQASwitch;           // Turn on Zpos exclusion zone (true=on)
+  float fEventZPosQAExclusionZone[2]; // Set limits of the Zpos exclusion zone
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoQAEventCut, 1)
+#endif
+
+};
+
+inline void AliFemtoQAEventCut::SetEventMult(const int& lo, const int& hi){fEventMult[0]=lo; fEventMult[1]=hi;}
+inline void AliFemtoQAEventCut::SetEventMultQASwitch(const bool Switch) { fEventMultQASwitch = Switch; }
+inline void AliFemtoQAEventCut::SetEventMultQAExclusionZone(const int& lo, const int& hi) { fEventMultQAExclusionZone[0]=lo; fEventMultQAExclusionZone[1]=hi; }
+inline void AliFemtoQAEventCut::SetVertZPos(const float& lo, const float& hi){fVertZPos[0]=lo; fVertZPos[1]=hi;}
+inline void AliFemtoQAEventCut::SetEventZPosQASwitch(const bool Switch) { fEventZPosQASwitch = Switch; }
+inline void AliFemtoQAEventCut::SetEventZPosQAExclusionZone(const float& lo, const float& hi)  { fEventZPosQAExclusionZone[0]=lo; fEventZPosQAExclusionZone[1]=hi; }
+inline int  AliFemtoQAEventCut::NEventsPassed() const {return fNEventsPassed;}
+inline int  AliFemtoQAEventCut::NEventsFailed() const {return fNEventsFailed;}
+inline AliFemtoQAEventCut* AliFemtoQAEventCut::Clone() { AliFemtoQAEventCut* c = new AliFemtoQAEventCut(*this); return c;}
+inline AliFemtoQAEventCut::AliFemtoQAEventCut(AliFemtoQAEventCut& c) : AliFemtoEventCut(c), fAcceptBadVertex(kFALSE), fNEventsPassed(0), fNEventsFailed(0), fHighOrLowSwitch(0), fEventMultQASwitch(kFALSE), fEventZPosQASwitch(kFALSE) {
+  fEventMult[0] = c.fEventMult[0];
+  fEventMult[1] = c.fEventMult[1];
+  fVertZPos[0] = c.fVertZPos[0];
+  fVertZPos[1] = c.fVertZPos[1];
+  
+  fHighOrLowSwitch = c.fHighOrLowSwitch;
+  fEventMultQASwitch = c.fEventMultQASwitch;
+  fEventZPosQASwitch = c.fEventZPosQASwitch;
+  fEventMultQAExclusionZone[0] = c.fEventMultQAExclusionZone[0];
+  fEventMultQAExclusionZone[1] = c.fEventMultQAExclusionZone[1];
+  fEventZPosQAExclusionZone[0] = c.fEventZPosQAExclusionZone[0];
+  fEventZPosQAExclusionZone[1] = c.fEventZPosQAExclusionZone[1];
+}
+
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoQATrackCut.cxx b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoQATrackCut.cxx
new file mode 100644 (file)
index 0000000..218b19a
--- /dev/null
@@ -0,0 +1,494 @@
+/***************************************************************************
+ *
+ * $Id: AliFemtoQATrackCut.cxx 24360 2008-03-10 09:48:27Z akisiel $ 
+ *
+ * 
+ ***************************************************************************
+ *
+ * 
+ *              
+ *
+ ***************************************************************************
+ *
+ * $Log$
+ * Revision 1.3  2007/05/22 09:01:42  akisiel
+ * Add the possibiloity to save cut settings in the ROOT file
+ *
+ * Revision 1.2  2007/05/21 10:38:25  akisiel
+ * More coding rule conformance
+ *
+ * Revision 1.1  2007/05/16 10:25:06  akisiel
+ * Making the directory structure of AliFemtoUser flat. All files go into one common directory
+ *
+ * Revision 1.4  2007/05/03 09:46:10  akisiel
+ * Fixing Effective C++ warnings
+ *
+ * Revision 1.3  2007/04/27 07:25:59  akisiel
+ * Make revisions needed for compilation from the main AliRoot tree
+ *
+ * Revision 1.1.1.1  2007/04/25 15:38:41  panos
+ * Importing the HBT code dir
+ *
+ * Revision 1.4  2007-04-03 16:00:08  mchojnacki
+ * Changes to iprove memory managing
+ *
+ * Revision 1.3  2007/03/13 15:30:03  mchojnacki
+ * adding reader for simulated data
+ *
+ * Revision 1.2  2007/03/08 14:58:03  mchojnacki
+ * adding some alice stuff
+ *
+ * Revision 1.1.1.1  2007/03/07 10:14:49  mchojnacki
+ * First version on CVS
+ *
+ **************************************************************************/
+
+#include "AliFemtoQATrackCut.h"
+#include <cstdio>
+
+#ifdef __ROOT__ 
+ClassImp(AliFemtoQATrackCut)
+#endif
+
+
+// electron
+// 0.13 - 1.8
+// 0       7.594129e-02    8.256141e-03
+// 1       -5.535827e-01   8.170825e-02
+// 2       1.728591e+00    3.104210e-01
+// 3       -2.827893e+00   5.827802e-01
+// 4       2.503553e+00    5.736207e-01
+// 5       -1.125965e+00   2.821170e-01
+// 6       2.009036e-01    5.438876e-02
+
+// pion
+// 0.13 - 2.0
+// 0       1.063457e+00    8.872043e-03
+// 1       -4.222208e-01   2.534402e-02
+// 2       1.042004e-01    1.503945e-02
+
+// kaon
+// 0.18 - 2.0
+// 0       -7.289406e-02   1.686074e-03
+// 1       4.415666e-01    1.143939e-02
+// 2       -2.996790e-01   1.840964e-02
+// 3       6.704652e-02    7.783990e-03
+
+// proton
+// 0.26 - 2.0
+// 0       -3.730200e-02   2.347311e-03
+// 1       1.163684e-01    1.319316e-02
+// 2       8.354116e-02    1.997948e-02
+// 3       -4.608098e-02   8.336400e-03
+
+
+AliFemtoQATrackCut::AliFemtoQATrackCut() :
+    fCharge(0),
+    fLabel(0),
+    fStatus(0),
+    fminTPCclsF(0),
+    fminTPCncls(0),
+    fminITScls(0),
+    fminTPCchiNdof(0),
+    fMaxTPCncls(1000),
+    fMaxITSchiNdof(1000.0),
+    fMaxTPCchiNdof(1000.0),
+    fMaxSigmaToVertex(1000.0),
+    fNTracksPassed(0),
+    fNTracksFailed(0),
+    fRemoveKinks(kFALSE),
+    fMostProbable(0),
+    fTPCnclsExclusionSwitch(kFALSE),
+    fTPCchiNdofExclusionSwitch(kFALSE)
+{
+  // Default constructor
+  fNTracksPassed = fNTracksFailed = 0;
+  fCharge = 0;  // takes both charges 0
+  fPt[0]=0.0;              fPt[1] = 100.0;//100
+  fRapidity[0]=-2;       fRapidity[1]=2;//-2 2
+  fPidProbElectron[0]=-1;fPidProbElectron[1]=2;
+  fPidProbPion[0]=-1;    fPidProbPion[1]=2;
+  fPidProbKaon[0]=-1;fPidProbKaon[1]=2;
+  fPidProbProton[0]=-1;fPidProbProton[1]=2;
+  fPidProbMuon[0]=-1;fPidProbMuon[1]=2;
+  fLabel=false;
+  fStatus=0;
+  fminTPCclsF=0;
+  fminITScls=0;
+  fTPCnclsExclusionSwitch = false;
+  fTPCnclsExclusion[0] = 0;
+  fTPCnclsExclusion[1] = 1000;
+  fTPCchiNdofExclusionSwitch = false;
+  fTPCchiNdofExclusion[0] = 0.0;
+  fTPCchiNdofExclusion[1] = 1000.0;
+}
+//------------------------------
+AliFemtoQATrackCut::~AliFemtoQATrackCut(){
+  /* noop */
+}
+//------------------------------
+bool AliFemtoQATrackCut::Pass(const AliFemtoTrack* track)
+{
+  // test the particle and return 
+  // true if it meets all the criteria
+  // false if it doesn't meet at least one of the criteria
+  float tMost[5];
+  
+  //cout<<"AliFemtoESD  cut"<<endl;
+  //cout<<fPidProbPion[0]<<" < pi ="<<track->PidProbPion()<<" <"<<fPidProbPion[1]<<endl;
+  if (fStatus!=0)
+    {
+      //cout<<" status "<<track->Label()<<" "<<track->Flags()<<" "<<track->TPCnclsF()<<" "<<track->ITSncls()<<endl;
+      if ((track->Flags()&fStatus)!=fStatus)
+       {
+         //      cout<<track->Flags()<<" "<<fStatus<<" no go through status"<<endl;
+         return false;
+       }
+       
+    }
+  if (fRemoveKinks) {
+    if ((track->KinkIndex(0)) || (track->KinkIndex(1)) || (track->KinkIndex(2)))
+      return false;
+  }
+  if (fminTPCclsF>track->TPCnclsF())
+    {
+      //cout<<" No go because TPC Number of ClsF"<<fminTPCclsF<< " "<<track->TPCnclsF()<<endl;
+      return false;
+    }
+
+  // TPC number of clusters:
+  if (fTPCnclsExclusionSwitch) {
+    bool outTPCnclsExclusionZone[2];
+      outTPCnclsExclusionZone[0] = false;
+      outTPCnclsExclusionZone[1] = false;
+    if ( (fminTPCncls > track->TPCncls()) || (fTPCnclsExclusion[0] < track->TPCncls()) ) {
+      //cout<<" No go because TPC Number of ClsF"<<fminTPCclsF<< " "<<track->TPCnclsF()<<endl;
+      outTPCnclsExclusionZone[0] = true;
+    }
+    if ( (fMaxTPCncls < track->TPCncls()) || (fTPCnclsExclusion[1] > track->TPCncls()) ) {
+      //cout<<" No go because TPC Number of Cls"<<fMaxTPCclsF<< " "<<track->TPCnclsF()<<endl;
+      outTPCnclsExclusionZone[1] = true;
+    } 
+    if ( outTPCnclsExclusionZone[0] * outTPCnclsExclusionZone[1] ) { return false; }
+  } 
+  else {
+    if (fminTPCncls > track->TPCncls()) {
+      //cout<<" No go because TPC Number of ClsF"<<fminTPCclsF<< " "<<track->TPCnclsF()<<endl;
+      return false;
+    }
+    if (fMaxTPCncls < track->TPCncls()) {
+      //cout<<" No go because TPC Number of Cls"<<fMaxTPCclsF<< " "<<track->TPCnclsF()<<endl;
+      return false;
+    }
+  }
+
+  if (fminITScls>track->ITSncls())
+    {
+      //cout<<" No go because ITS Number of Cls"<<fminITScls<< " "<<track->ITSncls()<<endl;
+      return false;
+    }
+       
+  if (fMaxSigmaToVertex < track->SigmaToVertex()) {
+    return false;
+  }
+  
+  if (track->ITSncls() > 0) 
+    if ((track->ITSchi2()/track->ITSncls()) > fMaxITSchiNdof) {
+      return false;
+    }
+
+  // TPC chiNdof of tracks:
+  if (fTPCchiNdofExclusionSwitch && (track->TPCncls() > 0)) {
+    bool outTPCchiNdofExclusionZone[2];
+      outTPCchiNdofExclusionZone[0] = false;
+      outTPCchiNdofExclusionZone[1] = false;
+    if ( (fminTPCchiNdof > (track->TPCchi2()/track->TPCncls())) || (fTPCchiNdofExclusion[0] < (track->TPCchi2()/track->TPCncls())) ) {
+      //cout<<" No go because TPC Number of ClsF"<<fminTPCclsF<< " "<<track->TPCnclsF()<<endl;
+      outTPCchiNdofExclusionZone[0] = true;
+    }
+    if ( (fMaxTPCchiNdof < (track->TPCchi2()/track->TPCncls())) || (fTPCchiNdofExclusion[1] > (track->TPCchi2()/track->TPCncls())) ) {
+      //cout<<" No go because TPC Number of Cls"<<fMaxTPCclsF<< " "<<track->TPCnclsF()<<endl;
+      outTPCchiNdofExclusionZone[1] = true;
+    } 
+    if ( outTPCchiNdofExclusionZone[0] * outTPCchiNdofExclusionZone[1] ) { return false; }
+  } 
+  else {
+    if (fminTPCchiNdof > (track->TPCchi2()/track->TPCncls())) {
+      //cout<<" No go because TPC Number of ClsF"<<fminTPCclsF<< " "<<track->TPCnclsF()<<endl;
+      return false;
+    }
+    if (fMaxTPCchiNdof < (track->TPCchi2()/track->TPCncls())) {
+      //cout<<" No go because TPC Number of Cls"<<fMaxTPCclsF<< " "<<track->TPCnclsF()<<endl;
+      return false;
+    }
+  }
+
+  if (fLabel)
+    {
+      //cout<<"labels"<<endl;
+      if(track->Label()<0)
+       {
+         fNTracksFailed++;
+         //   cout<<"No Go Through the cut"<<endl;
+         //  cout<<fLabel<<" Label="<<track->Label()<<endl;
+         return false;
+       }    
+    }
+  if (fCharge!=0)
+    {              
+      //cout<<"AliFemtoESD  cut ch "<<endl;
+      //cout<<fCharge<<" Charge="<<track->Charge()<<endl;
+      if (track->Charge()!= fCharge)   
+       {
+         fNTracksFailed++;
+         //  cout<<"No Go Through the cut"<<endl;
+         // cout<<fCharge<<" Charge="<<track->Charge()<<endl;
+         return false;
+       }
+    }
+  float tEnergy = ::sqrt(track->P().Mag2()+fMass*fMass);
+  float tRapidity = 0.5*::log((tEnergy+track->P().z())/(tEnergy-track->P().z()));
+  float tPt = ::sqrt((track->P().x())*(track->P().x())+(track->P().y())*(track->P().y()));
+  if ((tRapidity<fRapidity[0])||(tRapidity>fRapidity[1]))
+    {
+      fNTracksFailed++;
+      //cout<<"No Go Through the cut"<<endl;   
+      //cout<<fRapidity[0]<<" < Rapidity ="<<tRapidity<<" <"<<fRapidity[1]<<endl;
+      return false;
+    }
+  if ((tPt<fPt[0])||(tPt>fPt[1]))
+    {
+      fNTracksFailed++;
+      //cout<<"No Go Through the cut"<<endl;
+      //cout<<fPt[0]<<" < Pt ="<<Pt<<" <"<<fPt[1]<<endl;
+      return false;
+    }
+//   cout << "Track has pids: " 
+//        << track->PidProbElectron() << " " 
+//        << track->PidProbMuon() << " " 
+//        << track->PidProbPion() << " " 
+//        << track->PidProbKaon() << " " 
+//        << track->PidProbProton() << " " 
+//        << track->PidProbElectron()+track->PidProbMuon()+track->PidProbPion()+track->PidProbKaon()+track->PidProbProton() << endl;
+
+    
+  if ((track->PidProbElectron()<fPidProbElectron[0])||(track->PidProbElectron()>fPidProbElectron[1]))
+    {
+      fNTracksFailed++;
+      //cout<<"No Go Through the cut"<<endl;
+      //cout<<fPidProbElectron[0]<<" < e ="<<track->PidProbElectron()<<" <"<<fPidProbElectron[1]<<endl;
+      return false;
+    }
+  if ((track->PidProbPion()<fPidProbPion[0])||(track->PidProbPion()>fPidProbPion[1]))
+    {
+      fNTracksFailed++;
+      //cout<<"No Go Through the cut"<<endl;
+      //cout<<fPidProbPion[0]<<" < pi ="<<track->PidProbPion()<<" <"<<fPidProbPion[1]<<endl;
+      return false;
+    }
+  if ((track->PidProbKaon()<fPidProbKaon[0])||(track->PidProbKaon()>fPidProbKaon[1]))
+    {
+      fNTracksFailed++;
+      //cout<<"No Go Through the cut"<<endl;
+      //cout<<fPidProbKaon[0]<<" < k ="<<track->PidProbKaon()<<" <"<<fPidProbKaon[1]<<endl;
+      return false;
+    }
+  if ((track->PidProbProton()<fPidProbProton[0])||(track->PidProbProton()>fPidProbProton[1]))
+    {
+      fNTracksFailed++;
+      //cout<<"No Go Through the cut"<<endl;
+      //cout<<fPidProbProton[0]<<" < p  ="<<track->PidProbProton()<<" <"<<fPidProbProton[1]<<endl;
+      return false;
+    }
+  if ((track->PidProbMuon()<fPidProbMuon[0])||(track->PidProbMuon()>fPidProbMuon[1]))
+    {
+      fNTracksFailed++;
+      //cout<<"No Go Through the cut"<<endl;
+      //cout<<fPidProbMuon[0]<<" <  mi="<<track->PidProbMuon()<<" <"<<fPidProbMuon[1]<<endl;
+      return false;
+    }
+
+  if (fMostProbable) {
+    tMost[0] = track->PidProbElectron()*PidFractionElectron(track->P().Mag());
+    tMost[1] = 0.0;
+    tMost[2] = track->PidProbPion()*PidFractionPion(track->P().Mag());
+    tMost[3] = track->PidProbKaon()*PidFractionKaon(track->P().Mag());
+    tMost[4] = track->PidProbProton()*PidFractionProton(track->P().Mag());
+    int imost=0;
+    float ipidmax = 0.0;
+    for (int ip=0; ip<5; ip++)
+      if (tMost[ip] > ipidmax) { ipidmax = tMost[ip]; imost = ip; };
+    if (imost != fMostProbable) return false;
+  }
+  
+  // cout<<"Go Through the cut"<<endl;
+  // cout<<fLabel<<" Label="<<track->Label()<<endl;
+  // cout<<fCharge<<" Charge="<<track->Charge()<<endl;
+  // cout<<fPt[0]<<" < Pt ="<<Pt<<" <"<<fPt[1]<<endl;
+  //cout<<fRapidity[0]<<" < Rapidity ="<<tRapidity<<" <"<<fRapidity[1]<<endl;
+  //cout<<fPidProbElectron[0]<<" <  e="<<track->PidProbElectron()<<" <"<<fPidProbElectron[1]<<endl;
+  //cout<<fPidProbPion[0]<<" <  pi="<<track->PidProbPion()<<" <"<<fPidProbPion[1]<<endl;
+  //cout<<fPidProbKaon[0]<<" <  k="<<track->PidProbKaon()<<" <"<<fPidProbKaon[1]<<endl;
+  //cout<<fPidProbProton[0]<<" <  p="<<track->PidProbProton()<<" <"<<fPidProbProton[1]<<endl;
+  //cout<<fPidProbMuon[0]<<" <  mi="<<track->PidProbMuon()<<" <"<<fPidProbMuon[1]<<endl;
+  fNTracksPassed++ ;
+  return true;
+    
+    
+}
+//------------------------------
+AliFemtoString AliFemtoQATrackCut::Report()
+{
+  // Prepare report from the execution
+  string tStemp;
+  char tCtemp[100];
+  snprintf(tCtemp , 100, "Particle mass:\t%E\n",this->Mass());
+  tStemp=tCtemp;
+  snprintf(tCtemp , 100, "Particle charge:\t%d\n",fCharge);
+  tStemp+=tCtemp;
+  snprintf(tCtemp , 100, "Particle pT:\t%E - %E\n",fPt[0],fPt[1]);
+  tStemp+=tCtemp;
+  snprintf(tCtemp , 100, "Particle rapidity:\t%E - %E\n",fRapidity[0],fRapidity[1]);
+  tStemp+=tCtemp;
+  snprintf(tCtemp , 100, "Number of tracks which passed:\t%ld  Number which failed:\t%ld\n",fNTracksPassed,fNTracksFailed);
+  tStemp += tCtemp;
+  AliFemtoString returnThis = tStemp;
+  return returnThis;
+}
+TList *AliFemtoQATrackCut::ListSettings()
+{
+  // return a list of settings in a writable form
+  TList *tListSetttings = new TList();
+  char buf[200];
+  snprintf(buf, 200, "AliFemtoQATrackCut.mass=%f", this->Mass());
+  tListSetttings->AddLast(new TObjString(buf));
+
+  snprintf(buf, 200, "AliFemtoQATrackCut.charge=%i", fCharge);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoQATrackCut.pidprobpion.minimum=%f", fPidProbPion[0]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoQATrackCut.pidprobpion.maximum=%f", fPidProbPion[1]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoQATrackCut.pidprobkaon.minimum=%f", fPidProbKaon[0]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoQATrackCut.pidprobkaon.maximum=%f", fPidProbKaon[1]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoQATrackCut.pidprobproton.minimum=%f", fPidProbProton[0]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoQATrackCut.pidprobproton.maximum=%f", fPidProbProton[1]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoQATrackCut.pidprobelectron.minimum=%f", fPidProbElectron[0]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoQATrackCut.pidprobelectron.maximum=%f", fPidProbElectron[1]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoQATrackCut.pidprobMuon.minimum=%f", fPidProbMuon[0]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoQATrackCut.pidprobMuon.maximum=%f", fPidProbMuon[1]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoQATrackCut.minimumtpcclusters=%i", fminTPCclsF);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoQATrackCut.minimumitsclusters=%i", fminTPCclsF);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoQATrackCut.pt.minimum=%f", fPt[0]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoQATrackCut.pt.maximum=%f", fPt[1]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoQATrackCut.rapidity.minimum=%f", fRapidity[0]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoQATrackCut.rapidity.maximum=%f", fRapidity[1]);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoQATrackCut.removekinks=%i", fRemoveKinks);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoQATrackCut.maxitschindof=%f", fMaxITSchiNdof);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoQATrackCut.maxtpcchindof=%f", fMaxTPCchiNdof);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoQATrackCut.maxsigmatovertex=%f", fMaxSigmaToVertex);
+  tListSetttings->AddLast(new TObjString(buf));
+  if (fMostProbable) {
+    if (fMostProbable == 2)
+      snprintf(buf, 200, "AliFemtoQATrackCut.mostprobable=%s", "Pion");
+    if (fMostProbable == 3)
+      snprintf(buf, 200, "AliFemtoQATrackCut.mostprobable=%s", "Kaon");
+    if (fMostProbable == 4)
+      snprintf(buf, 200, "AliFemtoQATrackCut.mostprobable=%s", "Proton");
+    tListSetttings->AddLast(new TObjString(buf));
+  }
+  return tListSetttings;
+}
+void AliFemtoQATrackCut::SetRemoveKinks(const bool& flag)
+{
+  fRemoveKinks = flag;
+}
+                           
+                           // electron
+// 0.13 - 1.8
+// 0       7.594129e-02    8.256141e-03
+// 1       -5.535827e-01   8.170825e-02
+// 2       1.728591e+00    3.104210e-01
+// 3       -2.827893e+00   5.827802e-01
+// 4       2.503553e+00    5.736207e-01
+// 5       -1.125965e+00   2.821170e-01
+// 6       2.009036e-01    5.438876e-02
+float AliFemtoQATrackCut::PidFractionElectron(float mom) const
+{
+  // Provide a parameterized fraction of electrons dependent on momentum
+  if (mom<0.13) return 0.0;
+  if (mom>1.8) return 0.0;
+  return (7.594129e-02 
+         -5.535827e-01*mom        
+         +1.728591e+00*mom*mom    
+         -2.827893e+00*mom*mom*mom 
+         +2.503553e+00*mom*mom*mom*mom    
+         -1.125965e+00*mom*mom*mom*mom*mom      
+         +2.009036e-01*mom*mom*mom*mom*mom*mom);   
+}
+
+// pion
+// 0.13 - 2.0
+// 0       1.063457e+00    8.872043e-03
+// 1       -4.222208e-01   2.534402e-02
+// 2       1.042004e-01    1.503945e-02
+float AliFemtoQATrackCut::PidFractionPion(float mom) const
+{
+  // Provide a parameterized fraction of pions dependent on momentum
+  if (mom<0.13) return 0.0;
+  if (mom>2.0) return 0.0;
+  return ( 1.063457e+00
+          -4.222208e-01*mom
+          +1.042004e-01*mom*mom);
+}
+
+// kaon
+// 0.18 - 2.0
+// 0       -7.289406e-02   1.686074e-03
+// 1       4.415666e-01    1.143939e-02
+// 2       -2.996790e-01   1.840964e-02
+// 3       6.704652e-02    7.783990e-03
+float AliFemtoQATrackCut::PidFractionKaon(float mom) const
+{
+  // Provide a parameterized fraction of kaons dependent on momentum
+  if (mom<0.18) return 0.0;
+  if (mom>2.0) return 0.0;
+  return (-7.289406e-02
+         +4.415666e-01*mom        
+         -2.996790e-01*mom*mom    
+         +6.704652e-02*mom*mom*mom);
+}
+
+// proton
+// 0.26 - 2.0
+// 0       -3.730200e-02   2.347311e-03
+// 1       1.163684e-01    1.319316e-02
+// 2       8.354116e-02    1.997948e-02
+// 3       -4.608098e-02   8.336400e-03
+float AliFemtoQATrackCut::PidFractionProton(float mom) const
+{
+  // Provide a parameterized fraction of protons dependent on momentum
+  if (mom<0.26) return  0.0;
+  if (mom>2.0) return 0.0;
+  return (-3.730200e-02  
+         +1.163684e-01*mom           
+         +8.354116e-02*mom*mom       
+         -4.608098e-02*mom*mom*mom);  
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoQATrackCut.h b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoQATrackCut.h
new file mode 100644 (file)
index 0000000..973d676
--- /dev/null
@@ -0,0 +1,133 @@
+///////////////////////////////////////////////////////////////////////////
+//                                                                       //
+// AliFemtoQATrackCut: A basic track cut that used information from     //
+// ALICE ESD to accept or reject the track.                              //  
+// Enables the selection on charge, transverse momentum, rapidity,       //
+// pid probabilities, number of ITS and TPC clusters                     //
+// Author: Marek Chojnacki (WUT), mchojnacki@knf.pw.edu.pl               //
+//                                                                       //
+///////////////////////////////////////////////////////////////////////////
+
+#ifndef AliFemtoQATrackCut_H
+#define AliFemtoQATrackCut_H
+
+//#ifndef StMaker_H
+//#include "StMaker.h"
+//#endif
+
+#include "AliFemtoTrackCut.h"
+
+class AliFemtoQATrackCut : public AliFemtoTrackCut 
+{
+
+ public:
+  AliFemtoQATrackCut();
+  virtual ~AliFemtoQATrackCut();
+
+  virtual bool Pass(const AliFemtoTrack* aTrack);
+
+  virtual AliFemtoString Report();
+  virtual TList *ListSettings();
+  virtual AliFemtoParticleType Type(){return hbtTrack;}
+
+  void SetPt(const float& lo, const float& hi);
+  void SetRapidity(const float& lo, const float& hi);
+  void SetCharge(const int& ch);
+  void SetPidProbElectron(const float& lo, const float& hi);
+  void SetPidProbPion(const float& lo, const float& hi);
+  void SetPidProbKaon(const float& lo, const float& hi);
+  void SetPidProbProton(const float& lo, const float& hi);
+  void SetPidProbMuon(const float& lo, const float& hi);
+  void SetLabel(const bool& flag);
+  void SetStatus(const long& w);
+  void SetminTPCclsF(const short& s);
+  void SetminTPCncls(const short& s);
+  void SetminITScls(const int& s);
+  void SetminTPCchiNdof(const float& s);
+  void SetRemoveKinks(const bool& flag);
+  void SetMaxTPCncls(const short& s);
+  void SetMaxITSChiNdof(const float& maxchi);
+  void SetMaxTPCChiNdof(const float& maxchi);
+  void SetMaxSigmaToVertex(const float& maxsig);
+  void SetMostProbablePion();
+  void SetMostProbableKaon();
+  void SetMostProbableProton();
+  void SetNoMostProbable(); 
+  
+  void SetTPCnclsExclusionSwitch(const bool& excluSwitch);
+  void SetTPCnclsExclusion(const short& lo, const short& hi);
+  void SetTPCchiNdofExclusionSwitch(const bool& excluSwitch);
+  void SetTPCchiNdofExclusion(const float& lo, const float& hi);
+
+ private:   // here are the quantities I want to cut on...
+
+  int               fCharge;             // particle charge
+  float             fPt[2];              // bounds for transverse momentum
+  float             fRapidity[2];        // bounds for rapidity
+  float             fPidProbElectron[2]; // bounds for electron probability
+  float             fPidProbPion[2];     // bounds for pion probability
+  float             fPidProbKaon[2];     // bounds for kaon probability
+  float             fPidProbProton[2];   // bounds for proton probability
+  float             fPidProbMuon[2];     // bounds for muon probability 
+  bool              fLabel;              // if true label<0 will not pass throught 
+  long              fStatus;             // staus flag
+
+  short             fminTPCclsF;         // min number of findable clusters in the TPC
+  short             fminTPCncls;         // min number of clusters in the TPC
+  int               fminITScls;          // min number of clusters assigned in the ITS 
+  float             fminTPCchiNdof;      // min allowed chi2/ndof for TPC clusters
+  short             fMaxTPCncls;         // maximum allowed clusters in the TPC
+  float             fMaxITSchiNdof;      // maximum allowed chi2/ndof for ITS clusters
+  float             fMaxTPCchiNdof;      // maximum allowed chi2/ndof for TPC clusters
+  float             fMaxSigmaToVertex;   // maximum allowed sigma to primary vertex
+  long              fNTracksPassed;      // passed tracks count
+  long              fNTracksFailed;      // failed tracks count
+  bool              fRemoveKinks;        // if true particles with any kink label will not pass
+  int               fMostProbable;       // this particle type is required to be most probable
+  
+  bool    fTPCnclsExclusionSwitch;       // turn on/off TPCncls exclusion zone (true=on)
+  short   fTPCnclsExclusion[2];          // lower and upper limit of TPCncls QA exclusion zone
+  bool    fTPCchiNdofExclusionSwitch;        // turn on/off TPCchi exclusion zone (true=on)
+  float   fTPCchiNdofExclusion[2];           // lower and upper limit of TPCchi QA exclusion zone
+
+  float PidFractionElectron(float mom) const;
+  float PidFractionPion(float mom) const;
+  float PidFractionKaon(float mom) const;
+  float PidFractionProton(float mom) const;
+
+#ifdef __ROOT__ 
+  ClassDef(AliFemtoQATrackCut, 1)
+#endif
+    };
+
+
+inline void AliFemtoQATrackCut::SetPt(const float& lo, const float& hi){fPt[0]=lo; fPt[1]=hi;}
+inline void AliFemtoQATrackCut::SetRapidity(const float& lo,const float& hi){fRapidity[0]=lo; fRapidity[1]=hi;}
+inline void AliFemtoQATrackCut::SetCharge(const int& ch){fCharge = ch;}
+inline void AliFemtoQATrackCut::SetPidProbElectron(const float& lo,const float& hi){fPidProbElectron[0]=lo; fPidProbElectron[1]=hi;}
+inline void AliFemtoQATrackCut::SetPidProbPion(const float& lo,const float& hi){fPidProbPion[0]=lo; fPidProbPion[1]=hi;}
+inline void AliFemtoQATrackCut::SetPidProbKaon(const float& lo,const float& hi){fPidProbKaon[0]=lo; fPidProbKaon[1]=hi;}
+inline void AliFemtoQATrackCut::SetPidProbProton(const float& lo,const float& hi){fPidProbProton[0]=lo; fPidProbProton[1]=hi;}
+inline void AliFemtoQATrackCut::SetPidProbMuon(const float& lo,const float& hi){fPidProbMuon[0]=lo; fPidProbMuon[1]=hi;}
+inline void AliFemtoQATrackCut::SetLabel(const bool& flag){fLabel=flag;}
+inline void AliFemtoQATrackCut::SetStatus(const long& status){fStatus=status;}
+inline void AliFemtoQATrackCut::SetminTPCclsF(const short& minTPCclsF){fminTPCclsF=minTPCclsF;}
+inline void AliFemtoQATrackCut::SetminTPCncls(const short& s){fminTPCncls=s;}
+inline void AliFemtoQATrackCut::SetminITScls(const int& minITScls){fminITScls=minITScls;}
+inline void AliFemtoQATrackCut::SetminTPCchiNdof(const float& s){fminTPCchiNdof = s;}
+inline void AliFemtoQATrackCut::SetMostProbablePion() { fMostProbable = 2; }
+inline void AliFemtoQATrackCut::SetMostProbableKaon() { fMostProbable = 3; }
+inline void AliFemtoQATrackCut::SetMostProbableProton() { fMostProbable = 4; }
+inline void AliFemtoQATrackCut::SetNoMostProbable() { fMostProbable = 0; }
+inline void AliFemtoQATrackCut::SetMaxTPCncls(const short& s){fMaxTPCncls=s;}
+inline void AliFemtoQATrackCut::SetMaxITSChiNdof(const float& maxchi) { fMaxITSchiNdof = maxchi; }
+inline void AliFemtoQATrackCut::SetMaxTPCChiNdof(const float& maxchi) { fMaxTPCchiNdof = maxchi; }
+inline void AliFemtoQATrackCut::SetMaxSigmaToVertex(const float& maxsig) { fMaxSigmaToVertex = maxsig; }
+
+inline void AliFemtoQATrackCut::SetTPCnclsExclusionSwitch(const bool& excluSwitch) { fTPCnclsExclusionSwitch = excluSwitch; }
+inline void AliFemtoQATrackCut::SetTPCnclsExclusion(const short& lo, const short& hi) {fTPCnclsExclusion[0] = lo; fTPCnclsExclusion[1] = hi;}
+inline void AliFemtoQATrackCut::SetTPCchiNdofExclusionSwitch(const bool& excluSwitch) { fTPCchiNdofExclusionSwitch = excluSwitch; }
+inline void AliFemtoQATrackCut::SetTPCchiNdofExclusion(const float& lo, const float& hi) {fTPCchiNdofExclusion[0] = lo; fTPCchiNdofExclusion[1] = hi;}
+
+#endif
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoQPairCut.cxx b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoQPairCut.cxx
new file mode 100644 (file)
index 0000000..e2a1f51
--- /dev/null
@@ -0,0 +1,136 @@
+/////////////////////////////////////////////////////////////////////////////
+//                                                                         //
+// AliFemtoQPairCut - a simple cut which selects pairs based on the values //
+// of their respective q components                                        /
+//                                                                         //
+/////////////////////////////////////////////////////////////////////////////
+/***************************************************************************
+ *
+ * $Id$
+ ***************************************************************************
+ *          
+ *
+ ***************************************************************************
+ *
+ * $Log$
+ * Revision 1.2.6.1  2007/11/01 17:10:38  akisiel
+ * Fix code rule conformace
+ *
+ * Revision 1.2  2007/05/22 09:01:42  akisiel
+ * Add the possibiloity to save cut settings in the ROOT file
+ *
+ * Revision 1.1  2007/05/16 10:25:06  akisiel
+ * Making the directory structure of AliFemtoUser flat. All files go into one common directory
+ *
+ * Revision 1.4  2007/05/03 09:46:10  akisiel
+ * Fixing Effective C++ warnings
+ *
+ * Revision 1.3  2007/04/27 07:25:59  akisiel
+ * Make revisions needed for compilation from the main AliRoot tree
+ *
+ * Revision 1.1.1.1  2007/04/25 15:38:41  panos
+ * Importing the HBT code dir
+ *
+ * Revision 1.1.1.1  2007/03/07 10:14:49  mchojnacki
+ * First version on CVS
+ *
+ *
+ **************************************************************************/
+
+#include "AliFemtoQPairCut.h"
+#include <string>
+#include <cstdio>
+
+#ifdef __ROOT__
+ClassImp(AliFemtoQPairCut)
+#endif
+    
+//__________________
+AliFemtoQPairCut::AliFemtoQPairCut():
+  fNPairsPassed(0),
+  fNPairsFailed(0)
+{
+  // Default constructor
+  fNPairsPassed = fNPairsFailed = 0;
+  fQlong[0]=-1.0; fQlong[1]=100.0;
+  fQout[0]=-1.0;  fQout[1]=100.0;
+  fQside[0]=-1.0; fQside[1]=100.0;
+  fQinv[0]=-1.0;  fQinv[1]=100.0;
+}
+//__________________
+AliFemtoQPairCut::~AliFemtoQPairCut()
+{
+//  /* no-op */
+}
+//__________________
+bool AliFemtoQPairCut::Pass(const AliFemtoPair* pair)
+{
+  // Select pairs based on their q values
+  //bool temp = true;
+  //temp ? fNPairsPassed++ : fNPairsFailed++;
+  if ((fabs(pair->QLongCMS())<fQlong[0])||(fabs(pair->QLongCMS())>fQlong[1]))
+  {
+       fNPairsFailed++;
+       return false;
+  }
+  if ((fabs(pair->QOutCMS())<fQout[0])||(fabs(pair->QOutCMS())>fQout[1]))
+  {
+       fNPairsFailed++;
+       return false;
+  }
+  if ((fabs(pair->QSideCMS())<fQside[0])||(fabs(pair->QSideCMS())>fQside[1]))
+  {
+       fNPairsFailed++;
+       return false;
+  }
+    if ((fabs(pair->KStar())<fQinv[0])||(fabs(pair->KStar())>fQinv[1]))
+  {
+       fNPairsFailed++;
+       return false;
+  }
+  fNPairsPassed++;
+  return true;
+}
+//__________________
+AliFemtoString AliFemtoQPairCut::Report()
+{
+  // Prepare a report
+  string stemp = "AliFemtoQ Pair Cut \n";
+  char ctemp[100];
+  snprintf(ctemp , 100, "Number of pairs which passed:\t%ld  Number which failed:\t%ld\n",fNPairsPassed,fNPairsFailed);
+  stemp += ctemp;
+  AliFemtoString returnThis = stemp;
+  return returnThis;
+}
+//__________________
+TList *AliFemtoQPairCut::ListSettings()
+{
+  // return a list of settings in a writable form
+  TList *tListSetttings = new TList();
+  char buf[200];
+  snprintf(buf, 200, "AliFemtoQPairCut.qout.maximum=%f", fQout[0]);
+  tListSetttings->AddLast(new TObjString(buf));
+
+  snprintf(buf, 200, "AliFemtoQPairCut.qout.minimum=%f", fQout[1]);
+  tListSetttings->AddLast(new TObjString(buf));
+
+  snprintf(buf, 200, "AliFemtoQPairCut.qside.maximum=%f", fQside[0]);
+  tListSetttings->AddLast(new TObjString(buf));
+
+  snprintf(buf, 200, "AliFemtoQPairCut.qside.minimum=%f", fQside[1]);
+  tListSetttings->AddLast(new TObjString(buf));
+
+  snprintf(buf, 200, "AliFemtoQPairCut.qlong.maximum=%f", fQlong[0]);
+  tListSetttings->AddLast(new TObjString(buf));
+
+  snprintf(buf, 200, "AliFemtoQPairCut.qlong.minimum=%f", fQlong[1]);
+  tListSetttings->AddLast(new TObjString(buf));
+
+  snprintf(buf, 200, "AliFemtoQPairCut.qinv.maximum=%f", fQinv[0]);
+  tListSetttings->AddLast(new TObjString(buf));
+
+  snprintf(buf, 200, "AliFemtoQPairCut.qinv.minimum=%f", fQinv[1]);
+  tListSetttings->AddLast(new TObjString(buf));
+
+  return tListSetttings;
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoQPairCut.h b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoQPairCut.h
new file mode 100644 (file)
index 0000000..5400876
--- /dev/null
@@ -0,0 +1,88 @@
+/////////////////////////////////////////////////////////////////////////////
+//                                                                         //
+// AliFemtoQPairCut - a simple cut which selects pairs based on the values //
+// of their respective q components                                        /
+//                                                                         //
+/////////////////////////////////////////////////////////////////////////////
+
+/***************************************************************************
+ *
+ * $Id $
+ *
+ ***************************************************************************
+ *         
+ *
+ ***************************************************************************
+ *
+ * $Log$
+ * Revision 1.2.6.1  2007/11/01 17:10:38  akisiel
+ * Fix code rule conformace
+ *
+ * Revision 1.2  2007/05/22 09:01:42  akisiel
+ * Add the possibiloity to save cut settings in the ROOT file
+ *
+ * Revision 1.1  2007/05/16 10:25:06  akisiel
+ * Making the directory structure of AliFemtoUser flat. All files go into one common directory
+ *
+ * Revision 1.1.1.1  2007/04/25 15:38:41  panos
+ * Importing the HBT code dir
+ *
+ * Revision 1.1.1.1  2007/03/07 10:14:49  mchojnacki
+ * First version on CVS
+ *
+ *
+ **************************************************************************/
+
+
+#ifndef ALIFEMTOQPAIRCUT_H
+#define ALIFEMTOQPAIRCUT_H
+
+// do I need these lines ?
+//#ifndef StMaker_H
+//#include "StMaker.h"
+//#endif
+
+#include "AliFemtoPairCut.h"
+
+class AliFemtoQPairCut : public AliFemtoPairCut{
+public:
+  AliFemtoQPairCut();
+  ~AliFemtoQPairCut();
+
+  virtual bool Pass(const AliFemtoPair* pair);
+  virtual AliFemtoString Report();
+  virtual TList *ListSettings();
+
+  void Setqlong(const float& lo, const float& hi);
+  void Setqout(const float& lo, const float& hi);
+  void Setqside(const float& lo, const float& hi);
+  void Setqinv(const float& lo, const float& hi);
+  AliFemtoQPairCut* Clone();
+
+
+private:
+  long fNPairsPassed;  // Number of pairs that passed the cut
+  long fNPairsFailed;  // Number of pairs that failed the cut
+  float fQlong[2];     // Qlong range
+  float fQout[2];      // Qout range
+  float fQside[2];     // Qside range
+  float fQinv[2];      // Qinv range
+  
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoQPairCut, 1)
+#endif
+};
+
+
+inline AliFemtoQPairCut* AliFemtoQPairCut::Clone() 
+{ 
+    AliFemtoQPairCut* c = new AliFemtoQPairCut(*this); 
+    return c;
+}
+inline void AliFemtoQPairCut::Setqlong(const float& lo,const float& hi){fQlong[0]=lo; fQlong[1]=hi;}
+inline void AliFemtoQPairCut::Setqout(const float& lo,const float& hi) {fQout[0]=lo;  fQout[1]=hi;}
+inline void AliFemtoQPairCut::Setqside(const float& lo,const float& hi){fQside[0]=lo; fQside[1]=hi;}
+inline void AliFemtoQPairCut::Setqinv(const float& lo,const float& hi) {fQinv[0]=lo;  fQinv[1]=hi;}
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoQinvCorrFctnEMCIC.cxx b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoQinvCorrFctnEMCIC.cxx
new file mode 100644 (file)
index 0000000..a3c97ab
--- /dev/null
@@ -0,0 +1,241 @@
+/***************************************************************************
+ *
+ * $Id: AliFemtoQinvCorrFctnEMCIC.cxx  $
+ *
+ * Author: Nicolas Bock, Ohio State University, bock@mps.ohio-state.edu
+ ***************************************************************************
+ *
+ * Description: Calculates of the Qinv Correlation Function, and also
+ *              produces histograms to calculate EMCICs          
+ *
+ ***************************************************************************
+ *
+ **************************************************************************/
+
+
+#include "AliFemtoQinvCorrFctnEMCIC.h"
+//#include "AliFemtoHisto.h"
+#include <cstdio>
+#include <TVector2.h>
+
+#ifdef __ROOT__ 
+ClassImp(AliFemtoQinvCorrFctnEMCIC)
+#endif
+
+//____________________________
+AliFemtoQinvCorrFctnEMCIC::AliFemtoQinvCorrFctnEMCIC(char* title, const int& nbins, const float& QinvLo, const float& QinvHi):
+AliFemtoQinvCorrFctn(title, nbins, QinvLo, QinvHi),
+/*fESumReal(0),
+  fEMultReal(0),
+  fPtMultReal(0),
+  fPzMultReal(0),*/
+  fESumMix(0),
+  fEMultMix(0),
+  fPtMultMix(0),
+  fPzMultMix(0)
+
+{
+  
+
+  // set up emcic histograms
+  /*char tTitESum[100] = "ESumReal";
+  strncat(tTitESum,title, 100);
+  fESumReal = new TH1D(tTitESum,title,nbins,QinvLo,QinvHi);
+  char tTitEMult[100] = "EMultReal";
+  strncat(tTitEMult,title, 100);
+  fEMultReal = new TH1D(tTitEMult,title,nbins,QinvLo,QinvHi);
+  char tTitPt[100] = "PtMultReal";
+  strncat(tTitPt,title, 100);
+  fPtMultReal = new TH1D(tTitPt,title,nbins,QinvLo,QinvHi);
+  char tTitPz[100] = "PzMultReal";
+  strncat(tTitPz,title, 100);
+  fPzMultReal = new TH1D(tTitPz,title,nbins,QinvLo,QinvHi);*/
+  char tTitESum2[101] = "ESumMix";
+  strncat(tTitESum2,title, 100);
+  fESumMix = new TH1D(tTitESum2,title,nbins,QinvLo,QinvHi);
+  char tTitEMult2[101] = "EMultMix";
+  strncat(tTitEMult2,title, 100);
+  fEMultMix = new TH1D(tTitEMult2,title,nbins,QinvLo,QinvHi);
+  char tTitPt2[101] = "PtMultMix";
+  strncat(tTitPt2,title, 100);
+  fPtMultMix = new TH1D(tTitPt2,title,nbins,QinvLo,QinvHi);
+  char tTitPz2[101] = "PzMultMix";
+  strncat(tTitPz2,title, 100);
+  fPzMultMix = new TH1D(tTitPz2,title,nbins,QinvLo,QinvHi);
+
+
+
+  // to enable error bar calculation...
+  
+  /*  fESumReal->Sumw2();
+  fEMultReal->Sumw2();
+  fPtMultReal->Sumw2();
+  fPzMultReal->Sumw2();*/
+  fESumMix->Sumw2();
+  fEMultMix->Sumw2();
+  fPtMultMix->Sumw2();
+  fPzMultMix->Sumw2();
+}
+
+//____________________________
+AliFemtoQinvCorrFctnEMCIC::AliFemtoQinvCorrFctnEMCIC(const AliFemtoQinvCorrFctnEMCIC& aCorrFctn) :
+  AliFemtoQinvCorrFctn(aCorrFctn),
+  /*fESumReal(0),
+  fEMultReal(0),
+  fPtMultReal(0),
+  fPzMultReal(0),*/
+  fESumMix(0),
+  fEMultMix(0),
+  fPtMultMix(0),
+  fPzMultMix(0)
+{
+  // copy constructor
+  
+  /*fESumReal= new TH1D(*aCorrFctn.fESumReal);
+  fEMultReal= new TH1D(*aCorrFctn.fEMultReal);
+  fPtMultReal= new TH1D(*aCorrFctn.fPtMultReal);
+  fPzMultReal= new TH1D(*aCorrFctn.fPzMultReal);*/
+  fESumMix= new TH1D(*aCorrFctn.fESumMix);
+  fEMultMix= new TH1D(*aCorrFctn.fEMultMix);
+  fPtMultMix= new TH1D(*aCorrFctn.fPtMultMix);
+  fPzMultMix= new TH1D(*aCorrFctn.fPzMultMix);
+
+}
+//____________________________
+AliFemtoQinvCorrFctnEMCIC::~AliFemtoQinvCorrFctnEMCIC(){
+  // destructor
+  
+  /*delete fESumReal;
+  delete fEMultReal;
+  delete fPtMultReal;
+  delete fPzMultReal;*/
+  delete fESumMix;
+  delete fEMultMix;
+  delete fPtMultMix;
+  delete fPzMultMix;
+
+}
+//_________________________
+AliFemtoQinvCorrFctnEMCIC& AliFemtoQinvCorrFctnEMCIC::operator=(const AliFemtoQinvCorrFctnEMCIC& aCorrFctn)
+{
+  // assignment operator
+  if (this == &aCorrFctn)
+    return *this;
+
+  /*if (fESumReal) delete fESumReal;
+  fESumReal= new TH1D(*aCorrFctn.fESumReal);
+  if (fEMultReal) delete fEMultReal;
+  fEMultReal= new TH1D(*aCorrFctn.fEMultReal);
+  if (fPtMultReal) delete fPtMultReal;
+  fPtMultReal= new TH1D(*aCorrFctn.fPtMultReal);
+  if (fPzMultReal) delete fPzMultReal;
+  fPzMultReal= new TH1D(*aCorrFctn.fPzMultReal);
+  if (fESumMix) delete fESumMix;*/
+  
+  fESumMix= new TH1D(*aCorrFctn.fESumMix);
+  if (fEMultMix) delete fEMultMix;
+  fEMultMix= new TH1D(*aCorrFctn.fEMultMix);
+  if (fPtMultMix) delete fPtMultMix;
+  fPtMultMix= new TH1D(*aCorrFctn.fPtMultMix);
+  if (fPzMultMix) delete fPzMultMix;
+  fPzMultMix= new TH1D(*aCorrFctn.fPzMultMix);
+
+  return *this;
+}
+
+//____________________________
+void AliFemtoQinvCorrFctnEMCIC::AddRealPair(AliFemtoPair* pair){
+  // add true pair
+  
+  if (fPairCut)
+    if (!fPairCut->Pass(pair)) return;
+  AliFemtoQinvCorrFctn::AddRealPair(pair);
+  
+  //double tQinv = fabs(pair->QInv());   // note - qInv() will be negative for identical pairs...
+  
+// The EMCICs are calculated here for real pairs
+  /*AliFemtoLorentzVector tMom1 = pair->Track1()->FourMomentum();
+  AliFemtoLorentzVector tMom2 = pair->Track2()->FourMomentum();
+  double tE1 = tMom1.e();
+  double tE2 = tMom2.e();
+  double tPz1 = tMom1.pz();
+  double tPz2 = tMom2.pz();
+  
+  TVector2 tPt1;  
+  TVector2 tPt2; 
+  tPt1.Set(tMom1.px(),tMom1.py());
+  tPt2.Set(tMom2.px(),tMom2.py());
+  double tPt1DotPt2 = tPt1*tPt2;
+  
+  fESumReal->Fill(tQinv,tE1+tE2);
+  fEMultReal->Fill(tQinv,tE1*tE2);
+  fPzMultReal->Fill(tQinv,tPz1*tPz2);
+  fPtMultReal->Fill(tQinv,tPt1DotPt2);*/
+
+}
+//____________________________
+void AliFemtoQinvCorrFctnEMCIC::AddMixedPair(AliFemtoPair* pair){
+  // add mixed (background) pair
+  if (fPairCut)
+    if (!fPairCut->Pass(pair)) return;
+  AliFemtoQinvCorrFctn::AddMixedPair(pair);
+  double tQinv = fabs(pair->QInv());   // note - qInv() will be negative for identical pairs...
+  
+
+  // The EMCICs are calculated here for mixed pairs
+  AliFemtoLorentzVector tMom1 = pair->Track1()->FourMomentum();
+  AliFemtoLorentzVector tMom2 = pair->Track2()->FourMomentum();
+  double tE1 = tMom1.e();
+  double tE2 = tMom2.e();
+  double tPz1 = tMom1.pz();
+  double tPz2 = tMom2.pz();
+  
+  TVector2 tPt1;  
+  TVector2 tPt2; 
+  tPt1.Set(tMom1.px(),tMom1.py());
+  tPt2.Set(tMom2.px(),tMom2.py());
+  double tPt1DotPt2 = tPt1*tPt2;
+  
+  fESumMix->Fill(tQinv,tE1+tE2);
+  fEMultMix->Fill(tQinv,tE1*tE2);
+  fPzMultMix->Fill(tQinv,tPz1*tPz2);
+  fPtMultMix->Fill(tQinv,tPt1DotPt2);
+
+
+
+}
+//____________________________
+void AliFemtoQinvCorrFctnEMCIC::Write(){
+  // Write out neccessary objects
+  AliFemtoQinvCorrFctn::Write();  //Write num and den
+  /*fESumReal->Write();
+  fEMultReal->Write();
+  fPtMultReal->Write();
+  fPzMultReal->Write(); */
+  fESumMix->Write();
+  fEMultMix->Write();
+  fPtMultMix->Write();
+  fPzMultMix->Write();
+
+}
+//______________________________
+TList* AliFemtoQinvCorrFctnEMCIC::GetOutputList()
+{
+  // Prepare the list of objects to be written to the output
+  TList *tOutputList;
+  tOutputList = (TList*)AliFemtoQinvCorrFctn::GetOutputList();
+  cout << "Getting list from Qinv CF emicic" << endl;
+  /*tOutputList->Add(fESumReal);
+  tOutputList->Add(fEMultReal);
+  tOutputList->Add(fPtMultReal);
+  tOutputList->Add(fPzMultReal); */
+  tOutputList->Add(fESumMix);
+  tOutputList->Add(fEMultMix);
+  tOutputList->Add(fPtMultMix);
+  tOutputList->Add(fPzMultMix);
+  return tOutputList;
+}
+
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoQinvCorrFctnEMCIC.h b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoQinvCorrFctnEMCIC.h
new file mode 100644 (file)
index 0000000..3048b7d
--- /dev/null
@@ -0,0 +1,78 @@
+/***************************************************************************
+ *
+ * $Id: AliFemtoQinvCorrFctnEMCIC.h  $
+ *
+ * Author: Nicolas Bock, Ohio State University, bock@mps.ohio-state.edu
+ ***************************************************************************
+ *
+ * Description: Calculates of the Qinv Correlation Function, and also
+ *              produces histograms to calculate Energy Momentum Conservation
+ *              Induced Correlations  (EMCICs)
+ *
+ * This Class produces the following histograms as function of Qinv
+ * (for both real and mixed pairs):
+ *        1)   E1 + E2
+ *        2)   E1 * E2
+ *        3)   Pt1*Pt2
+ *        4)   Pz1*Pz2
+ *  
+ * The class is derived from AliFemtoQinvCorrFctn, therefore it produces
+ * also the histograms in that class. 
+ * 
+ * NOTE: The EMCIC histograms are not averaged in this class, to obtain 
+ * the average, the user needs to divide the real pair histograms by 
+ * the numerator, and the mixed pairs by denominator
+ *
+ ***************************************************************************
+ *
+ **************************************************************************/
+
+#ifndef ALIFEMTOQINVCORRFCTNEMCIC_H
+#define ALIFEMTOQINVCORRFCTNEMCIC_H
+
+#include "TH1D.h"
+#include "AliFemtoCorrFctn.h"
+#include "AliFemtoQinvCorrFctn.h"
+
+
+class AliFemtoQinvCorrFctnEMCIC : public AliFemtoQinvCorrFctn 
+{
+ public:
+  AliFemtoQinvCorrFctnEMCIC(char* title, const int& nbins, 
+                           const float& QinvLo, const float& QinvHi);
+  AliFemtoQinvCorrFctnEMCIC(const AliFemtoQinvCorrFctnEMCIC& aCorrFctn);
+  virtual ~AliFemtoQinvCorrFctnEMCIC();
+  
+  AliFemtoQinvCorrFctnEMCIC& operator=(const AliFemtoQinvCorrFctnEMCIC& aCorrFctn);
+
+  virtual void AddRealPair(AliFemtoPair* aPair);
+  virtual void AddMixedPair(AliFemtoPair* aPair);
+
+  
+
+  virtual TList* GetOutputList();
+  void Write();
+  
+ private:
+  //Emcic histograms:  
+  /*TH1D* fESumReal;   //  <E1+E2>   from real Pairs 
+  TH1D* fEMultReal;  //  <E1*E2>   from real Pairs 
+  TH1D* fPtMultReal; //  <Pt1*Pt2> from real Pairs 
+  TH1D* fPzMultReal; //  <Pz1*Pz2> from real Pairs */
+  TH1D* fESumMix;    //  <E1+E2>   from mixed Pairs 
+  TH1D* fEMultMix;   //  <E1*E2>   from mixed Pairs
+  TH1D* fPtMultMix;  //  <PT1*Pt2> from mixed Pairs
+  TH1D* fPzMultMix;  //  <Pz1*Pz2> from mixed Pairs
+
+
+
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoQinvCorrFctnEMCIC, 1)
+#endif
+};
+
+
+
+#endif
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoShareQualityCorrFctn.cxx b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoShareQualityCorrFctn.cxx
new file mode 100644 (file)
index 0000000..47115ef
--- /dev/null
@@ -0,0 +1,382 @@
+////////////////////////////////////////////////////////////////////////////////
+///                                                                          ///
+/// AliFemtoShareQualityCorrFctn - A correlation function that saves the     ///
+/// amount of sharing and splitting hits per pair as a function of qinv      ///
+/// Authors: Adam Kisiel kisiel@mps.ohio-state.edu                           ///
+///                                                                          ///
+////////////////////////////////////////////////////////////////////////////////
+
+#include "AliFemtoShareQualityCorrFctn.h"
+//#include "AliFemtoHisto.hh"
+#include <cstdio>
+
+#ifdef __ROOT__ 
+ClassImp(AliFemtoShareQualityCorrFctn)
+#endif
+
+//____________________________
+AliFemtoShareQualityCorrFctn::AliFemtoShareQualityCorrFctn(char* title, const int& nbins, const float& QinvLo, const float& QinvHi):
+  AliFemtoCorrFctn(),
+  fShareNumerator(0),
+  fShareDenominator(0),
+  fQualityNumerator(0),
+  fQualityDenominator(0),
+  fTPCSepNumerator(0),
+  fTPCSepDenominator(0)
+{
+  // set up numerator
+  //  title = "Num Qinv (MeV/c)";
+  char tTitNum[101] = "NumShare";
+  strncat(tTitNum,title, 100);
+  fShareNumerator = new TH2D(tTitNum,title,nbins,QinvLo,QinvHi,100,0.0,1.00001);
+  // set up denominator
+  //title = "Den Qinv (MeV/c)";
+  char tTitDen[101] = "DenShare";
+  strncat(tTitDen,title, 100);
+  fShareDenominator = new TH2D(tTitDen,title,nbins,QinvLo,QinvHi,100,0.0,1.00001);
+
+  char tTit2Num[101] = "NumQuality";
+  strncat(tTit2Num,title, 100);
+  fQualityNumerator = new TH2D(tTit2Num,title,nbins,QinvLo,QinvHi,150,-0.500001,1.000001);
+  // set up denominator
+  //title = "Den Qinv (MeV/c)";
+  char tTit2Den[101] = "DenQuality";
+  strncat(tTit2Den,title, 100);
+  fQualityDenominator = new TH2D(tTit2Den,title,nbins,QinvLo,QinvHi,150,-0.500001,1.000001);
+  // set up ratio
+  //title = "Ratio Qinv (MeV/c)";
+  // this next bit is unfortunately needed so that we can have many histos of same "title"
+  // it is neccessary if we typedef TH2D to TH1d (which we do)
+  //mShareNumerator->SetDirectory(0);
+  //mShareDenominator->SetDirectory(0);
+  //mRatio->SetDirectory(0);
+
+  char tTit3Num[101] = "NumTPCSep";
+  strncat(tTit3Num,title, 100);
+  fTPCSepNumerator = new TH2D(tTit3Num,title,nbins,QinvLo,QinvHi,150,0.0,100.0);
+  // set up denominator
+  //title = "Den Qinv (MeV/c)";
+  char tTit3Den[101] = "DenTPCSep";
+  strncat(tTit3Den,title, 100);
+  fTPCSepDenominator = new TH2D(tTit3Den,title,nbins,QinvLo,QinvHi,150,0.0,100.0);
+
+  // to enable error bar calculation...
+  fShareNumerator->Sumw2();
+  fShareDenominator->Sumw2();
+
+  fQualityNumerator->Sumw2();
+  fQualityDenominator->Sumw2();
+  
+  fTPCSepNumerator->Sumw2();
+  fTPCSepDenominator->Sumw2();
+}
+
+//____________________________
+AliFemtoShareQualityCorrFctn::AliFemtoShareQualityCorrFctn(const AliFemtoShareQualityCorrFctn& aCorrFctn) :
+  AliFemtoCorrFctn(),
+  fShareNumerator(0),
+  fShareDenominator(0),
+  fQualityNumerator(0),
+  fQualityDenominator(0),
+  fTPCSepNumerator(0),
+  fTPCSepDenominator(0)
+{
+  // copy constructor
+  if (aCorrFctn.fShareNumerator)
+    fShareNumerator = new TH2D(*aCorrFctn.fShareNumerator);
+  if (aCorrFctn.fShareDenominator)
+    fShareDenominator = new TH2D(*aCorrFctn.fShareDenominator);
+  if (aCorrFctn.fQualityNumerator)
+    fQualityNumerator = new TH2D(*aCorrFctn.fQualityNumerator);
+  if (aCorrFctn.fQualityDenominator)
+    fQualityDenominator = new TH2D(*aCorrFctn.fQualityDenominator);
+  if (aCorrFctn.fTPCSepNumerator)
+    fTPCSepNumerator = new TH2D(*aCorrFctn.fTPCSepNumerator);
+  if (aCorrFctn.fTPCSepDenominator)
+    fTPCSepDenominator = new TH2D(*aCorrFctn.fTPCSepDenominator);
+}
+//____________________________
+AliFemtoShareQualityCorrFctn::~AliFemtoShareQualityCorrFctn(){
+  // destructor
+  delete fShareNumerator;
+  delete fShareDenominator;
+  delete fQualityNumerator;
+  delete fQualityDenominator;
+  delete fTPCSepNumerator;
+  delete fTPCSepDenominator;
+}
+//_________________________
+AliFemtoShareQualityCorrFctn& AliFemtoShareQualityCorrFctn::operator=(const AliFemtoShareQualityCorrFctn& aCorrFctn)
+{
+  // assignment operator
+  if (this == &aCorrFctn)
+    return *this;
+
+  if (aCorrFctn.fShareNumerator)
+    fShareNumerator = new TH2D(*aCorrFctn.fShareNumerator);
+  else
+    fShareNumerator = 0;
+  if (aCorrFctn.fShareDenominator)
+    fShareDenominator = new TH2D(*aCorrFctn.fShareDenominator);
+  else
+    fShareDenominator = 0;
+  if (aCorrFctn.fQualityNumerator)
+    fQualityNumerator = new TH2D(*aCorrFctn.fQualityNumerator);
+  else
+    fQualityNumerator = 0;
+  if (aCorrFctn.fQualityDenominator)
+    fQualityDenominator = new TH2D(*aCorrFctn.fQualityDenominator);
+  else
+    fQualityDenominator = 0;
+  if (aCorrFctn.fTPCSepNumerator)
+    fTPCSepNumerator = new TH2D(*aCorrFctn.fTPCSepNumerator);
+  else
+    fTPCSepNumerator = 0;
+  if (aCorrFctn.fTPCSepDenominator)
+    fTPCSepDenominator = new TH2D(*aCorrFctn.fTPCSepDenominator);
+  else
+    fTPCSepDenominator = 0;
+
+  return *this;
+}
+//_________________________
+void AliFemtoShareQualityCorrFctn::Finish(){
+  // here is where we should normalize, fit, etc...
+  // we should NOT Draw() the histos (as I had done it below),
+  // since we want to insulate ourselves from root at this level
+  // of the code.  Do it instead at root command line with browser.
+  //  mShareNumerator->Draw();
+  //mShareDenominator->Draw();
+  //mRatio->Draw();
+
+}
+
+//____________________________
+AliFemtoString AliFemtoShareQualityCorrFctn::Report(){
+  // create report
+  string stemp = "Qinv Correlation Function Report:\n";
+  char ctemp[100];
+  snprintf(ctemp , 100, "Number of entries in numerator:\t%E\n",fShareNumerator->GetEntries());
+  stemp += ctemp;
+  snprintf(ctemp , 100, "Number of entries in denominator:\t%E\n",fShareDenominator->GetEntries());
+  stemp += ctemp;
+  //  stemp += mCoulombWeight->Report();
+  AliFemtoString returnThis = stemp;
+  return returnThis;
+}
+//____________________________
+void AliFemtoShareQualityCorrFctn::AddRealPair( AliFemtoPair* pair){
+  // add real (effect) pair
+  if (fPairCut)
+    if (!fPairCut->Pass(pair)) return;
+
+  double tQinv = fabs(pair->QInv());   // note - qInv() will be negative for identical pairs...
+  Int_t nh = 0;
+  Int_t an = 0;
+  Int_t ns = 0;
+  
+  for (unsigned int imap=0; imap<pair->Track1()->Track()->TPCclusters().GetNbits(); imap++) {
+    // If both have clusters in the same row
+    if (pair->Track1()->Track()->TPCclusters().TestBitNumber(imap) && 
+       pair->Track2()->Track()->TPCclusters().TestBitNumber(imap)) {
+      // Do they share it ?
+      if (pair->Track1()->Track()->TPCsharing().TestBitNumber(imap) &&
+         pair->Track2()->Track()->TPCsharing().TestBitNumber(imap))
+       {
+//       if (tQinv < 0.01) {
+//         cout << "Shared cluster in row " << imap << endl; 
+//       }
+         an++;
+         nh+=2;
+         ns+=2;
+       }
+      
+      // Different hits on the same padrow
+      else {
+       an--;
+       nh+=2;
+      }
+    }
+    else if (pair->Track1()->Track()->TPCclusters().TestBitNumber(imap) ||
+            pair->Track2()->Track()->TPCclusters().TestBitNumber(imap)) {
+      // One track has a hit, the other does not
+      an++;
+      nh++;
+    }
+  }
+//    if (tQinv < 0.01) {
+//     cout << "Qinv of the pair is " << tQinv << endl;
+//     cout << "Clusters: " << endl;
+//     for (unsigned int imap=0; imap<pair->Track1()->Track()->TPCclusters().GetNbits(); imap++) {
+//       cout << imap ;
+//       if (pair->Track1()->Track()->TPCclusters().TestBitNumber(imap)) cout << " 1 ";
+//       else cout << " 0 " ;
+//       if (pair->Track2()->Track()->TPCclusters().TestBitNumber(imap)) cout << " 1 ";
+//       else cout << " 0 " ;
+//       cout << "     ";
+//       if (pair->Track1()->Track()->TPCsharing().TestBitNumber(imap)) cout << " S ";
+//       else cout << " X ";
+//       if (pair->Track2()->Track()->TPCsharing().TestBitNumber(imap)) cout << " S ";
+//       else cout << " X ";
+//       cout << endl;
+//     }
+//   }
+
+  Float_t hsmval = 0.0;
+  Float_t hsfval = 0.0;
+
+  if (nh >0) {
+    hsmval = an*1.0/nh;
+    hsfval = ns*1.0/nh;
+  }
+
+//   if ((tQinv < 0.005) && (hsmval<-0.0)) {
+//     cout << "Quality  Sharity " << hsmval << " " << hsfval << " " << pair->Track1()->Track() << " " << pair->Track2()->Track() << endl;
+//     cout << "Qinv of the pair is " << tQinv << endl;
+//     cout << "Clusters: " << endl;
+//     for (unsigned int imap=0; imap<pair->Track1()->Track()->TPCclusters().GetNbits(); imap++) {
+//       cout << imap ;
+//       if (pair->Track1()->Track()->TPCclusters().TestBitNumber(imap)) cout << " 1 ";
+//       else cout << " 0 " ;
+//       if (pair->Track2()->Track()->TPCclusters().TestBitNumber(imap)) cout << " 1 ";
+//       else cout << " 0 " ;
+//       cout << "     ";
+//       if (pair->Track1()->Track()->TPCsharing().TestBitNumber(imap)) cout << " S ";
+//       else cout << " X ";
+//       if (pair->Track2()->Track()->TPCsharing().TestBitNumber(imap)) cout << " S ";
+//       else cout << " X ";
+//       cout << endl;
+//     }
+//     cout << "Momentum1 " 
+//      << pair->Track1()->Track()->P().x() << " " 
+//      << pair->Track1()->Track()->P().y() << " "  
+//      << pair->Track1()->Track()->P().z() << " "  
+//      << pair->Track1()->Track()->Label() << " "  
+//      << pair->Track1()->Track()->TrackId() << " "  
+//      << pair->Track1()->Track()->Flags() << " "
+//      << pair->Track1()->Track()->KinkIndex(0) << " "
+//      << pair->Track1()->Track()->KinkIndex(1) << " "
+//      << pair->Track1()->Track()->KinkIndex(2) << " "
+//      << pair->Track1()->Track()->ITSchi2() << " "
+//      << pair->Track1()->Track()->ITSncls() << " "
+//      << pair->Track1()->Track()->TPCchi2() << " "
+//      << pair->Track1()->Track()->TPCncls() << " "
+//      << endl;
+//     cout << "Momentum2 " 
+//      << pair->Track2()->Track()->P().x() << " "  
+//      << pair->Track2()->Track()->P().y() << " "  
+//      << pair->Track2()->Track()->P().z() << " "  
+//      << pair->Track2()->Track()->Label() << " "  
+//      << pair->Track2()->Track()->TrackId() << " "  
+//      << pair->Track2()->Track()->Flags() << " " 
+//      << pair->Track2()->Track()->KinkIndex(0) << " "
+//      << pair->Track2()->Track()->KinkIndex(1) << " "
+//      << pair->Track2()->Track()->KinkIndex(2) << " "
+//      << pair->Track2()->Track()->ITSchi2() << " "
+//      << pair->Track2()->Track()->ITSncls() << " "
+//      << pair->Track2()->Track()->TPCchi2() << " "
+//      << pair->Track2()->Track()->TPCncls() << " "
+//      << endl;
+//   }
+
+  double distx = pair->Track1()->Track()->NominalTpcEntrancePoint().x() - pair->Track2()->Track()->NominalTpcEntrancePoint().x();
+  double disty = pair->Track1()->Track()->NominalTpcEntrancePoint().y() - pair->Track2()->Track()->NominalTpcEntrancePoint().y();
+  double distz = pair->Track1()->Track()->NominalTpcEntrancePoint().z() - pair->Track2()->Track()->NominalTpcEntrancePoint().z();
+  double dist = sqrt(distx*distx + disty*disty + distz*distz);
+
+  fShareNumerator->Fill(tQinv, hsfval);
+  fQualityNumerator->Fill(tQinv, hsmval);
+  fTPCSepNumerator->Fill(tQinv, dist);
+
+  //  cout << "AliFemtoShareQualityCorrFctn::AddRealPair : " << pair->qInv() << " " << tQinv <<
+  //" " << pair->Track1().FourMomentum() << " " << pair->Track2().FourMomentum() << endl;
+}
+//____________________________
+void AliFemtoShareQualityCorrFctn::AddMixedPair( AliFemtoPair* pair){
+  // add mixed (background) pair
+  if (fPairCut)
+    if (!fPairCut->Pass(pair)) return;
+
+  double weight = 1.0;
+  double tQinv = fabs(pair->QInv());   // note - qInv() will be negative for identical pairs...
+  Int_t nh = 0;
+  Int_t an = 0;
+  Int_t ns = 0;
+  
+  for (unsigned int imap=0; imap<pair->Track1()->Track()->TPCclusters().GetNbits(); imap++) {
+    // If both have clusters in the same row
+    if (pair->Track1()->Track()->TPCclusters().TestBitNumber(imap) && 
+       pair->Track2()->Track()->TPCclusters().TestBitNumber(imap)) {
+      // Do they share it ?
+      if (pair->Track1()->Track()->TPCsharing().TestBitNumber(imap) &&
+         pair->Track2()->Track()->TPCsharing().TestBitNumber(imap))
+       {
+         //      cout << "A shared cluster !!!" << endl;
+         //    cout << "imap idx1 idx2 " 
+         //         << imap << " "
+         //         << tP1idx[imap] << " " << tP2idx[imap] << endl;
+         an++;
+         nh+=2;
+         ns+=2;
+       }
+      
+      // Different hits on the same padrow
+      else {
+       an--;
+       nh+=2;
+      }
+    }
+    else if (pair->Track1()->Track()->TPCclusters().TestBitNumber(imap) ||
+            pair->Track2()->Track()->TPCclusters().TestBitNumber(imap)) {
+      // One track has a hit, the other does not
+      an++;
+      nh++;
+    }
+  }
+  
+  Float_t hsmval = 0.0;
+  Float_t hsfval = 0.0;
+
+  if (nh >0) {
+    hsmval = an*1.0/nh;
+    hsfval = ns*1.0/nh;
+  }
+
+  double distx = pair->Track1()->Track()->NominalTpcEntrancePoint().x() - pair->Track2()->Track()->NominalTpcEntrancePoint().x();
+  double disty = pair->Track1()->Track()->NominalTpcEntrancePoint().y() - pair->Track2()->Track()->NominalTpcEntrancePoint().y();
+  double distz = pair->Track1()->Track()->NominalTpcEntrancePoint().z() - pair->Track2()->Track()->NominalTpcEntrancePoint().z();
+  double dist = sqrt(distx*distx + disty*disty + distz*distz);
+
+  fShareDenominator->Fill(tQinv,hsfval,weight);
+  fQualityDenominator->Fill(tQinv,hsmval,weight);
+  fTPCSepDenominator->Fill(tQinv, dist, weight);
+
+}
+
+
+void AliFemtoShareQualityCorrFctn::WriteHistos()
+{
+  // Write out result histograms
+  fShareNumerator->Write();
+  fShareDenominator->Write();
+  fQualityNumerator->Write();
+  fQualityDenominator->Write();
+  fTPCSepNumerator->Write();
+  fTPCSepDenominator->Write();
+  
+}
+//______________________________
+TList* AliFemtoShareQualityCorrFctn::GetOutputList()
+{
+  // Prepare the list of objects to be written to the output
+  TList *tOutputList = new TList();
+
+  tOutputList->Add(fShareNumerator); 
+  tOutputList->Add(fShareDenominator);  
+  tOutputList->Add(fQualityNumerator);  
+  tOutputList->Add(fQualityDenominator);  
+  tOutputList->Add(fTPCSepNumerator);  
+  tOutputList->Add(fTPCSepDenominator);  
+
+  return tOutputList;
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoShareQualityCorrFctn.h b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoShareQualityCorrFctn.h
new file mode 100644 (file)
index 0000000..e0d704e
--- /dev/null
@@ -0,0 +1,50 @@
+////////////////////////////////////////////////////////////////////////////////
+///                                                                          ///
+/// AliFemtoShareQualityCorrFctn - A correlation function that saves the     ///
+/// amount of sharing and splitting hits per pair as a function of qinv      ///
+/// Authors: Adam Kisiel kisiel@mps.ohio-state.edu                           ///
+///                                                                          ///
+////////////////////////////////////////////////////////////////////////////////
+
+#ifndef AliFemtoShareQualityCorrFctn_hh
+#define AliFemtoShareQualityCorrFctn_hh
+
+#include "TH1D.h"
+#include "TH2D.h"
+#include "AliFemtoCorrFctn.h"
+
+class AliFemtoShareQualityCorrFctn : public AliFemtoCorrFctn {
+public:
+  AliFemtoShareQualityCorrFctn(char* title, const int& nbins, const float& QinvLo, const float& QinvHi);
+  AliFemtoShareQualityCorrFctn(const AliFemtoShareQualityCorrFctn& aCorrFctn);
+  virtual ~AliFemtoShareQualityCorrFctn();
+
+  AliFemtoShareQualityCorrFctn& operator=(const AliFemtoShareQualityCorrFctn& aCorrFctn);
+
+  virtual AliFemtoString Report();
+  virtual void AddRealPair(AliFemtoPair* aPair);
+  virtual void AddMixedPair(AliFemtoPair* aPair);
+
+  virtual void Finish();
+
+  void WriteHistos();
+  virtual TList* GetOutputList();
+private:
+  
+  TH2D *fShareNumerator;        // Share fraction for real pairs
+  TH2D *fShareDenominator;      // share fraction for mixed pairs
+  TH2D *fQualityNumerator;      // quality for real pairs
+  TH2D *fQualityDenominator;    // quality for mixed pairs 
+
+  TH2D *fTPCSepNumerator;       // TPCSep for real pairs
+  TH2D *fTPCSepDenominator;     // TPCSep for mixed pairs 
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoShareQualityCorrFctn, 1)
+#endif
+};
+
+
+#endif
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoShareQualityKTPairCut.cxx b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoShareQualityKTPairCut.cxx
new file mode 100644 (file)
index 0000000..1dd00f8
--- /dev/null
@@ -0,0 +1,112 @@
+/////////////////////////////////////////////////////////////////////////////
+//                                                                         //
+// AliFemtoShareQualityKTPairCut - a pair cut which checks for some pair   //
+// qualities that attempt to identify slit/doubly reconstructed tracks     //
+// and selects pairs based on their transverse momentum kT                 //
+//                                                                         //
+/////////////////////////////////////////////////////////////////////////////
+/***************************************************************************
+ *
+ * $Id: AliFemtoShareQualityKTPairCut.cxx,v 1.1.2.1 2007/10/19 13:35:33 akisiel Exp $
+ *
+ * Author: Adam Kisiel, Ohio State, kisiel@mps.ohio-state.edu
+ ***************************************************************************
+ *
+ * Description: part of STAR HBT Framework: AliFemtoMaker package
+ *   a cut to remove "shared" and "split" pairs
+ *
+ ***************************************************************************
+ *
+ *
+ **************************************************************************/
+
+#include "AliFemtoShareQualityKTPairCut.h"
+#include <string>
+#include <cstdio>
+
+#ifdef __ROOT__
+ClassImp(AliFemtoShareQualityKTPairCut)
+#endif
+
+//__________________
+AliFemtoShareQualityKTPairCut::AliFemtoShareQualityKTPairCut():
+  AliFemtoShareQualityPairCut(),
+  fKTMin(0),
+  fKTMax(1.0e6)
+{
+}
+//__________________
+AliFemtoShareQualityKTPairCut::AliFemtoShareQualityKTPairCut(const AliFemtoShareQualityKTPairCut& c) : 
+  AliFemtoShareQualityPairCut(c),
+  fKTMin(0),
+  fKTMax(1.0e6)
+{ 
+  fKTMin = c.fKTMin;
+  fKTMax = c.fKTMax;
+}
+
+//__________________
+AliFemtoShareQualityKTPairCut::~AliFemtoShareQualityKTPairCut(){
+  /* no-op */
+}
+//__________________
+AliFemtoShareQualityKTPairCut& AliFemtoShareQualityKTPairCut::operator=(const AliFemtoShareQualityKTPairCut& c){
+  if (this != &c) {
+    AliFemtoPairCut::operator=(c);
+    
+    fKTMin = c.fKTMin;
+    fKTMax = c.fKTMax;
+  }
+
+  return *this;
+}
+//__________________
+bool AliFemtoShareQualityKTPairCut::Pass(const AliFemtoPair* pair){
+  // Accept a pair base on its Kt and sharity and quality
+  bool temp = true;
+  
+  if (pair->KT() < fKTMin)
+    temp = false;
+
+  if (pair->KT() > fKTMax)
+    temp = false;
+
+  if (temp) {
+    temp = AliFemtoShareQualityPairCut::Pass(pair);
+  }
+  else
+    fNPairsFailed++;
+
+  return temp;
+}
+//__________________
+AliFemtoString AliFemtoShareQualityKTPairCut::Report(){
+  // Prepare a report from execution
+  string stemp = "AliFemtoShareQuality Pair Cut - remove shared and split pairs\n";  char ctemp[100];
+  snprintf(ctemp , 100, "Accept pair with kT in range %f , %f",fKTMin,fKTMax);
+  stemp += ctemp;
+  snprintf(ctemp , 100, "Number of pairs which passed:\t%ld  Number which failed:\t%ld\n",fNPairsPassed,fNPairsFailed);
+  stemp += ctemp;
+  AliFemtoString returnThis = stemp;
+  return returnThis;}
+//__________________
+
+TList *AliFemtoShareQualityKTPairCut::ListSettings()
+{
+  // return a list of settings in a writable form
+  TList *tListSetttings =  AliFemtoShareQualityPairCut::ListSettings();
+  char buf[200];
+  snprintf(buf, 200, "AliFemtoShareQualityKTPairCut.ktmax=%f", fKTMax);
+  tListSetttings->AddLast(new TObjString(buf));
+  snprintf(buf, 200, "AliFemtoShareQualityKTPairCut.ktmin=%f", fKTMin);
+  tListSetttings->AddLast(new TObjString(buf));
+
+  return tListSetttings;
+}
+
+void AliFemtoShareQualityKTPairCut::SetKTRange(double ktmin, double ktmax)
+{
+  // Set the accepted kT range
+  fKTMin = ktmin;
+  fKTMax = ktmax;
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoShareQualityKTPairCut.h b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoShareQualityKTPairCut.h
new file mode 100644 (file)
index 0000000..380cd90
--- /dev/null
@@ -0,0 +1,52 @@
+/***************************************************************************
+ *
+ * $Id: AliFemtoShareQualityKTPairCut.h,v 1.1.2.1 2007/10/19 13:35:33 akisiel Exp $
+ *
+ * Author: Adam Kisiel, Ohio State University, kisiel@mps.ohio-state.edu
+ ***************************************************************************
+ *
+ * Description: part of STAR HBT Framework: AliFemtoMaker package
+ *   a cut to remove "shared" and "split" pairs
+ *
+ ***************************************************************************
+ *
+ *
+ **************************************************************************/
+
+
+#ifndef ALIFEMTOSHAREQUALITYKTPAIRCUT_H
+#define ALIFEMTOSHAREQUALITYKTPAIRCUT_H
+
+// do I need these lines ?
+//#ifndef StMaker_H
+//#include "StMaker.h"
+//#endif
+
+#include "AliFemtoPairCut.h"
+#include "AliFemtoShareQualityPairCut.h"
+
+class AliFemtoShareQualityKTPairCut : public AliFemtoShareQualityPairCut{
+public:
+  AliFemtoShareQualityKTPairCut();
+  AliFemtoShareQualityKTPairCut(const AliFemtoShareQualityKTPairCut& c);
+  virtual ~AliFemtoShareQualityKTPairCut(); 
+  AliFemtoShareQualityKTPairCut& operator=(const AliFemtoShareQualityKTPairCut& c);
+
+  virtual bool Pass(const AliFemtoPair* pair);
+  virtual AliFemtoString Report();
+  virtual TList *ListSettings();
+  AliFemtoShareQualityKTPairCut* Clone();
+  void SetKTRange(double ktmin, double ktmax);
+  
+ protected:
+  Double_t fKTMin;          // Minimum allowed pair transverse momentum
+  Double_t fKTMax;          // Maximum allowed pair transverse momentum 
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoShareQualityKTPairCut, 0)
+#endif
+};
+
+inline AliFemtoShareQualityKTPairCut* AliFemtoShareQualityKTPairCut::Clone() { AliFemtoShareQualityKTPairCut* c = new AliFemtoShareQualityKTPairCut(*this); return c;}
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoShareQualityPairCut.cxx b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoShareQualityPairCut.cxx
new file mode 100644 (file)
index 0000000..6c56c10
--- /dev/null
@@ -0,0 +1,172 @@
+/////////////////////////////////////////////////////////////////////////////
+//                                                                         //
+// AliFemtoShareQualityPairCut - a pair cut which checks for some pair     //
+// qualities that attempt to identify slit/doubly reconstructed tracks     //
+//                                                                         //
+/////////////////////////////////////////////////////////////////////////////
+/***************************************************************************
+ *
+ * $Id$
+ *
+ * Author: Adam Kisiel, Ohio State, kisiel@mps.ohio-state.edu
+ ***************************************************************************
+ *
+ * Description: part of STAR HBT Framework: AliFemtoMaker package
+ *   a cut to remove "shared" and "split" pairs
+ *
+ ***************************************************************************
+ *
+ *
+ **************************************************************************/
+
+#include "AliFemtoShareQualityPairCut.h"
+#include <string>
+#include <cstdio>
+
+#ifdef __ROOT__
+ClassImp(AliFemtoShareQualityPairCut)
+#endif
+
+//__________________
+AliFemtoShareQualityPairCut::AliFemtoShareQualityPairCut():
+  fNPairsPassed(0),
+  fNPairsFailed(0),
+  fShareQualityMax(1.0),
+  fShareFractionMax(1.0),
+  fRemoveSameLabel(0)
+{
+  // Default constructor
+  // Nothing to do
+}
+//__________________
+AliFemtoShareQualityPairCut::~AliFemtoShareQualityPairCut(){
+  /* no-op */
+}
+AliFemtoShareQualityPairCut& AliFemtoShareQualityPairCut::operator=(const AliFemtoShareQualityPairCut& cut)
+{
+  if (this != &cut) {
+    AliFemtoPairCut::operator=(cut);
+    fNPairsPassed = 0;
+    fNPairsFailed = 0;
+    fShareQualityMax = cut.fShareQualityMax;
+    fShareFractionMax = cut.fShareFractionMax;
+    fRemoveSameLabel = cut.fRemoveSameLabel;
+  }
+  
+  return *this;
+}
+//__________________
+bool AliFemtoShareQualityPairCut::Pass(const AliFemtoPair* pair){
+  // Check for pairs that are possibly shared/double reconstruction
+  bool temp;
+  
+  Int_t nh = 0;
+  Int_t an = 0;
+  Int_t ns = 0;
+  
+  if ((fShareFractionMax < 1.0) && ( fShareQualityMax < 1.0)) {
+    for (unsigned int imap=0; imap<pair->Track1()->Track()->TPCclusters().GetNbits(); imap++) {
+      // If both have clusters in the same row
+      if (pair->Track1()->Track()->TPCclusters().TestBitNumber(imap) && 
+         pair->Track2()->Track()->TPCclusters().TestBitNumber(imap)) {
+       // Do they share it ?
+       if (pair->Track1()->Track()->TPCsharing().TestBitNumber(imap) &&
+           pair->Track2()->Track()->TPCsharing().TestBitNumber(imap))
+         {
+           //    cout << "A shared cluster !!!" << endl;
+           //  cout << "imap idx1 idx2 " 
+           //       << imap << " "
+           //       << tP1idx[imap] << " " << tP2idx[imap] << endl;
+           an++;
+           nh+=2;
+           ns+=2;
+         }
+       
+       // Different hits on the same padrow
+       else {
+         an--;
+         nh+=2;
+       }
+      }
+      else if (pair->Track1()->Track()->TPCclusters().TestBitNumber(imap) ||
+              pair->Track2()->Track()->TPCclusters().TestBitNumber(imap)) {
+       // One track has a hit, the other does not
+       an++;
+       nh++;
+      }
+    }
+    
+    Float_t hsmval = 0.0;
+    Float_t hsfval = 0.0;
+    
+    if (nh >0) {
+      hsmval = an*1.0/nh;
+      hsfval = ns*1.0/nh;
+    }
+    //  if (hsmval > -0.4) {
+    //   cout << "Pair quality: " << hsmval << " " << an << " " << nh << " " 
+    //        << (pair->Track1()->Track()) << " " 
+    //        << (pair->Track2()->Track()) << endl;
+    //   cout << "Bits: " << pair->Track1()->Track()->TPCclusters().GetNbits() << endl;
+    //  }
+    //   if (hsfval > 0.0) {
+    //     cout << "Pair sharity: " << hsfval << " " << ns << " " << nh << "    " << hsmval << " " << an << " " << nh << endl;
+    //   }
+    
+    temp = (hsmval < fShareQualityMax) && (hsfval < fShareFractionMax);
+  }
+  else
+    temp = true;
+
+  if (fRemoveSameLabel) {
+    if (abs(pair->Track1()->Track()->Label()) == abs(pair->Track2()->Track()->Label())) {
+//       cout << "Found a pair with same label " << pair->Track1()->Track()->Label() << endl;
+//       cout << "Quality Sharity Passed " << hsmval << " " << hsfval << " " << pair->QInv() << " " << temp << endl;
+      temp = kFALSE;
+    }
+  }
+
+  temp ? fNPairsPassed++ : fNPairsFailed++;
+  return temp;
+}
+//__________________
+AliFemtoString AliFemtoShareQualityPairCut::Report(){
+  // Prepare the report from the execution
+  string stemp = "AliFemtoShareQuality Pair Cut - remove shared and split pairs\n";  char ctemp[100];
+  snprintf(ctemp , 100, "Number of pairs which passed:\t%ld  Number which failed:\t%ld\n",fNPairsPassed,fNPairsFailed);
+  stemp += ctemp;
+  AliFemtoString returnThis = stemp;
+  return returnThis;}
+//__________________
+
+void AliFemtoShareQualityPairCut::SetShareQualityMax(Double_t aShareQualityMax) {
+  fShareQualityMax = aShareQualityMax;
+}
+
+Double_t AliFemtoShareQualityPairCut::GetAliFemtoShareQualityMax() const {
+  return fShareQualityMax;
+}
+
+void AliFemtoShareQualityPairCut::SetShareFractionMax(Double_t aShareFractionMax) {
+  fShareFractionMax = aShareFractionMax;
+}
+Double_t AliFemtoShareQualityPairCut::GetAliFemtoShareFractionMax() const {
+  return fShareFractionMax;
+}
+
+TList *AliFemtoShareQualityPairCut::ListSettings()
+{
+  // return a list of settings in a writable form
+  TList *tListSetttings = new TList();
+  char buf[200];
+  snprintf(buf, 200, "AliFemtoShareQualityPairCut.sharequalitymax=%f", fShareQualityMax);
+  snprintf(buf, 200, "AliFemtoShareQualityPairCut.sharefractionmax=%f", fShareFractionMax);
+  tListSetttings->AddLast(new TObjString(buf));
+
+  return tListSetttings;
+}
+
+void     AliFemtoShareQualityPairCut::SetRemoveSameLabel(Bool_t aRemove)
+{
+  fRemoveSameLabel = aRemove;
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoShareQualityPairCut.h b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoShareQualityPairCut.h
new file mode 100644 (file)
index 0000000..d78bd4e
--- /dev/null
@@ -0,0 +1,76 @@
+/////////////////////////////////////////////////////////////////////////////
+//                                                                         //
+// AliFemtoShareQualityPairCut - a pair cut which checks for some pair     //
+// qualities that attempt to identify slit/doubly reconstructed tracks     //
+//                                                                         //
+/////////////////////////////////////////////////////////////////////////////
+/***************************************************************************
+ *
+ * $Id$
+ *
+ * Author: Adam Kisiel, Ohio State University, kisiel@mps.ohio-state.edu
+ ***************************************************************************
+ *
+ * Description: part of STAR HBT Framework: AliFemtoMaker package
+ *   a cut to remove "shared" and "split" pairs
+ *
+ ***************************************************************************
+ *
+ *
+ **************************************************************************/
+
+
+#ifndef ALIFEMTOSHAREQUALITYPAIRCUT_H
+#define ALIFEMTOSHAREQUALITYPAIRCUT_H
+
+// do I need these lines ?
+//#ifndef StMaker_H
+//#include "StMaker.h"
+//#endif
+
+#include "AliFemtoPairCut.h"
+
+class AliFemtoShareQualityPairCut : public AliFemtoPairCut{
+public:
+  AliFemtoShareQualityPairCut();
+  AliFemtoShareQualityPairCut(const AliFemtoShareQualityPairCut& cut);
+  virtual ~AliFemtoShareQualityPairCut();
+  AliFemtoShareQualityPairCut& operator=(const AliFemtoShareQualityPairCut& cut);
+  
+  virtual bool Pass(const AliFemtoPair* pair);
+  virtual AliFemtoString Report();
+  virtual TList *ListSettings();
+  virtual AliFemtoPairCut* Clone();
+  void SetShareQualityMax(Double_t aAliFemtoShareQualityMax);
+  Double_t GetAliFemtoShareQualityMax() const;
+  void SetShareFractionMax(Double_t aAliFemtoShareFractionMax);
+  Double_t GetAliFemtoShareFractionMax() const;
+  void     SetRemoveSameLabel(Bool_t aRemove);
+  
+ protected:
+  long fNPairsPassed;          // Number of pairs consideered that passed the cut 
+  long fNPairsFailed;          // Number of pairs consideered that failed the cut
+
+ private:
+  Double_t fShareQualityMax;   // Maximum allowed pair quality
+  Double_t fShareFractionMax;  // Maximum allowed share fraction
+  Bool_t   fRemoveSameLabel;   // If 1 pairs with two tracks with the same label will be removed 
+
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoShareQualityPairCut, 0)
+#endif
+};
+
+inline AliFemtoShareQualityPairCut::AliFemtoShareQualityPairCut(const AliFemtoShareQualityPairCut& c) : 
+  AliFemtoPairCut(c),
+  fNPairsPassed(0),
+  fNPairsFailed(0),
+  fShareQualityMax(1.0),
+  fShareFractionMax(1.0),
+  fRemoveSameLabel(0)// no cut
+{ /* no-op */ }
+
+inline AliFemtoPairCut* AliFemtoShareQualityPairCut::Clone() { AliFemtoShareQualityPairCut* c = new AliFemtoShareQualityPairCut(*this); return c;}
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoShareQualityQAPairCut.cxx b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoShareQualityQAPairCut.cxx
new file mode 100644 (file)
index 0000000..babb17f
--- /dev/null
@@ -0,0 +1,230 @@
+/////////////////////////////////////////////////////////////////////////////
+//                                                                         //
+// AliFemtoShareQualityQAPairCut - a pair cut which checks for some pair     //
+// qualities that attempt to identify slit/doubly reconstructed tracks     //
+//                                                                         //
+/////////////////////////////////////////////////////////////////////////////
+/***************************************************************************
+ *
+ * $Id: AliFemtoShareQualityQAPairCut.cxx 24360 2008-03-10 09:48:27Z akisiel $
+ *
+ * Author: Adam Kisiel, Ohio State, kisiel@mps.ohio-state.edu
+ ***************************************************************************
+ *
+ * Description: part of STAR HBT Framework: AliFemtoMaker package
+ *   a cut to remove "shared" and "split" pairs
+ *
+ ***************************************************************************
+ *
+ *
+ **************************************************************************/
+
+#include "AliFemtoShareQualityQAPairCut.h"
+#include <string>
+#include <cstdio>
+
+#ifdef __ROOT__
+ClassImp(AliFemtoShareQualityQAPairCut)
+#endif
+
+//__________________
+AliFemtoShareQualityQAPairCut::AliFemtoShareQualityQAPairCut():
+  fNPairsPassed(0),
+  fNPairsFailed(0),
+  fShareQualityMax(1.0),
+  fShareQualitymin(-0.5),
+  fShareFractionMax(1.0),
+  fShareFractionmin(0.0),
+  fRemoveSameLabel(0),
+  fShareQualityQASwitch(0),
+  fShareFractionQASwitch(0)
+{ 
+  fShareQualityQASwitch  = false;
+  fShareQualityQAExclusionZone[0] = -0.5;
+  fShareQualityQAExclusionZone[1] = 1.0;
+  fShareFractionQASwitch = false; 
+  fShareFractionQAExclusionZone[0] = 0.0;
+  fShareFractionQAExclusionZone[1] = 1.0;
+}
+
+//__________________
+AliFemtoShareQualityQAPairCut::~AliFemtoShareQualityQAPairCut(){
+  /* no-op */
+}
+//__________________
+AliFemtoShareQualityQAPairCut& AliFemtoShareQualityQAPairCut::operator=(const AliFemtoShareQualityQAPairCut& cut)
+{
+  if (this != &cut) {
+    AliFemtoPairCut::operator=(cut);
+    fNPairsPassed = 0;
+    fNPairsFailed = 0;
+    fShareQualityMax = 1.0;
+    fShareQualitymin = -0.5;
+    fShareFractionMax = 1.0;
+    fShareFractionmin = 0.0;
+    fRemoveSameLabel = 0;
+    fShareQualityQASwitch = 0;
+    fShareFractionQASwitch = 0;
+    fShareQualityQASwitch  = cut.fShareQualityQASwitch;
+    fShareQualityQAExclusionZone[0]  = cut.fShareQualityQAExclusionZone[0];
+    fShareQualityQAExclusionZone[1]  = cut.fShareQualityQAExclusionZone[1];
+    fShareFractionQASwitch = cut.fShareFractionQASwitch; 
+    fShareFractionQAExclusionZone[0]  = cut.fShareFractionQAExclusionZone[0];
+    fShareFractionQAExclusionZone[1]  = cut.fShareFractionQAExclusionZone[1];
+  }
+
+  return *this;
+  
+}
+//__________________
+bool AliFemtoShareQualityQAPairCut::Pass(const AliFemtoPair* pair){
+  // Check for pairs that are possibly shared/double reconstruction
+  bool pass;
+  
+  Int_t nh = 0;
+  Int_t an = 0;
+  Int_t ns = 0;
+  
+  for (unsigned int imap=0; imap<pair->Track1()->Track()->TPCclusters().GetNbits(); imap++) {
+    // If both have clusters in the same row
+    if (pair->Track1()->Track()->TPCclusters().TestBitNumber(imap) && 
+       pair->Track2()->Track()->TPCclusters().TestBitNumber(imap)) {
+      // Do they share it ?
+      if (pair->Track1()->Track()->TPCsharing().TestBitNumber(imap) &&
+         pair->Track2()->Track()->TPCsharing().TestBitNumber(imap))
+       {
+         //      cout << "A shared cluster !!!" << endl;
+         //    cout << "imap idx1 idx2 " 
+         //         << imap << " "
+         //         << tP1idx[imap] << " " << tP2idx[imap] << endl;
+         an++;
+         nh+=2;
+         ns+=2;
+       }
+      
+      // Different hits on the same padrow
+      else {
+       an--;
+       nh+=2;
+      }
+    }
+    else if (pair->Track1()->Track()->TPCclusters().TestBitNumber(imap) ||
+            pair->Track2()->Track()->TPCclusters().TestBitNumber(imap)) {
+      // One track has a hit, the other does not
+      an++;
+      nh++;
+    }
+  }
+  
+  Float_t hsmval = 0.0;
+  Float_t hsfval = 0.0;
+
+  if (nh >0) {
+    hsmval = an*1.0/nh;
+    hsfval = ns*1.0/nh;
+  }
+  //  if (hsmval > -0.4) {
+//   cout << "Pair quality: " << hsmval << " " << an << " " << nh << " " 
+//        << (pair->Track1()->Track()) << " " 
+//        << (pair->Track2()->Track()) << endl;
+//   cout << "Bits: " << pair->Track1()->Track()->TPCclusters().GetNbits() << endl;
+    //  }
+//   if (hsfval > 0.0) {
+//     cout << "Pair sharity: " << hsfval << " " << ns << " " << nh << "    " << hsmval << " " << an << " " << nh << endl;
+//   }
+
+  // Determine if pair pass/fail cuts:
+  if (fShareQualityQASwitch) {
+    pass = (((hsmval >= fShareQualitymin)  && (hsmval < fShareQualityQAExclusionZone[0]))  || 
+           ((hsmval >= fShareQualityQAExclusionZone[1])  && (hsmval < fShareQualityMax))) &&
+      (hsfval >= fShareFractionmin) && (hsfval < fShareFractionMax);
+  }
+  else if (fShareFractionQASwitch) {
+    pass = (((hsfval >= fShareFractionmin)  && (hsfval < fShareFractionQAExclusionZone[0]))  || 
+           ((hsfval >= fShareFractionQAExclusionZone[1])  && (hsfval < fShareFractionMax))) &&
+      (hsmval >= fShareQualitymin) && (hsmval < fShareQualityMax);
+  }
+  else {
+    pass = (hsmval >= fShareQualitymin)  && (hsmval < fShareQualityMax) && 
+      (hsfval >= fShareFractionmin) && (hsfval < fShareFractionMax);
+  }
+
+  if (fRemoveSameLabel) {
+    if (abs(pair->Track1()->Track()->Label()) == abs(pair->Track2()->Track()->Label())) {
+      cout << "Found a pair with same label " << pair->Track1()->Track()->Label() << endl;
+      cout << "Quality Sharity Passed " << hsmval << " " << hsfval << " " << pair->QInv() << " " << pass << endl;
+      pass = kFALSE;
+    }
+  }
+
+  pass ? fNPairsPassed++ : fNPairsFailed++;
+  return pass;
+}
+//__________________
+AliFemtoString AliFemtoShareQualityQAPairCut::Report(){
+  // Prepare the report from the execution
+  string stemp = "AliFemtoShareQuality Pair Cut - remove shared and split pairs\n";  char ctemp[100];
+  snprintf(ctemp , 100, "Number of pairs which passed:\t%ld  Number which failed:\t%ld\n",fNPairsPassed,fNPairsFailed);
+  stemp += ctemp;
+  AliFemtoString returnThis = stemp;
+  return returnThis;}
+//__________________
+
+void AliFemtoShareQualityQAPairCut::SetShareQualityMax(Double_t aShareQualityMax) {
+  fShareQualityMax = aShareQualityMax;
+}
+
+void AliFemtoShareQualityQAPairCut::SetShareQualitymin(Double_t aShareQualitymin) {
+  fShareQualitymin = aShareQualitymin;
+}
+
+void AliFemtoShareQualityQAPairCut::SetShareQualityQASwitch(bool aSwitch) {
+  fShareQualityQASwitch = aSwitch;
+}
+
+void AliFemtoShareQualityQAPairCut::SetShareQualityQAExclusionZone(Double_t lo, Double_t hi) {
+  fShareQualityQAExclusionZone[0] = lo;
+  fShareQualityQAExclusionZone[1] = hi;
+}
+
+Double_t AliFemtoShareQualityQAPairCut::GetAliFemtoShareQualityMax() const {
+  return fShareQualityMax;
+}
+
+void AliFemtoShareQualityQAPairCut::SetShareFractionMax(Double_t aShareFractionMax) {
+  fShareFractionMax = aShareFractionMax;
+}
+
+void AliFemtoShareQualityQAPairCut::SetShareFractionmin(Double_t aShareFractionmin) {
+  fShareFractionmin = aShareFractionmin;
+}
+
+void AliFemtoShareQualityQAPairCut::SetShareFractionQASwitch(bool aSwitch) {
+  fShareFractionQASwitch = aSwitch;
+}
+
+void AliFemtoShareQualityQAPairCut::SetShareFractionQAExclusionZone(Double_t lo, Double_t hi) {
+  fShareFractionQAExclusionZone[0] = lo;
+  fShareFractionQAExclusionZone[1] = hi;
+}
+
+Double_t AliFemtoShareQualityQAPairCut::GetAliFemtoShareFractionMax() const {
+  return fShareFractionMax;
+}
+
+TList *AliFemtoShareQualityQAPairCut::ListSettings()
+{
+  // return a list of settings in a writable form
+  TList *tListSetttings = new TList();
+  char buf[200];
+  snprintf(buf, 200, "AliFemtoShareQualityQAPairCut.sharequalitymax=%f", fShareQualityMax);
+  snprintf(buf, 200, "AliFemtoShareQualityQAPairCut.sharefractionmax=%f", fShareFractionMax);
+  tListSetttings->AddLast(new TObjString(buf));
+
+  return tListSetttings;
+}
+
+void     AliFemtoShareQualityQAPairCut::SetRemoveSameLabel(Bool_t aRemove)
+{
+  fRemoveSameLabel = aRemove;
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoShareQualityQAPairCut.h b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoShareQualityQAPairCut.h
new file mode 100644 (file)
index 0000000..a6739bc
--- /dev/null
@@ -0,0 +1,100 @@
+/////////////////////////////////////////////////////////////////////////////
+//                                                                         //
+// AliFemtoShareQualityQAPairCut - a pair cut which checks for some pair     //
+// qualities that attempt to identify slit/doubly reconstructed tracks     //
+//                                                                         //
+/////////////////////////////////////////////////////////////////////////////
+/***************************************************************************
+ *
+ * $Id: AliFemtoShareQualityQAPairCut.h 24360 2008-03-10 09:48:27Z akisiel $
+ *
+ * Author: Adam Kisiel, Ohio State University, kisiel@mps.ohio-state.edu
+ ***************************************************************************
+ *
+ * Description: part of STAR HBT Framework: AliFemtoMaker package
+ *   a cut to remove "shared" and "split" pairs
+ *
+ ***************************************************************************
+ *
+ *
+ **************************************************************************/
+
+
+#ifndef AliFemtoShareQualityQAPairCut_H
+#define AliFemtoShareQualityQAPairCut_H
+
+// do I need these lines ?
+//#ifndef StMaker_H
+//#include "StMaker.h"
+//#endif
+
+#include "AliFemtoPairCut.h"
+
+class AliFemtoShareQualityQAPairCut : public AliFemtoPairCut{
+public:
+  AliFemtoShareQualityQAPairCut();
+  AliFemtoShareQualityQAPairCut(const AliFemtoShareQualityQAPairCut& cut);
+  virtual ~AliFemtoShareQualityQAPairCut();
+  AliFemtoShareQualityQAPairCut& operator=(const AliFemtoShareQualityQAPairCut& cut);
+  
+  virtual bool Pass(const AliFemtoPair* pair);
+  virtual AliFemtoString Report();
+  virtual TList *ListSettings();
+  virtual AliFemtoPairCut* Clone();
+  void SetShareQualityMax(Double_t aAliFemtoShareQualityMax);
+  void SetShareQualitymin(Double_t aAliFemtoShareQualitymin);
+  void SetShareQualityQASwitch(bool aSwitch);
+  void SetShareQualityQAExclusionZone(Double_t lo, Double_t hi);
+  Double_t GetAliFemtoShareQualityMax() const;
+  void SetShareFractionMax(Double_t aAliFemtoShareFractionMax);
+  void SetShareFractionmin(Double_t aAliFemtoShareFractionmin);
+  void SetShareFractionQASwitch(bool aSwitch);
+  void SetShareFractionQAExclusionZone(Double_t lo, Double_t hi);
+  Double_t GetAliFemtoShareFractionMax() const;
+  void     SetRemoveSameLabel(Bool_t aRemove);
+  
+ protected:
+  long fNPairsPassed;          // Number of pairs consideered that passed the cut 
+  long fNPairsFailed;          // Number of pairs consideered that failed the cut
+
+ private:
+  Double_t fShareQualityMax;   // Maximum allowed pair quality
+  Double_t fShareQualitymin;   // Minimum allowed pair quality
+  Double_t fShareFractionMax;  // Maximum allowed share fraction
+  Double_t fShareFractionmin;  // Minimum allowed share fraction
+  Bool_t   fRemoveSameLabel;   // If 1 pairs with two tracks with the same label will be removed 
+  
+  bool     fShareQualityQASwitch;             // Turn on QA Exclusion Zone (true=on)
+  Double_t fShareQualityQAExclusionZone[2];   // Set Exclusion Zone limits
+  bool     fShareFractionQASwitch;             // Turn on QA Exclusion Zone (true=on)
+  Double_t fShareFractionQAExclusionZone[2];   // Set Exclusion Zone limits
+
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoShareQualityQAPairCut, 0)
+#endif
+};
+
+inline AliFemtoShareQualityQAPairCut::AliFemtoShareQualityQAPairCut(const AliFemtoShareQualityQAPairCut& c) : 
+  AliFemtoPairCut(c),
+  fNPairsPassed(0),
+  fNPairsFailed(0),
+  fShareQualityMax(1.0),
+  fShareQualitymin(-0.5),
+  fShareFractionMax(1.0),
+  fShareFractionmin(0.0),
+  fRemoveSameLabel(0),// no cut
+  fShareQualityQASwitch(0),
+  fShareFractionQASwitch(0)
+{ 
+  fShareQualityQASwitch  = c.fShareQualityQASwitch;
+  fShareQualityQAExclusionZone[0]  = c.fShareQualityQAExclusionZone[0];
+  fShareQualityQAExclusionZone[1]  = c.fShareQualityQAExclusionZone[1];
+  fShareFractionQASwitch = c.fShareFractionQASwitch; 
+  fShareFractionQAExclusionZone[0]  = c.fShareFractionQAExclusionZone[0];
+  fShareFractionQAExclusionZone[1]  = c.fShareFractionQAExclusionZone[1];
+}
+
+inline AliFemtoPairCut* AliFemtoShareQualityQAPairCut::Clone() { AliFemtoShareQualityQAPairCut* c = new AliFemtoShareQualityQAPairCut(*this); return c;}
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoShareQualityTPCEntranceSepPairCut.cxx b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoShareQualityTPCEntranceSepPairCut.cxx
new file mode 100644 (file)
index 0000000..ead416c
--- /dev/null
@@ -0,0 +1,108 @@
+/////////////////////////////////////////////////////////////////////////////
+//                                                                         //
+// AliFemtoShareQualityTPCEntranceSepPairCut - a pair cut which checks     //
+// for some pair qualities that attempt to identify slit/doubly            //
+// reconstructed tracks and also selects pairs based on their separation   //
+// at the entrance to the TPC                                              //
+//                                                                         //
+/////////////////////////////////////////////////////////////////////////////
+/***************************************************************************
+ *
+ * $Id: AliFemtoShareQualityTPCEntranceSepPairCut.cxx,v 1.1.2.1 2007/10/19 13:35:33 akisiel Exp $
+ *
+ * Author: Adam Kisiel, Ohio State, kisiel@mps.ohio-state.edu
+ ***************************************************************************
+ *
+ * Description: part of STAR HBT Framework: AliFemtoMaker package
+ *   a cut to remove "shared" and "split" pairs
+ *
+ ***************************************************************************
+ *
+ *
+ **************************************************************************/
+
+#include "AliFemtoShareQualityTPCEntranceSepPairCut.h"
+#include <string>
+#include <cstdio>
+
+#ifdef __ROOT__
+ClassImp(AliFemtoShareQualityTPCEntranceSepPairCut)
+#endif
+
+//__________________
+AliFemtoShareQualityTPCEntranceSepPairCut::AliFemtoShareQualityTPCEntranceSepPairCut():
+  AliFemtoShareQualityPairCut(),
+  fDTPCMin(0)
+{
+}
+//__________________
+AliFemtoShareQualityTPCEntranceSepPairCut::AliFemtoShareQualityTPCEntranceSepPairCut(const AliFemtoShareQualityTPCEntranceSepPairCut& c) : 
+  AliFemtoShareQualityPairCut(c),
+  fDTPCMin(0)
+{ 
+  fDTPCMin = c.fDTPCMin;
+}
+
+//__________________
+AliFemtoShareQualityTPCEntranceSepPairCut::~AliFemtoShareQualityTPCEntranceSepPairCut(){
+  /* no-op */
+}
+//__________________
+
+AliFemtoShareQualityTPCEntranceSepPairCut& AliFemtoShareQualityTPCEntranceSepPairCut::operator=(const AliFemtoShareQualityTPCEntranceSepPairCut& c)
+{
+  if (this != &c) {
+    AliFemtoShareQualityPairCut::operator=(c);
+    fDTPCMin = c.fDTPCMin;
+  }
+
+  return *this;
+}
+//__________________
+bool AliFemtoShareQualityTPCEntranceSepPairCut::Pass(const AliFemtoPair* pair){
+  // Accept pairs based on their TPC entrance separation and
+  // quality and sharity
+  bool temp = true;
+  
+  double distx = pair->Track1()->Track()->NominalTpcEntrancePoint().x() - pair->Track2()->Track()->NominalTpcEntrancePoint().x();
+  double disty = pair->Track1()->Track()->NominalTpcEntrancePoint().y() - pair->Track2()->Track()->NominalTpcEntrancePoint().y();
+  double distz = pair->Track1()->Track()->NominalTpcEntrancePoint().z() - pair->Track2()->Track()->NominalTpcEntrancePoint().z();
+  double dist = sqrt(distx*distx + disty*disty + distz*distz);
+
+  temp = dist > fDTPCMin;
+
+  if (temp) {
+    temp = AliFemtoShareQualityPairCut::Pass(pair);
+  }
+  else
+    fNPairsFailed++;
+
+  return temp;
+}
+//__________________
+AliFemtoString AliFemtoShareQualityTPCEntranceSepPairCut::Report(){
+  // Prepare a report from the execution
+  string stemp = "AliFemtoShareQualityTPCEntranceSep Pair Cut - remove shared and split pairs and pairs with small separation at the entrance to the TPC\n";  char ctemp[100];
+  snprintf(ctemp , 100, "Accept pair with TPC entrance separation more that %f",fDTPCMin);
+  stemp += ctemp;
+  snprintf(ctemp , 100, "Number of pairs which passed:\t%ld  Number which failed:\t%ld\n",fNPairsPassed,fNPairsFailed);
+  stemp += ctemp;
+  AliFemtoString returnThis = stemp;
+  return returnThis;}
+//__________________
+
+TList *AliFemtoShareQualityTPCEntranceSepPairCut::ListSettings()
+{
+  // return a list of settings in a writable form
+  TList *tListSetttings =  AliFemtoShareQualityPairCut::ListSettings();
+  char buf[200];
+  snprintf(buf, 200, "AliFemtoShareQualityTPCEntranceSepPairCut.tpcentsepmin=%f", fDTPCMin);
+  tListSetttings->AddLast(new TObjString(buf));
+
+  return tListSetttings;
+}
+
+void AliFemtoShareQualityTPCEntranceSepPairCut::SetTPCEntranceSepMinimum(double dtpc)
+{
+  fDTPCMin = dtpc;
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoShareQualityTPCEntranceSepPairCut.h b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoShareQualityTPCEntranceSepPairCut.h
new file mode 100644 (file)
index 0000000..d36bb0c
--- /dev/null
@@ -0,0 +1,59 @@
+/////////////////////////////////////////////////////////////////////////////
+//                                                                         //
+// AliFemtoShareQualityTPCEntranceSepPairCut - a pair cut which checks     //
+// for some pair qualities that attempt to identify slit/doubly            //
+// reconstructed tracks and also selects pairs based on their separation   //
+// at the entrance to the TPC                                              //
+//                                                                         //
+/////////////////////////////////////////////////////////////////////////////
+/***************************************************************************
+ *
+ * $Id: AliFemtoShareQualityTPCEntranceSepPairCut.h,v 1.1.2.1 2007/10/19 13:35:33 akisiel Exp $
+ *
+ * Author: Adam Kisiel, Ohio State University, kisiel@mps.ohio-state.edu
+ ***************************************************************************
+ *
+ * Description: part of STAR HBT Framework: AliFemtoMaker package
+ *   a cut to remove "shared" and "split" pairs
+ *
+ ***************************************************************************
+ *
+ *
+ **************************************************************************/
+
+
+#ifndef ALIFEMTOSHAREQUALITYTPCENTRANCESEPPAIRCUT_H
+#define ALIFEMTOSHAREQUALITYTPCENTRANCESEPPAIRCUT_H
+
+// do I need these lines ?
+//#ifndef StMaker_H
+//#include "StMaker.h"
+//#endif
+
+#include "AliFemtoPairCut.h"
+#include "AliFemtoShareQualityPairCut.h"
+
+class AliFemtoShareQualityTPCEntranceSepPairCut : public AliFemtoShareQualityPairCut{
+public:
+  AliFemtoShareQualityTPCEntranceSepPairCut();
+  AliFemtoShareQualityTPCEntranceSepPairCut(const AliFemtoShareQualityTPCEntranceSepPairCut& c);
+  virtual ~AliFemtoShareQualityTPCEntranceSepPairCut();
+  AliFemtoShareQualityTPCEntranceSepPairCut& operator=(const AliFemtoShareQualityTPCEntranceSepPairCut& c);
+
+  virtual bool Pass(const AliFemtoPair* pair);
+  virtual AliFemtoString Report();
+  virtual TList *ListSettings();
+  virtual AliFemtoPairCut* Clone();
+  void SetTPCEntranceSepMinimum(double dtpc);
+  
+ protected:
+  Double_t fDTPCMin;          // Minimum allowed pair nominal separation at the entrance to the TPC
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoShareQualityTPCEntranceSepPairCut, 0)
+#endif
+};
+
+inline AliFemtoPairCut* AliFemtoShareQualityTPCEntranceSepPairCut::Clone() { AliFemtoShareQualityTPCEntranceSepPairCut* c = new AliFemtoShareQualityTPCEntranceSepPairCut(*this); return c;}
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoShareQualityTPCEntranceSepQAPairCut.cxx b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoShareQualityTPCEntranceSepQAPairCut.cxx
new file mode 100644 (file)
index 0000000..70cf0b1
--- /dev/null
@@ -0,0 +1,147 @@
+/////////////////////////////////////////////////////////////////////////////
+//                                                                         //
+// AliFemtoShareQualityTPCEntranceSepQAPairCut - a pair cut which checks     //
+// for some pair qualities that attempt to identify slit/doubly            //
+// reconstructed tracks and also selects pairs based on their separation   //
+// at the entrance to the TPC                                              //
+//                                                                         //
+/////////////////////////////////////////////////////////////////////////////
+/***************************************************************************
+ *
+ * $Id: AliFemtoShareQualityTPCEntranceSepQAPairCut.cxx,v 1.1.2.1 2007/10/19 13:35:33 akisiel Exp $
+ *
+ * Author: Adam Kisiel, Ohio State, kisiel@mps.ohio-state.edu
+ ***************************************************************************
+ *
+ * Description: part of STAR HBT Framework: AliFemtoMaker package
+ *   a cut to remove "shared" and "split" pairs
+ *
+ ***************************************************************************
+ *
+ *
+ **************************************************************************/
+
+#include "AliFemtoShareQualityTPCEntranceSepQAPairCut.h"
+#include <string>
+#include <cstdio>
+
+#ifdef __ROOT__
+ClassImp(AliFemtoShareQualityTPCEntranceSepQAPairCut)
+#endif
+
+//__________________
+AliFemtoShareQualityTPCEntranceSepQAPairCut::AliFemtoShareQualityTPCEntranceSepQAPairCut():
+  AliFemtoShareQualityQAPairCut(),
+  fDTPCMin(0.0),
+  fDTPCMax(1000.0),
+  fDTPCQASwitch(0)
+{
+  fDTPCQASwitch = false;
+  fDTPCQAExclusionZone[0] = 0.0;
+  fDTPCQAExclusionZone[1] = 1000.0;
+}
+//__________________
+AliFemtoShareQualityTPCEntranceSepQAPairCut::AliFemtoShareQualityTPCEntranceSepQAPairCut(const AliFemtoShareQualityTPCEntranceSepQAPairCut& c) : 
+  AliFemtoShareQualityQAPairCut(c),
+  fDTPCMin(0),
+  fDTPCMax(1000.0),
+  fDTPCQASwitch(0)
+{ 
+  fDTPCMin = c.fDTPCMin;
+  fDTPCMax = c.fDTPCMax;
+  fDTPCQASwitch = c.fDTPCQASwitch;
+  fDTPCQAExclusionZone[0] = c.fDTPCQAExclusionZone[0];
+  fDTPCQAExclusionZone[1] = c.fDTPCQAExclusionZone[1];
+}
+
+//__________________
+AliFemtoShareQualityTPCEntranceSepQAPairCut& AliFemtoShareQualityTPCEntranceSepQAPairCut::operator=(const AliFemtoShareQualityTPCEntranceSepQAPairCut& aCut)
+{
+  // assignment operator
+  if (this == &aCut)
+    return *this;
+
+  fDTPCMin = aCut.fDTPCMin;
+  fDTPCMax = aCut.fDTPCMax;
+  fDTPCQASwitch = aCut.fDTPCQASwitch;
+  fDTPCQAExclusionZone[0] = aCut.fDTPCQAExclusionZone[0];
+  fDTPCQAExclusionZone[1] = aCut.fDTPCQAExclusionZone[1];
+
+  return *this;
+}
+
+//__________________
+AliFemtoShareQualityTPCEntranceSepQAPairCut::~AliFemtoShareQualityTPCEntranceSepQAPairCut(){
+  /* no-op */
+}
+//__________________
+bool AliFemtoShareQualityTPCEntranceSepQAPairCut::Pass(const AliFemtoPair* pair){
+  // Accept pairs based on their TPC entrance separation and
+  // quality and sharity
+  bool pass = true;
+  
+  double distx = pair->Track1()->Track()->NominalTpcEntrancePoint().x() - pair->Track2()->Track()->NominalTpcEntrancePoint().x();
+  double disty = pair->Track1()->Track()->NominalTpcEntrancePoint().y() - pair->Track2()->Track()->NominalTpcEntrancePoint().y();
+  double distz = pair->Track1()->Track()->NominalTpcEntrancePoint().z() - pair->Track2()->Track()->NominalTpcEntrancePoint().z();
+  double dist = sqrt(distx*distx + disty*disty + distz*distz);
+
+  if (fDTPCQASwitch) {
+    pass = ((dist > fDTPCMin) && (dist < fDTPCQAExclusionZone[0])) ||
+           ((dist > fDTPCQAExclusionZone[1]) && (dist < fDTPCMax));
+  }
+  else {
+    pass = (dist > fDTPCMin) && (dist < fDTPCMax);
+  }
+
+  if (pass) {
+    pass = AliFemtoShareQualityQAPairCut::Pass(pair);
+  }
+  else
+    fNPairsFailed++;
+
+  return pass;
+}
+//__________________
+AliFemtoString AliFemtoShareQualityTPCEntranceSepQAPairCut::Report(){
+  // Prepare a report from the execution
+  string stemp = "AliFemtoShareQualityTPCEntranceSep Pair Cut - remove shared and split pairs and pairs with small separation at the entrance to the TPC\n";  char ctemp[100];
+  snprintf(ctemp , 100, "Accept pair with TPC entrance separation more that %f",fDTPCMin);
+  stemp += ctemp;
+  snprintf(ctemp , 100, "Number of pairs which passed:\t%ld  Number which failed:\t%ld\n",fNPairsPassed,fNPairsFailed);
+  stemp += ctemp;
+  AliFemtoString returnThis = stemp;
+  return returnThis;}
+//__________________
+
+TList *AliFemtoShareQualityTPCEntranceSepQAPairCut::ListSettings()
+{
+  // return a list of settings in a writable form
+  TList *tListSetttings =  AliFemtoShareQualityQAPairCut::ListSettings();
+  char buf[200];
+  snprintf(buf, 200, "AliFemtoShareQualityTPCEntranceSepQAPairCut.tpcentsepmin=%f", fDTPCMin);
+  tListSetttings->AddLast(new TObjString(buf));
+
+  return tListSetttings;
+}
+
+void AliFemtoShareQualityTPCEntranceSepQAPairCut::SetTPCEntranceSepMinimum(double dtpc)
+{
+  fDTPCMin = dtpc;
+}
+
+void AliFemtoShareQualityTPCEntranceSepQAPairCut::SetTPCEntranceSepMaximum(double dtpc)
+{
+  fDTPCMax = dtpc;
+}
+
+void AliFemtoShareQualityTPCEntranceSepQAPairCut::SetTPCEntranceSepQASwitch(bool Switch)
+{
+  fDTPCQASwitch = Switch;
+}
+
+void AliFemtoShareQualityTPCEntranceSepQAPairCut::SetTPCEntranceSepQAExclusionZone(double lo, double hi)
+{
+  fDTPCQAExclusionZone[0] = lo;
+  fDTPCQAExclusionZone[1] = hi;
+}
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoShareQualityTPCEntranceSepQAPairCut.h b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoShareQualityTPCEntranceSepQAPairCut.h
new file mode 100644 (file)
index 0000000..3a52239
--- /dev/null
@@ -0,0 +1,66 @@
+/////////////////////////////////////////////////////////////////////////////
+//                                                                         //
+// AliFemtoShareQualityTPCEntranceSepQAPairCut - a pair cut which checks     //
+// for some pair qualities that attempt to identify slit/doubly            //
+// reconstructed tracks and also selects pairs based on their separation   //
+// at the entrance to the TPC                                              //
+//                                                                         //
+/////////////////////////////////////////////////////////////////////////////
+/***************************************************************************
+ *
+ * $Id: AliFemtoShareQualityTPCEntranceSepQAPairCut.h,v 1.1.2.1 2007/10/19 13:35:33 akisiel Exp $
+ *
+ * Author: Adam Kisiel, Ohio State University, kisiel@mps.ohio-state.edu
+ ***************************************************************************
+ *
+ * Description: part of STAR HBT Framework: AliFemtoMaker package
+ *   a cut to remove "shared" and "split" pairs
+ *
+ ***************************************************************************
+ *
+ *
+ **************************************************************************/
+
+
+#ifndef AliFemtoShareQualityTPCEntranceSepQAPairCut_H
+#define AliFemtoShareQualityTPCEntranceSepQAPairCut_H
+
+// do I need these lines ?
+//#ifndef StMaker_H
+//#include "StMaker.h"
+//#endif
+
+#include "AliFemtoPairCut.h"
+#include "AliFemtoShareQualityQAPairCut.h"
+
+class AliFemtoShareQualityTPCEntranceSepQAPairCut : public AliFemtoShareQualityQAPairCut{
+public:
+  AliFemtoShareQualityTPCEntranceSepQAPairCut();
+  AliFemtoShareQualityTPCEntranceSepQAPairCut(const AliFemtoShareQualityTPCEntranceSepQAPairCut& c);
+  virtual ~AliFemtoShareQualityTPCEntranceSepQAPairCut();
+
+  AliFemtoShareQualityTPCEntranceSepQAPairCut& operator=(const AliFemtoShareQualityTPCEntranceSepQAPairCut& aCut);
+
+  virtual bool Pass(const AliFemtoPair* pair);
+  virtual AliFemtoString Report();
+  virtual TList *ListSettings();
+  virtual AliFemtoPairCut* Clone();
+  void SetTPCEntranceSepMinimum(double dtpc);
+  void SetTPCEntranceSepMaximum(double dtpc);
+  void SetTPCEntranceSepQASwitch(bool Switch);
+  void SetTPCEntranceSepQAExclusionZone(double lo, double hi);
+  
+ protected:
+  Double_t fDTPCMin;                // Minimum allowed pair nominal separation at the entrance to the TPC
+  Double_t fDTPCMax;                // Maximum allowed pair nominal separation at the entrance to the TPC
+  bool     fDTPCQASwitch;           // Turn on QA Exclusion Zone (true=on)
+  Double_t fDTPCQAExclusionZone[2]; // Exclusion Zone for pair nominal separation at the entrance to the TPC
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoShareQualityTPCEntranceSepQAPairCut, 0)
+#endif
+};
+
+inline AliFemtoPairCut* AliFemtoShareQualityTPCEntranceSepQAPairCut::Clone() { AliFemtoShareQualityTPCEntranceSepQAPairCut* c = new AliFemtoShareQualityTPCEntranceSepQAPairCut(*this); return c;}
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoTPCInnerCorrFctn.cxx b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoTPCInnerCorrFctn.cxx
new file mode 100644 (file)
index 0000000..8d54022
--- /dev/null
@@ -0,0 +1,235 @@
+////////////////////////////////////////////////////////////////////////////////
+///                                                                          ///
+/// AliFemtoTPCInnerCorrFctn - A correlation function that saves the         ///
+/// distance at the entrance to the TPC between two tracks as a function     ///
+/// of qinv                                                                  ///
+/// Authors: Adam Kisiel kisiel@mps.ohio-state.edu                           ///
+///                                                                          ///
+////////////////////////////////////////////////////////////////////////////////
+
+#include "AliFemtoTPCInnerCorrFctn.h"
+//#include "AliFemtoHisto.hh"
+#include <cstdio>
+
+#ifdef __ROOT__ 
+ClassImp(AliFemtoTPCInnerCorrFctn)
+#endif
+
+//____________________________
+AliFemtoTPCInnerCorrFctn::AliFemtoTPCInnerCorrFctn(char* title, const int& nbins, const float& QinvLo, const float& QinvHi):
+  fDTPCNumerator(0),
+  fDTPCDenominator(0),
+  fRadDNumerator(0),
+  fRadDDenominator(0),
+  fRadius(100)
+{
+  // set up numerator
+  //  title = "Num Qinv (MeV/c)";
+  char tTitNum[101] = "NumDTPC";
+  strncat(tTitNum,title, 100);
+  fDTPCNumerator = new TH2D(tTitNum,title,nbins,QinvLo,QinvHi,100,0.0,20.0);
+  // set up denominator
+  //title = "Den Qinv (MeV/c)";
+  char tTitDen[101] = "DenDTPC";
+  strncat(tTitDen,title, 100);
+  fDTPCDenominator = new TH2D(tTitDen,title,nbins,QinvLo,QinvHi,100,0.0,20.0);
+
+  char tTitNumR[101] = "NumRadD";
+  strncat(tTitNumR,title, 100);
+  fRadDNumerator = new TH2D(tTitNumR,title,50,-0.1,0.1,50,-0.1,0.1);
+  // set up denominator
+  //title = "Den Qinv (MeV/c)";
+  char tTitDenR[101] = "DenRadD";
+  strncat(tTitDenR,title, 100);
+  fRadDDenominator = new TH2D(tTitDenR,title,50,-0.1,0.1,50,-0.1,0.1);
+
+  // to enable error bar calculation...
+  fDTPCNumerator->Sumw2();
+  fDTPCDenominator->Sumw2();
+  fRadDNumerator->Sumw2();
+  fRadDDenominator->Sumw2();
+}
+
+//____________________________
+AliFemtoTPCInnerCorrFctn::AliFemtoTPCInnerCorrFctn(const AliFemtoTPCInnerCorrFctn& aCorrFctn) :
+  AliFemtoCorrFctn(),
+  fDTPCNumerator(0),
+  fDTPCDenominator(0),
+  fRadDNumerator(0),
+  fRadDDenominator(0),
+  fRadius(100)
+{
+  // copy constructor
+  if (aCorrFctn.fDTPCNumerator)
+    fDTPCNumerator = new TH2D(*aCorrFctn.fDTPCNumerator);
+  if (aCorrFctn.fDTPCDenominator)
+    fDTPCDenominator = new TH2D(*aCorrFctn.fDTPCDenominator);
+  if (aCorrFctn.fRadDNumerator)
+    fRadDNumerator = new TH2D(*aCorrFctn.fRadDNumerator);
+  if (aCorrFctn.fRadDDenominator)
+    fRadDDenominator = new TH2D(*aCorrFctn.fRadDDenominator);
+}
+//____________________________
+AliFemtoTPCInnerCorrFctn::~AliFemtoTPCInnerCorrFctn(){
+  // destructor
+  delete fDTPCNumerator;
+  delete fDTPCDenominator;
+  delete fRadDNumerator;
+  delete fRadDDenominator;
+}
+//_________________________
+AliFemtoTPCInnerCorrFctn& AliFemtoTPCInnerCorrFctn::operator=(const AliFemtoTPCInnerCorrFctn& aCorrFctn)
+{
+  // assignment operator
+  if (this == &aCorrFctn)
+    return *this;
+
+  if (aCorrFctn.fDTPCNumerator)
+    fDTPCNumerator = new TH2D(*aCorrFctn.fDTPCNumerator);
+  else
+    fDTPCNumerator = 0;
+  if (aCorrFctn.fDTPCDenominator)
+    fDTPCDenominator = new TH2D(*aCorrFctn.fDTPCDenominator);
+  else
+    fDTPCDenominator = 0;
+
+  if (aCorrFctn.fRadDNumerator)
+    fRadDNumerator = new TH2D(*aCorrFctn.fRadDNumerator);
+  else
+    fRadDNumerator = 0;
+  if (aCorrFctn.fRadDDenominator)
+    fRadDDenominator = new TH2D(*aCorrFctn.fRadDDenominator);
+  else
+    fRadDDenominator = 0;
+
+  fRadius = aCorrFctn.fRadius;
+
+  return *this;
+}
+//_________________________
+void AliFemtoTPCInnerCorrFctn::Finish(){
+  // here is where we should normalize, fit, etc...
+  // we should NOT Draw() the histos (as I had done it below),
+  // since we want to insulate ourselves from root at this level
+  // of the code.  Do it instead at root command line with browser.
+  //  mShareNumerator->Draw();
+  //mShareDenominator->Draw();
+  //mRatio->Draw();
+
+}
+
+//____________________________
+AliFemtoString AliFemtoTPCInnerCorrFctn::Report(){
+  // create report
+  string stemp = "Entrace TPC distance Correlation Function Report:\n";
+  char ctemp[100];
+  snprintf(ctemp , 100, "Number of entries in numerator:\t%E\n",fDTPCNumerator->GetEntries());
+  stemp += ctemp;
+  snprintf(ctemp , 100, "Number of entries in denominator:\t%E\n",fDTPCDenominator->GetEntries());
+  stemp += ctemp;
+  //  stemp += mCoulombWeight->Report();
+  AliFemtoString returnThis = stemp;
+  return returnThis;
+}
+//____________________________
+void AliFemtoTPCInnerCorrFctn::AddRealPair( AliFemtoPair* pair){
+  // add real (effect) pair
+  if (fPairCut)
+    if (!fPairCut->Pass(pair)) return;
+
+  double pih = TMath::Pi();
+  double pit = TMath::Pi()*2;
+
+  double tQinv = fabs(pair->QInv());   // note - qInv() will be negative for identical pairs...
+  double distx = pair->Track1()->Track()->NominalTpcEntrancePoint().x() - pair->Track2()->Track()->NominalTpcEntrancePoint().x();
+  double disty = pair->Track1()->Track()->NominalTpcEntrancePoint().y() - pair->Track2()->Track()->NominalTpcEntrancePoint().y();
+  double distz = pair->Track1()->Track()->NominalTpcEntrancePoint().z() - pair->Track2()->Track()->NominalTpcEntrancePoint().z();
+  double dist = sqrt(distx*distx + disty*disty + distz*distz);
+
+  fDTPCNumerator->Fill(tQinv, dist);
+
+  if (tQinv < 0.1) {
+    double phi1 = pair->Track1()->Track()->P().Phi();
+    double phi2 = pair->Track2()->Track()->P().Phi();
+    double chg1 = pair->Track1()->Track()->Charge();
+    double chg2 = pair->Track2()->Track()->Charge();
+    double ptv1 = pair->Track1()->Track()->Pt();
+    double ptv2 = pair->Track2()->Track()->Pt();
+    double eta1 = pair->Track1()->Track()->P().PseudoRapidity();
+    double eta2 = pair->Track2()->Track()->P().PseudoRapidity();
+    double arg1 = -0.3 * 0.5 * chg1 * fRadius/(2*ptv1);
+    double arg2 = -0.3 * 0.5 * chg2 * fRadius/(2*ptv2);
+    double phid = phi2 - phi1 + TMath::ASin(arg2) - TMath::ASin(arg1);
+
+    while (phid>pih) phid -= pit;
+    while (phid<-pih) phid += pit;
+    //    dist = phi2 - phi1 + TMath::ASin(-0.3 * 0.5 * chg2 * fRadius/(2*ptv2)) - TMath::ASin(-0.3 * 0.5 * chg1 * fRadius/(2*ptv1));
+    double etad = eta2 - eta1;
+    fRadDNumerator->Fill(phid, etad);
+  }
+}
+//____________________________
+void AliFemtoTPCInnerCorrFctn::AddMixedPair( AliFemtoPair* pair){
+  // add mixed (background) pair
+  if (fPairCut)
+    if (!fPairCut->Pass(pair)) return;
+
+  double pih = TMath::Pi();
+  double pit = TMath::Pi()*2;
+
+  double tQinv = fabs(pair->QInv());   // note - qInv() will be negative for identical pairs...
+  double distx = pair->Track1()->Track()->NominalTpcEntrancePoint().x() - pair->Track2()->Track()->NominalTpcEntrancePoint().x();
+  double disty = pair->Track1()->Track()->NominalTpcEntrancePoint().y() - pair->Track2()->Track()->NominalTpcEntrancePoint().y();
+  double distz = pair->Track1()->Track()->NominalTpcEntrancePoint().z() - pair->Track2()->Track()->NominalTpcEntrancePoint().z();
+  double dist = sqrt(distx*distx + disty*disty + distz*distz);
+
+  fDTPCDenominator->Fill(tQinv,dist);
+
+  if (tQinv < 0.1) {
+    double phi1 = pair->Track1()->Track()->P().Phi();
+    double phi2 = pair->Track2()->Track()->P().Phi();
+    double chg1 = pair->Track1()->Track()->Charge();
+    double chg2 = pair->Track2()->Track()->Charge();
+    double ptv1 = pair->Track1()->Track()->Pt();
+    double ptv2 = pair->Track2()->Track()->Pt();
+    double eta1 = pair->Track1()->Track()->P().PseudoRapidity();
+    double eta2 = pair->Track2()->Track()->P().PseudoRapidity();
+    double arg1 = -0.3 * 0.5 * chg1 * fRadius/(2*ptv1);
+    double arg2 = -0.3 * 0.5 * chg2 * fRadius/(2*ptv2);
+    double phid = phi2 - phi1 + TMath::ASin(arg2) - TMath::ASin(arg1);
+
+    while (phid>pih) phid -= pit;
+    while (phid<-pih) phid += pit;
+    //    dist = phi2 - phi1 + TMath::ASin(-0.3 * 0.5 * chg2 * fRadius/(2*ptv2)) - TMath::ASin(-0.3 * 0.5 * chg1 * fRadius/(2*ptv1));
+    double etad = eta2 - eta1;
+    fRadDDenominator->Fill(phid, etad);
+  }
+}
+
+
+void AliFemtoTPCInnerCorrFctn::WriteHistos()
+{
+  // Write out result histograms
+  fDTPCNumerator->Write();
+  fDTPCDenominator->Write();
+  fRadDNumerator->Write();
+  fRadDDenominator->Write();
+}
+//______________________________
+TList* AliFemtoTPCInnerCorrFctn::GetOutputList()
+{
+  // Prepare the list of objects to be written to the output
+  TList *tOutputList = new TList();
+
+  tOutputList->Add(fDTPCNumerator); 
+  tOutputList->Add(fDTPCDenominator);  
+  tOutputList->Add(fRadDNumerator); 
+  tOutputList->Add(fRadDDenominator);  
+
+  return tOutputList;
+}
+
+void AliFemtoTPCInnerCorrFctn::SetRadius(double rad)
+{
+  fRadius = rad;
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoTPCInnerCorrFctn.h b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoTPCInnerCorrFctn.h
new file mode 100644 (file)
index 0000000..b98f36d
--- /dev/null
@@ -0,0 +1,49 @@
+////////////////////////////////////////////////////////////////////////////////
+///                                                                          ///
+/// AliFemtoTPCInnerCorrFctn - A correlation function that saves the         ///
+/// distance at the entrance to the TPC between two tracks as a function     ///
+/// of qinv                                                                  ///
+/// Authors: Adam Kisiel kisiel@mps.ohio-state.edu                           ///
+///                                                                          ///
+////////////////////////////////////////////////////////////////////////////////
+
+#ifndef AliFemtoTPCInnerCorrFctn_hh
+#define AliFemtoTPCInnerCorrFctn_hh
+
+#include "TH1D.h"
+#include "TH2D.h"
+#include "AliFemtoCorrFctn.h"
+
+class AliFemtoTPCInnerCorrFctn : public AliFemtoCorrFctn {
+public:
+  AliFemtoTPCInnerCorrFctn(char* title, const int& nbins, const float& QinvLo, const float& QinvHi);
+  AliFemtoTPCInnerCorrFctn(const AliFemtoTPCInnerCorrFctn& aCorrFctn);
+  virtual ~AliFemtoTPCInnerCorrFctn();
+
+  AliFemtoTPCInnerCorrFctn& operator=(const AliFemtoTPCInnerCorrFctn& aCorrFctn);
+
+  virtual AliFemtoString Report();
+  virtual void AddRealPair(AliFemtoPair* aPair);
+  virtual void AddMixedPair(AliFemtoPair* aPair);
+  void SetRadius(double rad);
+
+  virtual void Finish();
+
+  void WriteHistos();
+  virtual TList* GetOutputList();
+private:
+  
+  TH2D *fDTPCNumerator;        // Distance at the entrance to the TPC for real pairs
+  TH2D *fDTPCDenominator;      // Distance at the entrance to tht TPC for mixed pairs
+  TH2D *fRadDNumerator;        // Distance at the radius for real pairs
+  TH2D *fRadDDenominator;      // Distance at the radius for mixed pairs
+  Double_t fRadius;            // Radius at which to calculate the distance
+
+#ifdef __ROOT__
+  ClassDef(AliFemtoTPCInnerCorrFctn, 1)
+#endif
+};
+
+
+#endif
+
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoYlm.cxx b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoYlm.cxx
new file mode 100644 (file)
index 0000000..a4cd836
--- /dev/null
@@ -0,0 +1,269 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoYlm - the class to calculate varous components of spherical        //
+//  harmonics                                                                 //
+//                                                                            //
+// Authors: Adam Kisiel kisiel@mps.ohio-state.edu                             //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+
+#include "AliFemtoYlm.h"
+#include <TMath.h>
+#include <iostream>
+
+double *AliFemtoYlm::fgPrefactors = 0x0;
+int    *AliFemtoYlm::fgPrefshift = 0x0;
+int    *AliFemtoYlm::fgPlmshift = 0x0;
+
+AliFemtoYlm::AliFemtoYlm() {
+  InitializeYlms();
+}
+
+AliFemtoYlm::~AliFemtoYlm() {}
+
+
+AliFemtoYlm::AliFemtoYlm(const AliFemtoYlm& aYlm){
+  fgPrefshift = aYlm.fgPrefshift;
+  InitializeYlms();
+}
+
+AliFemtoYlm& AliFemtoYlm::operator=(const AliFemtoYlm& aYlm){
+  if (this == &aYlm)
+    return *this;
+
+  InitializeYlms();
+
+  return *this;
+}
+
+std::complex<double> AliFemtoYlm::Ceiphi(double phi){
+  return std::complex<double>(cos(phi),sin(phi));
+}
+
+double AliFemtoYlm::Legendre(int ell, int em, double ctheta){
+  // Calculate a single Legendre value
+  // *** Warning - NOT optimal - calculated all Plms up to L !!!
+  double lbuf[36];
+  AliFemtoYlm::LegendreUpToYlm(ell, ctheta, lbuf);
+
+  return lbuf[fgPlmshift[ell]-abs(em)];
+}
+
+std::complex<double> AliFemtoYlm::Ylm(int ell,int m,double theta,double phi){
+  // Calculate Ylm spherical input
+  double ctheta;
+  std::complex<double> answer;
+  std::complex<double> ci(0.0,1.0);
+  ctheta=cos(theta);
+  answer = (fgPrefactors[fgPrefshift[ell]+m]*Legendre(ell,m,ctheta))*Ceiphi(m*phi);
+
+  return answer;
+}
+
+std::complex<double> AliFemtoYlm::Ylm(int ell, int m, double x, double y, double z){
+  // Calculate Ylm cartesian input
+  std::complex<double> answer; 
+  double ctheta,phi;
+  double r = sqrt(x*x+y*y+z*z);
+  if ( r < 1e-10 || fabs(z) < 1e-10 ) ctheta = 0.0;
+  else ctheta=z/r;
+  phi=atan2(y,x);
+  answer = (fgPrefactors[fgPrefshift[ell]+m]*Legendre(ell,m,ctheta))*Ceiphi(m*phi);
+
+  return answer;       
+}
+
+double AliFemtoYlm::ReYlm(int ell, int m, double theta, double phi){
+       return real(AliFemtoYlm::Ylm(ell,m,theta,phi));
+}
+
+double AliFemtoYlm::ImYlm(int ell, int m, double theta, double phi){
+       return imag(AliFemtoYlm::Ylm(ell,m,theta,phi));
+}
+
+double AliFemtoYlm::ReYlm(int ell, int m, double x,double y,double z){
+       return real(AliFemtoYlm::Ylm(ell,m,x,y,z));
+}
+
+double AliFemtoYlm::ImYlm(int ell, int m, double x,double y,double z){
+       return imag(AliFemtoYlm::Ylm(ell,m,x,y,z));
+}
+
+void AliFemtoYlm::InitializeYlms()
+{
+  // Calculate prefactors for fast Ylm calculation
+
+  double oneoversqrtpi = 1.0/TMath::Sqrt(TMath::Pi());
+
+  fgPrefactors = (double *) malloc(sizeof(double) * 36);
+  fgPrefshift  = (int *) malloc(sizeof(int) * 6);
+  fgPlmshift   = (int *) malloc(sizeof(int) * 6);
+
+  // l=0 prefactors
+  fgPrefactors[0] = 0.5*oneoversqrtpi;
+
+  // l=1 prefactors
+  fgPrefactors[1] = 0.5*sqrt(3.0/2.0)*oneoversqrtpi;
+  fgPrefactors[2] = 0.5*sqrt(3.0)*oneoversqrtpi;
+  fgPrefactors[3] = -fgPrefactors[1];
+
+  // l=2 prefactors
+  fgPrefactors[4] = 0.25*sqrt(15.0/2.0)*oneoversqrtpi;
+  fgPrefactors[5] = 0.5*sqrt(15.0/2.0)*oneoversqrtpi;
+  fgPrefactors[6] = 0.25*sqrt(5.0)*oneoversqrtpi;
+  fgPrefactors[7] = -fgPrefactors[5];
+  fgPrefactors[8] = fgPrefactors[4];
+
+  // l=3 prefactors
+  fgPrefactors[9]  = 0.125*sqrt(35.0)*oneoversqrtpi;
+  fgPrefactors[10] = 0.25*sqrt(105.0/2.0)*oneoversqrtpi;
+  fgPrefactors[11] = 0.125*sqrt(21.0)*oneoversqrtpi;
+  fgPrefactors[12] = 0.25*sqrt(7.0)*oneoversqrtpi;
+  fgPrefactors[13] = -fgPrefactors[11];
+  fgPrefactors[14] = fgPrefactors[10];
+  fgPrefactors[15] = -fgPrefactors[9];
+
+  // l=4 prefactors
+  fgPrefactors[16] = 3.0/16.0*sqrt(35.0/2.0)*oneoversqrtpi;
+  fgPrefactors[17] = 3.0/8.0*sqrt(35.0)*oneoversqrtpi;
+  fgPrefactors[18] = 3.0/8.0*sqrt(5.0/2.0)*oneoversqrtpi;
+  fgPrefactors[19] = 3.0/8.0*sqrt(5.0)*oneoversqrtpi;
+  fgPrefactors[20] = 3.0/16.0*oneoversqrtpi;
+  fgPrefactors[21] = -fgPrefactors[19];
+  fgPrefactors[22] = fgPrefactors[18];
+  fgPrefactors[23] = -fgPrefactors[17];
+  fgPrefactors[24] = fgPrefactors[16];
+
+  // l=5 prefactors
+  fgPrefactors[25] = 3.0/32.0*sqrt(77.0)*oneoversqrtpi;
+  fgPrefactors[26] = 3.0/16.0*sqrt(385.0/2.0)*oneoversqrtpi;
+  fgPrefactors[27] = 1.0/32.0*sqrt(385.0)*oneoversqrtpi;
+  fgPrefactors[28] = 1.0/8.0*sqrt(1155.0/2.0)*oneoversqrtpi;
+  fgPrefactors[29] = 1.0/16.0*sqrt(165.0/2.0)*oneoversqrtpi;
+  fgPrefactors[30] = 1.0/16.0*sqrt(11.0)*oneoversqrtpi;
+  fgPrefactors[31] = -fgPrefactors[29];
+  fgPrefactors[32] = fgPrefactors[28];
+  fgPrefactors[33] = -fgPrefactors[27];
+  fgPrefactors[34] = fgPrefactors[26];
+  fgPrefactors[35] = -fgPrefactors[25];
+
+  fgPrefshift[0] = 0;
+  fgPrefshift[1] = 2;
+  fgPrefshift[2] = 6;
+  fgPrefshift[3] = 12;
+  fgPrefshift[4] = 20;
+  fgPrefshift[5] = 30;
+
+  fgPlmshift[0] = 0;
+  fgPlmshift[1] = 2;
+  fgPlmshift[2] = 5;
+  fgPlmshift[3] = 9;
+  fgPlmshift[4] = 14;
+  fgPlmshift[5] = 20;
+}
+
+void AliFemtoYlm::LegendreUpToYlm(int lmax, double ctheta, double *lbuf)
+{
+  // Calculate a set of legendre polynomials up to a given l
+  // with spherical input
+  double sins[6];
+  double coss[6];
+  sins[0] = 0.0;
+  coss[0] = 1.0;
+  sins[1] = sqrt(1-ctheta*ctheta);
+  coss[1] = ctheta;
+  for (int iter=2; iter<6; iter++) {
+    sins[iter] = sins[iter-1]*sins[1];
+    coss[iter] = coss[iter-1]*coss[1];
+  }
+
+  // Legendre polynomials l=0
+  lbuf[0] = 1.0;
+
+  // Legendre polynomials l=1
+  if (lmax>0) {
+    lbuf[1] = sins[1];
+    lbuf[2] = coss[1];
+  }
+
+  // Legendre polynomials l=2
+  if (lmax>1) {
+    lbuf[3] = sins[2];
+    lbuf[4] = sins[1]*coss[1];
+    lbuf[5] = 3*coss[2]-1;
+  }
+
+  // Legendre polynomials l=3
+  if (lmax>2) {
+    lbuf[6] = sins[3];
+    lbuf[7] = sins[2]*coss[1];
+    lbuf[8] = (5*coss[2]-1)*sins[1];
+    lbuf[9] = 5*coss[3]-3*coss[1];
+  }
+
+  // Legendre polynomials l=4
+  if (lmax>3) {
+    lbuf[10] = sins[4];
+    lbuf[11] = sins[3]*coss[1];
+    lbuf[12] = (7*coss[2]-1)*sins[2];
+    lbuf[13] = (7*coss[3]-3*coss[1])*sins[1];
+    lbuf[14] = 35*coss[4]-30*coss[2]+3;
+  }
+
+  // Legendre polynomials l=5
+  if (lmax>4) {
+    lbuf[15] = sins[5];
+    lbuf[16] = sins[4]*coss[1];
+    lbuf[17] = (9*coss[2]-1)*sins[3];
+    lbuf[18] = (3*coss[3]-1*coss[1])*sins[2];
+    lbuf[19] = (21*coss[4]-14*coss[2]+1)*sins[1];
+    lbuf[20] = 63*coss[5]-70*coss[3]+15*coss[1];
+  }
+}
+
+void AliFemtoYlm::YlmUpToL(int lmax, double x, double y, double z, std::complex<double> *ylms)
+{
+  // Calculate a set of Ylms up to a given l
+  // with cartesian input
+  double ctheta,phi;
+
+  double r = sqrt(x*x+y*y+z*z);
+  if ( r < 1e-10 || fabs(z) < 1e-10 ) ctheta = 0.0;
+  else ctheta=z/r;
+  phi=atan2(y,x);
+  
+  YlmUpToL(lmax, ctheta, phi, ylms);
+
+}
+
+void AliFemtoYlm::YlmUpToL(int lmax, double ctheta, double phi, std::complex<double> *ylms)
+{
+  // Calculate a set of Ylms up to a given l
+  // with spherical input
+  int lcur = 0;  
+  double lpol;
+  
+  double coss[6];
+  double sins[6];
+
+  double lbuf[36];
+  LegendreUpToYlm(lmax, ctheta, lbuf);
+
+  for (int iter=1; iter<=lmax; iter++) {
+    coss[iter-1] = cos(iter*phi);
+    sins[iter-1] = sin(iter*phi);
+  }
+  ylms[lcur++] = fgPrefactors[0]*lbuf[0] * std::complex<double>(1,0);
+  
+  for (int il = 1; il<=lmax; il++) {
+    // First im = 0
+    ylms[lcur+il] = fgPrefactors[fgPrefshift[il]]*lbuf[fgPlmshift[il]]*std::complex<double>(1.0,0.0);
+    // Im != 0
+    for (int im=1; im<=il; im++) {
+      lpol = lbuf[fgPlmshift[il]-im];
+      ylms[lcur+il-im] = fgPrefactors[fgPrefshift[il]-im]*lpol*std::complex<double>(coss[im-1],-sins[im-1]);
+      ylms[lcur+il+im] = fgPrefactors[fgPrefshift[il]+im]*lpol*std::complex<double>(coss[im-1],sins[im-1]);
+    }
+    lcur += 2*il + 1;
+  }
+}
diff --git a/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoYlm.h b/PWGCF/FEMTOSCOPY/AliFemtoUser/AliFemtoYlm.h
new file mode 100644 (file)
index 0000000..888a54b
--- /dev/null
@@ -0,0 +1,49 @@
+////////////////////////////////////////////////////////////////////////////////
+//                                                                            //
+// AliFemtoYlm - the class to calculate varous components of spherical        //
+//  harmonics                                                                 //
+//                                                                            //
+// Authors: Adam Kisiel kisiel@mps.ohio-state.edu                             //
+//                                                                            //
+////////////////////////////////////////////////////////////////////////////////
+
+#ifndef ALIFEMTOYLM_H
+#define ALIFEMTOYLM_H
+#include <cstdlib>
+#include <cmath>
+#include <complex>
+#include <TMath.h>
+
+class AliFemtoYlm {
+ public:
+  AliFemtoYlm();
+  ~AliFemtoYlm();
+
+  AliFemtoYlm(const AliFemtoYlm& aYlm);
+  AliFemtoYlm& operator=(const AliFemtoYlm& aYlm);
+
+  static double Legendre(int ell, int emm, double ctheta);
+  static void   LegendreUpToYlm(int lmax, double ctheta, double *lbuf);
+
+  static std::complex<double> Ylm(int ell,int m,double theta,double phi);
+  static std::complex<double> Ylm(int ell, int m, double x, double y, double z);
+
+  static void YlmUpToL(int lmax, double x, double y, double z, std::complex<double> *ylms);
+  static void YlmUpToL(int lmax, double ctheta, double phi, std::complex<double> *ylms);
+
+  static double ReYlm(int ell, int m, double theta, double phi);
+  static double ReYlm(int ell, int m, double x, double y, double z);
+  static double ImYlm(int ell, int m, double theta, double phi);
+  static double ImYlm(int ell, int m, double x, double y, double z);
+
+  static void InitializeYlms();
+  
+ private:
+  static std::complex<double> Ceiphi(double phi);
+
+  static double *fgPrefactors;
+  static int    *fgPrefshift;
+  static int    *fgPlmshift;
+};
+
+#endif
diff --git a/PWGCF/FEMTOSCOPY/Documentation/AliFemto.pdf b/PWGCF/FEMTOSCOPY/Documentation/AliFemto.pdf
new file mode 100644 (file)
index 0000000..7bf9211
Binary files /dev/null and b/PWGCF/FEMTOSCOPY/Documentation/AliFemto.pdf differ
diff --git a/PWGCF/FEMTOSCOPY/Documentation/AliFemto.tex b/PWGCF/FEMTOSCOPY/Documentation/AliFemto.tex
new file mode 100755 (executable)
index 0000000..c271dfc
--- /dev/null
@@ -0,0 +1,811 @@
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+%
+% AliFemto Documentation - User Guide and Reference Manual -- LaTeX source
+%  ALICE Experiment Femtoscopic Analysis framework
+%  Mike Lisa 17 May 2006
+% [Based on similar document for StHbt (STAR framework), Mike Lisa 22 May 2006]
+%
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+\documentclass[twoside]{article}
+
+\newcommand {\DocumentVersionNumber} {1.1}  %%% this is the Version Number
+
+
+\usepackage{natbib}
+
+
+%\usepackage[T1]{fontenc}
+%\renewcommand*\ttdefault{txtt}
+%\renewcommand*\familydefault{\ttdefault}
+
+
+
+\parindent 0pt
+\parskip 6pt
+\advance\textwidth by 80pt%
+\advance\evensidemargin by -80pt%
+
+%\renewcommand{\familydefault}{cmss}
+
+\usepackage{epsfig}
+%%%%%%\usepackage{pdffig}
+
+
+\usepackage{graphicx}
+\usepackage{psboxit}
+\usepackage{color}
+\usepackage{amsmath}
+\usepackage{amssymb}
+\usepackage{fancyhdr}
+\usepackage{times}
+\usepackage{verbatim}
+\usepackage{makeidx}
+\usepackage{subfigure}
+%%%\usepackage[dvips=true,hyperindex=true,colorlinks=true,linkcolor=blue,bookmarks=true]{hyperref}
+\usepackage[hyperindex=true,colorlinks=true,linkcolor=blue,bookmarks=true]{hyperref}
+
+\PScommands      % init boxit
+\makeindex
+
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+%
+% Define header and footer style
+%
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+\pagestyle{fancyplain}
+\rhead[\fancyplain{}{\bfseries\leftmark}]
+      {\fancyplain{}{\bfseries\rightmark}}
+\lhead[\fancyplain{}{\bfseries\rightmark}]
+      {\fancyplain{}{\bfseries\leftmark}}
+\rfoot[{}]{\fancyplain{}{\bfseries\thepage}}
+\lfoot[\fancyplain{}{\bfseries\thepage}]{}
+\cfoot{}
+
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+%
+% Typographic Conventions
+%
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+\newcommand{\name}[1]{\textsf{#1}}%  or class-, function-, package names
+\newcommand{\comp}[1]{\texttt{#1}}%  computer font
+\newcommand{\args}[1]{\textit{#1}}%   command arguments
+\newcommand{\meth}[1]{\textsf{#1}}%  class methods
+%%%
+%%% font for package names
+%%%
+\newcommand{\AliEn}{{\tt AliEn }}
+\newcommand{\AliFemto}{{\tt AliFemto }}
+\newcommand{\AliRoot}{{\tt AliRoot }}
+\newcommand{\ROOT}{{\tt ROOT }}
+\newcommand{\StHbt}{{\tt StHbt }}
+\newcommand{\cvs}{{\tt StHbt }}
+
+
+%% removed a bunch of unused (?) \newcommand statements
+
+
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+%
+% Define multiline labels for class reference
+%
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+\newcommand{\entrylabel}[1]{\mbox{\textbf{{#1}}}\hfil}%
+\newenvironment{entry}
+{\begin{list}{}%
+    {\renewcommand{\makelabel}{\entrylabel}%
+     \setlength{\labelwidth}{90pt}%
+     \setlength{\leftmargin}{\labelwidth}
+     \advance\leftmargin by \labelsep%
+      }%
+    }%
+  {\end{list}}
+
+\newcommand{\Entrylabel}[1]%
+{\raisebox{0pt}[1ex][0pt]{\makebox[\labelwidth][l]%
+    {\parbox[t]{\labelwidth}{\hspace{0pt}\textbf{{#1}}}}}}
+\newenvironment{Entry}%
+{\renewcommand{\entrylabel}{\Entrylabel}\begin{entry}}%
+  {\end{entry}}
+
+
+
+%%%
+%%% font for AliFemto class/method/attribute names
+%%% ---- at some point, let's find some nice font...
+%%% 
+\newcommand{\acf}[1]{{\tt \bf #1}}
+
+\begin{document}
+
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+%
+%    Title page
+%
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+\begin{titlepage}
+\pagestyle{empty}
+\vspace*{-35mm}
+\begin{center}
+  {\Large\bf AliFemto - A Femtoscopic Analysis Framework for ALICE}
+  \hfill\mbox{}\\[4.5cm]
+\mbox{\includegraphics[width=\textwidth]{AliFemtoTitle.pdf}}
+  \hfill\mbox{}\\[8cm]
+  {\LARGE User Guide and Reference Manual}\\[2cm]
+  {\LARGE Revision \DocumentVersionNumber}  \\[5mm] 
+  {\LARGE \today}  % replaced by cvs with current revision  
+  \vfill
+\end{center}
+\cleardoublepage
+\end{titlepage}
+\pagenumbering{roman}
+
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+%
+%    Table of contents
+%
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+\tableofcontents
+%\cleardoublepage
+\clearpage
+
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+%
+%    User Guide
+%
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+\pagenumbering{arabic}
+
+
+\setcounter{section}{-1}
+\section{About this document}
+
+This is the Users' Guide and Reference Manual for the \AliFemto software package,
+for use in the ALICE experiment at the Large Hadron Collider.
+The femtoscopy analysis effort in ALICE is in the Physics Working Group 2.  Thus,
+the software described here may be found in the {\tt PWG2/FEMTOSCOPY } area when
+\AliRoot is checked out.
+
+The files (.tex, .pdf, etc.) for this documentation are cvs-controlled along with
+the \AliFemto code in the ALICE repository under the {\tt PWG2/FEMTOSCOPY/Documentation } area.
+While earth-moving changes in the framework are not anticipated, this manuscript will be to some
+extent a ``living document.''  The reposisory version of the documentation
+should be considered the ``official'' source of information on the package at any given time.
+
+This document consists of two parts.  The Users' Guide introduces the package and, perhaps most
+interestingly to the reader, provides a blow-by-blow example of its use.  The Reference Manual
+is essentially a listing and short description of the classes and the limited inheritance
+scheme.
+
+\AliFemto will often be run in a larger framework than a simple \ROOT or \AliRoot session, e.g.
+\AliEn and the Task-Train framework in ALICE.  This manual focusses only on \AliFemto itself.
+For tutorials on how to run \AliFemto within these contexts, see
+the ALICE femtoscopy web pages\\
+ {\tt http://aliceinfo.cern.ch/Collaboration/PhysicsWorkingGroups/PWG2/Femtoscopy/}.
+
+
+
+
+\clearpage
+
+\part{Users' Guide}
+\clearpage
+
+
+\section{Introduction - Basics and Motivation}
+
+
+Femtoscopy-- the measurement of the space-time structure of dynamic systems at the fermi scale--
+is an integral tool in studies in high-energy particle (e.g. p+p) and heavy ion (e.g. Pb+Pb)
+collisions.  It can also be a non-trivial, somewhat subtle tool, with nonobvious experimental
+``traps'' which are periodically redisovered as expertise evaporates and algorithms are lost.
+
+Especially in large modern high energy experimental collaborations, complex experimental
+issues impact on this already-delicate tool.  Furthermore, by the nature of such collaborations,
+``Physics Working Groups'' (PWGs) are commonly formed, in which several collaborators work on
+similar physics topics (e.g. femtoscopy) which share common techniques and problems.  Sharing
+of experience and
+solutions among PWG members is invaluable to work through problems quickly and to assure quality
+and consistency in physics results.  In addition to regular discussions by phone/vrvs/email, sharing
+a common software analysis infrastructure allows for rapid and collaborative development, testing
+and sharing of solutions.  Production of quality physics results in a timely manner demands the
+use of all available collaborative tools; while cross-checks are always crucial to an analysis,
+re-creating the many aspects of a wheel is sometimes a (all-too-common) waste of valuable manpower.
+
+Just as code-sharing {\it within} a collaboration or PWG is desirable when analysis techniques
+are similar, code-sharing {\it between} collaborations or PWGs may be equally beneficial, if the
+similarities are sufficiently great.  Code reusability is often claimed as one of the most important
+benefits of well-designed object-oriented programming.  Through the development of standardized tools
+and inheritance schemes, high-energy physics has largely moved away from perpetual re-implementation
+of established algorithms.  
+Previously, the student who needed a particular ``twist'' to, say a resonance-finding technique,
+would often find it easiest to start from scratch in a self-contained Fortran code.  This was due
+to the fact that the {\it previous} student's Fortran code lacked extensibility; e.g. interfaces
+and common blocks were specialized for a particular, narrow purpose.  With care, languages such as
+C++ provide a natural solution.  The student can focus on {\it new} aspects of her problem (the purpose,
+after all, of research) and the science behind it.  The {\it same} objects and elements of the {\it same} 
+code, developed and refined by others, are at her disposal; likewise, she will make her own contributions
+and everybody benefits.
+Likewise, so long as the detector and reconstruction configurations of two experiments 
+are sufficiently similar, both collaborations may benefit by sharing some code.
+
+This document discusses a two-particle correlation software package for use in the ALICE experiment
+at the LHC.  It is based largely on the framework (StHbt) used since 1999 in the STAR experiment at
+RHIC, an experiment remarkably similar to ALICE in all respects.  StHbt, itself, was developed by
+femtoscopy experts from earlier heavy ion experiments at the AGS and SPS; as such, it distills the
+generic features of any heavy ion femtoscopic analysis.  The femtoscopy group in ALICE is arguably
+the most complete collection of the world's experts in this sub-field ever assembled.  It is hoped
+that this common analysis software will enable a maximum positive superposition of the experience
+of these experts.
+
+
+\subsection{Femtoscopy, HBT, and heavy ions}
+
+The feature distinguishing heavy ion from particle physics is the dominance of space-time
+geometry.  
+This is manifest in the fact that we seek the geometrically-largest systems in order to approximate
+the infinite system in which thermodynamic variables and phases of matter become meaningful.
+At all stages of the the dynamic system's evolution, geometry rules.
+The geometric overlap anisotropy of the entrance channel is known to dominate the subsequent
+evolution of the bulk, and focusing systematics of geometric entrance-channel quantities
+(e.g. reaction-plane, impact parameter) yields much more information than geometric averages
+over these quantities.  In the intermediate stage of the collision, path-lengh considerations
+are crucial to determine the physics of so-called ``jet quenching'' at the highest energies.
+Further, we seek a system in which coloured degrees of freedom
+are relevant over ``large'' length scales.  Much of the dynamic bulk physics is reflected in the
+end freeze-out stage in collective observables (e.g. flow) which are usually defined in terms
+of space-momentum correlations.
+Clearly, geometry is a key defining feature of our field; momentum space alone is less than
+half the story.
+
+However, particle momentum is precisely what we measure.  Geometrical information must be
+inferred.  The most direct and common method of doing so is through femtoscopy, the use of
+two-particle momentum-space correlations to probe fermi-scale emission zones.  Experimental
+and theoretical aspects of femtoscopy are discussed at length
+elsewhere~\citep[][and references within]{Lisa:2005dd}.  Without becoming mathematical, the
+main point is to measure the increase (or decrease) of the likelihood of measuring a particle
+with a particular momentum, given the presence of another particle; in other words, the effect
+on the conditional probability.  The effect to be measured is driven by the two-particle wavefunction, which
+depends on relative momentum (measured) and relative position (inferred).  The probability $A$
+as a function of a measured relative quantity (typically relative momentum 
+${\bf q}$, so $A \sim dN/d{\bf q}$) is usually dominated by detector acceptance and single-particle
+phasespace; the modification due to two-particle effects represent only a small perturbation.
+Thus, some sort of comparison to a reference distribution $B({\bf q})$ is usually performed.
+Ideally, $B$ contains all single- and two-particle acceptance and efficiency effects and lacks
+only the sought-for correlation.  The distribution $B$ is often generated by so-called ``mixed-event''
+techniques, and the correlation function $C$, ideally containing only 2-particle
+correlations due to the relative wavefunction, given by
+\begin{equation}
+\label{eq:usualC}
+C({\bf q})=\frac{A({\bf q})}{B({\bf q})}
+\end{equation}
+It should be stressed, however, that neither using ${\bf q}={\bf p_1}-{\bf p_2}$ as a two-particle
+variable, generating histrograms/distributions $A$ or $B$, nor taking any ratio $C$ must be associated
+with a correlation analysis, in general.  See Section~\ref{sec:bones} below.
+
+Briefly, some terminology which the reader may encounter.  Two-particle femtoscopic measurements
+are related to the pioneering work of Hanbury-Brown and Twiss over half a century ago, to measure
+the angular size of stars~\cite{HanburyBrown:1954}.  (The relationship, however, is somewhat more
+oblique than often realized.)  Thus, similar analyses in high-energy physics
+are often referred to as ``HBT'' studies.  For reference,
+the first actual application to high-energy physics was performed by Goldhaber, Goldhaber,
+Lee and Pais~\cite{Goldhaber:1960sf} shortly thereafter; thus correlations for pions reflect
+the ``GGLP effect.''  The rubrik of femtoscopy~\cite{Lednicky:2002fq} is nowadays
+used in general.
+
+
+
+
+\subsection{The bones of a femtoscopic analysis}
+\label{sec:bones}
+Similar algorithmic requirements and characteristics appear in a wide range of femtoscopic (and non-femtoscopic)
+analyses.  AliFemto was designed as a common analysis framework for collaborators conducting diverse
+analyses sharing nevertheless a large overlap of techniques.
+
+The design was driven by asking two questions: ``What {\it is} a femtoscopy-style analysis, in general?'' and
+``What sorts of actions will be common to most analyses and what sorts will be person-specific?''  
+
+The first question may be answered with the following rough procedure.  Names of class types inside square brackets []
+are discussed in Sections~\ref{sec:AliFemtoDiagramEtc} and~\ref{sec:coreUser}.
+
+\begin{enumerate}
+\item\label{it:read}  Obtain an event (usually, data associated with one collision) from somewhere. [\name{AliFemtoEventReader}]
+\item\label{it:write} (Optional) Write the event (or portions thereof) to a file,                       [\name{AliFemtoEventReader}]\\
+                      The output file does not neccessarily use the same format as the input.
+\item\label{it:EvCut} Decide to use or discard (``cut on'') the event in the analysis.               [\name{AliFemtoEventCut}]
+\item\label{it:TrCut} Select (``cut on'') the particles of interest.                                 [\name{AliFemtoParticleCut}]
+\item\label{it:Reals} Form pairs of particles coming from the present event.                         [\name{AliFemtoAnalysis}]
+\item\label{it:PrCut} Cut on these pairs.                                                            [\name{AliFemtoPairCut}]
+\item\label{it:Num}   Do ``something'' with these pairs.                                             [\name{AliFemtoCorrFctn}]\\
+                      {\it Usually}, but not neccessarily, this involves calculation of some relative
+                      variable (e.g. a relative momentum) and incrementing a histogram.
+%%\item\label{it:Num}   Send pairs passing the PairCut to the several CorrFctns for further processing. 
+\item\label{it:Mix}   {\it Usually,} form other pairs of particles to construct a reference pair     
+                      distribution.                                                                  [\name{AliFemtoAnalysis}]\\
+                      {\it Usually} this is related to generating pairs (``mixed'' pairs) of
+                      particles between the present event and similar events which are sitting in 
+                      the EventBuffer.
+\item\label{it:PrCut2} Cut on these pairs.                                                           [\name{AliFemtoPairCut}]\\
+                      {\it Almost always}, it is an identical cut as used in step~\ref{it:PrCut}.
+\item\label{it:Den}   Do ``something'' with these pairs.                                             [\name{AliFemtoCorrFctn}]\\
+                      {\it Usually}, but not neccessarily, this involves calculation of some relative
+                      variable (usually the same one as in step~\ref{it:Num}) and incrementing a histogram.
+\item\label{it:Store} Store the present event into the EventBuffer.                                  [\name{AliFemtoAnalysis}]
+\item\label{it:loop}  Return to step~\ref{it:read} for the next event.                               [\name{AliFemtoManager}]
+\end{enumerate}
+
+The first question is thus addressed by implementing the above basic functionality in methods of common classes.
+Considerations about the second question are reflected in the class inheritance structure and division of classes
+into ``central'' and User classes.  We discuss this below.
+
+\section{The Structure and use of \AliFemto}
+\label{sec:AliFemtoDiagramEtc}
+
+\AliFemto is a flexible and extendable software package in the \ROOT framework for performing two-particle
+femtoscopic studies.  The basic design and structure of the package is essentially unchanged since its
+original deployment in the STAR Experiment at RHIC in 1999.  However, its functionality and features
+have been developed considerably by continuous use in experimental and model analyses by the STAR-HBT
+group since then.  The  package was designed from the beginning to be independent of the STAR analysis framework
+(root4star).  Thus, it is easily used for ALICE-specific analyses (either in \AliRoot or ``vanilla'' \ROOT)
+or for model studies in any root flavor.
+
+{\bf Important note:}
+In this Section, we discuss the structure of the code, and a specific example of how to use it in ``vanilla'' or pure \AliRoot
+mode.  In other words, here we run with a simple \ROOT macro.  If we run instead in the ALICE {\tt task} framework, then the
+operations described here are performed by the {\tt AliFemtoTask}, rather than the user directly.  Translation between these
+modes of operation is transparent.  For tutorials on how to run \AliFemto within the {\tt task} framework, \AliEn, etc, see
+the ALICE femtoscopy web pages\\
+ {\tt http://aliceinfo.cern.ch/Collaboration/PhysicsWorkingGroups/PWG2/Femtoscopy/}.
+
+
+\subsection{Top level}
+\label{sec:topLevel}
+The top-level structure of AliFemto is shown in Figure~\ref{fig:TopLevelUML} in simplified Unified Modeling Language (UML)~\cite{UMLreference} format.
+Here, we describe generally the classes shown, and their interaction.  See the Reference Manual for details.
+
+\begin{figure}[t]
+\includegraphics[width=\textwidth]{TopLevelUML.pdf}
+\caption{The large-view structure of the code.  
+Yellow classes at the periphery are bases for user-written
+classes.\label{fig:TopLevelUML}
+}
+\end{figure}
+
+
+\subsubsection{AliFemtoManager}
+
+There is a single \name{AliFemtoManager} object for any \AliFemto session.
+\name{AliFemtoManager} controls all \AliFemto actions; it is this (through
+the four methods \meth{Init()}, \meth{ProcessEvent()}, \meth{Report()}, and \meth{Finish()}) with which the user 
+interfaces.
+There is only one AliFemtoManager, instantiated by the user (or the {\tt AliFemtoTask}-- see beginning of
+Section~\ref{sec:AliFemtoDiagramEtc}), and objects are ``plugged into'' it by the user at runtime;
+see Section~\ref{sec:example} for an example.
+
+In order to proceed with an \AliFemto study, the \name{AliFemtoManager} must have an \name{AliFemtoEventReader}, which passes event information
+to it.  Optionally, the \name{AliFemtoManager} may also have one or more {\it other} \name{AliFemtoEventReader}
+objects, which are in ``Write'' mode and
+which takes the event data and writes it to a fiile.  This is useful in order to change data format or to write out only a selection
+of the events or information within events.  Also optionally (but usually the case), the \name{AliFemtoManager} will have one or more
+\name{AliFemtoAnalysis}
+objects; it is these which perform correlation studies.  In principle, the \name{AliFemtoManager} may have neither Writers or Analyses, but
+in this case nothing gets done with the data.
+
+\subsubsection{AliFemtoEventReader}
+\label{sec:AliFemtoEventReader}
+
+Typical users will not need to write \name{AliFemtoEventReader}s, but will instead use a standard one.  We discuss its basics here
+just for reference.
+
+
+The job of the \name{AliFemtoEventReader} is to pass events, upon request, to the \name{AliFemtoManager}.  
+How the events are obtained (reading from
+a data or simulation file, reading from some location in memory filled by someone else, random generation within the \name{AliFemtoReader} itself...) is
+immaterial.  Regardless
+of the data format read in by the \name{AliFemtoReader}, the data is passed to the \name{AliFemtoManager} in the form of an \name{AliFemtoEvent}.  
+(See the Reference Manual for full details on the content and structure of \name{AliFemtoEvent}.)
+In this way, all
+of \AliFemto code is unaware of external data sources or formats; all such dependency is confined to the \name{AliFemtoEventReader}-derived classes.
+
+
+\name{AliFemtoEventReader} is, itself, a base class, with a pure virtual method \meth{ReturnHbtEvent()}.  For any given application/datasource (e.g.
+ALICE ESDs, Geant kine banks, RQMD files), a class must be written which inherits from AliFemtoEventReader.
+In the simillar STAR package, of order 10 specific Reader classes
+are available for use now; they will be developed for ALICE as needed. 
+It is expected that the typical user will not need to write his own \name{AliFemtoEventReader} class, but simply select one already written.
+It is one of these derived classes which is ``plugged into'' the \name{AliFemtoManager}.  Once the user instantiates and configures
+the Reader, she typically does not interact with it anymore.  A specific example is given in Section~\ref{sec:example}
+
+
+
+\subsubsection{AliFemtoAnalysis}
+\label{sec:AliFemtoAnalysis}
+
+Typical users will not need to write \name{AliFemtoAnalysis} objects, but will instead select among standard ones.  We discuss the basics here
+just for reference.
+
+
+The most important element of an \AliFemto study is the Analysis.  All Analysis classes derive from the interface class
+\name{AliFemtoAnalysis}, which has three important pure virtual methods.  
+They must implement (even if it is a ``do-nothing'' method) a \meth{Finish()} method, which will be invoked by
+the \name{AliFemtoManager} just before the session ends.  Also, each \{name{AliFemtoAnalysis} class must generate 
+a \meth{Report()} (c.f. Section~\ref{sec:reports}).
+
+
+Finally and most importantly, an \name{AliFemtoAnalysis} class must be able to \meth{Process()}
+an \name{AliFemtoEvent}.  What it does with the \name{AliFemtoEvent}, even if it simply ignores it, is 
+of course not important to the \name{AliFemtoManager}.
+In practice, naturally, an Analysis {\it does} process the data, making cuts and extracting correlations.
+The simplest \name{AliFemtoAnalysis}-derived class, \name{AliFemtoSimpleAnalysis}, is a good example of this.  We discuss this in
+Section~\ref{sec:analysisLevel}.
+
+\subsubsection{Action flow}
+Briefly, each time \name{AliFemtoManager}::\meth{ProcessEvent()} is invoked by the user (or Task, or whatever),
+it obtains an \name{AliFemtoEvent} from its \name{AliFemtoEventReader}. 
+It then passes this \name{AliFemtoEvent} to each of its Writers through the \meth{WriteHbtEvent()} method.
+Finally, it passes the \name{AliFemtoEvent} to each of its {\name AliFemtoAnalysis::}{\meth ProcessEvent({\args AliFemtoEvent*})}.
+
+
+
+\subsection{Analysis level}
+\label{sec:analysisLevel}
+
+The \name{AliFemtoAnalysis} is usually the focus of any \AliFemto session.  As discussed in Section~\ref{sec:AliFemtoAnalysis},
+the only requirement of such an object in principle is that it must accept an \name{AliFemtoEvent} object via its \meth{ProcessEvent} method.
+However, in practice, \name{AliFemtoAnalysis}-derived classes almost always contain Cuts, CorrFctns, etc.  We describe these
+here.
+
+A UML representation of the class structure of an Analysis is shown in Figure~\ref{fig:analysisUML}.
+
+\begin{figure}[t]
+\includegraphics[width=\textwidth]{Analysis.pdf}
+\caption{The basics of an Analysis configuration in UML representation.  Most classes shown are base classes.
+Appending ``= 0'' to a method name denotes pure virtuality-- the method is not defined in the base class, but must
+be defined in any instantiated class which derives from it.  Yellow classes at the periphery are bases for user-written
+classes.\label{fig:analysisUML}
+}
+\end{figure}
+
+\subsubsection{AliFemtoEventCut}
+
+The first action of an \name{AliFemtoAnalysis} is usually to invoke the method \name{AliFemtoEventCut::{\meth Pass(\args{AliFemtoEvent*})}}.
+This returns
+a boolean value (and may, internally, store information about the \name{AliFemtoEvent} passed to it).  If the event does not
+Pass, no further processing is done by the AliFemtoAnalysis-- control returns to the \name{AliFemtoManager}.
+
+The Reference Manual gives the full implementation of a simple \name{AliFemtoEventCut}.
+
+
+\subsubsection{AliFemtoParticleCuts}
+\label{sec:AliFemtoParticleCuts}
+
+Depending on the topological nature of the particles being selected,
+one uses the class \name{AliFemtoTrackCut}, \name{AliFemtoV0Cut}, \name{AliFemtoKinkCut}, or \name{AliFemtoXiCut}.
+All of these inherit from \name{AliFemtoParticleCut};
+see Figure~\ref{fig:analysisUML}.  As with all cuts, these classes have pure virtural \meth{Pass()} methods.
+An Analysis has two \name{AliFemtoParticle} cuts, corresponding to the two particles used in the correlation analysis.
+
+There is ``special'' behaviour when the \name{AliFemtoParticle} cuts are applied.  For each AliFemtoTrack/V0/Kink/Xi which Passes the cuts,
+an \name{AliFemtoParticle} is created.  (The \name{AliFemtoParticle} objects themselves
+are created and used within the Analysis-- the user is not concerned with them.)
+It is the \name{AliFemtoParticle} objects (not \name{AliFemtoTracks} etc) which are used at further steps in the Analysis
+for the current event.  {\bf Important:} all \name{AliFemtoParticleCut}-derived objects set the mass of the particle it selects.  Based on
+kinematic and PID information, the user, through the \name{AliFemtoParticleCut}, decides e.g. that the Track is a proton; the user needs to
+tell the \name{AliFemtoParticleCut} the mass of the proton; c.f. Section~\ref{sec:example}.  When the \name{AliFemtoParticle} corresponding to this
+\name{AliFemtoTrack} is created, it is at this point that the mass of the proton is assigned to the particle.
+
+\subsubsection{AliFemtoPairCut}
+
+As the name suggests, user-written classes which derive from \name{AliFemtoPairCut} must have a \meth{Pass()} method selecting
+\name{AliFemtoPairs} for further processing.  (\name{AliFemtoPair}s are created and used internally; the user does not interact with them.)
+These cuts may, for example, try to discriminate ``fake'' pairs caused by splitting or (for the reference pair distribution)
+those tracks which would merge.
+
+Importantly, the Analysis will automatically apply the {\it same} \name{AliFemtoPair} cut to pairs generated from ``real'' and from ``mixed''
+events.  Almost always, this is very important for femtoscopic analyses.  However, if neccessary, one may circumvent this behaviour
+by attaching \name{AliFemtoPairCut} objects to the correlation function object itself.  In this case, different PairCuts may be applied to ``real'' and
+reference distributions.
+
+\subsubsection{AliFemtoCorrFctn}
+
+The ``end result'' of most femtoscopic studies is the correlation function.  These compare somehow (often via a ratio of
+distributions, c.f. Equation~\ref{eq:usualC}) ``real'' and reference pairs.  In general, then, a user-written class which
+derives from \name{AliFemtoCorrFctn} should implement \meth{AddRealPair(\args{AliFemtoPair})} and \meth{AddMixedPair(\args{AliFemtoPair})}
+methods.  These methods may do whatever the user
+wishes, of course.
+
+Most CorrFctn classes are rather simple.  See the Reference Manual for a full listing of an example.
+
+Often, one wishes to construct several correlation functions simultaneously (e.g. one in $Q_{inv}$, $\vec{q}_{3D}$, $\Theta_{opening}$ etc).
+For this reason, every \name{AliFemtoAnalysis} may have several \name{AliFemtoCorrFctn} objects.
+The same \name{AliFemtoPair}s are sent to each \name{AliFemtoCorrFctn}.
+
+
+\subsubsection{Action flow}
+
+The most important action of each \name{AliFemtoAnalysis} is in its \meth{ProcessEvent(\args{AliFemtoEvent*})} method.
+corresponds approximately to steps~\ref{it:EvCut}-\ref{it:Store} of the list in Section~\ref{sec:bones}.
+Upon being given an Event by the Manager, it first sends it to its EventCut.  If \name{AliFemtoEventCut::\meth{Pass(\args{AliFemtoEvent*})}}
+returns false, the  method returns with no further action.
+
+Otherwise, an \name{AliFemtoPicoEvent} (essentially two lists of \name{AliFemtoParticle}s, c.f. Section~\ref{sec:AliFemtoParticleCuts}) is formed from 
+the particles which Pass the \name{AliFemtoParticleCuts}.  All possible pairs of these Particles are tested by the 
+\name{AliFemtoPairCut::\meth{Pass()}} method,
+and those which Pass are sent to each of the \name{AliFemtoCorrFctn}'s \meth{AddRealPair(\args{AliFemtoPair*})} methods.
+
+Then, ``mixed'' \name{AliFemtoPair}s are formed by combining all \name{AliFemtoParticles} from the present event with those of previously-processed
+events, which have been stored in a collection of \name{AliFemtoPicoEvents}.  (C.f. Figure~\ref{fig:analysisUML}; the user need not interact
+with this aspect of the code.)  All such Pairs are formed.  These are evaluated by the \name{AliFemtoPairCut} and those which Pass are sent to
+each of the \name{AliFemtoCorrFctn::\meth{AddMixedPair(\args{AliFemtoPair*})}} methods.
+
+Finally, the AliFemtoPicoEvent is put into the list (c.f. Figure~\ref{fig:analysisUML}) of such objects for mixing with future events,
+and control returns to the AliFemtoManager.
+
+As mentioned previously, the above procedure is just one typical of Analyses.  In principle, one's specific Analysis class might
+email the user each pair, or each particle at random.
+
+
+\subsection{Reports}
+\label{sec:reports}
+
+Note that most classes above have \meth{Report()} methods.  These are simple user-written methods returning strings which can tell something about
+what happened to that class during the study.  E.g. a \name{AliFemtoEventCut} might Report on how many events passed/failed the
+cut.  The content of the Report is up to the user; it might be even an empty string or your spouse's name.
+
+
+At the end of the session, the Reports of the various objects are concatenated in the following way.
+
+Each AliFemtoAnalysis
+collects Reports from its AliFemtoEventCut, AliFemtoParticleCut (for both the first and second particle), AliFemtoPairCut, and all
+of its AliFemtoCorrFctn objects.  These are concatenated with any other information coming from the AliFemtoAnalysis itself.
+This constitutes the Report of the AliFemtoAnalysis.
+
+The AliFemtoManager collects Reports from each of its AliFemtoEventReader objects (both those in read and write mode)
+and from each of its AliFemtoAnalysis objects.  These are concatenated and constitute the final Report
+printed to the screen (or log file).  
+
+%==========================================================
+%==================== Example =============================
+%==========================================================
+
+
+\subsection{Example macro}
+\label{sec:example}
+
+Here, we show a specific macro which may be used to perform two Analyses which produce several CorrFctns.  The example
+shown is for use in ``pure'' root.  It may also be used as a simple macro in AliRoot or, as been previously mentioned,
+it is straightforward to wrap it in a Task or Train (or, in STAR, the BFC Chain).
+
+Figures~\ref{fig:exampleMacroGload}-\ref{fig:exampleEventLoop} in this Section are only cartoons suggesting what the
+code in the macro does-- they are not UML.  All classes in this specific example are user-written
+classes, with the exception of AliFemtoManager.  (Several of them such as the \name{AliFemtoEventReaderESD} class,
+have already been written and are provided in the \cvs checkout.)
+ For details, see Sections~\ref{sec:topLevel} and~\ref{sec:analysisLevel}.
+
+
+\subsubsection{Initialization and plugging in the Reader}
+%--------------------- Example Step 1 ----------------------
+
+\begin{figure}[t]
+\includegraphics[width=\textwidth]{ExampleMacro1.pdf}
+\caption{The preliminaries in a \AliFemto macro: loading of the libraries, instantiation of top-level structure, and
+instantiating and plugging in a Reader.
+The cartoon is meant so suggest the action of the macro commands; it is not a UML diagram.
+\label{fig:exampleMacroGload}
+}
+\end{figure}
+
+\begin{figure}[t]
+\includegraphics[width=\textwidth]{ExampleMacro2.pdf}
+\caption{The construction of a specific \name{AliFemtoAnalysis}, including its cuts and collection of three CorrFctn
+objects.  The dark shaded region in the cartoon denotes a collection.
+\label{fig:exampleFirstAnalysisStart}
+}
+\end{figure}
+
+\begin{figure}[t]
+\includegraphics[width=\textwidth]{ExampleMacro3.pdf}
+\caption{The final step in configuring the first Analysis is to set the number of events to mix when constructing
+the ``background'' distribution.  This finished Analysis (dark grey box) is then added to the collection of Analyses
+for the \name{AliFemtoManager} (large light grey box), thus making the connection between these objects.
+\label{fig:exampleFirstAnalysisFinish}
+}
+\end{figure}
+
+\begin{figure}[t]
+\includegraphics[width=\textwidth]{ExampleMacro4.pdf}
+\caption{A second Analysis is instantiated, configured, and added to the collection.  The same
+proceedure is followed as for the fist Analysis (Figures~\ref{fig:exampleFirstAnalysisStart}
+and~\ref{fig:exampleFirstAnalysisFinish}), though the two Analyses know nothing about each other.
+\label{fig:exampleSecondAnalysis}
+}
+\end{figure}
+
+\begin{figure}[t]
+\includegraphics[width=\textwidth]{ExampleMacro5.pdf}
+\caption{Construction of the AliFemto study complete, event looping is trivial.  Note that all
+interaction with the code is through only a few methods of the AliFemtoManager object.
+\label{fig:exampleEventLoop}
+}
+\end{figure}
+
+Figure~\ref{fig:exampleMacroGload} shows the beginning of the macro.  
+As usual in a root macro, libraries are loaded first.  For the femtoscopic analysis itself, only the AliFemto and AliFemtoUser
+libraries need be loaded.  All internal \AliFemto classes such as \name{AliFemtoPair} are found in the AliFemto directory.
+That directory also has a few simple CorrFcn, Reader, and Cut classes.  The user will probably want to start with these and
+elaborate upon them; in this case, her new classes should go into the AliFemtoUser area.
+
+In this example
+we use the specific \name{AliFemtoEventReader}-derived class \name{AliFemtoEventReaderESD}; not surprisingly, this Reader needs
+the ESD library loaded as well.
+
+
+
+Since all Readers are user-written, their configuration
+methods will be specific to the class used.  This is as it should be, since attempts to ``foresee'' all possible
+uses of the Reader classes will ultimately result in limitations later on, and sloppy work-arounds.
+
+The \name{AliFemtoManager} is instantiated; note that its pointer is declared outside the scope of the macro, at the top.
+Finally, the \name{AliFemtoEventReaderESD} object is ``plugged in'' to the \name{AliFemtoManager}.  This is indicated by the arrow
+in the cartoon; recall that this is not a UML diagram.
+
+\subsubsection{Adding Analyses}
+%--------------------- Example Step 2 ----------------------
+
+
+In Figure~\ref{fig:exampleFirstAnalysisStart} we see construction of a specific Analysis  (c.f.
+Section~\ref{sec:analysisLevel}).
+An \name{AliFemtoAnalysis}-derived class, \name{AliFemtoVertexAnalysis}, is
+instantiated.  (For reference, this class takes care to ``mix'' only those events close to each other in
+primary vertex position; it is very commonly used.)  All configuration (vertex range, number of bins) takes
+place in the constructor, in this specific class.
+
+The Cuts are (i) instantiated, (ii) configured, and (iii) ``plugged into'' this Analysis.
+Finally, three correlation functions are instantiated, configured, and added to the collection
+of CorrFctns for this analysis.  (The collection is suggested by the dark-shaded box in the cartoon.)
+We note that one of the CorrFctn classes there is \name{OpeningAngleCorrFctn}.  The fact that its name
+does not begin with ``AliFemto'' is a clue that this class is user-written, for her own purposes; it would
+not be included in ALICE nightly builds and would sit in the AliFemtoUser area.
+
+Two notes:  Firstly, we see that the same AliFemtoTrackCut is used for both the first and second particle-- this
+is an analysis of identical pions.  Secondly, as mentioned in  Section~\ref{sec:AliFemtoParticleCuts}, all AliFemtoParticleCuts
+{\it must} define a particle mass.  This is not special to this specific example.
+
+%--------------------- Example Step 3 ----------------------
+
+
+In Figure~\ref{fig:exampleFirstAnalysisStart}, the conglomeration of Analysis-related objects is not related to
+the AliFemtoManager instantiated in the previous Figure.  In Figure~\ref{fig:exampleFirstAnalysisFinish}, the connection
+is made.  Firstly, the ``final detail'' for the Analysis is completed-- the number of events to mix for the reference
+distribution is set, and the now-fully-configured Analysis is added to the collection of Analyses (denoted by the large
+grey box).
+
+%--------------------- Example Step 4 ----------------------
+
+
+The structure is now complete in principle-- a useful correlation study may proceed.
+We may add one or more completely seperate Analyses, if we wish.  This is shown in
+Figure~\ref{fig:exampleSecondAnalysis}.  The only points here are that the second
+(and any subsequent) Analyses are set up similarly to the first one discussed above, and
+there is no connection the Analyses in the AliFemtoManager's collection of Analyses.
+
+
+\subsubsection{Processing data}
+\label{sec:ProcessingData}
+%--------------------- Example Step 5 ----------------------
+
+
+Finally, Figure~\ref{fig:exampleEventLoop} moves beyond construction of the collection
+of objects, and commands a processing of the data.  We note that all ``external'' interaction
+is with the AliFemtoManager class.  If the Reader needs to interact with the ``outside world''
+(e.g. by opening a file or pointing to a location in memory), then it is up to that specific
+class, using its own specific methods, to take care of that.
+
+In Figure~\ref{fig:exampleEventLoop}, the processing is ordered within a ``pure root'' macro
+directly.  This can be different in other frameworks.  For example, in the STAR Maker schema~\cite{StarMaker},
+the AliFemtoManager Init(), ProcessEvent(), Report() and Finish() methods will be invoked by the AliFemtoMaker
+Init(), Make(), and Finish() methods.  Indeed, the AliFemtoMaker does almost nothing else than perform these
+simple invocations.
+
+
+\section{Code Organization}
+
+
+\subsection{Directory structure: core and user classes}
+\label{sec:coreUser}
+
+The femtoscopy analysis effort in ALICE falls in the soft physics working group (PWG2).
+Thus, when checking out the full \AliRoot from \cvs, it will be found in the {\tt PWG2/FEMTOSCOPY/}
+area.  (One may also check out only PWG2 files using\\
+{\tt cvs -qz2 -d :pserver:cvs@alisoft.cern.ch:/soft/cvsroot co PWG2}.\\  This is useful if running
+\AliFemto in ``standalone'' mode.)
+
+In this directory are found two subdirectories.  The first is {\tt AliFemto/},
+which holds about 80 classes (as of \today), such as \name{AliFemtoManager}, \name{AliFemtoPair}, etc.
+It also holds all of the base classes for user-derived code (e.g. \name{AliFemtoCorrFctn}) and one
+or two simple examples of classes which derive from these (e.g. \name{AliFemtoQinvCorrFctn}).  These
+last might be useful templates for users writing more sophisticated Cuts, CorrFctns, Readers, Analyses, etc.
+The {\tt AliFemto/} subdirectory is included in the official nightly build.  Files there must obey
+ALICE coding standards, and limited \cvs access is anticipated.
+
+The second directory is {\tt AliFemtoUser/}.  Files in this subdirectory are not included in the nightly
+build.  This area is meant to be a repository for user code, typically Cuts, CorrFctns, etc, which might
+be of interest to others working on some analysis.  It is \cvs archived, and widespread read/write \cvs access
+is anticipated.
+
+Seperate shared object (.so) libraries are built for the {\tt AliFemto/} and {\tt AliFemtoUser/}
+area; c.f. the macro snip in Figure~\ref{fig:exampleMacroGload}.
+
+
+\section{Known problems}
+
+As of \today, there are no known problems with \AliFemto.  However, this Users' Guide is incomplete, in that
+it does not discuss so-called ``theoretical'' correlation studies covered in the \name{AliFemtoModel*} classes.
+This will be remedied in the next version of the Users' Guide.  In the meantime, see an excellent tutorial
+on the subject on the ALICE femtoscopy webpage\\
+ {\tt http://aliceinfo.cern.ch/Collaboration/PhysicsWorkingGroups/PWG2/Femtoscopy/}.
+
+
+
+\clearpage
+
+\part{Reference Manual}
+\label{part:RefMan}
+
+The Reference Manual is being finalized.
+
+\clearpage
+
+
+
+%%%%%%%%\section{References}
+\begin{thebibliography}{99}
+
+ \bibitem{UMLreference}
+   The Unified Modeling Language (UML), 
+   http://www.omg.org/technology/documents/formal/uml.htm ;
+   http://en.wikipedia.org/wiki/Unified\_Modeling\_Language
+
+\bibitem{Lisa:2005dd}
+  M.~A.~Lisa, S.~Pratt, R.~Soltz and U.~Wiedemann,
+  %``Femtoscopy in relativistic heavy ion collisions,''
+  Ann.\ Rev.\ Nucl.\ Part.\ Sci.\  {\bf 55}, 357 (2005)
+  [arXiv:nucl-ex/0505014].
+  %%CITATION = NUCL-EX 0505014;%%
+
+\bibitem{HanburyBrown:1954}
+  Hanbury-Brown, R., and Twiss, R.Q.
+  %''A new type of interferometer for use in radio-astronomy'',
+  Phil. Mag. {\bf 45}, 663 (1954).
+
+\bibitem{Goldhaber:1960sf}
+  Goldhaber, Gerson and Goldhaber, Sulamith and Lee, Won-Yong
+                  and Pais, Abraham, 
+  %''Influence of Bose-Einstein statistics on the antiproton
+                  proton  annihilation process''
+  Phys. Rev. {\bf 120} 300 (1960).
+
+\bibitem{Lednicky:2002fq}
+   Lednicky, R.,
+   %''Progress in correlation femtoscopy,''
+   nucl-th/0212089
+
+
+\bibitem{StarMaker}
+%Unfortunately, the best (!?!?) documentation of the basic STAR Maker analysis framework is
+%a brief presentation by Victor Perevoztchikov which may be found on the STAR computing
+%tutorial website:
+Tutorial by Victor Perevoztchikov 
+http://www.star.bnl.gov/STAR/comp/train/tut/Maker-in-STAR/Victor-Makers.html
+
+\end{thebibliography}
+
+
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+%
+% The End
+%
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+
+\printindex
+
+\end{document}
diff --git a/PWGCF/FEMTOSCOPY/Documentation/AliFemtoTitle.pdf b/PWGCF/FEMTOSCOPY/Documentation/AliFemtoTitle.pdf
new file mode 100644 (file)
index 0000000..f3cd133
Binary files /dev/null and b/PWGCF/FEMTOSCOPY/Documentation/AliFemtoTitle.pdf differ
diff --git a/PWGCF/FEMTOSCOPY/Documentation/Analysis.pdf b/PWGCF/FEMTOSCOPY/Documentation/Analysis.pdf
new file mode 100644 (file)
index 0000000..8cdf582
Binary files /dev/null and b/PWGCF/FEMTOSCOPY/Documentation/Analysis.pdf differ
diff --git a/PWGCF/FEMTOSCOPY/Documentation/ExampleMacro1.pdf b/PWGCF/FEMTOSCOPY/Documentation/ExampleMacro1.pdf
new file mode 100644 (file)
index 0000000..3c56c68
Binary files /dev/null and b/PWGCF/FEMTOSCOPY/Documentation/ExampleMacro1.pdf differ
diff --git a/PWGCF/FEMTOSCOPY/Documentation/ExampleMacro2.pdf b/PWGCF/FEMTOSCOPY/Documentation/ExampleMacro2.pdf
new file mode 100644 (file)
index 0000000..9fcab79
Binary files /dev/null and b/PWGCF/FEMTOSCOPY/Documentation/ExampleMacro2.pdf differ
diff --git a/PWGCF/FEMTOSCOPY/Documentation/ExampleMacro3.pdf b/PWGCF/FEMTOSCOPY/Documentation/ExampleMacro3.pdf
new file mode 100644 (file)
index 0000000..11cf5a5
Binary files /dev/null and b/PWGCF/FEMTOSCOPY/Documentation/ExampleMacro3.pdf differ
diff --git a/PWGCF/FEMTOSCOPY/Documentation/ExampleMacro4.pdf b/PWGCF/FEMTOSCOPY/Documentation/ExampleMacro4.pdf
new file mode 100644 (file)
index 0000000..43c3137
Binary files /dev/null and b/PWGCF/FEMTOSCOPY/Documentation/ExampleMacro4.pdf differ
diff --git a/PWGCF/FEMTOSCOPY/Documentation/ExampleMacro5.pdf b/PWGCF/FEMTOSCOPY/Documentation/ExampleMacro5.pdf
new file mode 100644 (file)
index 0000000..26f951c
Binary files /dev/null and b/PWGCF/FEMTOSCOPY/Documentation/ExampleMacro5.pdf differ
diff --git a/PWGCF/FEMTOSCOPY/Documentation/TopLevelUML.pdf b/PWGCF/FEMTOSCOPY/Documentation/TopLevelUML.pdf
new file mode 100644 (file)
index 0000000..15f8692
Binary files /dev/null and b/PWGCF/FEMTOSCOPY/Documentation/TopLevelUML.pdf differ
diff --git a/PWGCF/FEMTOSCOPY/macros/AddTaskFemto.C b/PWGCF/FEMTOSCOPY/macros/AddTaskFemto.C
new file mode 100644 (file)
index 0000000..0611f5c
--- /dev/null
@@ -0,0 +1,67 @@
+//=============================================================================
+//
+// *** AddTaskFemto.C ***
+//
+// This macro initialize a complete AnalysisTask object for femtoscopy.
+//
+//=============================================================================
+
+AliAnalysisTaskFemto *AddTaskFemto(const char *configMacroName="ConfigFemtoAnalysis.C", const char *configMacroParameters="" )
+{
+// Creates a proton analysis task and adds it to the analysis manager.
+  
+  // A. Get the pointer to the existing analysis manager via the static access method.
+  //==============================================================================
+  AliAnalysisManager *mgr = AliAnalysisManager::GetAnalysisManager();
+  if (!mgr) {
+    Error("AddTaskFemto", "No analysis manager to connect to.");
+    return NULL;
+  }  
+
+  // B. Check the analysis type using the event handlers connected to the analysis
+  //    manager. The availability of MC handler cann also be checked here.
+  //==============================================================================
+  if (!mgr->GetInputEventHandler()) {
+    ::Error("AddTaskFemto", "This task requires an input event handler");
+    return NULL;
+  }  
+  TString type = mgr->GetInputEventHandler()->GetDataType(); // can be "ESD" or "AOD"
+  cout << "Found " <<type << " event handler" << endl;
+
+  // C. Create the task, add it to manager.
+  //===========================================================================
+//  gSystem->SetIncludePath("-I$ROOTSYS/include  -I./PWG2AOD/AOD -I./PWG2femtoscopy/FEMTOSCOPY/AliFemto -I./PWG2femtoscopyUser/FEMTOSCOPY/AliFemtoUser -I$ALICE_ROOT/include");
+
+  if (TProofMgr::GetListOfManagers()->GetEntries()) {
+//     if (dynamic_cast<TProofLite *> gProof) {
+//       char *macrocommand[10000];
+//       sprintf(macrocommand, ".L %s", configMacroName);
+//       gProof->Exec(macrocommand);
+//     }
+//     else
+    gProof->Load(configMacroName);
+  }  
+  //  gROOT->LoadMacro("ConfigFemtoAnalysis.C++");
+
+  AliAnalysisTaskFemto *taskfemto = new AliAnalysisTaskFemto("TaskFemto",configMacroName,configMacroParameters);
+  mgr->AddTask(taskfemto);
+
+  // D. Configure the analysis task. Extra parameters can be used via optional
+  // arguments of the AddTaskXXX() function.
+  //===========================================================================
+  
+  // E. Create ONLY the output containers for the data produced by the task.
+  // Get and connect other common input/output containers via the manager as below
+  //==============================================================================
+  TString outputfile = AliAnalysisManager::GetCommonFileName();  
+  outputfile += ":PWG2FEMTO";
+  AliAnalysisDataContainer *cout_femto  = mgr->CreateContainer("femtolist",  TList::Class(),
+                                                              AliAnalysisManager::kOutputContainer,outputfile);
+
+
+   mgr->ConnectInput(taskfemto, 0, mgr->GetCommonInputContainer());
+   mgr->ConnectOutput(taskfemto, 0, cout_femto);
+
+   // Return task pointer at the end
+   return taskfemto;
+}
diff --git a/PWGCF/FEMTOSCOPY/macros/Batch/ConfigFemtoAnalysis.C b/PWGCF/FEMTOSCOPY/macros/Batch/ConfigFemtoAnalysis.C
new file mode 100644 (file)
index 0000000..06750da
--- /dev/null
@@ -0,0 +1,131 @@
+// ConfigFemtoAnalysis.C - macro to create the splitting/merging
+// test with the pion correlation function.
+// As a default the anti-splitting and anti-merging cuts are open
+// and the two correlation functions:
+// AliFemtoShareQualityCorrFctn and AliFemtoTPCInnerCorrFctn 
+// can be used to study the splitting (former) and merging (latter) effect
+// If ones needs to produce a "clean" sample with both effects removed, 
+// one needs to change the cut values to the "reasonable" ones, or perform
+// the full systematic analysis with the above-mentioned functions 
+
+// Author: Adam Kisiel. Adam.Kisiel@cern.ch
+
+// parameters:
+//
+// returns:
+// a pointer to the created AliFemtoManager
+
+#include "AliFemtoManager.h"
+#include "AliFemtoEventReaderESDChain.h"
+#include "AliFemtoSimpleAnalysis.h"
+#include "AliFemtoBasicEventCut.h"
+#include "AliFemtoESDTrackCut.h"
+#include "AliFemtoCutMonitorParticleYPt.h"
+#include "AliFemtoShareQualityTPCEntranceSepPairCut.h"
+#include "AliFemtoQinvCorrFctn.h"
+#include "AliFemtoShareQualityCorrFctn.h"
+#include "AliFemtoTPCInnerCorrFctn.h"
+#include "AliFemtoVertexMultAnalysis.h"
+
+AliFemtoManager *ConfigFemtoAnalysis()
+{
+  double PionMass = 0.13956995;
+  int chargePi = 1;
+  
+  // Set-up the reader for ALICE ESD
+  AliFemtoEventReaderESDChain* Reader=new AliFemtoEventReaderESDChain();
+  // Read only constrained momenta - primordial particles
+  Reader->SetConstrained(true);
+  Reader->SetReadTPCInner(true);
+  
+  // Setup the manager 
+  AliFemtoManager* Manager=new AliFemtoManager();
+  // Point to the data source - the reader
+  Manager->SetEventReader(Reader);
+  
+  // Setup the analysis
+  AliFemtoSimpleAnalysis* an =new AliFemtoSimpleAnalysis();
+  // Number of events to construct the background
+  an->SetNumEventsToMix(3);
+
+  // The event selector
+  AliFemtoBasicEventCut* mec = new AliFemtoBasicEventCut();
+  // Accept events with the given multiplicity
+  mec->SetEventMult(0,100000);
+  // and z-vertex distance to the center of the TPC
+  mec->SetVertZPos(-1000,1000);
+       
+  // The track selector
+  AliFemtoESDTrackCut* dtc = new AliFemtoESDTrackCut();
+  // We want positive pions
+  dtc->SetPidProbPion(0.2,1.001);
+  dtc->SetPidProbMuon(0.0,0.8);
+  dtc->SetPidProbKaon(0.0,0.1);
+  dtc->SetPidProbProton(0.0,0.1);
+  dtc->SetMostProbablePion();
+  dtc->SetCharge(chargePi);
+  // so we set the correct mass
+  dtc->SetMass(PionMass);
+  // we select low pt
+  dtc->SetPt(0.1,0.7);
+  dtc->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+  dtc->SetminTPCncls(95);
+  dtc->SetRemoveKinks(kTRUE);
+  dtc->SetLabel(kFALSE);
+  dtc->SetMaxITSChiNdof(3.0);
+  dtc->SetMaxTPCChiNdof(2.0);
+  dtc->SetMaxSigmaToVertex(3.0);
+
+  AliFemtoCutMonitorParticleYPt *cutPass = new AliFemtoCutMonitorParticleYPt("cutPass", 0.13957);
+  AliFemtoCutMonitorParticleYPt *cutFail = new AliFemtoCutMonitorParticleYPt("cutFail", 0.13957);
+  dtc->AddCutMonitor(cutPass, cutFail);
+
+  // Pair selector
+  AliFemtoShareQualityTPCEntranceSepPairCut *sqpc = new AliFemtoShareQualityTPCEntranceSepPairCut();
+  // remove split track pairs and pairs that share hits
+  
+  // Set maximim allowed "quality" for the pair
+  //  1.0 - accept all pairs
+  // -0.5 - reject all pairs
+  // a reasonable value should lie between 0.0 and 0.5
+  sqpc->SetShareQualityMax(1.0);
+
+  // Set maximum allowed shared hits fraction per pair
+  //  1.0 - accept all pairs
+  //  0.0 - reject all pairs
+  // a reasonable value is small but nno-zero (0.05)
+  sqpc->SetShareFractionMax(1.0);
+
+  // Set minimum allowed separation between nominal TPC entrance points
+  // of the two tracks in the pair
+  // 0.0 - accept all pairs
+  // a reasonable value is 3.0 [cm]
+  sqpc->SetTPCEntranceSepMinimum(0.0);
+  sqpc->SetRemoveSameLabel(kFALSE);
+
+  // Add the cuts to the analysis
+  an->SetEventCut(mec);
+  an->SetFirstParticleCut(dtc);
+  an->SetSecondParticleCut(dtc);
+  an->SetPairCut(sqpc);
+  
+  // Setup correlation functions
+  // A simple qinv correlation function
+  AliFemtoQinvCorrFctn *cqinv= new AliFemtoQinvCorrFctn("qinvcf",75,0.0,0.4);
+  
+  // A correlation function to monitor the splitting and cluster sharing in TPC
+  AliFemtoShareQualityCorrFctn *csqqinv= new AliFemtoShareQualityCorrFctn("sqqinvcf",75,0.0,0.4);
+  
+  // A correlation function to monitor the distance at the entrance to the TPC
+  AliFemtoTPCInnerCorrFctn *tpcin = new AliFemtoTPCInnerCorrFctn("tpcin",80, 0.0, 0.4);
+  
+  // add the correlation functions to the analysis
+  an->AddCorrFctn(cqinv);
+  an->AddCorrFctn(csqqinv);
+  an->AddCorrFctn(tpcin);
+
+  // Add the analysis to the manager
+  Manager->AddAnalysis(an);    
+
+  return Manager;
+}
diff --git a/PWGCF/FEMTOSCOPY/macros/Batch/runBatch.C b/PWGCF/FEMTOSCOPY/macros/Batch/runBatch.C
new file mode 100644 (file)
index 0000000..fc5c5eb
--- /dev/null
@@ -0,0 +1,147 @@
+void runBatch(const char *chainlistfile) {
+  TStopwatch timer;
+  timer.Start();
+
+  printf("*** Connect to AliEn ***\n");
+  TGrid::Connect("alien://");
+  gSystem->Load("libProofPlayer.so");
+
+  //____________________________________________________//
+  //_____________Setting up STEERBase.par_______________//
+  //____________________________________________________//
+  setupPar("STEERBase");
+  gSystem->Load("libSTEERBase.so");
+
+  //____________________________________________________//
+  //_____________Setting up ESD.par_____________________//
+  //____________________________________________________//
+  setupPar("ESD");
+  gSystem->Load("libVMC.so");
+  gSystem->Load("libESD.so");
+
+  //____________________________________________________//
+  //_____________Setting up AOD.par_____________________//
+  //____________________________________________________//
+  setupPar("AOD");
+  gSystem->Load("libAOD.so");
+
+  //_________________________________________________________//
+  //_____________Setting up ANALYSIS.par_____________________//
+  //_________________________________________________________//
+  setupPar("ANALYSIS");
+  gSystem->Load("libANALYSIS.so");
+
+  //_________________________________________________________//
+  //_____________Setting up ANALYSISalice.par________________//
+  //_________________________________________________________//
+  setupPar("ANALYSISalice");
+  gSystem->Load("libANALYSISalice.so");
+
+  //____________________________________________________//
+  //_____________Setting up PWG2AOD.par_________________//
+  //____________________________________________________//
+  setupPar("PWG2AOD");
+  gSystem->Load("libPWG2AOD.so");
+  
+  //____________________________________________________//
+  //_____________Setting up PWG2femtoscopy.par__________//
+  //____________________________________________________//
+  setupPar("PWG2femtoscopy");
+  gSystem->Load("libPWG2femtoscopy.so");
+  
+  //____________________________________________________//
+  //_____________Setting up PWG2femtoscopyUser.par______//
+  //____________________________________________________//
+  setupPar("PWG2femtoscopyUser");
+  gSystem->Load("libPWG2femtoscopyUser.so");
+  
+  //ANALYSIS PART
+  gSystem->SetIncludePath("-I$ROOTSYS/include  -I\"/usr/local/CERN/root/include\" -I./PWG2femtoscopy/FEMTOSCOPY/AliFemto -I./PWG2femtoscopyUser/FEMTOSCOPY/AliFemtoUser -I./ESD -I./AOD -I./ANALYSIS -I./PWG2AOD/AOD");
+  //  gROOT->LoadMacro("ConfigFemtoAnalysis.C++");
+  //  gROOT->LoadMacro("AliAnalysisTaskFemto.cxx+");
+  //  const char *collectionfile = "wn.xml";
+
+  //____________________________________________//
+  //Usage of event tags
+  AliTagAnalysis *analysis = new AliTagAnalysis();
+  TChain *chain = 0x0;
+  chain = analysis->GetChainFromCollection(chainlistfile,"esdTree");
+
+  //____________________________________________//
+  // Make the analysis manager
+  AliAnalysisManager *mgr = new AliAnalysisManager("TestManager");
+  AliESDInputHandler* esdH = new AliESDInputHandler;
+  esdH->SetInactiveBranches("FMD CaloCluster");
+  mgr->SetInputEventHandler(esdH);  
+
+  AliMCEventHandler *mcH = new AliMCEventHandler;
+  mgr->SetMCtruthEventHandler(mcH);
+
+  mgr->SetCommonFileName("Femto.ESD.root");
+  //____________________________________________//
+  // 1st Pt task
+//   AliAnalysisTaskFemto *task1 = new AliAnalysisTaskFemto("TaskFemto");
+
+//   mgr->AddTask(task1);
+
+//   // Create containers for input/output
+//   //  AliAnalysisDataContainer *cinput1 = mgr->GetCommonInputContainer();
+//   AliAnalysisDataContainer *cinput1 = mgr->CreateContainer("input0", 
+//                                                        TTree::Class(), AliAnalysisManager::kInputContainer);
+//   AliAnalysisDataContainer *coutput1 = mgr->CreateContainer("clist1", TList::Class(),AliAnalysisManager::kOutputContainer,"Femto.ESD.root");
+  
+  gROOT->LoadMacro("AddTaskFemto.C");
+  AliAnalysisTaskFemto *taskfemto = AddTaskFemto("$ALICE_ROOT/PWG2/FEMTOSCOPY/macros/Batch/ConfigFemtoAnalysis.C");
+
+//   cout << "What ???" << endl;
+//   int deb;
+//   cin >> deb;
+
+  //____________________________________________//
+  //  cinput1->SetData(chain);
+//   mgr->ConnectInput(task1,0,cinput1);
+//   mgr->ConnectOutput(task1,0,coutput1);
+
+  if (!mgr->InitAnalysis()) return;
+  mgr->PrintStatus();
+  mgr->StartAnalysis("local",chain);
+
+  timer.Stop();
+  timer.Print();
+}
+
+Int_t setupPar(const char* pararchivename) {
+  ///////////////////
+  // Setup PAR File//
+  ///////////////////
+  if (pararchivename) {
+    char processline[1024];
+    sprintf(processline,".! tar xvzf %s.par",pararchivename);
+    gROOT->ProcessLine(processline);
+    const char* ocwd = gSystem->WorkingDirectory();
+    gSystem->ChangeDirectory(pararchivename);
+
+    // check for BUILD.sh and execute
+    if (!gSystem->AccessPathName("PROOF-INF/BUILD.sh")) {
+      printf("*******************************\n");
+      printf("*** Building PAR archive    ***\n");
+      printf("*******************************\n");
+
+      if (gSystem->Exec("PROOF-INF/BUILD.sh")) {
+        Error("runProcess","Cannot Build the PAR Archive! - Abort!");
+        return -1;
+      }
+    }
+    // check for SETUP.C and execute
+    if (!gSystem->AccessPathName("PROOF-INF/SETUP.C")) {
+      printf("*******************************\n");
+      printf("*** Setup PAR archive       ***\n");
+      printf("*******************************\n");
+      gROOT->Macro("PROOF-INF/SETUP.C");
+    }
+    
+    gSystem->ChangeDirectory("../");
+  }
+
+  return 1;
+}
diff --git a/PWGCF/FEMTOSCOPY/macros/BatchMC/runBatch.C b/PWGCF/FEMTOSCOPY/macros/BatchMC/runBatch.C
new file mode 100644 (file)
index 0000000..8580b3f
--- /dev/null
@@ -0,0 +1,106 @@
+void runBatch() {
+  TStopwatch timer;
+  timer.Start();
+
+  printf("*** Connect to AliEn ***\n");
+  TGrid::Connect("alien://");
+  gSystem->Load("libProofPlayer.so");
+  gSystem->Load("libVMC.so");
+
+  // Use precompiled libraries for the analysis framework
+  gSystem->Load("libSTEERBase.so");
+  gSystem->Load("libVMC.so");
+  gSystem->Load("libESD.so");
+  gSystem->Load("libAOD.so");
+  gSystem->Load("libANALYSIS.so");
+  gSystem->Load("libANALYSISalice.so");
+
+  // Use par files only for PWG2 code
+
+  //____________________________________________________//
+  //_____________Setting up PWG2AOD.par_________________//
+  //____________________________________________________//
+  setupPar("PWG2AOD");
+  gSystem->Load("libPWG2AOD.so");
+  
+  //____________________________________________________//
+  //_____________Setting up PWG2femtoscopy.par__________//
+  //____________________________________________________//
+  setupPar("PWG2femtoscopy");
+  gSystem->Load("libPWG2femtoscopy.so");
+  
+  //____________________________________________________//
+  //_____________Setting up PWG2femtoscopyUser.par______//
+  //____________________________________________________//
+  setupPar("PWG2femtoscopyUser");
+  gSystem->Load("libPWG2femtoscopyUser.so");
+  
+  //ANALYSIS PART
+  const char *collectionfile="wn.xml";
+
+  //____________________________________________//
+  //Usage of event tags
+  AliTagAnalysis *analysis = new AliTagAnalysis();
+  TChain *chain = 0x0;
+  chain = analysis->GetChainFromCollection(collectionfile,"esdTree");
+
+  //____________________________________________//
+  // Make the analysis manager
+  AliAnalysisManager *mgr = new AliAnalysisManager("TestManager");
+  AliESDInputHandler* esdH = new AliESDInputHandler;
+  esdH->SetInactiveBranches("FMD CaloCluster");
+  mgr->SetInputEventHandler(esdH);  
+
+  AliMCEventHandler *mcH = new AliMCEventHandler;
+  mgr->SetMCtruthEventHandler(mcH);
+
+  //____________________________________________//
+  // 1st Pt task
+  gROOT->LoadMacro("AddTaskFemto.C");
+  AliAnalysisTaskFemto *taskfemto = AddTaskFemto();
+
+  //____________________________________________//
+  // Run the analysis
+  if (!mgr->InitAnalysis()) return;
+  mgr->PrintStatus();
+  mgr->StartAnalysis("local",chain);
+
+  timer.Stop();
+  timer.Print();
+}
+
+Int_t setupPar(const char* pararchivename) {
+  ///////////////////
+  // Setup PAR File//
+  ///////////////////
+  if (pararchivename) {
+    char processline[1024];
+    sprintf(processline,".! tar xvzf %s.par",pararchivename);
+    gROOT->ProcessLine(processline);
+    const char* ocwd = gSystem->WorkingDirectory();
+    gSystem->ChangeDirectory(pararchivename);
+
+    // check for BUILD.sh and execute
+    if (!gSystem->AccessPathName("PROOF-INF/BUILD.sh")) {
+      printf("*******************************\n");
+      printf("*** Building PAR archive    ***\n");
+      printf("*******************************\n");
+
+      if (gSystem->Exec("PROOF-INF/BUILD.sh")) {
+        Error("runProcess","Cannot Build the PAR Archive! - Abort!");
+        return -1;
+      }
+    }
+    // check for SETUP.C and execute
+    if (!gSystem->AccessPathName("PROOF-INF/SETUP.C")) {
+      printf("*******************************\n");
+      printf("*** Setup PAR archive       ***\n");
+      printf("*******************************\n");
+      gROOT->Macro("PROOF-INF/SETUP.C");
+    }
+    
+    gSystem->ChangeDirectory("../");
+  }
+
+  return 1;
+}
diff --git a/PWGCF/FEMTOSCOPY/macros/ConfigFemtoAnalysis.C b/PWGCF/FEMTOSCOPY/macros/ConfigFemtoAnalysis.C
new file mode 100644 (file)
index 0000000..0c176fc
--- /dev/null
@@ -0,0 +1,133 @@
+// ConfigFemtoAnalysis.C - macro to create the splitting/merging
+// test with the pion correlation function.
+// As a default the anti-splitting and anti-merging cuts are open
+// and the two correlation functions:
+// AliFemtoShareQualityCorrFctn and AliFemtoTPCInnerCorrFctn 
+// can be used to study the splitting (former) and merging (latter) effect
+// If ones needs to produce a "clean" sample with both effects removed, 
+// one needs to change the cut values to the "reasonable" ones, or perform
+// the full systematic analysis with the above-mentioned functions 
+
+// Author: Adam Kisiel. Adam.Kisiel@cern.ch
+
+// parameters:
+//
+// returns:
+// a pointer to the created AliFemtoManager
+
+#if !defined(__CINT__) || defined(__MAKECINT__)
+#include "AliFemtoManager.h"
+#include "AliFemtoEventReaderESDChain.h"
+#include "AliFemtoSimpleAnalysis.h"
+#include "AliFemtoBasicEventCut.h"
+#include "AliFemtoESDTrackCut.h"
+#include "AliFemtoCutMonitorParticleYPt.h"
+#include "AliFemtoShareQualityTPCEntranceSepPairCut.h"
+#include "AliFemtoQinvCorrFctn.h"
+#include "AliFemtoShareQualityCorrFctn.h"
+#include "AliFemtoTPCInnerCorrFctn.h"
+#include "AliFemtoVertexMultAnalysis.h"
+#endif
+
+AliFemtoManager *ConfigFemtoAnalysis()
+{
+  double PionMass = 0.13956995;
+  int chargePi = 1;
+  
+  // Set-up the reader for ALICE ESD
+  AliFemtoEventReaderESDChain* Reader=new AliFemtoEventReaderESDChain();
+  // Read only constrained momenta - primordial particles
+  Reader->SetConstrained(true);
+  Reader->SetReadTPCInner(true);
+  
+  // Setup the manager 
+  AliFemtoManager* Manager=new AliFemtoManager();
+  // Point to the data source - the reader
+  Manager->SetEventReader(Reader);
+  
+  // Setup the analysis
+  AliFemtoSimpleAnalysis* an =new AliFemtoSimpleAnalysis();
+  // Number of events to construct the background
+  an->SetNumEventsToMix(3);
+
+  // The event selector
+  AliFemtoBasicEventCut* mec = new AliFemtoBasicEventCut();
+  // Accept events with the given multiplicity
+  mec->SetEventMult(0,100000);
+  // and z-vertex distance to the center of the TPC
+  mec->SetVertZPos(-1000,1000);
+       
+  // The track selector
+  AliFemtoESDTrackCut* dtc = new AliFemtoESDTrackCut();
+  // We want positive pions
+  dtc->SetPidProbPion(0.2,1.001);
+  dtc->SetPidProbMuon(0.0,0.8);
+  dtc->SetPidProbKaon(0.0,0.1);
+  dtc->SetPidProbProton(0.0,0.1);
+  dtc->SetMostProbablePion();
+  dtc->SetCharge(chargePi);
+  // so we set the correct mass
+  dtc->SetMass(PionMass);
+  // we select low pt
+  dtc->SetPt(0.1,0.7);
+  dtc->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+  dtc->SetminTPCncls(95);
+  dtc->SetRemoveKinks(kTRUE);
+  dtc->SetLabel(kFALSE);
+  dtc->SetMaxITSChiNdof(3.0);
+  dtc->SetMaxTPCChiNdof(2.0);
+  dtc->SetMaxSigmaToVertex(3.0);
+
+  AliFemtoCutMonitorParticleYPt *cutPass = new AliFemtoCutMonitorParticleYPt("cutPass", 0.13957);
+  AliFemtoCutMonitorParticleYPt *cutFail = new AliFemtoCutMonitorParticleYPt("cutFail", 0.13957);
+  dtc->AddCutMonitor(cutPass, cutFail);
+
+  // Pair selector
+  AliFemtoShareQualityTPCEntranceSepPairCut *sqpc = new AliFemtoShareQualityTPCEntranceSepPairCut();
+  // remove split track pairs and pairs that share hits
+  
+  // Set maximim allowed "quality" for the pair
+  //  1.0 - accept all pairs
+  // -0.5 - reject all pairs
+  // a reasonable value should lie between 0.0 and 0.5
+  sqpc->SetShareQualityMax(1.0);
+
+  // Set maximum allowed shared hits fraction per pair
+  //  1.0 - accept all pairs
+  //  0.0 - reject all pairs
+  // a reasonable value is small but nno-zero (0.05)
+  sqpc->SetShareFractionMax(1.0);
+
+  // Set minimum allowed separation between nominal TPC entrance points
+  // of the two tracks in the pair
+  // 0.0 - accept all pairs
+  // a reasonable value is 3.0 [cm]
+  sqpc->SetTPCEntranceSepMinimum(0.0);
+  sqpc->SetRemoveSameLabel(kFALSE);
+
+  // Add the cuts to the analysis
+  an->SetEventCut(mec);
+  an->SetFirstParticleCut(dtc);
+  an->SetSecondParticleCut(dtc);
+  an->SetPairCut(sqpc);
+  
+  // Setup correlation functions
+  // A simple qinv correlation function
+  AliFemtoQinvCorrFctn *cqinv= new AliFemtoQinvCorrFctn("qinvcf",75,0.0,0.4);
+  
+  // A correlation function to monitor the splitting and cluster sharing in TPC
+  AliFemtoShareQualityCorrFctn *csqqinv= new AliFemtoShareQualityCorrFctn("sqqinvcf",75,0.0,0.4);
+  
+  // A correlation function to monitor the distance at the entrance to the TPC
+  AliFemtoTPCInnerCorrFctn *tpcin = new AliFemtoTPCInnerCorrFctn("tpcin",80, 0.0, 0.4);
+  
+  // add the correlation functions to the analysis
+  an->AddCorrFctn(cqinv);
+  an->AddCorrFctn(csqqinv);
+  an->AddCorrFctn(tpcin);
+
+  // Add the analysis to the manager
+  Manager->AddAnalysis(an);    
+
+  return Manager;
+}
diff --git a/PWGCF/FEMTOSCOPY/macros/Local/AliFemtoSplittingMergingQA.C b/PWGCF/FEMTOSCOPY/macros/Local/AliFemtoSplittingMergingQA.C
new file mode 100644 (file)
index 0000000..6855b75
--- /dev/null
@@ -0,0 +1,165 @@
+// AliFemtoSplittingMergingQA.C - macro to create the splitting/merging
+// test with the pion correlation function.
+// As a default the anti-splitting and anti-merging cuts are open
+// and the two correlation functions:
+// AliFemtoShareQualityCorrFctn and AliFemtoTPCInnerCorrFctn 
+// can be used to study the splitting (former) and merging (latter) effect
+// If ones needs to produce a "clean" sample with both effects removed, 
+// one needs to change the cut values to the "reasonable" ones, or perform
+// the full systematic analysis with the above-mentioned functions 
+
+// Author: Adam Kisiel. Adam.Kisiel@cern.ch
+
+// parameters:
+// listFileName - a text file containing a list of ESDs (with full paths) 
+// to analyze
+void AliFemtoSplittingMergingQA(const char *listFileName)
+{
+  double PionMass = 0.13956995;
+  double chargePi = 1.0;
+  
+  // Load the neccessary libraries
+  gSystem->Load("libTree");
+  gSystem->Load("libGeom");
+  gSystem->Load("libEG");
+  gSystem->Load("libCint");
+  gSystem->Load("libESD");
+  gSystem->Load("libPWG2femtoscopy");
+  gSystem->Load("libPWG2femtoscopyUser");
+
+  // Set-up the reader for ALICE ESD
+  AliFemtoEventReaderESD* Reader=new AliFemtoEventReaderESD();
+  // Read only constrained momenta - primordial particles
+  Reader->SetConstrained(true);
+  Reader->SetReadTPCInner(true);
+  // Read the file list from the filename supplied by the user
+  Reader->SetInputFile(listFileName);
+  
+  // Setup the manager 
+  AliFemtoManager* Manager=new AliFemtoManager();
+  // Point to the data source - the reader
+  Manager->SetEventReader(Reader);
+  
+  // Setup the analysis
+  AliFemtoSimpleAnalysis* an =new AliFemtoSimpleAnalysis();
+  // Number of events to construct the background
+  an->SetNumEventsToMix(3);
+
+  // The event selector
+  AliFemtoBasicEventCut* mec = new AliFemtoBasicEventCut();
+  // Accept events with the given multiplicity
+  mec->SetEventMult(0,100000);
+  // and z-vertex distance to the center of the TPC
+  mec->SetVertZPos(-1000,1000);
+       
+  // The track selector
+  AliFemtoESDTrackCut* dtc = new AliFemtoESDTrackCut();
+  // We want positive pions
+  dtc->SetPidProbPion(0.2,1.001);
+  dtc->SetPidProbMuon(0.0,0.8);
+  dtc->SetPidProbKaon(0.0,0.1);
+  dtc->SetPidProbProton(0.0,0.1);
+  dtc->SetMostProbablePion();
+  dtc->SetCharge(1.0);
+  // so we set the correct mass
+  dtc->SetMass(PionMass);
+  // we select low pt
+  dtc->SetPt(0.1,0.7);
+  dtc->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+  dtc->SetminTPCncls(95);
+  dtc->SetRemoveKinks(kTRUE);
+  dtc->SetLabel(kFALSE);
+  dtc->SetMaxITSChiNdof(3.0);
+  dtc->SetMaxTPCChiNdof(2.0);
+  dtc->SetMaxSigmaToVertex(3.0);
+
+  AliFemtoCutMonitorParticleYPt *cutPass = new AliFemtoCutMonitorParticleYPt("cutPass", 0.13957);
+  AliFemtoCutMonitorParticleYPt *cutFail = new AliFemtoCutMonitorParticleYPt("cutFail", 0.13957);
+  dtc->AddCutMonitor(cutPass, cutFail);
+
+  // Pair selector
+  AliFemtoShareQualityTPCEntranceSepPairCut *sqpc = new AliFemtoShareQualityTPCEntranceSepPairCut();
+  // remove split track pairs and pairs that share hits
+  
+  // Set maximim allowed "quality" for the pair
+  //  1.0 - accept all pairs
+  // -0.5 - reject all pairs
+  // a reasonable value should lie between 0.0 and 0.5
+  sqpc->SetShareQualityMax(1.0);
+
+  // Set maximum allowed shared hits fraction per pair
+  //  1.0 - accept all pairs
+  //  0.0 - reject all pairs
+  // a reasonable value is small but nno-zero (0.05)
+  sqpc->SetShareFractionMax(1.0);
+
+  // Set minimum allowed separation between nominal TPC entrance points
+  // of the two tracks in the pair
+  // 0.0 - accept all pairs
+  // a reasonable value is 3.0 [cm]
+  sqpc->SetTPCEntranceSepMinimum(0.0);
+  sqpc->SetRemoveSameLabel(kFALSE);
+
+  // Add the cuts to the analysis
+  an->SetEventCut(mec);
+  an->SetFirstParticleCut(dtc);
+  an->SetSecondParticleCut(dtc);
+  an->SetPairCut(sqpc);
+  
+  // Setup correlation functions
+  // A simple qinv correlation function
+  AliFemtoQinvCorrFctn *cqinv= new AliFemtoQinvCorrFctn("qinvcf",75,0.0,0.4);
+  
+  // A correlation function to monitor the splitting and cluster sharing in TPC
+  AliFemtoShareQualityCorrFctn *csqqinv= new AliFemtoShareQualityCorrFctn("sqqinvcf",75,0.0,0.4);
+  
+  // A correlation function to monitor the distance at the entrance to the TPC
+  AliFemtoTPCInnerCorrFctn *tpcin = new AliFemtoTPCInnerCorrFctn("tpcin",80, 0.0, 0.4);
+  
+  // add the correlation functions to the analysis
+  an->AddCorrFctn(cqinv);
+  an->AddCorrFctn(csqqinv);
+  an->AddCorrFctn(tpcin);
+
+  // Add the analysis to the manager
+  Manager->AddAnalysis(an);    
+
+  // Run the event loop
+  long nE= 100000;
+  if (Manager->Init())
+    cout<<" Problem"<<endl;
+       
+  int Status=0;
+  long int nEP=0;
+  while ((!Status)&&(nEP<nE))
+    {
+      nEP++;
+      cout<<" next event "<<nEP<<endl;
+      Status=Manager->ProcessEvent();
+    } 
+       
+  // Save the results
+  char ofname[200];
+  sprintf(ofname, "QinvCF.In.root");
+
+  TFile f1 (ofname,"RECREATE","Data");
+  cqinv->Numerator()->Write();
+  cqinv->Denominator()->Write();
+  csqqinv->WriteHistos();
+  tpcin->WriteHistos();
+  cutPass->Write();
+  cutFail->Write();
+
+  // Save the cut settings in the output file 
+  f1.mkdir("Settings");
+  f1.cd("Settings");
+  
+  TList *tListSettings = an->ListSettings();
+  tListSettings->Write();
+
+  f1.Close();
+
+  TFile f2("Listout.root","RECREATE");
+  TList *tOutList = an->GetOutputList();
+  tOutList->Write();
+}
diff --git a/PWGCF/FEMTOSCOPY/macros/Local/runLocal.C b/PWGCF/FEMTOSCOPY/macros/Local/runLocal.C
new file mode 100644 (file)
index 0000000..177f85a
--- /dev/null
@@ -0,0 +1,141 @@
+void runLocal(const char *chainlistfile, int dataFromAlien=0) {
+  TStopwatch timer;
+  timer.Start();
+
+  printf("*** Connect to AliEn ***\n");
+  if (dataFromAlien)
+    TGrid::Connect("alien://");
+  gSystem->Load("libProofPlayer.so");
+
+  //____________________________________________________//
+  //_____________Setting up STEERBase.par_______________//
+  //____________________________________________________//
+  setupPar("STEERBase");
+  gSystem->Load("libSTEERBase.so");
+
+  //____________________________________________________//
+  //_____________Setting up ESD.par_____________________//
+  //____________________________________________________//
+  setupPar("ESD");
+  gSystem->Load("libVMC.so");
+  gSystem->Load("libESD.so");
+
+  //____________________________________________________//
+  //_____________Setting up AOD.par_____________________//
+  //____________________________________________________//
+  setupPar("AOD");
+  gSystem->Load("libAOD.so");
+
+  //_________________________________________________________//
+  //_____________Setting up ANALYSIS.par_____________________//
+  //_________________________________________________________//
+  setupPar("ANALYSIS");
+  gSystem->Load("libANALYSIS.so");
+
+  //_________________________________________________________//
+  //_____________Setting up ANALYSISalice.par________________//
+  //_________________________________________________________//
+  setupPar("ANALYSISalice");
+  gSystem->Load("libANALYSISalice.so");
+
+  //____________________________________________________//
+  //_____________Setting up PWG2AOD.par_________________//
+  //____________________________________________________//
+  setupPar("PWG2AOD");
+  gSystem->Load("libPWG2AOD.so");
+  
+  //____________________________________________________//
+  //_____________Setting up PWG2femtoscopy.par__________//
+  //____________________________________________________//
+  setupPar("PWG2femtoscopy");
+  gSystem->Load("libPWG2femtoscopy.so");
+  
+  //____________________________________________________//
+  //_____________Setting up PWG2femtoscopyUser.par______//
+  //____________________________________________________//
+  setupPar("PWG2femtoscopyUser");
+  gSystem->Load("libPWG2femtoscopyUser.so");
+  
+  //ANALYSIS PART
+  gSystem->SetIncludePath("-I$ROOTSYS/include  -I\"/usr/local/CERN/root/include\" -I./PWG2femtoscopy/FEMTOSCOPY/AliFemto -I./PWG2femtoscopyUser/FEMTOSCOPY/AliFemtoUser -I./ESD -I./AOD -I./ANALYSIS -I./PWG2AOD/AOD");
+  gROOT->LoadMacro("ConfigFemtoAnalysis.C++");
+
+  //____________________________________________//
+  //Usage of event tags
+  AliTagAnalysis *analysis = new AliTagAnalysis();
+  TChain *chain = 0x0;
+  //  chain = analysis->GetChainFromCollection(collectionfile,"esdTree");
+
+  if (dataFromAlien) {
+    AliTagAnalysis *analysis = new AliTagAnalysis();
+    chain = analysis->GetChainFromCollection(chainlistfile,"esdTree");
+  }
+  else {
+    gROOT->LoadMacro("CreateESDChain.C");
+    chain = CreateESDChain(chainlistfile,500);
+  }
+
+  //____________________________________________//
+  // Make the analysis manager
+  AliAnalysisManager *mgr = new AliAnalysisManager("TestManager");
+  AliESDInputHandler* esdH = new AliESDInputHandler;
+  esdH->SetInactiveBranches("FMD CaloCluster");
+  mgr->SetInputEventHandler(esdH);  
+  //____________________________________________//
+  // 1st Pt task
+  AliAnalysisTaskFemto *task1 = new AliAnalysisTaskFemto("TaskFemto");
+
+  mgr->AddTask(task1);
+
+  // Create containers for input/output
+  AliAnalysisDataContainer *cinput1 = mgr->GetCommonInputContainer();
+  AliAnalysisDataContainer *coutput1 = mgr->CreateContainer("clist1", TList::Class(),AliAnalysisManager::kOutputContainer,"Femto.ESD.root");
+  
+  //____________________________________________//
+  cinput1->SetData(chain);
+  mgr->ConnectInput(task1,0,cinput1);
+  mgr->ConnectOutput(task1,0,coutput1);
+
+  if (!mgr->InitAnalysis()) return;
+  mgr->PrintStatus();
+  mgr->StartAnalysis("local",chain);
+
+  timer.Stop();
+  timer.Print();
+}
+
+Int_t setupPar(const char* pararchivename) {
+  ///////////////////
+  // Setup PAR File//
+  ///////////////////
+  if (pararchivename) {
+    char processline[1024];
+    sprintf(processline,".! tar xvzf %s.par",pararchivename);
+    gROOT->ProcessLine(processline);
+    const char* ocwd = gSystem->WorkingDirectory();
+    gSystem->ChangeDirectory(pararchivename);
+
+    // check for BUILD.sh and execute
+    if (!gSystem->AccessPathName("PROOF-INF/BUILD.sh")) {
+      printf("*******************************\n");
+      printf("*** Building PAR archive    ***\n");
+      printf("*******************************\n");
+
+      if (gSystem->Exec("PROOF-INF/BUILD.sh")) {
+        Error("runProcess","Cannot Build the PAR Archive! - Abort!");
+        return -1;
+      }
+    }
+    // check for SETUP.C and execute
+    if (!gSystem->AccessPathName("PROOF-INF/SETUP.C")) {
+      printf("*******************************\n");
+      printf("*** Setup PAR archive       ***\n");
+      printf("*******************************\n");
+      gROOT->Macro("PROOF-INF/SETUP.C");
+    }
+    
+    gSystem->ChangeDirectory("../");
+  }
+
+  return 1;
+}
diff --git a/PWGCF/FEMTOSCOPY/macros/Proof/runProof.C b/PWGCF/FEMTOSCOPY/macros/Proof/runProof.C
new file mode 100644 (file)
index 0000000..234bfec
--- /dev/null
@@ -0,0 +1,108 @@
+void runProof(const char *chainlistfile, int nEvents=0, int offset=0, int domc=0, int prooflite=0) {
+  TStopwatch timer;
+  timer.Start();
+  
+  printf("*** Open PROOF ***");
+  if (prooflite) 
+    TProof::Open("");
+  else
+    TProof::Open("alicecaf");
+
+  gSystem->Load("libProofPlayer.so");
+  gSystem->Load("libVMC.so");
+  gSystem->Load("libXMLIO.so");
+
+  gProof->UploadPackage("STEERBase.par");
+  gProof->EnablePackage("STEERBase");
+  gProof->UploadPackage("ESD.par");
+  gProof->EnablePackage("ESD");
+  gProof->UploadPackage("AOD.par");
+  gProof->EnablePackage("AOD");
+  gProof->UploadPackage("ANALYSIS.par");
+  gProof->EnablePackage("ANALYSIS");
+  gProof->UploadPackage("ANALYSISalice.par");
+  gProof->EnablePackage("ANALYSISalice");
+  gProof->UploadPackage("PWG2AOD.par");
+  gProof->EnablePackage("PWG2AOD");
+  gProof->UploadPackage("PWG2femtoscopy.par");
+  gProof->EnablePackage("PWG2femtoscopy");
+  gProof->UploadPackage("PWG2femtoscopyUser.par");
+  gProof->EnablePackage("PWG2femtoscopyUser");
+    
+  gSystem->SetIncludePath("-I$ROOTSYS/include -I./STEERBase/ -I./ESD/ -I./AOD/ -I./ANALYSIS/ -I./ANALYSISalice/ -I./PWG2AOD/AOD -I./PWG2femtoscopy/FEMTOSCOPY/AliFemto -I./PWG2femtoscopyUser/FEMTOSCOPY/AliFemtoUser");
+  gProof->Exec(".L AddTaskFemto.C",kTRUE);
+  gROOT->LoadMacro("AddTaskFemto.C");
+  cout << "Loaded AddTaskFemto macro "<< endl;
+
+  gProof->ShowEnabledPackages();
+
+  //ANALYSIS PART
+  TChain *chain = 0x0;
+  if (prooflite) {
+    gROOT->LoadMacro("CreateESDChain.C");
+    chain = CreateESDChain(chainlistfile,10000);
+  }
+
+  //____________________________________________//
+  // Make the analysis manager
+  AliAnalysisManager *mgr = new AliAnalysisManager("TestManager");
+  AliESDInputHandler* esdH = new AliESDInputHandler;
+
+  esdH->SetInactiveBranches("FMD CaloCluster");
+  mgr->SetInputEventHandler(esdH);  
+
+  if (domc) {
+    AliMCEventHandler *mcH = new AliMCEventHandler;
+    mgr->SetMCtruthEventHandler(mcH);
+  }
+  //____________________________________________//
+  // 1st Pt task
+
+  AliAnalysisTaskFemto *taskfemto = AddTaskFemto();
+
+  if (!mgr->InitAnalysis()) return;
+  mgr->PrintStatus();
+  if (prooflite) 
+    mgr->StartAnalysis("proof",chain,2000000,0);
+  else 
+    mgr->StartAnalysis("proof",chainlistfile,nEvents,offset);
+
+  timer.Stop();
+  timer.Print();
+}
+
+Int_t setupPar(const char* pararchivename) {
+  ///////////////////
+  // Setup PAR File//
+  ///////////////////
+  if (pararchivename) {
+    char processline[1024];
+    sprintf(processline,".! tar xvzf %s.par",pararchivename);
+    gROOT->ProcessLine(processline);
+    const char* ocwd = gSystem->WorkingDirectory();
+    gSystem->ChangeDirectory(pararchivename);
+
+    // check for BUILD.sh and execute
+    if (!gSystem->AccessPathName("PROOF-INF/BUILD.sh")) {
+      printf("*******************************\n");
+      printf("*** Building PAR archive    ***\n");
+      printf("*******************************\n");
+
+      if (gSystem->Exec("PROOF-INF/BUILD.sh")) {
+        Error("runProcess","Cannot Build the PAR Archive! - Abort!");
+        return -1;
+      }
+    }
+    // check for SETUP.C and execute
+    if (!gSystem->AccessPathName("PROOF-INF/SETUP.C")) {
+      printf("*******************************\n");
+      printf("*** Setup PAR archive       ***\n");
+      printf("*******************************\n");
+      gROOT->Macro("PROOF-INF/SETUP.C");
+    }
+    
+    gSystem->ChangeDirectory("../");
+  }
+
+  return 1;
+}
diff --git a/PWGCF/FEMTOSCOPY/macros/Train/AddTaskFemto.C b/PWGCF/FEMTOSCOPY/macros/Train/AddTaskFemto.C
new file mode 100644 (file)
index 0000000..2c74884
--- /dev/null
@@ -0,0 +1,67 @@
+//=============================================================================
+//
+// *** AddTaskFemto.C ***
+//
+// This macro initialize a complete AnalysisTask object for femtoscopy.
+//
+//=============================================================================
+
+AliAnalysisTaskFemto *AddTaskFemto(TString configMacroName, const char *containerName="femtolist", const char *configMacroParameters="" )
+{
+// Creates a proton analysis task and adds it to the analysis manager.
+  
+  // A. Get the pointer to the existing analysis manager via the static access method.
+  //==============================================================================
+  AliAnalysisManager *mgr = AliAnalysisManager::GetAnalysisManager();
+  if (!mgr) {
+    Error("AddTaskFemto", "No analysis manager to connect to.");
+    return NULL;
+  }  
+
+  // B. Check the analysis type using the event handlers connected to the analysis
+  //    manager. The availability of MC handler cann also be checked here.
+  //==============================================================================
+  if (!mgr->GetInputEventHandler()) {
+    ::Error("AddTaskFemto", "This task requires an input event handler");
+    return NULL;
+  }  
+  TString type = mgr->GetInputEventHandler()->GetDataType(); // can be "ESD" or "AOD"
+  cout << "Found " <<type << " event handler" << endl;
+
+  // C. Create the task, add it to manager.
+  //===========================================================================
+//  gSystem->SetIncludePath("-I$ROOTSYS/include  -I./PWG2AOD/AOD -I./PWG2femtoscopy/FEMTOSCOPY/AliFemto -I./PWG2femtoscopyUser/FEMTOSCOPY/AliFemtoUser -I$ALICE_ROOT/include");
+
+  if (TProofMgr::GetListOfManagers()->GetEntries()) {
+//     if (dynamic_cast<TProofLite *> gProof) {
+//       char *macrocommand[10000];
+//       sprintf(macrocommand, ".L %s", configMacroName);
+//       gProof->Exec(macrocommand);
+//     }
+//     else
+    gProof->Load(configMacroName);
+  }  
+  //  gROOT->LoadMacro("ConfigFemtoAnalysis.C++");
+
+  AliAnalysisTaskFemto *taskfemto = new AliAnalysisTaskFemto("TaskFemto","$ALICE_ROOT/"+configMacroName,configMacroParameters);
+  mgr->AddTask(taskfemto);
+
+  // D. Configure the analysis task. Extra parameters can be used via optional
+  // arguments of the AddTaskXXX() function.
+  //===========================================================================
+  
+  // E. Create ONLY the output containers for the data produced by the task.
+  // Get and connect other common input/output containers via the manager as below
+  //==============================================================================
+  TString outputfile = AliAnalysisManager::GetCommonFileName();  
+  outputfile += ":PWG2FEMTO";
+  AliAnalysisDataContainer *cout_femto  = mgr->CreateContainer(containerName,  TList::Class(),
+                                                              AliAnalysisManager::kOutputContainer,outputfile);
+
+
+   mgr->ConnectInput(taskfemto, 0, mgr->GetCommonInputContainer());
+   mgr->ConnectOutput(taskfemto, 0, cout_femto);
+
+   // Return task pointer at the end
+   return taskfemto;
+}
diff --git a/PWGCF/FEMTOSCOPY/macros/Train/DEtaDPhi/ConfigFemtoAnalysis.C b/PWGCF/FEMTOSCOPY/macros/Train/DEtaDPhi/ConfigFemtoAnalysis.C
new file mode 100644 (file)
index 0000000..df72535
--- /dev/null
@@ -0,0 +1,387 @@
+
+/*********************************************************************
+ *                                                                   *
+ * Configfemtoanalysis.C - configuration macro for the femtoscopic   *
+ * analysis, meant as a QA process for two-particle effects          *
+ *                                                                   *
+ * Author: Adam Kisiel (Adam.Kisiel@cern.ch)                         *
+ *                                                                   *
+ *********************************************************************/
+
+#if !defined(__CINT__) || defined(__MAKECINT_)
+#include "AliFemtoManager.h"
+#include "AliFemtoEventReaderESDChain.h"
+#include "AliFemtoEventReaderESDChainKine.h"
+#include "AliFemtoEventReaderAODChain.h"
+#include "AliFemtoSimpleAnalysis.h"
+#include "AliFemtoBasicEventCut.h"
+#include "AliFemtoESDTrackCut.h"
+#include "AliFemtoCorrFctn.h"
+#include "AliFemtoCutMonitorParticleYPt.h"
+#include "AliFemtoCutMonitorParticleVertPos.h"
+#include "AliFemtoCutMonitorParticleMomRes.h"
+#include "AliFemtoCutMonitorParticlePID.h"
+#include "AliFemtoCutMonitorEventMult.h"
+#include "AliFemtoCutMonitorEventVertex.h"
+#include "AliFemtoShareQualityTPCEntranceSepPairCut.h"
+#include "AliFemtoPairCutAntiGamma.h"
+#include "AliFemtoPairCutRadialDistance.h"
+#include "AliFemtoQinvCorrFctn.h"
+#include "AliFemtoCorrFctnNonIdDR.h"
+#include "AliFemtoShareQualityCorrFctn.h"
+#include "AliFemtoTPCInnerCorrFctn.h"
+#include "AliFemtoVertexMultAnalysis.h"
+#include "AliFemtoCorrFctn3DSpherical.h"
+#include "AliFemtoChi2CorrFctn.h"
+#include "AliFemtoCorrFctnTPCNcls.h"
+#include "AliFemtoBPLCMS3DCorrFctn.h"
+#include "AliFemtoCorrFctn3DLCMSSym.h"
+#include "AliFemtoModelBPLCMSCorrFctn.h"
+#include "AliFemtoModelCorrFctn3DSpherical.h"
+#include "AliFemtoModelGausLCMSFreezeOutGenerator.h"
+#include "AliFemtoModelGausRinvFreezeOutGenerator.h"
+#include "AliFemtoModelManager.h"
+#include "AliFemtoModelWeightGeneratorBasic.h"
+#include "AliFemtoModelWeightGeneratorLednicky.h"
+#include "AliFemtoCorrFctnDirectYlm.h"
+#include "AliFemtoModelCorrFctnDirectYlm.h"
+#include "AliFemtoModelCorrFctnSource.h"
+#include "AliFemtoCutMonitorParticlePtPDG.h"
+#include "AliFemtoKTPairCut.h"
+#incude "AliFemtoPairCutPt.h"
+#endif
+
+//________________________________________________________________________
+AliFemtoManager* ConfigFemtoAnalysis() {
+
+  double PionMass = 0.13956995;
+  double KaonMass = 0.493677;
+  double ProtonMass = 0.938272013;
+       
+
+  int runmults[10] = {1, 1, 1, 1, 1, 1, 1, 1, 1, 1};
+  int multbins[11] = {0.001, 50, 100, 200, 300, 400, 500, 600, 700, 800, 900};
+  
+  int runch[3] = {1, 1, 1};
+  const char *chrgs[3] = { "PP", "APAP", "PAP" };
+  
+
+  int runktdep = 1;
+  double ktrng[3] = {0.0, 0.75, 100.0};
+  //  double ktrng[8] = {0.2, 0.3, 0.4, 0.5, 0.6, 0.7, 0.8, 1.0};
+
+  int numOfMultBins = 10;  
+  int numOfChTypes = 3;
+  int numOfkTbins = 2;
+
+  int runqinv = 1;
+  int runshlcms = 1;// 0:PRF(PAP), 1:LCMS(PP,APAP)
+
+  int runtype = 2; // Types 0 - global, 1 - ITS only, 2 - TPC Inner
+  int isrealdata = 1;
+
+  int gammacut = 1;
+  
+  double shqmax = 0.5;
+  int nbinssh = 100;
+
+  AliFemtoEventReaderAODChain *Reader = new AliFemtoEventReaderAODChain();
+  Reader->SetFilterBit(7);
+  Reader->SetCentralityPreSelection(0.001, 910);
+
+  AliFemtoManager* Manager = new AliFemtoManager();
+  Manager->SetEventReader(Reader);
+
+  AliFemtoVertexMultAnalysis    *anetaphitpc[320];
+  AliFemtoBasicEventCut         *mecetaphitpc[320];
+  AliFemtoCutMonitorEventMult   *cutPassEvMetaphitpc[320];
+  AliFemtoCutMonitorEventMult   *cutFailEvMetaphitpc[320];
+  AliFemtoCutMonitorEventVertex *cutPassEvVetaphitpc[320];
+  AliFemtoCutMonitorEventVertex *cutFailEvVetaphitpc[320];
+  AliFemtoESDTrackCut           *dtc1etaphitpc[320];
+  AliFemtoESDTrackCut           *dtc2etaphitpc[320];
+  AliFemtoCutMonitorParticleYPt *cutPass1YPtetaphitpc[320];
+  AliFemtoCutMonitorParticleYPt *cutFail1YPtetaphitpc[320];
+  AliFemtoCutMonitorParticlePID *cutPass1PIDetaphitpc[320];
+  AliFemtoCutMonitorParticlePID *cutFail1PIDetaphitpc[320];
+  AliFemtoCutMonitorParticleYPt *cutPass2YPtetaphitpc[320];
+  AliFemtoCutMonitorParticleYPt *cutFail2YPtetaphitpc[320];
+  AliFemtoCutMonitorParticlePID *cutPass2PIDetaphitpc[320];
+  AliFemtoCutMonitorParticlePID *cutFail2PIDetaphitpc[320];
+  //   AliFemtoPairCutAntiGamma      *sqpcetaphitpcdiff[320];
+  //   AliFemtoShareQualityTPCEntranceSepPairCut      *sqpcetaphitpcsame[320];
+  AliFemtoPairCutAntiGamma      *sqpcetaphitpc[320];
+  //  AliFemtoPairCutRadialDistance      *sqpcetaphitpc[320];
+  //  AliFemtoChi2CorrFctn          *cchiqinvetaphitpc[320];
+  AliFemtoPairCutPt             *ktpcuts[320];
+  AliFemtoCorrFctnDirectYlm     *cylmkttpc[320];
+  //AliFemtoCorrFctnDirectYlm     *cylmetaphitpc[320];
+  AliFemtoQinvCorrFctn          *cqinvkttpc[320];
+  AliFemtoQinvCorrFctn          *cqinvtpc[320];
+  AliFemtoCorrFctnNonIdDR       *ckstartpc[320];
+  AliFemtoCorrFctnDEtaDPhi      *cdedpetaphi[320];
+
+  //   AliFemtoCorrFctn3DLCMSSym     *cq3dlcmskttpc[20*2];
+  //   AliFemtoCorrFctnTPCNcls       *cqinvnclstpc[20];
+  //   AliFemtoShareQualityCorrFctn  *cqinvsqtpc[20*10];
+  //   AliFemtoChi2CorrFctn          *cqinvchi2tpc[20];
+  //   AliFemtoTPCInnerCorrFctn      *cqinvinnertpc[20*10];
+  
+  // *** Third QA task - HBT analysis with all pair cuts off, TPC only ***
+  // *** Begin pion-pion (positive) analysis ***
+  int aniter = 0;  
+
+  for (int imult = 0; imult < numOfMultBins; imult++) {
+    if (runmults[imult]) {
+
+      for (int ichg = 0; ichg < numOfChTypes; ichg++) {
+       if (runch[ichg]) {
+
+         aniter = ichg * numOfMultBins + imult;
+         anetaphitpc[aniter] = new AliFemtoVertexMultAnalysis(8, -8.0, 8.0, 4, multbins[imult], multbins[imult+1]);
+         anetaphitpc[aniter]->SetNumEventsToMix(5);
+         anetaphitpc[aniter]->SetMinSizePartCollection(1);
+
+         mecetaphitpc[aniter] = new AliFemtoBasicEventCut();
+         mecetaphitpc[aniter]->SetEventMult(0.001,100000);
+         mecetaphitpc[aniter]->SetVertZPos(-8,8);
+
+         if (isrealdata)
+           mecetaphitpc[aniter]->SetAcceptOnlyPhysics(kTRUE);
+                 
+         cutPassEvMetaphitpc[aniter] = new AliFemtoCutMonitorEventMult(Form("cutPass%stpcM%i", chrgs[ichg], imult));
+         cutFailEvMetaphitpc[aniter] = new AliFemtoCutMonitorEventMult(Form("cutFail%stpcM%i", chrgs[ichg], imult));
+         mecetaphitpc[aniter]->AddCutMonitor(cutPassEvMetaphitpc[aniter], cutFailEvMetaphitpc[aniter]);
+         
+         cutPassEvVetaphitpc[aniter] = new AliFemtoCutMonitorEventVertex(Form("cutPass%stpcM%i", chrgs[ichg], imult));
+         cutFailEvVetaphitpc[aniter] = new AliFemtoCutMonitorEventVertex(Form("cutFail%stpcM%i", chrgs[ichg], imult));
+         mecetaphitpc[aniter]->AddCutMonitor(cutPassEvVetaphitpc[aniter], cutFailEvVetaphitpc[aniter]);
+         
+         dtc1etaphitpc[aniter] = new AliFemtoESDTrackCut();
+         dtc2etaphitpc[aniter] = new AliFemtoESDTrackCut();
+
+         if (ichg == 0)
+           {
+             dtc1etaphitpc[aniter]->SetCharge(1.0);
+             //dtc2etaphitpc[aniter]->SetCharge(1.0);
+           }
+         else if (ichg == 1)
+           {
+             dtc1etaphitpc[aniter]->SetCharge(-1.0);
+             //dtc2etaphitpc[aniter]->SetCharge(-1.0);
+           }
+         else if (ichg == 2) 
+           {
+             dtc1etaphitpc[aniter]->SetCharge(-1.0);
+             dtc2etaphitpc[aniter]->SetCharge(1.0);
+           }
+         
+         dtc1etaphitpc[aniter]->SetEta(-0.8,0.8);
+         dtc1etaphitpc[aniter]->SetMass(ProtonMass);     
+         dtc1etaphitpc[aniter]->SetMostProbableProton();
+    
+         if(ichg==2)
+           {
+             dtc2etaphitpc[aniter]->SetEta(-0.8,0.8);
+             dtc2etaphitpc[aniter]->SetMass(ProtonMass);         
+             dtc2etaphitpc[aniter]->SetMostProbableProton();
+           }
+
+         
+         // Track quality cuts
+
+         if (runtype == 0) {
+           dtc1etaphitpc[aniter]->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+           //      dtc1etaphitpc[aniter]->SetStatus(AliESDtrack::kTPCrefit);
+           //    dtc1etaphitpc[aniter]->SetStatus(AliESDtrack::kITSrefit);
+           dtc1etaphitpc[aniter]->SetminTPCncls(80);
+           dtc1etaphitpc[aniter]->SetRemoveKinks(kTRUE);
+           dtc1etaphitpc[aniter]->SetLabel(kFALSE);
+           //    dtc1etaphitpc[aniter]->SetMaxITSChiNdof(6.0);
+           dtc1etaphitpc[aniter]->SetMaxTPCChiNdof(4.0);
+           dtc1etaphitpc[aniter]->SetMaxImpactXY(0.2);
+           //            dtc1etaphitpc[aniter]->SetMaxImpactXYPtDep(0.0182, 0.0350, -1.01);
+           dtc1etaphitpc[aniter]->SetMaxImpactZ(0.15);
+           //      dtc1etaphitpc[aniter]->SetMaxSigmaToVertex(6.0);
+         }
+         else if (runtype == 1) {
+           //      dtc1etaphitpc[aniter]->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+           //    dtc1etaphitpc[aniter]->SetStatus(AliESDtrack::kTPCrefit);
+           //      dtc1etaphitpc[aniter]->SetStatus(AliESDtrack::kITSrefit|AliESDtrack::kITSpureSA);
+           //      dtc1etaphitpc[aniter]->SetminTPCncls(70);
+           dtc1etaphitpc[aniter]->SetStatus(AliESDtrack::kITSrefit);
+           dtc1etaphitpc[aniter]->SetRemoveKinks(kTRUE);
+           dtc1etaphitpc[aniter]->SetLabel(kFALSE);
+           //    dtc1etaphitpc[aniter]->SetMaxITSChiNdof(6.0);
+           //      dtc1etaphitpc[aniter]->SetMaxTPCChiNdof(6.0);
+           dtc1etaphitpc[aniter]->SetMaxImpactXY(0.2);
+           dtc1etaphitpc[aniter]->SetMaxImpactZ(0.25);
+           //      dtc1etaphitpc[aniter]->SetMaxSigmaToVertex(6.0);
+         }
+         else if (runtype == 2) {
+           dtc1etaphitpc[aniter]->SetStatus(AliESDtrack::kTPCin);
+           dtc1etaphitpc[aniter]->SetminTPCncls(80);
+           dtc1etaphitpc[aniter]->SetRemoveKinks(kTRUE);
+           dtc1etaphitpc[aniter]->SetLabel(kFALSE);
+           dtc1etaphitpc[aniter]->SetMaxTPCChiNdof(4.0);
+           dtc1etaphitpc[aniter]->SetMaxImpactXY(2.4);
+           dtc1etaphitpc[aniter]->SetMaxImpactZ(3.0);
+
+
+           if(ichg==2)
+             {
+               dtc2etaphitpc[aniter]->SetStatus(AliESDtrack::kTPCin);
+               dtc2etaphitpc[aniter]->SetminTPCncls(80);
+               dtc2etaphitpc[aniter]->SetRemoveKinks(kTRUE);
+               dtc2etaphitpc[aniter]->SetLabel(kFALSE);
+               dtc2etaphitpc[aniter]->SetMaxTPCChiNdof(4.0);
+               dtc2etaphitpc[aniter]->SetMaxImpactXY(2.4);
+               dtc2etaphitpc[aniter]->SetMaxImpactZ(3.0);
+             }
+
+           
+         }
+         
+         cutPass1YPtetaphitpc[aniter] = new AliFemtoCutMonitorParticleYPt(Form("cutPass1%stpcM%i", chrgs[ichg], imult),ProtonMass);
+         cutFail1YPtetaphitpc[aniter] = new AliFemtoCutMonitorParticleYPt(Form("cutFail1%stpcM%i", chrgs[ichg], imult),ProtonMass);
+         dtc1etaphitpc[aniter]->AddCutMonitor(cutPass1YPtetaphitpc[aniter], cutFail1YPtetaphitpc[aniter]);
+         
+         cutPass1PIDetaphitpc[aniter] = new AliFemtoCutMonitorParticlePID(Form("cutPass1%stpcM%i", chrgs[ichg], imult),2);//0-pion,1-kaon,2-proton
+         cutFail1PIDetaphitpc[aniter] = new AliFemtoCutMonitorParticlePID(Form("cutFail1%stpcM%i", chrgs[ichg], imult),2);
+         dtc1etaphitpc[aniter]->AddCutMonitor(cutPass1PIDetaphitpc[aniter], cutFail1PIDetaphitpc[aniter]);
+
+         if(ichg==2)
+           {
+             cutPass2YPtetaphitpc[aniter] = new AliFemtoCutMonitorParticleYPt(Form("cutPass2%stpcM%i", chrgs[ichg], imult),ProtonMass);
+             cutFail2YPtetaphitpc[aniter] = new AliFemtoCutMonitorParticleYPt(Form("cutFail2%stpcM%i", chrgs[ichg], imult),ProtonMass);
+             dtc2etaphitpc[aniter]->AddCutMonitor(cutPass2YPtetaphitpc[aniter], cutFail2YPtetaphitpc[aniter]);
+
+             cutPass2PIDetaphitpc[aniter] = new AliFemtoCutMonitorParticlePID(Form("cutPass2%stpcM%i", chrgs[ichg], imult),2);//0-pion,1-kaon,2-proton
+             cutFail2PIDetaphitpc[aniter] = new AliFemtoCutMonitorParticlePID(Form("cutFail2%stpcM%i", chrgs[ichg], imult),2);
+             dtc2etaphitpc[aniter]->AddCutMonitor(cutPass2PIDetaphitpc[aniter], cutFail2PIDetaphitpc[aniter]);
+           }
+
+         sqpcetaphitpc[aniter] = new AliFemtoPairCutAntiGamma();
+
+         if (runtype == 0) {
+           sqpcetaphitpc[aniter]->SetShareQualityMax(1.0);
+           sqpcetaphitpc[aniter]->SetShareFractionMax(0.05);
+           sqpcetaphitpc[aniter]->SetRemoveSameLabel(kFALSE);
+           // sqpcetaphitpc[aniter]->SetMaxEEMinv(0.0);
+           // sqpcetaphitpc[aniter]->SetMaxThetaDiff(0.0);
+           //      sqpcetaphitpc[aniter]->SetTPCEntranceSepMinimum(1.5);
+           //sqpcetaphitpc[aniter]->SetRadialDistanceMinimum(0.12, 0.03);
+           //      sqpcetaphitpc[aniter]->SetEtaDifferenceMinimum(0.02);
+         }
+         else if (runtype == 1) {
+           sqpcetaphitpc[aniter]->SetShareQualityMax(1.0);
+           sqpcetaphitpc[aniter]->SetShareFractionMax(1.05);
+           sqpcetaphitpc[aniter]->SetRemoveSameLabel(kFALSE);
+           // sqpcetaphitpc[aniter]->SetMaxEEMinv(0.002);
+           // sqpcetaphitpc[aniter]->SetMaxThetaDiff(0.008);
+           //      sqpcetaphitpc[aniter]->SetTPCEntranceSepMinimum(5.0);
+           //sqpcetaphitpc[aniter]->SetRadialDistanceMinimum(1.2, 0.03);
+           //      sqpcetaphitpc[aniter]->SetEtaDifferenceMinimum(0.02);
+         }
+         else if (runtype == 2) {
+           sqpcetaphitpc[aniter]->SetUseAOD(kTRUE);
+           sqpcetaphitpc[aniter]->SetShareQualityMax(1.0);
+           sqpcetaphitpc[aniter]->SetShareFractionMax(0.05);
+           sqpcetaphitpc[aniter]->SetRemoveSameLabel(kFALSE);
+
+           if (gammacut == 0) {              
+             sqpcetaphitpc[aniter]->SetMaxEEMinv(0.0);
+             sqpcetaphitpc[aniter]->SetMaxThetaDiff(0.0);
+           }
+           else if (gammacut == 1) { 
+             sqpcetaphitpc[aniter]->SetMaxEEMinv(0.002);
+             sqpcetaphitpc[aniter]->SetMaxThetaDiff(0.008);
+           }
+
+           //phi-star cut - values from Johana
+           //      sqpcetaphitpc[aniter]->SetPhiStarDifferenceMinimum(0.012);
+           //      sqpcetaphitpc[aniter]->SetEtaDifferenceMinimum(0.017);
+
+         }
+         
+         anetaphitpc[aniter]->SetEventCut(mecetaphitpc[aniter]);
+
+         
+         if(ichg==2)
+           {
+             anetaphitpc[aniter]->SetFirstParticleCut(dtc1etaphitpc[aniter]);
+             anetaphitpc[aniter]->SetSecondParticleCut(dtc2etaphitpc[aniter]);
+           }
+         else
+           {
+             anetaphitpc[aniter]->SetFirstParticleCut(dtc1etaphitpc[aniter]);
+             anetaphitpc[aniter]->SetSecondParticleCut(dtc1etaphitpc[aniter]);
+           }
+
+         anetaphitpc[aniter]->SetPairCut(sqpcetaphitpc[aniter]);
+         
+
+         /*if (ichg == 2) {
+           ckstartpc[aniter] = new AliFemtoCorrFctnNonIdDR(Form("ckstar%stpcM%i", chrgs[ichg], imult),nbinssh,0.0,shqmax);
+           anetaphitpc[aniter]->AddCorrFctn(ckstartpc[aniter]);
+         }
+         else {  
+           cqinvtpc[aniter] = new AliFemtoQinvCorrFctn(Form("cqinv%stpcM%i", chrgs[ichg], imult),nbinssh,0.0,shqmax);
+           anetaphitpc[aniter]->AddCorrFctn(cqinvtpc[aniter]);
+           }*/
+
+          //cylmkttpc[aniter] = new AliFemtoCorrFctnDirectYlm(Form("cylm%stpcM%i", chrgs[ichg], imult),2,nbinssh, 0.0,shqmax,runshlcms);
+          //anetaphitpc[aniter]->AddCorrFctn(cylmkttpc[aniter]);
+
+         cdedpetaphi[aniter] = new AliFemtoCorrFctnDEtaDPhi(Form("cdedp%stpcM%i", chrgs[ichg], imult),45, 45);
+         anetaphitpc[aniter]->AddCorrFctn(cdedpetaphi[aniter]);
+
+         
+         if (runktdep) {
+           int ktm;
+           for (int ikt=0; ikt<numOfkTbins; ikt++) {
+
+             ktm = aniter * numOfkTbins + ikt;
+             ktpcuts[ktm] = new AliFemtoPairCutPt(ktrng[ikt], ktrng[ikt+1]);
+             
+             //              cylmkttpc[ktm] = new AliFemtoCorrFctnDirectYlm(Form("cylm%stpcM%ikT%i", chrgs[ichg], imult, ikt),3,
+             //                                                             nbinssh, 0.0,
+             //                                                             (imult>6)?shqmax*2.5:shqmax,
+             //                                                             runshlcms);
+             //              cylmkttpc[ktm]->SetPairSelectionCut(ktpcuts[ktm]);
+             //              anetaphitpc[aniter]->AddCorrFctn(cylmkttpc[ktm]);
+             
+             //cqinvkttpc[ktm] = new AliFemtoQinvCorrFctn(Form("cqinv%stpcM%ikT%i", chrgs[ichg], imult, ikt),nbinssh,0.0,(imult>6)?shqmax*2.5:shqmax);
+             //cqinvkttpc[ktm]->SetPairSelectionCut(ktpcuts[ktm]);
+             //anetaphitpc[aniter]->AddCorrFctn(cqinvkttpc[ktm]);
+
+             cdedpetaphi[ktm] = new AliFemtoCorrFctnDEtaDPhi(Form("cdedp%stpcM%ipT%i", chrgs[ichg], imult,ikt),45, 45);
+             cdedpetaphi[ktm]->SetPairSelectionCut(ktpcuts[ktm]);
+             anetaphitpc[aniter]->AddCorrFctn(cdedpetaphi[ktm]);
+
+             //              cqinvsqtpc[ktm] = new AliFemtoShareQualityCorrFctn(Form("cqinvsq%stpcM%ikT%i", chrgs[ichg], imult, ikt),nbinssh,0.0,shqmax);
+             //              cqinvsqtpc[ktm]->SetPairSelectionCut(ktpcuts[ktm]);
+             //              anetaphitpc[aniter]->AddCorrFctn(cqinvsqtpc[ktm]);
+
+             //              cqinvinnertpc[ktm] = new AliFemtoTPCInnerCorrFctn(Form("cqinvinner%stpcM%ikT%i", chrgs[ichg], imult, ikt),nbinssh,0.0,shqmax);
+             //              cqinvinnertpc[ktm]->SetPairSelectionCut(ktpcuts[ktm]);
+             //              cqinvinnertpc[ktm]->SetRadius(1.2);
+             //              anetaphitpc[aniter]->AddCorrFctn(cqinvinnertpc[ktm]);
+
+             //              if (run3d) {
+             //                cq3dlcmskttpc[ktm] = new AliFemtoCorrFctn3DLCMSSym(Form("cq3d%stpcM%ikT%i", chrgs[ichg], imult, ikt),60,(imult>3)?((imult>6)?((imult>7)?0.6:0.4):0.25):0.15);
+             //                cq3dlcmskttpc[ktm]->SetPairSelectionCut(ktpcuts[ktm]);
+             //                anetaphitpc[aniter]->AddCorrFctn(cq3dlcmskttpc[ktm]);
+             //              }
+           }
+         }
+         
+         Manager->AddAnalysis(anetaphitpc[aniter]);    
+       }
+      }
+    }
+  }
+  // *** End pion-pion (positive) analysis
+
+  return Manager;
+}                         
diff --git a/PWGCF/FEMTOSCOPY/macros/Train/DEtaDPhiKaons/ConfigFemtoAnalysis.C b/PWGCF/FEMTOSCOPY/macros/Train/DEtaDPhiKaons/ConfigFemtoAnalysis.C
new file mode 100644 (file)
index 0000000..6e168f9
--- /dev/null
@@ -0,0 +1,386 @@
+/*********************************************************************
+ *                                                                   *
+ * Configfemtoanalysis.C - configuration macro for the femtoscopic   *
+ * analysis, meant as a QA process for two-particle effects          *
+ *                                                                   *
+ * Author: Adam Kisiel (Adam.Kisiel@cern.ch)                         *
+ *                                                                   *
+ *********************************************************************/
+
+#if !defined(__CINT__) || defined(__MAKECINT_)
+#include "AliFemtoManager.h"
+#include "AliFemtoEventReaderESDChain.h"
+#include "AliFemtoEventReaderESDChainKine.h"
+#include "AliFemtoEventReaderAODChain.h"
+#include "AliFemtoSimpleAnalysis.h"
+#include "AliFemtoBasicEventCut.h"
+#include "AliFemtoESDTrackCut.h"
+#include "AliFemtoCorrFctn.h"
+#include "AliFemtoCutMonitorParticleYPt.h"
+#include "AliFemtoCutMonitorParticleVertPos.h"
+#include "AliFemtoCutMonitorParticleMomRes.h"
+#include "AliFemtoCutMonitorParticlePID.h"
+#include "AliFemtoCutMonitorEventMult.h"
+#include "AliFemtoCutMonitorEventVertex.h"
+#include "AliFemtoShareQualityTPCEntranceSepPairCut.h"
+#include "AliFemtoPairCutAntiGamma.h"
+#include "AliFemtoPairCutRadialDistance.h"
+#include "AliFemtoQinvCorrFctn.h"
+#include "AliFemtoCorrFctnNonIdDR.h"
+#include "AliFemtoShareQualityCorrFctn.h"
+#include "AliFemtoTPCInnerCorrFctn.h"
+#include "AliFemtoVertexMultAnalysis.h"
+#include "AliFemtoCorrFctn3DSpherical.h"
+#include "AliFemtoChi2CorrFctn.h"
+#include "AliFemtoCorrFctnTPCNcls.h"
+#include "AliFemtoBPLCMS3DCorrFctn.h"
+#include "AliFemtoCorrFctn3DLCMSSym.h"
+#include "AliFemtoModelBPLCMSCorrFctn.h"
+#include "AliFemtoModelCorrFctn3DSpherical.h"
+#include "AliFemtoModelGausLCMSFreezeOutGenerator.h"
+#include "AliFemtoModelGausRinvFreezeOutGenerator.h"
+#include "AliFemtoModelManager.h"
+#include "AliFemtoModelWeightGeneratorBasic.h"
+#include "AliFemtoModelWeightGeneratorLednicky.h"
+#include "AliFemtoCorrFctnDirectYlm.h"
+#include "AliFemtoModelCorrFctnDirectYlm.h"
+#include "AliFemtoModelCorrFctnSource.h"
+#include "AliFemtoCutMonitorParticlePtPDG.h"
+#include "AliFemtoKTPairCut.h"
+#incude "AliFemtoPairCutPt.h"
+#endif
+
+//________________________________________________________________________
+AliFemtoManager* ConfigFemtoAnalysis() {
+
+  double PionMass = 0.13956995;
+  double KaonMass = 0.493677;
+  double ProtonMass = 0.938272013;
+       
+
+  int runmults[10] = {1, 1, 1, 1, 1, 1, 1, 1, 1, 1};
+  int multbins[11] = {0.001, 50, 100, 200, 300, 400, 500, 600, 700, 800, 900};
+  
+  int runch[3] = {1, 1, 1};
+  const char *chrgs[3] = { "KPKP", "KMKM", "KMKP" };
+  
+
+  int runktdep = 1;
+  double ktrng[3] = {0.0, 0.75, 100.0};
+  //  double ktrng[8] = {0.2, 0.3, 0.4, 0.5, 0.6, 0.7, 0.8, 1.0};
+
+  int numOfMultBins = 10;  
+  int numOfChTypes = 3;
+  int numOfkTbins = 2;
+
+  int runqinv = 1;
+  int runshlcms = 1;// 0:PRF(PAP), 1:LCMS(PP,APAP)
+
+  int runtype = 2; // Types 0 - global, 1 - ITS only, 2 - TPC Inner
+  int isrealdata = 1;
+
+  int gammacut = 1;
+  
+  double shqmax = 0.5;
+  int nbinssh = 100;
+
+  AliFemtoEventReaderAODChain *Reader = new AliFemtoEventReaderAODChain();
+  Reader->SetFilterBit(7);
+  Reader->SetCentralityPreSelection(0.001, 910);
+
+  AliFemtoManager* Manager = new AliFemtoManager();
+  Manager->SetEventReader(Reader);
+
+  AliFemtoVertexMultAnalysis    *anetaphitpc[320];
+  AliFemtoBasicEventCut         *mecetaphitpc[320];
+  AliFemtoCutMonitorEventMult   *cutPassEvMetaphitpc[320];
+  AliFemtoCutMonitorEventMult   *cutFailEvMetaphitpc[320];
+  AliFemtoCutMonitorEventVertex *cutPassEvVetaphitpc[320];
+  AliFemtoCutMonitorEventVertex *cutFailEvVetaphitpc[320];
+  AliFemtoESDTrackCut           *dtc1etaphitpc[320];
+  AliFemtoESDTrackCut           *dtc2etaphitpc[320];
+  AliFemtoCutMonitorParticleYPt *cutPass1YPtetaphitpc[320];
+  AliFemtoCutMonitorParticleYPt *cutFail1YPtetaphitpc[320];
+  AliFemtoCutMonitorParticlePID *cutPass1PIDetaphitpc[320];
+  AliFemtoCutMonitorParticlePID *cutFail1PIDetaphitpc[320];
+  AliFemtoCutMonitorParticleYPt *cutPass2YPtetaphitpc[320];
+  AliFemtoCutMonitorParticleYPt *cutFail2YPtetaphitpc[320];
+  AliFemtoCutMonitorParticlePID *cutPass2PIDetaphitpc[320];
+  AliFemtoCutMonitorParticlePID *cutFail2PIDetaphitpc[320];
+  //   AliFemtoPairCutAntiGamma      *sqpcetaphitpcdiff[320];
+  //   AliFemtoShareQualityTPCEntranceSepPairCut      *sqpcetaphitpcsame[320];
+  AliFemtoPairCutAntiGamma      *sqpcetaphitpc[320];
+  //  AliFemtoPairCutRadialDistance      *sqpcetaphitpc[320];
+  //  AliFemtoChi2CorrFctn          *cchiqinvetaphitpc[320];
+  AliFemtoPairCutPt             *ktpcuts[320];
+  AliFemtoCorrFctnDirectYlm     *cylmkttpc[320];
+  //AliFemtoCorrFctnDirectYlm     *cylmetaphitpc[320];
+  AliFemtoQinvCorrFctn          *cqinvkttpc[320];
+  AliFemtoQinvCorrFctn          *cqinvtpc[320];
+  AliFemtoCorrFctnNonIdDR       *ckstartpc[320];
+  AliFemtoCorrFctnDEtaDPhi      *cdedpetaphi[320];
+
+  //   AliFemtoCorrFctn3DLCMSSym     *cq3dlcmskttpc[20*2];
+  //   AliFemtoCorrFctnTPCNcls       *cqinvnclstpc[20];
+  //   AliFemtoShareQualityCorrFctn  *cqinvsqtpc[20*10];
+  //   AliFemtoChi2CorrFctn          *cqinvchi2tpc[20];
+  //   AliFemtoTPCInnerCorrFctn      *cqinvinnertpc[20*10];
+  
+  // *** Third QA task - HBT analysis with all pair cuts off, TPC only ***
+  // *** Begin pion-pion (positive) analysis ***
+  int aniter = 0;  
+
+  for (int imult = 0; imult < numOfMultBins; imult++) {
+    if (runmults[imult]) {
+
+      for (int ichg = 0; ichg < numOfChTypes; ichg++) {
+       if (runch[ichg]) {
+
+         aniter = ichg * numOfMultBins + imult;
+         anetaphitpc[aniter] = new AliFemtoVertexMultAnalysis(8, -8.0, 8.0, 4, multbins[imult], multbins[imult+1]);
+         anetaphitpc[aniter]->SetNumEventsToMix(5);
+         anetaphitpc[aniter]->SetMinSizePartCollection(1);
+
+         mecetaphitpc[aniter] = new AliFemtoBasicEventCut();
+         mecetaphitpc[aniter]->SetEventMult(0.001,100000);
+         mecetaphitpc[aniter]->SetVertZPos(-8,8);
+
+         if (isrealdata)
+           mecetaphitpc[aniter]->SetAcceptOnlyPhysics(kTRUE);
+                 
+         cutPassEvMetaphitpc[aniter] = new AliFemtoCutMonitorEventMult(Form("cutPass%stpcM%i", chrgs[ichg], imult));
+         cutFailEvMetaphitpc[aniter] = new AliFemtoCutMonitorEventMult(Form("cutFail%stpcM%i", chrgs[ichg], imult));
+         mecetaphitpc[aniter]->AddCutMonitor(cutPassEvMetaphitpc[aniter], cutFailEvMetaphitpc[aniter]);
+         
+         cutPassEvVetaphitpc[aniter] = new AliFemtoCutMonitorEventVertex(Form("cutPass%stpcM%i", chrgs[ichg], imult));
+         cutFailEvVetaphitpc[aniter] = new AliFemtoCutMonitorEventVertex(Form("cutFail%stpcM%i", chrgs[ichg], imult));
+         mecetaphitpc[aniter]->AddCutMonitor(cutPassEvVetaphitpc[aniter], cutFailEvVetaphitpc[aniter]);
+         
+         dtc1etaphitpc[aniter] = new AliFemtoESDTrackCut();
+         dtc2etaphitpc[aniter] = new AliFemtoESDTrackCut();
+
+         if (ichg == 0)
+           {
+             dtc1etaphitpc[aniter]->SetCharge(1.0);
+             //dtc2etaphitpc[aniter]->SetCharge(1.0);
+           }
+         else if (ichg == 1)
+           {
+             dtc1etaphitpc[aniter]->SetCharge(-1.0);
+             //dtc2etaphitpc[aniter]->SetCharge(-1.0);
+           }
+         else if (ichg == 2) 
+           {
+             dtc1etaphitpc[aniter]->SetCharge(-1.0);
+             dtc2etaphitpc[aniter]->SetCharge(1.0);
+           }
+         
+         dtc1etaphitpc[aniter]->SetEta(-0.8,0.8);
+         dtc1etaphitpc[aniter]->SetMass(KaonMass);       
+         dtc1etaphitpc[aniter]->SetMostProbableKaon();
+    
+         if(ichg==2)
+           {
+             dtc2etaphitpc[aniter]->SetEta(-0.8,0.8);
+             dtc2etaphitpc[aniter]->SetMass(KaonMass);   
+             dtc2etaphitpc[aniter]->SetMostProbableKaon();
+           }
+
+         
+         // Track quality cuts
+
+         if (runtype == 0) {
+           dtc1etaphitpc[aniter]->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+           //      dtc1etaphitpc[aniter]->SetStatus(AliESDtrack::kTPCrefit);
+           //    dtc1etaphitpc[aniter]->SetStatus(AliESDtrack::kITSrefit);
+           dtc1etaphitpc[aniter]->SetminTPCncls(80);
+           dtc1etaphitpc[aniter]->SetRemoveKinks(kTRUE);
+           dtc1etaphitpc[aniter]->SetLabel(kFALSE);
+           //    dtc1etaphitpc[aniter]->SetMaxITSChiNdof(6.0);
+           dtc1etaphitpc[aniter]->SetMaxTPCChiNdof(4.0);
+           dtc1etaphitpc[aniter]->SetMaxImpactXY(0.2);
+           //            dtc1etaphitpc[aniter]->SetMaxImpactXYPtDep(0.0182, 0.0350, -1.01);
+           dtc1etaphitpc[aniter]->SetMaxImpactZ(0.15);
+           //      dtc1etaphitpc[aniter]->SetMaxSigmaToVertex(6.0);
+         }
+         else if (runtype == 1) {
+           //      dtc1etaphitpc[aniter]->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+           //    dtc1etaphitpc[aniter]->SetStatus(AliESDtrack::kTPCrefit);
+           //      dtc1etaphitpc[aniter]->SetStatus(AliESDtrack::kITSrefit|AliESDtrack::kITSpureSA);
+           //      dtc1etaphitpc[aniter]->SetminTPCncls(70);
+           dtc1etaphitpc[aniter]->SetStatus(AliESDtrack::kITSrefit);
+           dtc1etaphitpc[aniter]->SetRemoveKinks(kTRUE);
+           dtc1etaphitpc[aniter]->SetLabel(kFALSE);
+           //    dtc1etaphitpc[aniter]->SetMaxITSChiNdof(6.0);
+           //      dtc1etaphitpc[aniter]->SetMaxTPCChiNdof(6.0);
+           dtc1etaphitpc[aniter]->SetMaxImpactXY(0.2);
+           dtc1etaphitpc[aniter]->SetMaxImpactZ(0.25);
+           //      dtc1etaphitpc[aniter]->SetMaxSigmaToVertex(6.0);
+         }
+         else if (runtype == 2) {
+           dtc1etaphitpc[aniter]->SetStatus(AliESDtrack::kTPCin);
+           dtc1etaphitpc[aniter]->SetminTPCncls(80);
+           dtc1etaphitpc[aniter]->SetRemoveKinks(kTRUE);
+           dtc1etaphitpc[aniter]->SetLabel(kFALSE);
+           dtc1etaphitpc[aniter]->SetMaxTPCChiNdof(4.0);
+           dtc1etaphitpc[aniter]->SetMaxImpactXY(2.4);
+           dtc1etaphitpc[aniter]->SetMaxImpactZ(3.0);
+
+
+           if(ichg==2)
+             {
+               dtc2etaphitpc[aniter]->SetStatus(AliESDtrack::kTPCin);
+               dtc2etaphitpc[aniter]->SetminTPCncls(80);
+               dtc2etaphitpc[aniter]->SetRemoveKinks(kTRUE);
+               dtc2etaphitpc[aniter]->SetLabel(kFALSE);
+               dtc2etaphitpc[aniter]->SetMaxTPCChiNdof(4.0);
+               dtc2etaphitpc[aniter]->SetMaxImpactXY(2.4);
+               dtc2etaphitpc[aniter]->SetMaxImpactZ(3.0);
+             }
+
+           
+         }
+         
+         cutPass1YPtetaphitpc[aniter] = new AliFemtoCutMonitorParticleYPt(Form("cutPass1%stpcM%i", chrgs[ichg], imult),KaonMass);
+         cutFail1YPtetaphitpc[aniter] = new AliFemtoCutMonitorParticleYPt(Form("cutFail1%stpcM%i", chrgs[ichg], imult),KaonMass);
+         dtc1etaphitpc[aniter]->AddCutMonitor(cutPass1YPtetaphitpc[aniter], cutFail1YPtetaphitpc[aniter]);
+         
+         cutPass1PIDetaphitpc[aniter] = new AliFemtoCutMonitorParticlePID(Form("cutPass1%stpcM%i", chrgs[ichg], imult),1);//0-pion,1-kaon,2-proton
+         cutFail1PIDetaphitpc[aniter] = new AliFemtoCutMonitorParticlePID(Form("cutFail1%stpcM%i", chrgs[ichg], imult),1);
+         dtc1etaphitpc[aniter]->AddCutMonitor(cutPass1PIDetaphitpc[aniter], cutFail1PIDetaphitpc[aniter]);
+
+         if(ichg==2)
+           {
+             cutPass2YPtetaphitpc[aniter] = new AliFemtoCutMonitorParticleYPt(Form("cutPass2%stpcM%i", chrgs[ichg], imult),KaonMass);
+             cutFail2YPtetaphitpc[aniter] = new AliFemtoCutMonitorParticleYPt(Form("cutFail2%stpcM%i", chrgs[ichg], imult),KaonMass);
+             dtc2etaphitpc[aniter]->AddCutMonitor(cutPass2YPtetaphitpc[aniter], cutFail2YPtetaphitpc[aniter]);
+
+             cutPass2PIDetaphitpc[aniter] = new AliFemtoCutMonitorParticlePID(Form("cutPass2%stpcM%i", chrgs[ichg], imult),1);//0-pion,1-kaon,2-proton
+             cutFail2PIDetaphitpc[aniter] = new AliFemtoCutMonitorParticlePID(Form("cutFail2%stpcM%i", chrgs[ichg], imult),1);
+             dtc2etaphitpc[aniter]->AddCutMonitor(cutPass2PIDetaphitpc[aniter], cutFail2PIDetaphitpc[aniter]);
+           }
+
+         sqpcetaphitpc[aniter] = new AliFemtoPairCutAntiGamma();
+
+         if (runtype == 0) {
+           sqpcetaphitpc[aniter]->SetShareQualityMax(1.0);
+           sqpcetaphitpc[aniter]->SetShareFractionMax(0.05);
+           sqpcetaphitpc[aniter]->SetRemoveSameLabel(kFALSE);
+           // sqpcetaphitpc[aniter]->SetMaxEEMinv(0.0);
+           // sqpcetaphitpc[aniter]->SetMaxThetaDiff(0.0);
+           //      sqpcetaphitpc[aniter]->SetTPCEntranceSepMinimum(1.5);
+           //sqpcetaphitpc[aniter]->SetRadialDistanceMinimum(0.12, 0.03);
+           //      sqpcetaphitpc[aniter]->SetEtaDifferenceMinimum(0.02);
+         }
+         else if (runtype == 1) {
+           sqpcetaphitpc[aniter]->SetShareQualityMax(1.0);
+           sqpcetaphitpc[aniter]->SetShareFractionMax(1.05);
+           sqpcetaphitpc[aniter]->SetRemoveSameLabel(kFALSE);
+           // sqpcetaphitpc[aniter]->SetMaxEEMinv(0.002);
+           // sqpcetaphitpc[aniter]->SetMaxThetaDiff(0.008);
+           //      sqpcetaphitpc[aniter]->SetTPCEntranceSepMinimum(5.0);
+           //sqpcetaphitpc[aniter]->SetRadialDistanceMinimum(1.2, 0.03);
+           //      sqpcetaphitpc[aniter]->SetEtaDifferenceMinimum(0.02);
+         }
+         else if (runtype == 2) {
+           sqpcetaphitpc[aniter]->SetUseAOD(kTRUE);
+           sqpcetaphitpc[aniter]->SetShareQualityMax(1.0);
+           sqpcetaphitpc[aniter]->SetShareFractionMax(0.05);
+           sqpcetaphitpc[aniter]->SetRemoveSameLabel(kFALSE);
+
+           if (gammacut == 0) {              
+             sqpcetaphitpc[aniter]->SetMaxEEMinv(0.0);
+             sqpcetaphitpc[aniter]->SetMaxThetaDiff(0.0);
+           }
+           else if (gammacut == 1) { 
+             sqpcetaphitpc[aniter]->SetMaxEEMinv(0.002);
+             sqpcetaphitpc[aniter]->SetMaxThetaDiff(0.008);
+           }
+
+           //phi-star cut - values from Johana
+           //      sqpcetaphitpc[aniter]->SetPhiStarDifferenceMinimum(0.012);
+           //      sqpcetaphitpc[aniter]->SetEtaDifferenceMinimum(0.017);
+
+         }
+         
+         anetaphitpc[aniter]->SetEventCut(mecetaphitpc[aniter]);
+
+         
+         if(ichg==2)
+           {
+             anetaphitpc[aniter]->SetFirstParticleCut(dtc1etaphitpc[aniter]);
+             anetaphitpc[aniter]->SetSecondParticleCut(dtc2etaphitpc[aniter]);
+           }
+         else
+           {
+             anetaphitpc[aniter]->SetFirstParticleCut(dtc1etaphitpc[aniter]);
+             anetaphitpc[aniter]->SetSecondParticleCut(dtc1etaphitpc[aniter]);
+           }
+
+         anetaphitpc[aniter]->SetPairCut(sqpcetaphitpc[aniter]);
+         
+
+         /*if (ichg == 2) {
+           ckstartpc[aniter] = new AliFemtoCorrFctnNonIdDR(Form("ckstar%stpcM%i", chrgs[ichg], imult),nbinssh,0.0,shqmax);
+           anetaphitpc[aniter]->AddCorrFctn(ckstartpc[aniter]);
+         }
+         else {  
+           cqinvtpc[aniter] = new AliFemtoQinvCorrFctn(Form("cqinv%stpcM%i", chrgs[ichg], imult),nbinssh,0.0,shqmax);
+           anetaphitpc[aniter]->AddCorrFctn(cqinvtpc[aniter]);
+           }*/
+
+          //cylmkttpc[aniter] = new AliFemtoCorrFctnDirectYlm(Form("cylm%stpcM%i", chrgs[ichg], imult),2,nbinssh, 0.0,shqmax,runshlcms);
+          //anetaphitpc[aniter]->AddCorrFctn(cylmkttpc[aniter]);
+
+         cdedpetaphi[aniter] = new AliFemtoCorrFctnDEtaDPhi(Form("cdedp%stpcM%i", chrgs[ichg], imult),45, 45);
+         anetaphitpc[aniter]->AddCorrFctn(cdedpetaphi[aniter]);
+
+         
+         if (runktdep) {
+           int ktm;
+           for (int ikt=0; ikt<numOfkTbins; ikt++) {
+
+             ktm = aniter * numOfkTbins + ikt;
+             ktpcuts[ktm] = new AliFemtoPairCutPt(ktrng[ikt], ktrng[ikt+1]);
+             
+             //              cylmkttpc[ktm] = new AliFemtoCorrFctnDirectYlm(Form("cylm%stpcM%ikT%i", chrgs[ichg], imult, ikt),3,
+             //                                                             nbinssh, 0.0,
+             //                                                             (imult>6)?shqmax*2.5:shqmax,
+             //                                                             runshlcms);
+             //              cylmkttpc[ktm]->SetPairSelectionCut(ktpcuts[ktm]);
+             //              anetaphitpc[aniter]->AddCorrFctn(cylmkttpc[ktm]);
+             
+             //cqinvkttpc[ktm] = new AliFemtoQinvCorrFctn(Form("cqinv%stpcM%ikT%i", chrgs[ichg], imult, ikt),nbinssh,0.0,(imult>6)?shqmax*2.5:shqmax);
+             //cqinvkttpc[ktm]->SetPairSelectionCut(ktpcuts[ktm]);
+             //anetaphitpc[aniter]->AddCorrFctn(cqinvkttpc[ktm]);
+
+             cdedpetaphi[ktm] = new AliFemtoCorrFctnDEtaDPhi(Form("cdedp%stpcM%ipT%i", chrgs[ichg], imult,ikt),45, 45);
+             cdedpetaphi[ktm]->SetPairSelectionCut(ktpcuts[ktm]);
+             anetaphitpc[aniter]->AddCorrFctn(cdedpetaphi[ktm]);
+
+             //              cqinvsqtpc[ktm] = new AliFemtoShareQualityCorrFctn(Form("cqinvsq%stpcM%ikT%i", chrgs[ichg], imult, ikt),nbinssh,0.0,shqmax);
+             //              cqinvsqtpc[ktm]->SetPairSelectionCut(ktpcuts[ktm]);
+             //              anetaphitpc[aniter]->AddCorrFctn(cqinvsqtpc[ktm]);
+
+             //              cqinvinnertpc[ktm] = new AliFemtoTPCInnerCorrFctn(Form("cqinvinner%stpcM%ikT%i", chrgs[ichg], imult, ikt),nbinssh,0.0,shqmax);
+             //              cqinvinnertpc[ktm]->SetPairSelectionCut(ktpcuts[ktm]);
+             //              cqinvinnertpc[ktm]->SetRadius(1.2);
+             //              anetaphitpc[aniter]->AddCorrFctn(cqinvinnertpc[ktm]);
+
+             //              if (run3d) {
+             //                cq3dlcmskttpc[ktm] = new AliFemtoCorrFctn3DLCMSSym(Form("cq3d%stpcM%ikT%i", chrgs[ichg], imult, ikt),60,(imult>3)?((imult>6)?((imult>7)?0.6:0.4):0.25):0.15);
+             //                cq3dlcmskttpc[ktm]->SetPairSelectionCut(ktpcuts[ktm]);
+             //                anetaphitpc[aniter]->AddCorrFctn(cq3dlcmskttpc[ktm]);
+             //              }
+           }
+         }
+         
+         Manager->AddAnalysis(anetaphitpc[aniter]);    
+       }
+      }
+    }
+  }
+  // *** End pion-pion (positive) analysis
+
+  return Manager;
+}                         
diff --git a/PWGCF/FEMTOSCOPY/macros/Train/DEtaDPhiNoPID/ConfigFemtoAnalysis.C b/PWGCF/FEMTOSCOPY/macros/Train/DEtaDPhiNoPID/ConfigFemtoAnalysis.C
new file mode 100644 (file)
index 0000000..0dd8c1e
--- /dev/null
@@ -0,0 +1,386 @@
+/*********************************************************************
+ *                                                                   *
+ * Configfemtoanalysis.C - configuration macro for the femtoscopic   *
+ * analysis, meant as a QA process for two-particle effects          *
+ *                                                                   *
+ * Author: Adam Kisiel (Adam.Kisiel@cern.ch)                         *
+ *                                                                   *
+ *********************************************************************/
+
+#if !defined(__CINT__) || defined(__MAKECINT_)
+#include "AliFemtoManager.h"
+#include "AliFemtoEventReaderESDChain.h"
+#include "AliFemtoEventReaderESDChainKine.h"
+#include "AliFemtoEventReaderAODChain.h"
+#include "AliFemtoSimpleAnalysis.h"
+#include "AliFemtoBasicEventCut.h"
+#include "AliFemtoESDTrackCut.h"
+#include "AliFemtoCorrFctn.h"
+#include "AliFemtoCutMonitorParticleYPt.h"
+#include "AliFemtoCutMonitorParticleVertPos.h"
+#include "AliFemtoCutMonitorParticleMomRes.h"
+#include "AliFemtoCutMonitorParticlePID.h"
+#include "AliFemtoCutMonitorEventMult.h"
+#include "AliFemtoCutMonitorEventVertex.h"
+#include "AliFemtoShareQualityTPCEntranceSepPairCut.h"
+#include "AliFemtoPairCutAntiGamma.h"
+#include "AliFemtoPairCutRadialDistance.h"
+#include "AliFemtoQinvCorrFctn.h"
+#include "AliFemtoCorrFctnNonIdDR.h"
+#include "AliFemtoShareQualityCorrFctn.h"
+#include "AliFemtoTPCInnerCorrFctn.h"
+#include "AliFemtoVertexMultAnalysis.h"
+#include "AliFemtoCorrFctn3DSpherical.h"
+#include "AliFemtoChi2CorrFctn.h"
+#include "AliFemtoCorrFctnTPCNcls.h"
+#include "AliFemtoBPLCMS3DCorrFctn.h"
+#include "AliFemtoCorrFctn3DLCMSSym.h"
+#include "AliFemtoModelBPLCMSCorrFctn.h"
+#include "AliFemtoModelCorrFctn3DSpherical.h"
+#include "AliFemtoModelGausLCMSFreezeOutGenerator.h"
+#include "AliFemtoModelGausRinvFreezeOutGenerator.h"
+#include "AliFemtoModelManager.h"
+#include "AliFemtoModelWeightGeneratorBasic.h"
+#include "AliFemtoModelWeightGeneratorLednicky.h"
+#include "AliFemtoCorrFctnDirectYlm.h"
+#include "AliFemtoModelCorrFctnDirectYlm.h"
+#include "AliFemtoModelCorrFctnSource.h"
+#include "AliFemtoCutMonitorParticlePtPDG.h"
+#include "AliFemtoKTPairCut.h"
+#incude "AliFemtoPairCutPt.h"
+#endif
+
+//________________________________________________________________________
+AliFemtoManager* ConfigFemtoAnalysis() {
+
+  double PionMass = 0.13956995;
+  double KaonMass = 0.493677;
+  double ProtonMass = 0.938272013;
+       
+
+  int runmults[10] = {1, 1, 1, 1, 1, 1, 1, 1, 1, 1};
+  int multbins[11] = {0.001, 50, 100, 200, 300, 400, 500, 600, 700, 800, 900};
+  
+  int runch[3] = {1, 1, 1};
+  const char *chrgs[3] = { "plus", "minus", "mixed" };
+  
+
+  int runktdep = 1;
+  double ktrng[3] = {0.0, 0.75, 100.0};
+  //  double ktrng[8] = {0.2, 0.3, 0.4, 0.5, 0.6, 0.7, 0.8, 1.0};
+
+  int numOfMultBins = 10;  
+  int numOfChTypes = 3;
+  int numOfkTbins = 2;
+
+  int runqinv = 1;
+  int runshlcms = 1;// 0:PRF(PAP), 1:LCMS(PP,APAP)
+
+  int runtype = 2; // Types 0 - global, 1 - ITS only, 2 - TPC Inner
+  int isrealdata = 1;
+
+  int gammacut = 1;
+  
+  double shqmax = 0.5;
+  int nbinssh = 100;
+
+  AliFemtoEventReaderAODChain *Reader = new AliFemtoEventReaderAODChain();
+  Reader->SetFilterBit(7);
+  Reader->SetCentralityPreSelection(0.001, 910);
+
+  AliFemtoManager* Manager = new AliFemtoManager();
+  Manager->SetEventReader(Reader);
+
+  AliFemtoVertexMultAnalysis    *anetaphitpc[320];
+  AliFemtoBasicEventCut         *mecetaphitpc[320];
+  AliFemtoCutMonitorEventMult   *cutPassEvMetaphitpc[320];
+  AliFemtoCutMonitorEventMult   *cutFailEvMetaphitpc[320];
+  AliFemtoCutMonitorEventVertex *cutPassEvVetaphitpc[320];
+  AliFemtoCutMonitorEventVertex *cutFailEvVetaphitpc[320];
+  AliFemtoESDTrackCut           *dtc1etaphitpc[320];
+  AliFemtoESDTrackCut           *dtc2etaphitpc[320];
+  AliFemtoCutMonitorParticleYPt *cutPass1YPtetaphitpc[320];
+  AliFemtoCutMonitorParticleYPt *cutFail1YPtetaphitpc[320];
+  AliFemtoCutMonitorParticlePID *cutPass1PIDetaphitpc[320];
+  AliFemtoCutMonitorParticlePID *cutFail1PIDetaphitpc[320];
+  AliFemtoCutMonitorParticleYPt *cutPass2YPtetaphitpc[320];
+  AliFemtoCutMonitorParticleYPt *cutFail2YPtetaphitpc[320];
+  AliFemtoCutMonitorParticlePID *cutPass2PIDetaphitpc[320];
+  AliFemtoCutMonitorParticlePID *cutFail2PIDetaphitpc[320];
+  //   AliFemtoPairCutAntiGamma      *sqpcetaphitpcdiff[320];
+  //   AliFemtoShareQualityTPCEntranceSepPairCut      *sqpcetaphitpcsame[320];
+  AliFemtoPairCutAntiGamma      *sqpcetaphitpc[320];
+  //  AliFemtoPairCutRadialDistance      *sqpcetaphitpc[320];
+  //  AliFemtoChi2CorrFctn          *cchiqinvetaphitpc[320];
+  AliFemtoPairCutPt             *ktpcuts[320];
+  AliFemtoCorrFctnDirectYlm     *cylmkttpc[320];
+  //AliFemtoCorrFctnDirectYlm     *cylmetaphitpc[320];
+  AliFemtoQinvCorrFctn          *cqinvkttpc[320];
+  AliFemtoQinvCorrFctn          *cqinvtpc[320];
+  AliFemtoCorrFctnNonIdDR       *ckstartpc[320];
+  AliFemtoCorrFctnDEtaDPhi      *cdedpetaphi[320];
+
+  //   AliFemtoCorrFctn3DLCMSSym     *cq3dlcmskttpc[20*2];
+  //   AliFemtoCorrFctnTPCNcls       *cqinvnclstpc[20];
+  //   AliFemtoShareQualityCorrFctn  *cqinvsqtpc[20*10];
+  //   AliFemtoChi2CorrFctn          *cqinvchi2tpc[20];
+  //   AliFemtoTPCInnerCorrFctn      *cqinvinnertpc[20*10];
+  
+  // *** Third QA task - HBT analysis with all pair cuts off, TPC only ***
+  // *** Begin pion-pion (positive) analysis ***
+  int aniter = 0;  
+
+  for (int imult = 0; imult < numOfMultBins; imult++) {
+    if (runmults[imult]) {
+
+      for (int ichg = 0; ichg < numOfChTypes; ichg++) {
+       if (runch[ichg]) {
+
+         aniter = ichg * numOfMultBins + imult;
+         anetaphitpc[aniter] = new AliFemtoVertexMultAnalysis(8, -8.0, 8.0, 4, multbins[imult], multbins[imult+1]);
+         anetaphitpc[aniter]->SetNumEventsToMix(5);
+         anetaphitpc[aniter]->SetMinSizePartCollection(1);
+
+         mecetaphitpc[aniter] = new AliFemtoBasicEventCut();
+         mecetaphitpc[aniter]->SetEventMult(0.001,100000);
+         mecetaphitpc[aniter]->SetVertZPos(-8,8);
+
+         if (isrealdata)
+           mecetaphitpc[aniter]->SetAcceptOnlyPhysics(kTRUE);
+                 
+         cutPassEvMetaphitpc[aniter] = new AliFemtoCutMonitorEventMult(Form("cutPass%stpcM%i", chrgs[ichg], imult));
+         cutFailEvMetaphitpc[aniter] = new AliFemtoCutMonitorEventMult(Form("cutFail%stpcM%i", chrgs[ichg], imult));
+         mecetaphitpc[aniter]->AddCutMonitor(cutPassEvMetaphitpc[aniter], cutFailEvMetaphitpc[aniter]);
+         
+         cutPassEvVetaphitpc[aniter] = new AliFemtoCutMonitorEventVertex(Form("cutPass%stpcM%i", chrgs[ichg], imult));
+         cutFailEvVetaphitpc[aniter] = new AliFemtoCutMonitorEventVertex(Form("cutFail%stpcM%i", chrgs[ichg], imult));
+         mecetaphitpc[aniter]->AddCutMonitor(cutPassEvVetaphitpc[aniter], cutFailEvVetaphitpc[aniter]);
+         
+         dtc1etaphitpc[aniter] = new AliFemtoESDTrackCut();
+         dtc2etaphitpc[aniter] = new AliFemtoESDTrackCut();
+
+         if (ichg == 0)
+           {
+             dtc1etaphitpc[aniter]->SetCharge(1.0);
+             //dtc2etaphitpc[aniter]->SetCharge(1.0);
+           }
+         else if (ichg == 1)
+           {
+             dtc1etaphitpc[aniter]->SetCharge(-1.0);
+             //dtc2etaphitpc[aniter]->SetCharge(-1.0);
+           }
+         else if (ichg == 2) 
+           {
+             dtc1etaphitpc[aniter]->SetCharge(-1.0);
+             dtc2etaphitpc[aniter]->SetCharge(1.0);
+           }
+         
+         dtc1etaphitpc[aniter]->SetEta(-0.8,0.8);
+         //dtc1etaphitpc[aniter]->SetMass(KaonMass);     
+         //dtc1etaphitpc[aniter]->SetMostProbableKaon();
+    
+         if(ichg==2)
+           {
+             dtc2etaphitpc[aniter]->SetEta(-0.8,0.8);
+             //dtc2etaphitpc[aniter]->SetMass(KaonMass);         
+             //dtc2etaphitpc[aniter]->SetMostProbableKaon();
+           }
+
+         
+         // Track quality cuts
+
+         if (runtype == 0) {
+           dtc1etaphitpc[aniter]->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+           //      dtc1etaphitpc[aniter]->SetStatus(AliESDtrack::kTPCrefit);
+           //    dtc1etaphitpc[aniter]->SetStatus(AliESDtrack::kITSrefit);
+           dtc1etaphitpc[aniter]->SetminTPCncls(80);
+           dtc1etaphitpc[aniter]->SetRemoveKinks(kTRUE);
+           dtc1etaphitpc[aniter]->SetLabel(kFALSE);
+           //    dtc1etaphitpc[aniter]->SetMaxITSChiNdof(6.0);
+           dtc1etaphitpc[aniter]->SetMaxTPCChiNdof(4.0);
+           dtc1etaphitpc[aniter]->SetMaxImpactXY(0.2);
+           //            dtc1etaphitpc[aniter]->SetMaxImpactXYPtDep(0.0182, 0.0350, -1.01);
+           dtc1etaphitpc[aniter]->SetMaxImpactZ(0.15);
+           //      dtc1etaphitpc[aniter]->SetMaxSigmaToVertex(6.0);
+         }
+         else if (runtype == 1) {
+           //      dtc1etaphitpc[aniter]->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+           //    dtc1etaphitpc[aniter]->SetStatus(AliESDtrack::kTPCrefit);
+           //      dtc1etaphitpc[aniter]->SetStatus(AliESDtrack::kITSrefit|AliESDtrack::kITSpureSA);
+           //      dtc1etaphitpc[aniter]->SetminTPCncls(70);
+           dtc1etaphitpc[aniter]->SetStatus(AliESDtrack::kITSrefit);
+           dtc1etaphitpc[aniter]->SetRemoveKinks(kTRUE);
+           dtc1etaphitpc[aniter]->SetLabel(kFALSE);
+           //    dtc1etaphitpc[aniter]->SetMaxITSChiNdof(6.0);
+           //      dtc1etaphitpc[aniter]->SetMaxTPCChiNdof(6.0);
+           dtc1etaphitpc[aniter]->SetMaxImpactXY(0.2);
+           dtc1etaphitpc[aniter]->SetMaxImpactZ(0.25);
+           //      dtc1etaphitpc[aniter]->SetMaxSigmaToVertex(6.0);
+         }
+         else if (runtype == 2) {
+           dtc1etaphitpc[aniter]->SetStatus(AliESDtrack::kTPCin);
+           dtc1etaphitpc[aniter]->SetminTPCncls(80);
+           dtc1etaphitpc[aniter]->SetRemoveKinks(kTRUE);
+           dtc1etaphitpc[aniter]->SetLabel(kFALSE);
+           dtc1etaphitpc[aniter]->SetMaxTPCChiNdof(4.0);
+           dtc1etaphitpc[aniter]->SetMaxImpactXY(0.2);
+           dtc1etaphitpc[aniter]->SetMaxImpactZ(0.25);
+
+
+           if(ichg==2)
+             {
+               dtc2etaphitpc[aniter]->SetStatus(AliESDtrack::kTPCin);
+               dtc2etaphitpc[aniter]->SetminTPCncls(80);
+               dtc2etaphitpc[aniter]->SetRemoveKinks(kTRUE);
+               dtc2etaphitpc[aniter]->SetLabel(kFALSE);
+               dtc2etaphitpc[aniter]->SetMaxTPCChiNdof(4.0);
+               dtc2etaphitpc[aniter]->SetMaxImpactXY(0.2);
+               dtc2etaphitpc[aniter]->SetMaxImpactZ(0.25);
+             }
+
+           
+         }
+         
+         cutPass1YPtetaphitpc[aniter] = new AliFemtoCutMonitorParticleYPt(Form("cutPass1%stpcM%i", chrgs[ichg], imult),PionMass);
+         cutFail1YPtetaphitpc[aniter] = new AliFemtoCutMonitorParticleYPt(Form("cutFail1%stpcM%i", chrgs[ichg], imult),PionMass);
+         dtc1etaphitpc[aniter]->AddCutMonitor(cutPass1YPtetaphitpc[aniter], cutFail1YPtetaphitpc[aniter]);
+         
+         //cutPass1PIDetaphitpc[aniter] = new AliFemtoCutMonitorParticlePID(Form("cutPass1%stpcM%i", chrgs[ichg], imult),0);//0-pion,1-kaon,2-proton
+         //cutFail1PIDetaphitpc[aniter] = new AliFemtoCutMonitorParticlePID(Form("cutFail1%stpcM%i", chrgs[ichg], imult),0);
+         //dtc1etaphitpc[aniter]->AddCutMonitor(cutPass1PIDetaphitpc[aniter], cutFail1PIDetaphitpc[aniter]);
+
+         if(ichg==2)
+           {
+             cutPass2YPtetaphitpc[aniter] = new AliFemtoCutMonitorParticleYPt(Form("cutPass2%stpcM%i", chrgs[ichg], imult),PionMass);
+             cutFail2YPtetaphitpc[aniter] = new AliFemtoCutMonitorParticleYPt(Form("cutFail2%stpcM%i", chrgs[ichg], imult),PionMass);
+             dtc2etaphitpc[aniter]->AddCutMonitor(cutPass2YPtetaphitpc[aniter], cutFail2YPtetaphitpc[aniter]);
+
+             //cutPass2PIDetaphitpc[aniter] = new AliFemtoCutMonitorParticlePID(Form("cutPass2%stpcM%i", chrgs[ichg], imult),0);//0-pion,1-kaon,2-proton
+             //cutFail2PIDetaphitpc[aniter] = new AliFemtoCutMonitorParticlePID(Form("cutFail2%stpcM%i", chrgs[ichg], imult),0);
+             //dtc2etaphitpc[aniter]->AddCutMonitor(cutPass2PIDetaphitpc[aniter], cutFail2PIDetaphitpc[aniter]);
+           }
+
+         sqpcetaphitpc[aniter] = new AliFemtoPairCutAntiGamma();
+
+         if (runtype == 0) {
+           sqpcetaphitpc[aniter]->SetShareQualityMax(1.0);
+           sqpcetaphitpc[aniter]->SetShareFractionMax(0.05);
+           sqpcetaphitpc[aniter]->SetRemoveSameLabel(kFALSE);
+           // sqpcetaphitpc[aniter]->SetMaxEEMinv(0.0);
+           // sqpcetaphitpc[aniter]->SetMaxThetaDiff(0.0);
+           //      sqpcetaphitpc[aniter]->SetTPCEntranceSepMinimum(1.5);
+           //sqpcetaphitpc[aniter]->SetRadialDistanceMinimum(0.12, 0.03);
+           //      sqpcetaphitpc[aniter]->SetEtaDifferenceMinimum(0.02);
+         }
+         else if (runtype == 1) {
+           sqpcetaphitpc[aniter]->SetShareQualityMax(1.0);
+           sqpcetaphitpc[aniter]->SetShareFractionMax(1.05);
+           sqpcetaphitpc[aniter]->SetRemoveSameLabel(kFALSE);
+           // sqpcetaphitpc[aniter]->SetMaxEEMinv(0.002);
+           // sqpcetaphitpc[aniter]->SetMaxThetaDiff(0.008);
+           //      sqpcetaphitpc[aniter]->SetTPCEntranceSepMinimum(5.0);
+           //sqpcetaphitpc[aniter]->SetRadialDistanceMinimum(1.2, 0.03);
+           //      sqpcetaphitpc[aniter]->SetEtaDifferenceMinimum(0.02);
+         }
+         else if (runtype == 2) {
+           sqpcetaphitpc[aniter]->SetUseAOD(kTRUE);
+           sqpcetaphitpc[aniter]->SetShareQualityMax(1.0);
+           sqpcetaphitpc[aniter]->SetShareFractionMax(0.05);
+           sqpcetaphitpc[aniter]->SetRemoveSameLabel(kFALSE);
+
+           if (gammacut == 0) {              
+             sqpcetaphitpc[aniter]->SetMaxEEMinv(0.0);
+             sqpcetaphitpc[aniter]->SetMaxThetaDiff(0.0);
+           }
+           else if (gammacut == 1) { 
+             sqpcetaphitpc[aniter]->SetMaxEEMinv(0.002);
+             sqpcetaphitpc[aniter]->SetMaxThetaDiff(0.008);
+           }
+
+           //phi-star cut - values from Johana
+           //      sqpcetaphitpc[aniter]->SetPhiStarDifferenceMinimum(0.012);
+           //      sqpcetaphitpc[aniter]->SetEtaDifferenceMinimum(0.017);
+
+         }
+         
+         anetaphitpc[aniter]->SetEventCut(mecetaphitpc[aniter]);
+
+         
+         if(ichg==2)
+           {
+             anetaphitpc[aniter]->SetFirstParticleCut(dtc1etaphitpc[aniter]);
+             anetaphitpc[aniter]->SetSecondParticleCut(dtc2etaphitpc[aniter]);
+           }
+         else
+           {
+             anetaphitpc[aniter]->SetFirstParticleCut(dtc1etaphitpc[aniter]);
+             anetaphitpc[aniter]->SetSecondParticleCut(dtc1etaphitpc[aniter]);
+           }
+
+         anetaphitpc[aniter]->SetPairCut(sqpcetaphitpc[aniter]);
+         
+
+         /*if (ichg == 2) {
+           ckstartpc[aniter] = new AliFemtoCorrFctnNonIdDR(Form("ckstar%stpcM%i", chrgs[ichg], imult),nbinssh,0.0,shqmax);
+           anetaphitpc[aniter]->AddCorrFctn(ckstartpc[aniter]);
+         }
+         else {  
+           cqinvtpc[aniter] = new AliFemtoQinvCorrFctn(Form("cqinv%stpcM%i", chrgs[ichg], imult),nbinssh,0.0,shqmax);
+           anetaphitpc[aniter]->AddCorrFctn(cqinvtpc[aniter]);
+           }*/
+
+          //cylmkttpc[aniter] = new AliFemtoCorrFctnDirectYlm(Form("cylm%stpcM%i", chrgs[ichg], imult),2,nbinssh, 0.0,shqmax,runshlcms);
+          //anetaphitpc[aniter]->AddCorrFctn(cylmkttpc[aniter]);
+
+         cdedpetaphi[aniter] = new AliFemtoCorrFctnDEtaDPhi(Form("cdedp%stpcM%i", chrgs[ichg], imult),45, 45);
+         anetaphitpc[aniter]->AddCorrFctn(cdedpetaphi[aniter]);
+
+         
+         if (runktdep) {
+           int ktm;
+           for (int ikt=0; ikt<numOfkTbins; ikt++) {
+
+             ktm = aniter * numOfkTbins + ikt;
+             ktpcuts[ktm] = new AliFemtoPairCutPt(ktrng[ikt], ktrng[ikt+1]);
+             
+             //              cylmkttpc[ktm] = new AliFemtoCorrFctnDirectYlm(Form("cylm%stpcM%ikT%i", chrgs[ichg], imult, ikt),3,
+             //                                                             nbinssh, 0.0,
+             //                                                             (imult>6)?shqmax*2.5:shqmax,
+             //                                                             runshlcms);
+             //              cylmkttpc[ktm]->SetPairSelectionCut(ktpcuts[ktm]);
+             //              anetaphitpc[aniter]->AddCorrFctn(cylmkttpc[ktm]);
+             
+             //cqinvkttpc[ktm] = new AliFemtoQinvCorrFctn(Form("cqinv%stpcM%ikT%i", chrgs[ichg], imult, ikt),nbinssh,0.0,(imult>6)?shqmax*2.5:shqmax);
+             //cqinvkttpc[ktm]->SetPairSelectionCut(ktpcuts[ktm]);
+             //anetaphitpc[aniter]->AddCorrFctn(cqinvkttpc[ktm]);
+
+             cdedpetaphi[ktm] = new AliFemtoCorrFctnDEtaDPhi(Form("cdedp%stpcM%ipT%i", chrgs[ichg], imult,ikt),45, 45);
+             cdedpetaphi[ktm]->SetPairSelectionCut(ktpcuts[ktm]);
+             anetaphitpc[aniter]->AddCorrFctn(cdedpetaphi[ktm]);
+
+             //              cqinvsqtpc[ktm] = new AliFemtoShareQualityCorrFctn(Form("cqinvsq%stpcM%ikT%i", chrgs[ichg], imult, ikt),nbinssh,0.0,shqmax);
+             //              cqinvsqtpc[ktm]->SetPairSelectionCut(ktpcuts[ktm]);
+             //              anetaphitpc[aniter]->AddCorrFctn(cqinvsqtpc[ktm]);
+
+             //              cqinvinnertpc[ktm] = new AliFemtoTPCInnerCorrFctn(Form("cqinvinner%stpcM%ikT%i", chrgs[ichg], imult, ikt),nbinssh,0.0,shqmax);
+             //              cqinvinnertpc[ktm]->SetPairSelectionCut(ktpcuts[ktm]);
+             //              cqinvinnertpc[ktm]->SetRadius(1.2);
+             //              anetaphitpc[aniter]->AddCorrFctn(cqinvinnertpc[ktm]);
+
+             //              if (run3d) {
+             //                cq3dlcmskttpc[ktm] = new AliFemtoCorrFctn3DLCMSSym(Form("cq3d%stpcM%ikT%i", chrgs[ichg], imult, ikt),60,(imult>3)?((imult>6)?((imult>7)?0.6:0.4):0.25):0.15);
+             //                cq3dlcmskttpc[ktm]->SetPairSelectionCut(ktpcuts[ktm]);
+             //                anetaphitpc[aniter]->AddCorrFctn(cq3dlcmskttpc[ktm]);
+             //              }
+           }
+         }
+         
+         Manager->AddAnalysis(anetaphitpc[aniter]);    
+       }
+      }
+    }
+  }
+  // *** End pion-pion (positive) analysis
+
+  return Manager;
+}                         
diff --git a/PWGCF/FEMTOSCOPY/macros/Train/DataTrain1/ConfigFemtoAnalysis.C b/PWGCF/FEMTOSCOPY/macros/Train/DataTrain1/ConfigFemtoAnalysis.C
new file mode 100644 (file)
index 0000000..19f66e5
--- /dev/null
@@ -0,0 +1,539 @@
+/*********************************************************************
+ *                                                                   *
+ * ConfigFemtoAnalysis.C - configuration macro for the femtoscopic   *
+ * analysis, to be run in the analysis train.                        *
+ * Assumed input data: large (>10M) sample of MC pp events           *
+ * Inluded analysis:                                                 *
+ *    - positive pion HBT, 3 kt bins, 1D+3D functions                *
+ *    - negative pion HBT, 3 kt bins, 1D+3D functions                *
+ *    - positive kaon HBT, 1 kt bin,  1D+3D functions                *
+ *                                                                   *
+ * Author: Adam Kisiel (Adam.Kisiel@cern.ch)                         *
+ *                                                                   *
+ *********************************************************************/
+
+#if !defined(__CINT__) || defined(__MAKECINT_)
+#include "AliFemtoManager.h"
+#include "AliFemtoEventReaderESDChain.h"
+#include "AliFemtoEventReaderESDChainKine.h"
+#include "AliFemtoSimpleAnalysis.h"
+#include "AliFemtoBasicEventCut.h"
+#include "AliFemtoESDTrackCut.h"
+#include "AliFemtoCorrFctn.h"
+#include "AliFemtoCutMonitorParticleYPt.h"
+#include "AliFemtoCutMonitorParticleVertPos.h"
+#include "AliFemtoCutMonitorParticleMomRes.h"
+#include "AliFemtoCutMonitorEventMult.h"
+#include "AliFemtoCutMonitorEventVertex.h"
+#include "AliFemtoShareQualityTPCEntranceSepPairCut.h"
+#include "AliFemtoQinvCorrFctn.h"
+#include "AliFemtoShareQualityCorrFctn.h"
+#include "AliFemtoTPCInnerCorrFctn.h"
+#include "AliFemtoVertexMultAnalysis.h"
+#include "AliFemtoCorrFctn3DSpherical.h"
+#include "AliFemtoChi2CorrFctn.h"
+#include "AliFemtoCorrFctnTPCNcls.h"
+#include "AliFemtoModelBPLCMSCorrFctn.h"
+#include "AliFemtoModelCorrFctn3DSpherical.h"
+#include "AliFemtoModelGausLCMSFreezeOutGenerator.h"
+#include "AliFemtoModelGausRinvFreezeOutGenerator.h"
+#include "AliFemtoModelManager.h"
+#include "AliFemtoModelWeightGeneratorBasic.h"
+#include "AliFemtoModelWeightGeneratorLednicky.h"
+#include "AliFemtoCorrFctnDirectYlm.h"
+#include "AliFemtoModelCorrFctnDirectYlm.h"
+#include "AliFemtoModelCorrFctnSource.h"
+#include "AliFemtoCutMonitorParticlePtPDG.h"
+#include "AliFemtoKTPairCut.h"
+#endif
+
+//________________________________________________________________________
+AliFemtoManager* ConfigFemtoAnalysis() {
+
+  double PionMass = 0.13956995;
+  double KaonMass = 0.493677;
+  
+  AliFemtoEventReaderESDChain* Reader=new AliFemtoEventReaderESDChain();
+  Reader->SetConstrained(true);
+  Reader->SetUseTPCOnly(false);
+
+  AliFemtoManager* Manager=new AliFemtoManager();
+  Manager->SetEventReader(Reader);
+
+  int runPositivePions = 1;
+  int runNegativePions = 1;
+  int runPositiveKaons = 1;
+  int runNegativeKaons = 1;
+  int runPositiveNegativeKaons = 1;
+
+  // Z vertex mixing settings
+  int nZVertexBins = 4;
+  Double_t minZVertex = -10.0;
+  Double_t maxZVertex = 10.0;
+
+  if (runPositivePions) {
+    // *** Begin pion-pion (positive) analysis ***
+    AliFemtoVertexMultAnalysis *anpip = new AliFemtoVertexMultAnalysis(nZVertexBins, minZVertex, maxZVertex, 1, 2, 200000);
+    anpip->SetNumEventsToMix(10);
+    anpip->SetMinSizePartCollection(2);
+
+    AliFemtoBasicEventCut* mecpip = new AliFemtoBasicEventCut();
+    mecpip->SetEventMult(2,100000);
+    mecpip->SetVertZPos(-1000,1000);
+       
+    AliFemtoESDTrackCut* dtcpip = new AliFemtoESDTrackCut();
+    dtcpip->SetPidProbPion(0.2,1.001);
+    dtcpip->SetPidProbMuon(0.0,1.0);
+    dtcpip->SetPidProbKaon(0.0,1.0);
+    dtcpip->SetPidProbProton(0.0,1.0);
+    dtcpip->SetCharge(1.0);
+    dtcpip->SetPt(0.05,1.0);
+    dtcpip->SetRapidity(-0.9,0.9);
+    dtcpip->SetMass(PionMass);
+    // Track quality cuts
+    dtcpip->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+    //  dtcpip->SetStatus(AliESDtrack::kTPCrefit);
+    dtcpip->SetminTPCncls(50);
+    dtcpip->SetRemoveKinks(kTRUE);
+    dtcpip->SetLabel(kFALSE);
+    dtcpip->SetMaxITSChiNdof(2.5);
+    dtcpip->SetMaxTPCChiNdof(3.0);
+    dtcpip->SetMaxImpactXY(3.0);
+    dtcpip->SetMaxImpactZ(3.0);
+
+    // Track monitors
+    AliFemtoCutMonitorParticleYPt *cutPassYPtpip = new AliFemtoCutMonitorParticleYPt("cutPasspip", 0.13957);
+    AliFemtoCutMonitorParticleYPt *cutFailYPtpip = new AliFemtoCutMonitorParticleYPt("cutFailpip", 0.13957);
+    dtcpip->AddCutMonitor(cutPassYPtpip, cutFailYPtpip);
+
+    AliFemtoCutMonitorEventMult *cutPassEvMpip = new AliFemtoCutMonitorEventMult("cutPasspip");
+    AliFemtoCutMonitorEventMult *cutFailEvMpip = new AliFemtoCutMonitorEventMult("cutFailpip");
+    mecpip->AddCutMonitor(cutPassEvMpip, cutFailEvMpip);
+
+    AliFemtoCutMonitorEventVertex *cutPassEvVpip = new AliFemtoCutMonitorEventVertex("cutPasspip");
+    AliFemtoCutMonitorEventVertex *cutFailEvVpip = new AliFemtoCutMonitorEventVertex("cutFailpip");
+    mecpip->AddCutMonitor(cutPassEvVpip, cutFailEvVpip);
+
+    // Pair cut
+    AliFemtoShareQualityTPCEntranceSepPairCut *sqpcpip = new AliFemtoShareQualityTPCEntranceSepPairCut();
+    sqpcpip->SetShareQualityMax(0.0);
+    sqpcpip->SetShareFractionMax(0.02);
+    sqpcpip->SetRemoveSameLabel(kFALSE);
+    sqpcpip->SetTPCEntranceSepMinimum(2.0);
+
+    anpip->SetEventCut(mecpip);
+    anpip->SetFirstParticleCut(dtcpip);
+    anpip->SetSecondParticleCut(dtcpip);
+    anpip->SetPairCut(sqpcpip);
+
+    // Two-track quality monitoring
+    AliFemtoShareQualityCorrFctn *csqqinvpip= new AliFemtoShareQualityCorrFctn("sqqinvcfpip",40,0.0,0.4);
+    AliFemtoChi2CorrFctn *cchiqinvpip= new AliFemtoChi2CorrFctn("chicfpip",40,0.0,0.4);
+    AliFemtoCorrFctnTPCNcls *cqtpcnclspip = new AliFemtoCorrFctnTPCNcls("cqtpcnclspip",40,0.0,0.4);
+
+    // Intrdouce kT binning
+    AliFemtoKTPairCut *ktpairkT1pip = new AliFemtoKTPairCut(0.05,0.27);
+    AliFemtoKTPairCut *ktpairkT2pip = new AliFemtoKTPairCut(0.27,0.37);
+    AliFemtoKTPairCut *ktpairkT3pip = new AliFemtoKTPairCut(0.37,1.0);
+
+    // Purely experimental correlation function
+    AliFemtoCorrFctnDirectYlm *cylmkT1pip = new AliFemtoCorrFctnDirectYlm("cylmkT1pip",3,80,0.0,0.8,1);
+    cylmkT1pip->SetPairSelectionCut(ktpairkT1pip);
+    anpip->AddCorrFctn(cylmkT1pip);
+    
+    AliFemtoCorrFctnDirectYlm *cylmkT2pip = new AliFemtoCorrFctnDirectYlm("cylmkT2pip",3,80,0.0,0.8,1);
+    cylmkT2pip->SetPairSelectionCut(ktpairkT2pip);
+    anpip->AddCorrFctn(cylmkT2pip);
+    
+    AliFemtoCorrFctnDirectYlm *cylmkT3pip = new AliFemtoCorrFctnDirectYlm("cylmkT3pip",3,80,0.0,0.8,1);
+    cylmkT3pip->SetPairSelectionCut(ktpairkT3pip);
+    anpip->AddCorrFctn(cylmkT3pip);
+
+    AliFemtoQinvCorrFctn *cqinvkt1pip = new AliFemtoQinvCorrFctn("qinvcfkt1pip", 100,0.0,1.0);
+    cqinvkt1pip->SetPairSelectionCut(ktpairkT1pip);
+    anpip->AddCorrFctn(cqinvkt1pip);
+
+    AliFemtoQinvCorrFctn *cqinvkt2pip = new AliFemtoQinvCorrFctn("qinvcfkt2pip", 100,0.0,1.0);
+    cqinvkt2pip->SetPairSelectionCut(ktpairkT2pip);
+    anpip->AddCorrFctn(cqinvkt2pip);
+
+    AliFemtoQinvCorrFctn *cqinvkt3pip = new AliFemtoQinvCorrFctn("qinvcfkt3pip", 100,0.0,1.0);
+    cqinvkt3pip->SetPairSelectionCut(ktpairkT3pip);
+    anpip->AddCorrFctn(cqinvkt3pip);
+
+    // Add correlation functions to the analysis 
+    anpip->AddCorrFctn(csqqinvpip);
+    anpip->AddCorrFctn(cchiqinvpip);
+    anpip->AddCorrFctn(cqtpcnclspip);
+
+    Manager->AddAnalysis(anpip);       
+
+    // *** End pion-pion (positive) analysis
+  }
+
+  if (runNegativePions) {
+    // *** Begin pion-pion (negative) analysis ***
+    AliFemtoVertexMultAnalysis *anpim = new AliFemtoVertexMultAnalysis(nZVertexBins, minZVertex, maxZVertex, 1, 2, 200000);
+    anpim->SetNumEventsToMix(10);
+    anpim->SetMinSizePartCollection(2);
+
+    AliFemtoBasicEventCut* mecpim = new AliFemtoBasicEventCut();
+    mecpim->SetEventMult(2,100000);
+    mecpim->SetVertZPos(-1000,1000);
+       
+    AliFemtoESDTrackCut* dtcpim = new AliFemtoESDTrackCut();
+    dtcpim->SetPidProbPion(0.2,1.001);
+    dtcpim->SetPidProbMuon(0.0,1.0);
+    dtcpim->SetPidProbKaon(0.0,1.0);
+    dtcpim->SetPidProbProton(0.0,1.0);
+    dtcpim->SetCharge(1.0);
+    dtcpim->SetPt(0.05,1.0);
+    dtcpim->SetRapidity(-0.9,0.9);
+    dtcpim->SetMass(PionMass);
+    // Track quality cuts
+    dtcpim->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+    //  dtcpim->SetStatus(AliESDtrack::kTPCrefit);
+    dtcpim->SetminTPCncls(50);
+    dtcpim->SetRemoveKinks(kTRUE);
+    dtcpim->SetLabel(kFALSE);
+    dtcpim->SetMaxITSChiNdof(2.5);
+    dtcpim->SetMaxTPCChiNdof(3.0);
+    dtcpim->SetMaxImpactXY(3.0);
+    dtcpim->SetMaxImpactZ(3.0);
+
+    // Track monitors
+    AliFemtoCutMonitorParticleYPt *cutPassYPtpim = new AliFemtoCutMonitorParticleYPt("cutPasspim", 0.13957);
+    AliFemtoCutMonitorParticleYPt *cutFailYPtpim = new AliFemtoCutMonitorParticleYPt("cutFailpim", 0.13957);
+    dtcpim->AddCutMonitor(cutPassYPtpim, cutFailYPtpim);
+
+    AliFemtoCutMonitorEventMult *cutPassEvMpim = new AliFemtoCutMonitorEventMult("cutPasspim");
+    AliFemtoCutMonitorEventMult *cutFailEvMpim = new AliFemtoCutMonitorEventMult("cutFailpim");
+    mecpim->AddCutMonitor(cutPassEvMpim, cutFailEvMpim);
+
+    AliFemtoCutMonitorEventVertex *cutPassEvVpim = new AliFemtoCutMonitorEventVertex("cutPasspim");
+    AliFemtoCutMonitorEventVertex *cutFailEvVpim = new AliFemtoCutMonitorEventVertex("cutFailpim");
+    mecpim->AddCutMonitor(cutPassEvVpim, cutFailEvVpim);
+
+    // Pair cut
+    AliFemtoShareQualityTPCEntranceSepPairCut *sqpcpim = new AliFemtoShareQualityTPCEntranceSepPairCut();
+    sqpcpim->SetShareQualityMax(0.0);
+    sqpcpim->SetShareFractionMax(0.02);
+    sqpcpim->SetRemoveSameLabel(kFALSE);
+    sqpcpim->SetTPCEntranceSepMinimum(2.0);
+
+    anpim->SetEventCut(mecpim);
+    anpim->SetFirstParticleCut(dtcpim);
+    anpim->SetSecondParticleCut(dtcpim);
+    anpim->SetPairCut(sqpcpim);
+
+    // Two-track quality monitoring
+    AliFemtoShareQualityCorrFctn *csqqinvpim= new AliFemtoShareQualityCorrFctn("sqqinvcfpim",40,0.0,0.4);
+    AliFemtoChi2CorrFctn *cchiqinvpim= new AliFemtoChi2CorrFctn("chicfpim",40,0.0,0.4);
+    AliFemtoCorrFctnTPCNcls *cqtpcnclspim = new AliFemtoCorrFctnTPCNcls("cqtpcnclspim",40,0.0,0.4);
+
+    // Intrdouce kT binning
+    AliFemtoKTPairCut *ktpairkT1pim = new AliFemtoKTPairCut(0.05,0.27);
+    AliFemtoKTPairCut *ktpairkT2pim = new AliFemtoKTPairCut(0.27,0.37);
+    AliFemtoKTPairCut *ktpairkT3pim = new AliFemtoKTPairCut(0.37,1.0);
+
+    // Purely experimental correlation function
+    AliFemtoCorrFctnDirectYlm *cylmkT1pim = new AliFemtoCorrFctnDirectYlm("cylmkT1pim",3,80,0.0,0.8,1);
+    cylmkT1pim->SetPairSelectionCut(ktpairkT1pim);
+    anpim->AddCorrFctn(cylmkT1pim);
+    
+    AliFemtoCorrFctnDirectYlm *cylmkT2pim = new AliFemtoCorrFctnDirectYlm("cylmkT2pim",3,80,0.0,0.8,1);
+    cylmkT2pim->SetPairSelectionCut(ktpairkT2pim);
+    anpim->AddCorrFctn(cylmkT2pim);
+    
+    AliFemtoCorrFctnDirectYlm *cylmkT3pim = new AliFemtoCorrFctnDirectYlm("cylmkT3pim",3,80,0.0,0.8,1);
+    cylmkT3pim->SetPairSelectionCut(ktpairkT3pim);
+    anpim->AddCorrFctn(cylmkT3pim);
+
+    AliFemtoQinvCorrFctn *cqinvkt1pim = new AliFemtoQinvCorrFctn("qinvcfkt1pim", 100,0.0,1.0);
+    cqinvkt1pim->SetPairSelectionCut(ktpairkT1pim);
+    anpim->AddCorrFctn(cqinvkt1pim);
+
+    AliFemtoQinvCorrFctn *cqinvkt2pim = new AliFemtoQinvCorrFctn("qinvcfkt2pim", 100,0.0,1.0);
+    cqinvkt2pim->SetPairSelectionCut(ktpairkT2pim);
+    anpim->AddCorrFctn(cqinvkt2pim);
+
+    AliFemtoQinvCorrFctn *cqinvkt3pim = new AliFemtoQinvCorrFctn("qinvcfkt3pim", 100,0.0,1.0);
+    cqinvkt3pim->SetPairSelectionCut(ktpairkT3pim);
+    anpim->AddCorrFctn(cqinvkt3pim);
+
+    // Add correlation functions to the analysis 
+    anpim->AddCorrFctn(csqqinvpim);
+    anpim->AddCorrFctn(cchiqinvpim);
+    anpim->AddCorrFctn(cqtpcnclspim);
+
+    Manager->AddAnalysis(anpim);       
+
+    // *** End pion-pion (negative) analysis
+  }
+
+  if (runPositiveKaons) {
+    // *** Begin Kaon-Kaon (positive) analysis
+    AliFemtoVertexMultAnalysis *ankp = new AliFemtoVertexMultAnalysis(nZVertexBins, minZVertex, maxZVertex, 1, 2, 20000);
+    ankp->SetNumEventsToMix(5);
+    ankp->SetMinSizePartCollection(2);
+
+    AliFemtoBasicEventCut* meckp = new AliFemtoBasicEventCut();
+    meckp->SetEventMult(1,100000);
+    meckp->SetVertZPos(-1000,1000);
+       
+    AliFemtoESDTrackCut* dtckp = new AliFemtoESDTrackCut();
+    dtckp->SetPidProbKaon(0.7,1.001);
+    dtckp->SetPidProbMuon(0.0,0.5);
+    dtckp->SetPidProbPion(0.0,0.5);
+    dtckp->SetPidProbProton(0.0,0.5);
+    dtckp->SetCharge(1.0);
+    dtckp->SetMostProbableKaon();
+    dtckp->SetMomRangeTOFpidIs(0.6,10000.);
+    dtckp->SetPt(0.15,2.0);
+    dtckp->SetMass(KaonMass);
+    // Track quality cuts
+    dtckp->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+    dtckp->SetminTPCncls(50);
+    dtckp->SetRemoveKinks(kTRUE);
+    dtckp->SetLabel(kFALSE);
+    dtckp->SetMaxITSChiNdof(2.5);
+    dtckp->SetMaxTPCChiNdof(3.0);
+    dtckp->SetMaxImpactXY(3.0);
+    dtckp->SetMaxImpactZ(3.0);
+
+    AliFemtoCutMonitorParticleYPt *cutPassYPtkp = new AliFemtoCutMonitorParticleYPt("cutPasskp", 0.493677);
+    AliFemtoCutMonitorParticleYPt *cutFailYPtkp = new AliFemtoCutMonitorParticleYPt("cutFailkp", 0.493677);
+    dtckp->AddCutMonitor(cutPassYPtkp, cutFailYPtkp);
+
+    AliFemtoCutMonitorParticlePtPDG *cutPassPidkp = new AliFemtoCutMonitorParticlePtPDG("cutPasskp", 0.493677);
+    AliFemtoCutMonitorParticlePtPDG *cutFailPidkp = new AliFemtoCutMonitorParticlePtPDG("cutFailkp", 0.493677);
+    dtckp->AddCutMonitor(cutPassPidkp, cutFailPidkp);
+
+    AliFemtoCutMonitorParticleMomRes *cutPassMRkp = new AliFemtoCutMonitorParticleMomRes("cutPasskp");
+    AliFemtoCutMonitorParticleMomRes *cutFailMRkp = new AliFemtoCutMonitorParticleMomRes("cutFailkp");
+    dtckp->AddCutMonitor(cutPassMRkp, cutFailMRkp);
+
+    AliFemtoCutMonitorParticleVertPos *cutPassVPkp = new AliFemtoCutMonitorParticleVertPos("cutPasskp");
+    AliFemtoCutMonitorParticleVertPos *cutFailVPkp = new AliFemtoCutMonitorParticleVertPos("cutFailkp");
+    dtckp->AddCutMonitor(cutPassVPkp, cutFailVPkp);
+
+    AliFemtoCutMonitorEventMult *cutPassEvMkp = new AliFemtoCutMonitorEventMult("cutPasskp");
+    AliFemtoCutMonitorEventMult *cutFailEvMkp = new AliFemtoCutMonitorEventMult("cutFailkp");
+    meckp->AddCutMonitor(cutPassEvMkp, cutFailEvMkp);
+
+    AliFemtoCutMonitorEventVertex *cutPassEvVkp = new AliFemtoCutMonitorEventVertex("cutPasskp");
+    AliFemtoCutMonitorEventVertex *cutFailEvVkp = new AliFemtoCutMonitorEventVertex("cutFailkp");
+    meckp->AddCutMonitor(cutPassEvVkp, cutFailEvVkp);
+
+    AliFemtoShareQualityTPCEntranceSepPairCut *sqpckp = new AliFemtoShareQualityTPCEntranceSepPairCut();
+    sqpckp->SetShareQualityMax(0.0);
+    sqpckp->SetShareFractionMax(0.02);
+    sqpckp->SetRemoveSameLabel(kFALSE);
+    sqpckp->SetTPCEntranceSepMinimum(3.0);
+
+    ankp->SetEventCut(meckp);
+    ankp->SetFirstParticleCut(dtckp);
+    ankp->SetSecondParticleCut(dtckp);
+    ankp->SetPairCut(sqpckp);
+
+    AliFemtoQinvCorrFctn *cqinvkp= new AliFemtoQinvCorrFctn("qinvcf",100,0.0,1.0);
+
+    //###
+    ankp->AddCorrFctn(cqinvkp);
+
+    Manager->AddAnalysis(ankp);          
+
+    // *** End Kaon-Kaon (positive) analysis
+  }
+
+  if (runNegativeKaons) {
+    // *** Begin Kaon-Kaon (negative) analysis
+    AliFemtoVertexMultAnalysis *ankm = new AliFemtoVertexMultAnalysis(nZVertexBins, minZVertex, maxZVertex, 1, 2, 20000);
+    ankm->SetNumEventsToMix(5);
+    ankm->SetMinSizePartCollection(2);
+
+    AliFemtoBasicEventCut* meckm = new AliFemtoBasicEventCut();
+    meckm->SetEventMult(1,100000);
+    meckm->SetVertZPos(-1000,1000);
+       
+    AliFemtoESDTrackCut* dtckm = new AliFemtoESDTrackCut();
+    dtckm->SetPidProbKaon(0.7,1.001);
+    dtckm->SetPidProbMuon(0.0,0.5);
+    dtckm->SetPidProbPion(0.0,0.5);
+    dtckm->SetPidProbProton(0.0,0.5);
+    dtckp->SetMomRangeTOFpidIs(0.6,10000.);
+    dtckm->SetCharge(-1.0);
+    dtckm->SetMostProbableKaon();
+    dtckm->SetPt(0.15,2.0);
+    dtckm->SetMass(KaonMass);
+    // Track quality cuts
+    dtckm->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+    dtckm->SetminTPCncls(50);
+    dtckm->SetRemoveKinks(kTRUE);
+    dtckm->SetLabel(kFALSE);
+    dtckm->SetMaxITSChiNdof(2.5);
+    dtckm->SetMaxTPCChiNdof(3.0);
+    dtckm->SetMaxImpactXY(3.0);
+    dtckm->SetMaxImpactZ(3.0);
+
+    AliFemtoCutMonitorParticleYPt *cutPassYPtkm = new AliFemtoCutMonitorParticleYPt("cutPasskm", 0.493677);
+    AliFemtoCutMonitorParticleYPt *cutFailYPtkm = new AliFemtoCutMonitorParticleYPt("cutFailkm", 0.493677);
+    dtckm->AddCutMonitor(cutPassYPtkm, cutFailYPtkm);
+
+    AliFemtoCutMonitorParticlePtPDG *cutPassPidkm = new AliFemtoCutMonitorParticlePtPDG("cutPasskm", 0.493677);
+    AliFemtoCutMonitorParticlePtPDG *cutFailPidkm = new AliFemtoCutMonitorParticlePtPDG("cutFailkm", 0.493677);
+    dtckm->AddCutMonitor(cutPassPidkm, cutFailPidkm);
+
+    AliFemtoCutMonitorParticleMomRes *cutPassMRkm = new AliFemtoCutMonitorParticleMomRes("cutPasskm");
+    AliFemtoCutMonitorParticleMomRes *cutFailMRkm = new AliFemtoCutMonitorParticleMomRes("cutFailkm");
+    dtckm->AddCutMonitor(cutPassMRkm, cutFailMRkm);
+
+    AliFemtoCutMonitorParticleVertPos *cutPassVPkm = new AliFemtoCutMonitorParticleVertPos("cutPasskm");
+    AliFemtoCutMonitorParticleVertPos *cutFailVPkm = new AliFemtoCutMonitorParticleVertPos("cutFailkm");
+    dtckm->AddCutMonitor(cutPassVPkm, cutFailVPkm);
+
+    AliFemtoCutMonitorEventMult *cutPassEvMkm = new AliFemtoCutMonitorEventMult("cutPasskm");
+    AliFemtoCutMonitorEventMult *cutFailEvMkm = new AliFemtoCutMonitorEventMult("cutFailkm");
+    meckm->AddCutMonitor(cutPassEvMkm, cutFailEvMkm);
+
+    AliFemtoCutMonitorEventVertex *cutPassEvVkm = new AliFemtoCutMonitorEventVertex("cutPasskm");
+    AliFemtoCutMonitorEventVertex *cutFailEvVkm = new AliFemtoCutMonitorEventVertex("cutFailkm");
+    meckm->AddCutMonitor(cutPassEvVkm, cutFailEvVkm);
+
+    AliFemtoShareQualityTPCEntranceSepPairCut *sqpckm = new AliFemtoShareQualityTPCEntranceSepPairCut();
+    sqpckm->SetShareQualityMax(0.0);
+    sqpckm->SetShareFractionMax(0.02);
+    sqpckm->SetRemoveSameLabel(kFALSE);
+    sqpckm->SetTPCEntranceSepMinimum(3.0);
+
+    ankm->SetEventCut(meckm);
+    ankm->SetFirstParticleCut(dtckm);
+    ankm->SetSecondParticleCut(dtckm);
+    ankm->SetPairCut(sqpckm);
+
+    AliFemtoQinvCorrFctn *cqinvkm= new AliFemtoQinvCorrFctn("qinvcf",100,0.0,1.0);
+
+
+    //###
+    ankm->AddCorrFctn(cqinvkm);
+    Manager->AddAnalysis(ankm);          
+
+    // *** End Kaon-Kaon (negative) analysis
+  }
+
+  if (runPositiveNegativeKaons) {
+    // *** Begin Kaon+Kaon- analysis
+    AliFemtoVertexMultAnalysis *ankpkm = new AliFemtoVertexMultAnalysis(nZVertexBins, minZVertex, maxZVertex, 1, 2, 20000);
+    ankpkm->SetNumEventsToMix(5);
+    ankpkm->SetMinSizePartCollection(2);
+
+    AliFemtoBasicEventCut* meckpkm = new AliFemtoBasicEventCut();
+    meckpkm->SetEventMult(1,100000);
+    meckpkm->SetVertZPos(-1000,1000);
+       
+    AliFemtoESDTrackCut* dtckp = new AliFemtoESDTrackCut();
+    dtckp->SetPidProbKaon(0.7,1.001);
+    dtckp->SetPidProbMuon(0.0,0.5);
+    dtckp->SetPidProbPion(0.0,0.5);
+    dtckp->SetPidProbProton(0.0,0.5);
+    dtckp->SetMomRangeTOFpidIs(0.6,10000.);
+    dtckp->SetCharge(1.0);
+    dtckp->SetMostProbableKaon();
+    dtckp->SetPt(0.15,2.0);
+    dtckp->SetMass(KaonMass);
+    // Track quality cuts
+    dtckp->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+    dtckp->SetminTPCncls(50);
+    dtckp->SetRemoveKinks(kTRUE);
+    dtckp->SetLabel(kFALSE);
+    dtckp->SetMaxITSChiNdof(2.5);
+    dtckp->SetMaxTPCChiNdof(3.0);
+    dtckp->SetMaxImpactXY(3.0);
+    dtckp->SetMaxImpactZ(3.0);
+
+    AliFemtoESDTrackCut* dtckm = new AliFemtoESDTrackCut();
+    dtckm->SetPidProbKaon(0.7,1.001);
+    dtckm->SetPidProbMuon(0.0,0.5);
+    dtckm->SetPidProbPion(0.0,0.5);
+    dtckm->SetPidProbProton(0.0,0.5);
+    dtckm->SetMomRangeTOFpidIs(0.6,10000.);
+    dtckm->SetCharge(-1.0);
+    dtckm->SetMostProbableKaon();
+    dtckm->SetPt(0.15,2.0);
+    dtckm->SetMass(KaonMass);
+    // Track quality cuts
+    dtckm->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+    dtckm->SetminTPCncls(50);
+    dtckm->SetRemoveKinks(kTRUE);
+    dtckm->SetLabel(kFALSE);
+    dtckm->SetMaxITSChiNdof(2.5);
+    dtckm->SetMaxTPCChiNdof(3.0);
+    dtckm->SetMaxImpactXY(3.0);
+    dtckm->SetMaxImpactZ(3.0);
+
+
+    AliFemtoCutMonitorParticleYPt *cutPassYPtkp = new AliFemtoCutMonitorParticleYPt("cutPasskp", 0.493677);
+    AliFemtoCutMonitorParticleYPt *cutFailYPtkp = new AliFemtoCutMonitorParticleYPt("cutFailkp", 0.493677);
+    dtckp->AddCutMonitor(cutPassYPtkp, cutFailYPtkp);
+
+    AliFemtoCutMonitorParticleYPt *cutPassYPtkm = new AliFemtoCutMonitorParticleYPt("cutPasskm", 0.493677);
+    AliFemtoCutMonitorParticleYPt *cutFailYPtkm = new AliFemtoCutMonitorParticleYPt("cutFailkm", 0.493677);
+    dtckm->AddCutMonitor(cutPassYPtkm, cutFailYPtkm);
+
+    AliFemtoCutMonitorParticlePtPDG *cutPassPidkp = new AliFemtoCutMonitorParticlePtPDG("cutPasskp", 0.493677);
+    AliFemtoCutMonitorParticlePtPDG *cutFailPidkp = new AliFemtoCutMonitorParticlePtPDG("cutFailkp", 0.493677);
+    dtckp->AddCutMonitor(cutPassPidkp, cutFailPidkp);
+
+    AliFemtoCutMonitorParticlePtPDG *cutPassPidkm = new AliFemtoCutMonitorParticlePtPDG("cutPasskm", 0.493677);
+    AliFemtoCutMonitorParticlePtPDG *cutFailPidkm = new AliFemtoCutMonitorParticlePtPDG("cutFailkm", 0.493677);
+    dtckm->AddCutMonitor(cutPassPidkm, cutFailPidkm);
+  
+    AliFemtoCutMonitorParticleMomRes *cutPassMRkp = new AliFemtoCutMonitorParticleMomRes("cutPasskp");
+    AliFemtoCutMonitorParticleMomRes *cutFailMRkp = new AliFemtoCutMonitorParticleMomRes("cutFailkp");
+    dtckp->AddCutMonitor(cutPassMRkp, cutFailMRkp);
+
+    AliFemtoCutMonitorParticleMomRes *cutPassMRkm = new AliFemtoCutMonitorParticleMomRes("cutPasskm");
+    AliFemtoCutMonitorParticleMomRes *cutFailMRkm = new AliFemtoCutMonitorParticleMomRes("cutFailkm");
+    dtckm->AddCutMonitor(cutPassMRkm, cutFailMRkm);
+
+    AliFemtoCutMonitorParticleVertPos *cutPassVPkp = new AliFemtoCutMonitorParticleVertPos("cutPasskp");
+    AliFemtoCutMonitorParticleVertPos *cutFailVPkp = new AliFemtoCutMonitorParticleVertPos("cutFailkp");
+    dtckp->AddCutMonitor(cutPassVPkp, cutFailVPkp);
+
+    AliFemtoCutMonitorParticleVertPos *cutPassVPkm = new AliFemtoCutMonitorParticleVertPos("cutPasskm");
+    AliFemtoCutMonitorParticleVertPos *cutFailVPkm = new AliFemtoCutMonitorParticleVertPos("cutFailkm");
+    dtckm->AddCutMonitor(cutPassVPkm, cutFailVPkm);
+
+    AliFemtoCutMonitorEventMult *cutPassEvMkpkm = new AliFemtoCutMonitorEventMult("cutPasskpkm");
+    AliFemtoCutMonitorEventMult *cutFailEvMkpkm = new AliFemtoCutMonitorEventMult("cutFailkpkm");
+    meckpkm->AddCutMonitor(cutPassEvMkpkm, cutFailEvMkpkm);
+    AliFemtoCutMonitorEventVertex *cutPassEvVkpkm = new AliFemtoCutMonitorEventVertex("cutPasskpkm");
+    AliFemtoCutMonitorEventVertex *cutFailEvVkpkm = new AliFemtoCutMonitorEventVertex("cutFailkpkm");
+    meckpkm->AddCutMonitor(cutPassEvVkpkm, cutFailEvVkpkm);
+
+    AliFemtoShareQualityTPCEntranceSepPairCut *sqpckpkm = new AliFemtoShareQualityTPCEntranceSepPairCut();
+    sqpckpkm->SetShareQualityMax(0.0);
+    sqpckpkm->SetShareFractionMax(0.02);
+    sqpckpkm->SetRemoveSameLabel(kFALSE);
+    sqpckpkm->SetTPCEntranceSepMinimum(3.0);
+
+    ankpkm->SetEventCut(meckpkm);
+    ankpkm->SetFirstParticleCut(dtckp);
+    ankpkm->SetSecondParticleCut(dtckm);
+    ankpkm->SetPairCut(sqpckpkm);
+
+    AliFemtoQinvCorrFctn *cqinvkpkm= new AliFemtoQinvCorrFctn("qinvcf",100,0.0,1.0);
+
+    //###
+    ankpkm->AddCorrFctn(cqinvkpkm);
+    Manager->AddAnalysis(ankpkm);        
+
+    // *** End Kaon+Kaon-  analysis
+  }
+
+  return Manager;
+}                         
+                      
diff --git a/PWGCF/FEMTOSCOPY/macros/Train/PWG2FemtoExercise1/ConfigFemtoAnalysis.C b/PWGCF/FEMTOSCOPY/macros/Train/PWG2FemtoExercise1/ConfigFemtoAnalysis.C
new file mode 100644 (file)
index 0000000..f6c4ef4
--- /dev/null
@@ -0,0 +1,391 @@
+#include "AliFemtoManager.h"
+#include "AliFemtoEventReaderESDChain.h"
+#include "AliFemtoEventReaderESDChainKine.h"
+#include "AliFemtoSimpleAnalysis.h"
+#include "AliFemtoBasicEventCut.h"
+#include "AliFemtoESDTrackCut.h"
+#include "AliFemtoCutMonitorParticleYPt.h"
+#include "AliFemtoCutMonitorParticleVertPos.h"
+#include "AliFemtoCutMonitorParticleMomRes.h"
+#include "AliFemtoCutMonitorEventMult.h"
+#include "AliFemtoCutMonitorEventVertex.h"
+#include "AliFemtoShareQualityTPCEntranceSepPairCut.h"
+#include "AliFemtoQinvCorrFctn.h"
+#include "AliFemtoShareQualityCorrFctn.h"
+#include "AliFemtoTPCInnerCorrFctn.h"
+#include "AliFemtoVertexMultAnalysis.h"
+#include "AliFemtoCorrFctn3DSpherical.h"
+#include "AliFemtoChi2CorrFctn.h"
+#include "AliFemtoCorrFctnTPCNcls.h"
+#include "AliFemtoModelBPLCMSCorrFctn.h"
+#include "AliFemtoModelCorrFctn3DSpherical.h"
+#include "AliFemtoModelGausLCMSFreezeOutGenerator.h"
+#include "AliFemtoModelGausRinvFreezeOutGenerator.h"
+#include "AliFemtoModelManager.h"
+#include "AliFemtoModelWeightGeneratorBasic.h"
+#include "AliFemtoModelWeightGeneratorLednicky.h"
+#include "AliFemtoCorrFctnDirectYlm.h"
+#include "AliFemtoModelCorrFctnDirectYlm.h"
+#include "AliFemtoModelCorrFctnSource.h"
+#include "AliFemtoCutMonitorParticlePtPDG.h"
+
+//________________________________________________________________________
+AliFemtoManager* ConfigFemtoAnalysis() {
+
+  double PionMass = 0.13956995;
+  double KaonMass = 0.493677;
+  
+//   AliFemtoEventReaderESDChain* Reader=new AliFemtoEventReaderESDChain();
+//   Reader->SetConstrained(true);
+//   Reader->SetReadTPCInner(true);
+  AliFemtoEventReaderESDChainKine* Reader=new AliFemtoEventReaderESDChainKine();
+  Reader->SetConstrained(true);
+  //  Reader->SetReadTPCInner(true);
+  Reader->SetUseTPCOnly(false);
+
+  AliFemtoManager* Manager=new AliFemtoManager();
+  Manager->SetEventReader(Reader);
+       
+  // *** Begin pion-pion (positive) analysis ***
+
+  AliFemtoVertexMultAnalysis *anpip = new AliFemtoVertexMultAnalysis(3, -15.6, 15.6, 5, 2, 200);
+  anpip->SetNumEventsToMix(10);
+  anpip->SetMinSizePartCollection(2);
+
+  AliFemtoBasicEventCut* mecpip = new AliFemtoBasicEventCut();
+  mecpip->SetEventMult(2,100000);
+  mecpip->SetVertZPos(-1000,1000);
+       
+  AliFemtoESDTrackCut* dtcpip = new AliFemtoESDTrackCut();
+  dtcpip->SetPidProbPion(0.2,1.001);
+  dtcpip->SetPidProbMuon(0.0,1.0);
+  dtcpip->SetPidProbKaon(0.0,1.0);
+  dtcpip->SetPidProbProton(0.0,1.0);
+  dtcpip->SetCharge(1.0);
+  dtcpip->SetPt(0.15,0.5);
+  dtcpip->SetMass(PionMass);
+  // Track quality cuts
+  //  dtcpip->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+  dtcpip->SetStatus(AliESDtrack::kTPCrefit);
+  dtcpip->SetminTPCncls(50);
+  dtcpip->SetRemoveKinks(kTRUE);
+  dtcpip->SetLabel(kFALSE);
+  dtcpip->SetMaxITSChiNdof(2.5);
+  dtcpip->SetMaxTPCChiNdof(3.0);
+  dtcpip->SetMaxImpactXY(3.0);
+  dtcpip->SetMaxImpactZ(3.0);
+
+  AliFemtoCutMonitorParticleYPt *cutPassYPtpip = new AliFemtoCutMonitorParticleYPt("cutPasspip", 0.13957);
+  AliFemtoCutMonitorParticleYPt *cutFailYPtpip = new AliFemtoCutMonitorParticleYPt("cutFailpip", 0.13957);
+  dtcpip->AddCutMonitor(cutPassYPtpip, cutFailYPtpip);
+
+//   AliFemtoCutMonitorParticleMomRes *cutPassMR = new AliFemtoCutMonitorParticleMomRes("cutPass");
+//   AliFemtoCutMonitorParticleMomRes *cutFailMR = new AliFemtoCutMonitorParticleMomRes("cutFail");
+//   dtcpip->AddCutMonitor(cutPassMR, cutFailMR);
+
+//   AliFemtoCutMonitorParticleVertPos *cutPassVP = new AliFemtoCutMonitorParticleVertPos("VPcutPass");
+//   AliFemtoCutMonitorParticleVertPos *cutFailVP = new AliFemtoCutMonitorParticleVertPos("VPcutFail");
+//   dtcpip->AddCutMonitor(cutPassVP, cutFailVP);
+
+  AliFemtoCutMonitorEventMult *cutPassEvMpip = new AliFemtoCutMonitorEventMult("cutPasspip");
+  AliFemtoCutMonitorEventMult *cutFailEvMpip = new AliFemtoCutMonitorEventMult("cutFailpip");
+  mecpip->AddCutMonitor(cutPassEvMpip, cutFailEvMpip);
+
+  AliFemtoCutMonitorEventVertex *cutPassEvVpip = new AliFemtoCutMonitorEventVertex("cutPasspip");
+  AliFemtoCutMonitorEventVertex *cutFailEvVpip = new AliFemtoCutMonitorEventVertex("cutFailpip");
+  mecpip->AddCutMonitor(cutPassEvVpip, cutFailEvVpip);
+
+  AliFemtoShareQualityTPCEntranceSepPairCut *sqpcpip = new AliFemtoShareQualityTPCEntranceSepPairCut();
+  sqpcpip->SetShareQualityMax(0.0);
+  sqpcpip->SetShareFractionMax(0.02);
+  sqpcpip->SetRemoveSameLabel(kFALSE);
+  sqpcpip->SetTPCEntranceSepMinimum(2.0);
+
+  anpip->SetEventCut(mecpip);
+  anpip->SetFirstParticleCut(dtcpip);
+  anpip->SetSecondParticleCut(dtcpip);
+  anpip->SetPairCut(sqpcpip);
+
+  AliFemtoQinvCorrFctn *cqinvpip= new AliFemtoQinvCorrFctn("qinvcfpip", 100,0.0,1.0);
+  AliFemtoCorrFctn3DSpherical *cqsphpip = new AliFemtoCorrFctn3DSpherical("cqsphpip",60,0.0,0.3, 12, 12);
+
+  AliFemtoShareQualityCorrFctn *csqqinvpip= new AliFemtoShareQualityCorrFctn("sqqinvcfpip",40,0.0,0.4);
+  AliFemtoCorrFctnDirectYlm *cylmpip = new AliFemtoCorrFctnDirectYlm("cylmpip",2,60,0.0,0.3);
+    
+  AliFemtoChi2CorrFctn *cchiqinvpip= new AliFemtoChi2CorrFctn("chicfpip",40,0.0,0.4);
+  AliFemtoCorrFctnTPCNcls *cqtpcnclspip = new AliFemtoCorrFctnTPCNcls("cqtpcnclspip",40,0.0,0.4);
+
+  AliFemtoModelBPLCMSCorrFctn *c3dsmallpip;
+  AliFemtoModelCorrFctn *c1dpipip;
+  AliFemtoModelCorrFctn3DSpherical *c3dmsphpip;
+
+  // Setting up the model calculation
+  // First create the freeze-out generator
+  AliFemtoModelGausLCMSFreezeOutGenerator *tFreezepip = new AliFemtoModelGausLCMSFreezeOutGenerator();
+  tFreezepip->SetSizeOut(1.8*TMath::Sqrt(2.0));                                                
+  tFreezepip->SetSizeSide(1.3*TMath::Sqrt(2.0));                                               
+  tFreezepip->SetSizeLong(1.6*TMath::Sqrt(2.0));                                               
+
+  // And the weight generator                                                                    
+  AliFemtoModelWeightGeneratorBasic *tWeightpip = new AliFemtoModelWeightGeneratorBasic();
+  tWeightpip->SetPairType(AliFemtoModelWeightGenerator::PionPlusPionPlus());
+
+  // Create a manager that will connect it                                                                                                               
+  AliFemtoModelManager *tModelManagerpip = new AliFemtoModelManager();
+  tModelManagerpip->AcceptFreezeOutGenerator(tFreezepip);
+  tModelManagerpip->AcceptWeightGenerator(tWeightpip);
+  tModelManagerpip->CreateCopyHiddenInfo(kFALSE);
+
+  c3dsmallpip = new AliFemtoModelBPLCMSCorrFctn("c3dsmallpip",30, 0.0, 0.3);
+  c3dsmallpip->ConnectToManager(tModelManagerpip);
+
+  c1dpipip = new AliFemtoModelCorrFctn("c1dpipip",100,0.0,1.0);
+  c1dpipip->ConnectToManager(tModelManagerpip);
+
+  c3dmsphpip = new AliFemtoModelCorrFctn3DSpherical("c3dmsphpip",60, 0.0, 0.3, 12,12);
+  c3dmsphpip->ConnectToManager(tModelManagerpip);
+
+  AliFemtoModelCorrFctnDirectYlm *cmylmpip = new AliFemtoModelCorrFctnDirectYlm("mcylmpip",2,60,0.0,0.3);
+  cmylmpip->ConnectToManager(tModelManagerpip);
+
+  //###
+  anpip->AddCorrFctn(cqinvpip);
+  anpip->AddCorrFctn(cqsphpip);
+  anpip->AddCorrFctn(cylmpip);
+  anpip->AddCorrFctn(csqqinvpip);
+  anpip->AddCorrFctn(cchiqinvpip);
+  anpip->AddCorrFctn(cqtpcnclspip);
+  anpip->AddCorrFctn(c3dsmallpip);
+  anpip->AddCorrFctn(c1dpipip);
+  anpip->AddCorrFctn(c3dmsphpip);
+  anpip->AddCorrFctn(cmylmpip);
+
+  Manager->AddAnalysis(anpip); 
+
+  // *** End pion-pion (positive) analysis
+
+  // *** Begin pion-pion (negative) analysis ***
+
+  AliFemtoVertexMultAnalysis *anpim = new AliFemtoVertexMultAnalysis(3, -15.6, 15.6, 5, 2, 200);
+  anpim->SetNumEventsToMix(10);
+  anpim->SetMinSizePartCollection(2);
+
+  AliFemtoBasicEventCut* mecpim = new AliFemtoBasicEventCut();
+  mecpim->SetEventMult(2,100000);
+  mecpim->SetVertZPos(-1000,1000);
+       
+  AliFemtoESDTrackCut* dtcpim = new AliFemtoESDTrackCut();
+  dtcpim->SetPidProbPion(0.2,1.001);
+  dtcpim->SetPidProbMuon(0.0,1.0);
+  dtcpim->SetPidProbKaon(0.0,1.0);
+  dtcpim->SetPidProbProton(0.0,1.0);
+  dtcpim->SetCharge(-1.0);
+  dtcpim->SetPt(0.15,0.5);
+  dtcpim->SetMass(PionMass);
+  // Track quality cuts
+  //  dtcpim->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+  dtcpim->SetStatus(AliESDtrack::kTPCrefit);
+  dtcpim->SetminTPCncls(50);
+  dtcpim->SetRemoveKinks(kTRUE);
+  dtcpim->SetLabel(kFALSE);
+  dtcpim->SetMaxITSChiNdof(2.5);
+  dtcpim->SetMaxTPCChiNdof(3.0);
+  dtcpim->SetMaxImpactXY(3.0);
+  dtcpim->SetMaxImpactZ(3.0);
+
+  AliFemtoCutMonitorParticleYPt *cutPassYPtpim = new AliFemtoCutMonitorParticleYPt("cutPasspim", 0.13957);
+  AliFemtoCutMonitorParticleYPt *cutFailYPtpim = new AliFemtoCutMonitorParticleYPt("cutFailpim", 0.13957);
+  dtcpim->AddCutMonitor(cutPassYPtpim, cutFailYPtpim);
+
+//   AliFemtoCutMonitorParticleMomRes *cutPassMR = new AliFemtoCutMonitorParticleMomRes("cutPass");
+//   AliFemtoCutMonitorParticleMomRes *cutFailMR = new AliFemtoCutMonitorParticleMomRes("cutFail");
+//   dtcpim->AddCutMonitor(cutPassMR, cutFailMR);
+
+//   AliFemtoCutMonitorParticleVertPos *cutPassVP = new AliFemtoCutMonitorParticleVertPos("VPcutPass");
+//   AliFemtoCutMonitorParticleVertPos *cutFailVP = new AliFemtoCutMonitorParticleVertPos("VPcutFail");
+//   dtcpim->AddCutMonitor(cutPassVP, cutFailVP);
+
+  AliFemtoCutMonitorEventMult *cutPassEvMpim = new AliFemtoCutMonitorEventMult("cutPasspim");
+  AliFemtoCutMonitorEventMult *cutFailEvMpim = new AliFemtoCutMonitorEventMult("cutFailpim");
+  mecpim->AddCutMonitor(cutPassEvMpim, cutFailEvMpim);
+
+  AliFemtoCutMonitorEventVertex *cutPassEvVpim = new AliFemtoCutMonitorEventVertex("cutPasspim");
+  AliFemtoCutMonitorEventVertex *cutFailEvVpim = new AliFemtoCutMonitorEventVertex("cutFailpim");
+  mecpim->AddCutMonitor(cutPassEvVpim, cutFailEvVpim);
+
+  AliFemtoShareQualityTPCEntranceSepPairCut *sqpcpim = new AliFemtoShareQualityTPCEntranceSepPairCut();
+  sqpcpim->SetShareQualityMax(0.0);
+  sqpcpim->SetShareFractionMax(0.02);
+  sqpcpim->SetRemoveSameLabel(kFALSE);
+  sqpcpim->SetTPCEntranceSepMinimum(2.0);
+
+  anpim->SetEventCut(mecpim);
+  anpim->SetFirstParticleCut(dtcpim);
+  anpim->SetSecondParticleCut(dtcpim);
+  anpim->SetPairCut(sqpcpim);
+
+  AliFemtoQinvCorrFctn *cqinvpim= new AliFemtoQinvCorrFctn("qinvcfpim", 100,0.0,1.0);
+  AliFemtoCorrFctn3DSpherical *cqsphpim = new AliFemtoCorrFctn3DSpherical("cqsphpim",60,0.0,0.3, 12, 12);
+
+  AliFemtoShareQualityCorrFctn *csqqinvpim= new AliFemtoShareQualityCorrFctn("sqqinvcfpim",40,0.0,0.4);
+  AliFemtoCorrFctnDirectYlm *cylmpim = new AliFemtoCorrFctnDirectYlm("cylmpim",2,60,0.0,0.3);
+    
+  AliFemtoChi2CorrFctn *cchiqinvpim= new AliFemtoChi2CorrFctn("chicfpim",40,0.0,0.4);
+  AliFemtoCorrFctnTPCNcls *cqtpcnclspim = new AliFemtoCorrFctnTPCNcls("cqtpcnclspim",40,0.0,0.4);
+
+  AliFemtoModelBPLCMSCorrFctn *c3dsmallpim;
+  AliFemtoModelCorrFctn *c1dpipim;
+  AliFemtoModelCorrFctn3DSpherical *c3dmsphpim;
+
+  // Setting up the model calculation
+  // First create the freeze-out generator
+  AliFemtoModelGausLCMSFreezeOutGenerator *tFreezepim = new AliFemtoModelGausLCMSFreezeOutGenerator();
+  tFreezepim->SetSizeOut(1.8*TMath::Sqrt(2.0));                                                
+  tFreezepim->SetSizeSide(1.3*TMath::Sqrt(2.0));                                               
+  tFreezepim->SetSizeLong(1.6*TMath::Sqrt(2.0));                                               
+
+  // And the weight generator                                                                    
+  AliFemtoModelWeightGeneratorBasic *tWeightpim = new AliFemtoModelWeightGeneratorBasic();
+  tWeightpim->SetPairType(AliFemtoModelWeightGenerator::PionPlusPionPlus());
+
+  // Create a manager that will connect it                                                                                                               
+  AliFemtoModelManager *tModelManagerpim = new AliFemtoModelManager();
+  tModelManagerpim->AcceptFreezeOutGenerator(tFreezepim);
+  tModelManagerpim->AcceptWeightGenerator(tWeightpim);
+  tModelManagerpim->CreateCopyHiddenInfo(kFALSE);
+
+  c3dsmallpim = new AliFemtoModelBPLCMSCorrFctn("c3dsmallpim",30, 0.0, 0.3);
+  c3dsmallpim->ConnectToManager(tModelManagerpim);
+
+  c1dpipim = new AliFemtoModelCorrFctn("c1dpipim",100,0.0,1.0);
+  c1dpipim->ConnectToManager(tModelManagerpim);
+
+  c3dmsphpim = new AliFemtoModelCorrFctn3DSpherical("c3dmsphpim",60, 0.0, 0.3, 12,12);
+  c3dmsphpim->ConnectToManager(tModelManagerpim);
+
+  AliFemtoModelCorrFctnDirectYlm *cmylmpim = new AliFemtoModelCorrFctnDirectYlm("mcylmpim",2,60,0.0,0.3);
+  cmylmpim->ConnectToManager(tModelManagerpim);
+
+  //###
+  anpim->AddCorrFctn(cqinvpim);
+  anpim->AddCorrFctn(cqsphpim);
+  anpim->AddCorrFctn(cylmpim);
+  anpim->AddCorrFctn(csqqinvpim);
+  anpim->AddCorrFctn(cchiqinvpim);
+  anpim->AddCorrFctn(cqtpcnclspim);
+  anpim->AddCorrFctn(c3dsmallpim);
+  anpim->AddCorrFctn(c1dpipim);
+  anpim->AddCorrFctn(c3dmsphpim);
+  anpim->AddCorrFctn(cmylmpim);
+
+  Manager->AddAnalysis(anpim); 
+
+  // *** End pion-pion (negative) analysis
+
+  // *** Begin Kaon-Kaon (positive) analysis
+  AliFemtoVertexMultAnalysis *ankp = new AliFemtoVertexMultAnalysis(18, -15.6, 15.6, 1, 2, 20000);
+  ankp->SetNumEventsToMix(5);
+  ankp->SetMinSizePartCollection(2);
+
+  AliFemtoBasicEventCut* meckp = new AliFemtoBasicEventCut();
+  meckp->SetEventMult(1,100000);
+  meckp->SetVertZPos(-1000,1000);
+       
+  AliFemtoESDTrackCut* dtckp = new AliFemtoESDTrackCut();
+  dtckp->SetPidProbKaon(0.7,1.001);
+  dtckp->SetPidProbMuon(0.0,0.5);
+  dtckp->SetPidProbPion(0.0,0.5);
+  dtckp->SetPidProbProton(0.0,0.5);
+  dtckp->SetCharge(1.0);
+  dtckp->SetMostProbableKaon();
+  dtckp->SetPt(0.15,2.0);
+  dtckp->SetMass(KaonMass);
+  // Track quality cuts
+  //  dtckp->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+  dtckp->SetStatus(AliESDtrack::kTPCrefit);
+  //  dtckp->SetminTPCclsF(95);
+  dtckp->SetminTPCncls(50);
+  dtckp->SetRemoveKinks(kTRUE);
+  dtckp->SetLabel(kFALSE);
+  dtckp->SetMaxITSChiNdof(2.5);
+  dtckp->SetMaxTPCChiNdof(3.0);
+  dtckp->SetMaxSigmaToVertex(3.0);
+
+  AliFemtoCutMonitorParticleYPt *cutPassYPtkp = new AliFemtoCutMonitorParticleYPt("cutPasskp", 0.493677);
+  AliFemtoCutMonitorParticleYPt *cutFailYPtkp = new AliFemtoCutMonitorParticleYPt("cutFailkp", 0.493677);
+  dtckp->AddCutMonitor(cutPassYPtkp, cutFailYPtkp);
+
+  AliFemtoCutMonitorParticlePtPDG *cutPassPidkp = new AliFemtoCutMonitorParticlePtPDG("cutPasskp", 0.493677);
+  AliFemtoCutMonitorParticlePtPDG *cutFailPidkp = new AliFemtoCutMonitorParticlePtPDG("cutFailkp", 0.493677);
+  dtckp->AddCutMonitor(cutPassPidkp, cutFailPidkp);
+
+  AliFemtoCutMonitorParticleMomRes *cutPassMRkp = new AliFemtoCutMonitorParticleMomRes("cutPasskp");
+  AliFemtoCutMonitorParticleMomRes *cutFailMRkp = new AliFemtoCutMonitorParticleMomRes("cutFailkp");
+  dtckp->AddCutMonitor(cutPassMRkp, cutFailMRkp);
+
+  AliFemtoCutMonitorParticleVertPos *cutPassVPkp = new AliFemtoCutMonitorParticleVertPos("cutPasskp");
+  AliFemtoCutMonitorParticleVertPos *cutFailVPkp = new AliFemtoCutMonitorParticleVertPos("cutFailkp");
+  dtckp->AddCutMonitor(cutPassVPkp, cutFailVPkp);
+
+  AliFemtoCutMonitorEventMult *cutPassEvMkp = new AliFemtoCutMonitorEventMult("cutPasskp");
+  AliFemtoCutMonitorEventMult *cutFailEvMkp = new AliFemtoCutMonitorEventMult("cutFailkp");
+  meckp->AddCutMonitor(cutPassEvMkp, cutFailEvMkp);
+
+  AliFemtoCutMonitorEventVertex *cutPassEvVkp = new AliFemtoCutMonitorEventVertex("cutPasskp");
+  AliFemtoCutMonitorEventVertex *cutFailEvVkp = new AliFemtoCutMonitorEventVertex("cutFailkp");
+  meckp->AddCutMonitor(cutPassEvVkp, cutFailEvVkp);
+
+  AliFemtoShareQualityTPCEntranceSepPairCut *sqpckp = new AliFemtoShareQualityTPCEntranceSepPairCut();
+  sqpckp->SetShareQualityMax(0.0);
+  sqpckp->SetShareFractionMax(0.02);
+  sqpckp->SetRemoveSameLabel(kFALSE);
+  sqpckp->SetTPCEntranceSepMinimum(3.0);
+
+  ankp->SetEventCut(meckp);
+  ankp->SetFirstParticleCut(dtckp);
+  ankp->SetSecondParticleCut(dtckp);
+  ankp->SetPairCut(sqpckp);
+
+  AliFemtoQinvCorrFctn *cqinvkp= new AliFemtoQinvCorrFctn("qinvcf",100,0.0,1.0);
+
+  AliFemtoModelBPLCMSCorrFctn *c3dsmallkp;
+  AliFemtoModelCorrFctn *c1dpikp;
+
+  // Setting up the model calculation
+  // First create the freeze-out generator
+  AliFemtoModelGausRinvFreezeOutGenerator *tFreezekp = new AliFemtoModelGausRinvFreezeOutGenerator();
+  tFreezekp->SetSizeInv(1.8*TMath::Sqrt(2.0));
+  tFreezekp->SetSelectPrimaryFromHidden(false);
+
+  // And the weight generator                                                                    
+  AliFemtoModelWeightGeneratorBasic *tWeightkp = new AliFemtoModelWeightGeneratorBasic();
+  tWeightkp->SetPairType(AliFemtoModelWeightGenerator::KaonPlusKaonPlus());
+
+  // Create a manager that will connect it  
+  AliFemtoModelManager *tModelManagerkp = new AliFemtoModelManager();
+  tModelManagerkp->AcceptFreezeOutGenerator(tFreezekp);
+  tModelManagerkp->AcceptWeightGenerator(tWeightkp);
+  tModelManagerkp->CreateCopyHiddenInfo(kFALSE);
+
+  c3dsmallkp = new AliFemtoModelBPLCMSCorrFctn("c3dsmallkp",30, 0.0, 0.6);
+  c3dsmallkp->ConnectToManager(tModelManagerkp);
+
+  c1dpikp = new AliFemtoModelCorrFctn("c1dpikp",100,0.0,1.0);
+  c1dpikp->ConnectToManager(tModelManagerkp);
+
+  //###
+  ankp->AddCorrFctn(cqinvkp);
+  ankp->AddCorrFctn(c3dsmallkp);
+  ankp->AddCorrFctn(c1dpikp);
+
+  Manager->AddAnalysis(ankp);    
+
+  // *** End Kaon-Kaon (positive) analysis
+
+
+  return Manager;
+}                         
+                      
diff --git a/PWGCF/FEMTOSCOPY/macros/Train/PWG2FemtoExercise1/runBatch.C b/PWGCF/FEMTOSCOPY/macros/Train/PWG2FemtoExercise1/runBatch.C
new file mode 100644 (file)
index 0000000..823f79b
--- /dev/null
@@ -0,0 +1,147 @@
+void runBatch() {
+  TStopwatch timer;
+  timer.Start();
+  const char *chainlistfile="wn.xml";
+
+  printf("*** Connect to AliEn ***\n");
+//   if (dataFromAlien)
+  TGrid::Connect("alien://");
+  gSystem->Load("libProofPlayer.so");
+
+  //____________________________________________________//
+  //_____________Setting up STEERBase.par_______________//
+  //____________________________________________________//
+  setupPar("STEERBase");
+  gSystem->Load("libSTEERBase.so");
+
+  //____________________________________________________//
+  //_____________Setting up ESD.par_____________________//
+  //____________________________________________________//
+  setupPar("ESD");
+  gSystem->Load("libVMC.so");
+  gSystem->Load("libESD.so");
+
+  //____________________________________________________//
+  //_____________Setting up AOD.par_____________________//
+  //____________________________________________________//
+  setupPar("AOD");
+  gSystem->Load("libAOD.so");
+
+  //_________________________________________________________//
+  //_____________Setting up ANALYSIS.par_____________________//
+  //_________________________________________________________//
+  setupPar("ANALYSIS");
+  gSystem->Load("libANALYSIS.so");
+
+  //_________________________________________________________//
+  //_____________Setting up ANALYSISalice.par________________//
+  //_________________________________________________________//
+  setupPar("ANALYSISalice");
+  gSystem->Load("libANALYSISalice.so");
+
+  //____________________________________________________//
+  //_____________Setting up PWG2AOD.par_________________//
+  //____________________________________________________//
+  setupPar("PWG2AOD");
+  gSystem->Load("libPWG2AOD.so");
+  
+  //____________________________________________________//
+  //_____________Setting up PWG2femtoscopy.par__________//
+  //____________________________________________________//
+  setupPar("PWG2femtoscopy");
+  gSystem->Load("libPWG2femtoscopy.so");
+  
+  //____________________________________________________//
+  //_____________Setting up PWG2femtoscopyUser.par______//
+  //____________________________________________________//
+  setupPar("PWG2femtoscopyUser");
+  gSystem->Load("libPWG2femtoscopyUser.so");
+  
+  //ANALYSIS PART
+  gSystem->SetIncludePath("-I$ROOTSYS/include  -I\"/usr/local/CERN/root/include\" -I./PWG2femtoscopy/FEMTOSCOPY/AliFemto -I./PWG2femtoscopyUser/FEMTOSCOPY/AliFemtoUser -I./ESD -I./AOD -I./ANALYSIS -I./PWG2AOD/AOD");
+  gROOT->LoadMacro("ConfigFemtoAnalysis.C++");
+
+  //____________________________________________//
+  //Usage of event tags
+  AliTagAnalysis *analysis = new AliTagAnalysis();
+  TChain *chain = 0x0;
+  //  chain = analysis->GetChainFromCollection(collectionfile,"esdTree");
+
+//   if (dataFromAlien) {
+    AliTagAnalysis *analysis = new AliTagAnalysis();
+    chain = analysis->GetChainFromCollection(chainlistfile,"esdTree");
+//   }
+//   else {
+//     gROOT->LoadMacro("CreateESDChain.C");
+//     chain = CreateESDChain(chainlistfile,500);
+//   }
+
+  //____________________________________________//
+  // Make the analysis manager
+  AliAnalysisManager *mgr = new AliAnalysisManager("TestManager");
+  AliESDInputHandler* esdH = new AliESDInputHandler;
+  AliMCEventHandler *mcH = new AliMCEventHandler;
+
+  esdH->SetInactiveBranches("FMD CaloCluster");
+  mgr->SetInputEventHandler(esdH);  
+  mgr->SetMCtruthEventHandler(mcH);
+  //____________________________________________//
+  // 1st Pt task
+  AliAnalysisTaskFemto *task1 = new AliAnalysisTaskFemto("TaskFemto");
+
+  mgr->AddTask(task1);
+
+  // Create containers for input/output
+  //  AliAnalysisDataContainer *cinput1 = mgr->GetCommonInputContainer();
+  AliAnalysisDataContainer *cinput1 = mgr->CreateContainer("input0", 
+                                                          TTree::Class(), AliAnalysisManager::kInputContainer);
+  AliAnalysisDataContainer *coutput1 = mgr->CreateContainer("clist1", TList::Class(),AliAnalysisManager::kOutputContainer,"Femto.ESD.root");
+  
+  //____________________________________________//
+  cinput1->SetData(chain);
+  mgr->ConnectInput(task1,0,cinput1);
+  mgr->ConnectOutput(task1,0,coutput1);
+
+  if (!mgr->InitAnalysis()) return;
+  mgr->PrintStatus();
+  mgr->StartAnalysis("local",chain);
+
+  timer.Stop();
+  timer.Print();
+}
+
+Int_t setupPar(const char* pararchivename) {
+  ///////////////////
+  // Setup PAR File//
+  ///////////////////
+  if (pararchivename) {
+    char processline[1024];
+    sprintf(processline,".! tar xvzf %s.par",pararchivename);
+    gROOT->ProcessLine(processline);
+    const char* ocwd = gSystem->WorkingDirectory();
+    gSystem->ChangeDirectory(pararchivename);
+
+    // check for BUILD.sh and execute
+    if (!gSystem->AccessPathName("PROOF-INF/BUILD.sh")) {
+      printf("*******************************\n");
+      printf("*** Building PAR archive    ***\n");
+      printf("*******************************\n");
+
+      if (gSystem->Exec("PROOF-INF/BUILD.sh")) {
+        Error("runProcess","Cannot Build the PAR Archive! - Abort!");
+        return -1;
+      }
+    }
+    // check for SETUP.C and execute
+    if (!gSystem->AccessPathName("PROOF-INF/SETUP.C")) {
+      printf("*******************************\n");
+      printf("*** Setup PAR archive       ***\n");
+      printf("*******************************\n");
+      gROOT->Macro("PROOF-INF/SETUP.C");
+    }
+    
+    gSystem->ChangeDirectory("../");
+  }
+
+  return 1;
+}
diff --git a/PWGCF/FEMTOSCOPY/macros/Train/PWG2FemtoExercise1/runLocal.C b/PWGCF/FEMTOSCOPY/macros/Train/PWG2FemtoExercise1/runLocal.C
new file mode 100644 (file)
index 0000000..03bbf93
--- /dev/null
@@ -0,0 +1,146 @@
+void runLocal(const char *chainlistfile, int dataFromAlien=0) {
+  TStopwatch timer;
+  timer.Start();
+
+  printf("*** Connect to AliEn ***\n");
+  if (dataFromAlien)
+    TGrid::Connect("alien://");
+  gSystem->Load("libProofPlayer.so");
+
+  //____________________________________________________//
+  //_____________Setting up STEERBase.par_______________//
+  //____________________________________________________//
+  setupPar("STEERBase");
+  gSystem->Load("libSTEERBase.so");
+
+  //____________________________________________________//
+  //_____________Setting up ESD.par_____________________//
+  //____________________________________________________//
+  setupPar("ESD");
+  gSystem->Load("libVMC.so");
+  gSystem->Load("libESD.so");
+
+  //____________________________________________________//
+  //_____________Setting up AOD.par_____________________//
+  //____________________________________________________//
+  setupPar("AOD");
+  gSystem->Load("libAOD.so");
+
+  //_________________________________________________________//
+  //_____________Setting up ANALYSIS.par_____________________//
+  //_________________________________________________________//
+  setupPar("ANALYSIS");
+  gSystem->Load("libANALYSIS.so");
+
+  //_________________________________________________________//
+  //_____________Setting up ANALYSISalice.par________________//
+  //_________________________________________________________//
+  setupPar("ANALYSISalice");
+  gSystem->Load("libANALYSISalice.so");
+
+  //____________________________________________________//
+  //_____________Setting up PWG2AOD.par_________________//
+  //____________________________________________________//
+  setupPar("PWG2AOD");
+  gSystem->Load("libPWG2AOD.so");
+  
+  //____________________________________________________//
+  //_____________Setting up PWG2femtoscopy.par__________//
+  //____________________________________________________//
+  setupPar("PWG2femtoscopy");
+  gSystem->Load("libPWG2femtoscopy.so");
+  
+  //____________________________________________________//
+  //_____________Setting up PWG2femtoscopyUser.par______//
+  //____________________________________________________//
+  setupPar("PWG2femtoscopyUser");
+  gSystem->Load("libPWG2femtoscopyUser.so");
+  
+  //ANALYSIS PART
+  gSystem->SetIncludePath("-I$ROOTSYS/include  -I\"/usr/local/CERN/root/include\" -I./PWG2femtoscopy/FEMTOSCOPY/AliFemto -I./PWG2femtoscopyUser/FEMTOSCOPY/AliFemtoUser -I./ESD -I./AOD -I./ANALYSIS -I./PWG2AOD/AOD");
+  gROOT->LoadMacro("ConfigFemtoAnalysis.C++");
+
+  //____________________________________________//
+  //Usage of event tags
+  AliTagAnalysis *analysis = new AliTagAnalysis();
+  TChain *chain = 0x0;
+  //  chain = analysis->GetChainFromCollection(collectionfile,"esdTree");
+
+  if (dataFromAlien) {
+    AliTagAnalysis *analysis = new AliTagAnalysis();
+    chain = analysis->GetChainFromCollection(chainlistfile,"esdTree");
+  }
+  else {
+    gROOT->LoadMacro("CreateESDChain.C");
+    chain = CreateESDChain(chainlistfile,500);
+  }
+
+  //____________________________________________//
+  // Make the analysis manager
+  AliAnalysisManager *mgr = new AliAnalysisManager("TestManager");
+  AliESDInputHandler* esdH = new AliESDInputHandler;
+  AliMCEventHandler *mcH = new AliMCEventHandler;
+
+  esdH->SetInactiveBranches("FMD CaloCluster");
+  mgr->SetInputEventHandler(esdH);  
+  mgr->SetMCtruthEventHandler(mcH);
+  //____________________________________________//
+  // 1st Pt task
+  AliAnalysisTaskFemto *task1 = new AliAnalysisTaskFemto("TaskFemto");
+
+  mgr->AddTask(task1);
+
+  // Create containers for input/output
+  //  AliAnalysisDataContainer *cinput1 = mgr->GetCommonInputContainer();
+  AliAnalysisDataContainer *cinput1 = mgr->CreateContainer("input0", 
+                                                          TTree::Class(), AliAnalysisManager::kInputContainer);
+  AliAnalysisDataContainer *coutput1 = mgr->CreateContainer("clist1", TList::Class(),AliAnalysisManager::kOutputContainer,"Femto.ESD.root");
+  
+  //____________________________________________//
+  cinput1->SetData(chain);
+  mgr->ConnectInput(task1,0,cinput1);
+  mgr->ConnectOutput(task1,0,coutput1);
+
+  if (!mgr->InitAnalysis()) return;
+  mgr->PrintStatus();
+  mgr->StartAnalysis("local",chain);
+
+  timer.Stop();
+  timer.Print();
+}
+
+Int_t setupPar(const char* pararchivename) {
+  ///////////////////
+  // Setup PAR File//
+  ///////////////////
+  if (pararchivename) {
+    char processline[1024];
+    sprintf(processline,".! tar xvzf %s.par",pararchivename);
+    gROOT->ProcessLine(processline);
+    const char* ocwd = gSystem->WorkingDirectory();
+    gSystem->ChangeDirectory(pararchivename);
+
+    // check for BUILD.sh and execute
+    if (!gSystem->AccessPathName("PROOF-INF/BUILD.sh")) {
+      printf("*******************************\n");
+      printf("*** Building PAR archive    ***\n");
+      printf("*******************************\n");
+
+      if (gSystem->Exec("PROOF-INF/BUILD.sh")) {
+        Error("runProcess","Cannot Build the PAR Archive! - Abort!");
+        return -1;
+      }
+    }
+    // check for SETUP.C and execute
+    if (!gSystem->AccessPathName("PROOF-INF/SETUP.C")) {
+      printf("*******************************\n");
+      printf("*** Setup PAR archive       ***\n");
+      printf("*******************************\n");
+      gROOT->Macro("PROOF-INF/SETUP.C");
+    }
+    
+    gSystem->ChangeDirectory("../");
+  }
+
+  return 1;
+}
diff --git a/PWGCF/FEMTOSCOPY/macros/Train/PWG2Train2/ConfigFemtoAnalysis.C b/PWGCF/FEMTOSCOPY/macros/Train/PWG2Train2/ConfigFemtoAnalysis.C
new file mode 100644 (file)
index 0000000..c5d8e7b
--- /dev/null
@@ -0,0 +1,488 @@
+/*********************************************************************
+ *                                                                   *
+ * ConfigFemtoAnalysis.C - configuration macro for the femtoscopic   *
+ * analysis, to be run in the analysis train.                        *
+ * Assumed input data: large (>10M) sample of MC pp events           *
+ * Inluded analysis:                                                 *
+ *    - positive pion HBT, 3 kt bins, 1D+3D functions                *
+ *    - negative pion HBT, 3 kt bins, 1D+3D functions                *
+ *    - positive kaon HBT, 1 kt bin,  1D+3D functions                *
+ *                                                                   *
+ * Author: Adam Kisiel (Adam.Kisiel@cern.ch)                         *
+ *                                                                   *
+ *********************************************************************/
+
+#if !defined(__CINT__) || defined(__MAKECINT_)
+#include "AliFemtoManager.h"
+#include "AliFemtoEventReaderESDChain.h"
+#include "AliFemtoEventReaderESDChainKine.h"
+#include "AliFemtoSimpleAnalysis.h"
+#include "AliFemtoBasicEventCut.h"
+#include "AliFemtoESDTrackCut.h"
+#include "AliFemtoCorrFctn.h"
+#include "AliFemtoCutMonitorParticleYPt.h"
+#include "AliFemtoCutMonitorParticleVertPos.h"
+#include "AliFemtoCutMonitorParticleMomRes.h"
+#include "AliFemtoCutMonitorEventMult.h"
+#include "AliFemtoCutMonitorEventVertex.h"
+#include "AliFemtoShareQualityTPCEntranceSepPairCut.h"
+#include "AliFemtoQinvCorrFctn.h"
+#include "AliFemtoShareQualityCorrFctn.h"
+#include "AliFemtoTPCInnerCorrFctn.h"
+#include "AliFemtoVertexMultAnalysis.h"
+#include "AliFemtoCorrFctn3DSpherical.h"
+#include "AliFemtoChi2CorrFctn.h"
+#include "AliFemtoCorrFctnTPCNcls.h"
+#include "AliFemtoModelBPLCMSCorrFctn.h"
+#include "AliFemtoModelCorrFctn3DSpherical.h"
+#include "AliFemtoModelGausLCMSFreezeOutGenerator.h"
+#include "AliFemtoModelGausRinvFreezeOutGenerator.h"
+#include "AliFemtoModelManager.h"
+#include "AliFemtoModelWeightGeneratorBasic.h"
+#include "AliFemtoModelWeightGeneratorLednicky.h"
+#include "AliFemtoCorrFctnDirectYlm.h"
+#include "AliFemtoModelCorrFctnDirectYlm.h"
+#include "AliFemtoModelCorrFctnSource.h"
+#include "AliFemtoCutMonitorParticlePtPDG.h"
+#include "AliFemtoKTPairCut.h"
+#endif
+
+//________________________________________________________________________
+AliFemtoManager* ConfigFemtoAnalysis() {
+
+  double PionMass = 0.13956995;
+  double KaonMass = 0.493677;
+  
+  AliFemtoEventReaderESDChainKine* Reader=new AliFemtoEventReaderESDChainKine();
+  Reader->SetConstrained(true);
+  Reader->SetUseTPCOnly(false);
+
+  AliFemtoManager* Manager=new AliFemtoManager();
+  Manager->SetEventReader(Reader);
+       
+  // *** Begin pion-pion (positive) analysis ***
+
+  AliFemtoVertexMultAnalysis *anpip = new AliFemtoVertexMultAnalysis(3, -15.6, 15.6, 5, 2, 200000);
+  anpip->SetNumEventsToMix(10);
+  anpip->SetMinSizePartCollection(2);
+
+  AliFemtoBasicEventCut* mecpip = new AliFemtoBasicEventCut();
+  mecpip->SetEventMult(2,100000);
+  mecpip->SetVertZPos(-1000,1000);
+       
+  AliFemtoESDTrackCut* dtcpip = new AliFemtoESDTrackCut();
+  dtcpip->SetPidProbPion(0.2,1.001);
+  dtcpip->SetPidProbMuon(0.0,1.0);
+  dtcpip->SetPidProbKaon(0.0,1.0);
+  dtcpip->SetPidProbProton(0.0,1.0);
+  dtcpip->SetCharge(1.0);
+  dtcpip->SetPt(0.15,0.5);
+  dtcpip->SetMass(PionMass);
+  // Track quality cuts
+  dtcpip->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+  //  dtcpip->SetStatus(AliESDtrack::kTPCrefit);
+  dtcpip->SetminTPCncls(50);
+  dtcpip->SetRemoveKinks(kTRUE);
+  dtcpip->SetLabel(kFALSE);
+  dtcpip->SetMaxITSChiNdof(2.5);
+  dtcpip->SetMaxTPCChiNdof(3.0);
+  dtcpip->SetMaxImpactXY(3.0);
+  dtcpip->SetMaxImpactZ(3.0);
+
+  AliFemtoCutMonitorParticleYPt *cutPassYPtpip = new AliFemtoCutMonitorParticleYPt("cutPasspip", 0.13957);
+  AliFemtoCutMonitorParticleYPt *cutFailYPtpip = new AliFemtoCutMonitorParticleYPt("cutFailpip", 0.13957);
+  dtcpip->AddCutMonitor(cutPassYPtpip, cutFailYPtpip);
+
+  AliFemtoCutMonitorEventMult *cutPassEvMpip = new AliFemtoCutMonitorEventMult("cutPasspip");
+  AliFemtoCutMonitorEventMult *cutFailEvMpip = new AliFemtoCutMonitorEventMult("cutFailpip");
+  mecpip->AddCutMonitor(cutPassEvMpip, cutFailEvMpip);
+
+  AliFemtoCutMonitorEventVertex *cutPassEvVpip = new AliFemtoCutMonitorEventVertex("cutPasspip");
+  AliFemtoCutMonitorEventVertex *cutFailEvVpip = new AliFemtoCutMonitorEventVertex("cutFailpip");
+  mecpip->AddCutMonitor(cutPassEvVpip, cutFailEvVpip);
+
+  AliFemtoShareQualityTPCEntranceSepPairCut *sqpcpip = new AliFemtoShareQualityTPCEntranceSepPairCut();
+  sqpcpip->SetShareQualityMax(0.0);
+  sqpcpip->SetShareFractionMax(0.02);
+  sqpcpip->SetRemoveSameLabel(kFALSE);
+  sqpcpip->SetTPCEntranceSepMinimum(2.0);
+
+  anpip->SetEventCut(mecpip);
+  anpip->SetFirstParticleCut(dtcpip);
+  anpip->SetSecondParticleCut(dtcpip);
+  anpip->SetPairCut(sqpcpip);
+
+  AliFemtoCorrFctn3DSpherical *cqsphpip = new AliFemtoCorrFctn3DSpherical("cqsphpip",60,0.0,0.3, 12, 12);
+
+  AliFemtoShareQualityCorrFctn *csqqinvpip= new AliFemtoShareQualityCorrFctn("sqqinvcfpip",40,0.0,0.4);
+
+  // Intrdouce kT binning
+  AliFemtoKTPairCut *ktpairkT1pip = new AliFemtoKTPairCut(0.1,0.27);
+  AliFemtoKTPairCut *ktpairkT2pip = new AliFemtoKTPairCut(0.27,0.37);
+  AliFemtoKTPairCut *ktpairkT3pip = new AliFemtoKTPairCut(0.37,0.52);
+
+  AliFemtoCorrFctnDirectYlm *cylmkT1pip = new AliFemtoCorrFctnDirectYlm("cylmkT1pip",3,60,0.0,0.3,1);
+  cylmkT1pip->SetPairSelectionCut(ktpairkT1pip);
+  anpip->AddCorrFctn(cylmkT1pip);
+    
+  AliFemtoCorrFctnDirectYlm *cylmkT2pip = new AliFemtoCorrFctnDirectYlm("cylmkT2pip",3,60,0.0,0.3,1);
+  cylmkT2pip->SetPairSelectionCut(ktpairkT2pip);
+  anpip->AddCorrFctn(cylmkT2pip);
+    
+  AliFemtoCorrFctnDirectYlm *cylmkT3pip = new AliFemtoCorrFctnDirectYlm("cylmkT3pip",3,60,0.0,0.3,1);
+  cylmkT3pip->SetPairSelectionCut(ktpairkT3pip);
+  anpip->AddCorrFctn(cylmkT3pip);
+
+  AliFemtoQinvCorrFctn *cqinvkt1pip = new AliFemtoQinvCorrFctn("qinvcfkt1pip", 100,0.0,1.0);
+  cqinvkt1pip->SetPairSelectionCut(ktpairkT1pip);
+  anpip->AddCorrFctn(cqinvkt1pip);
+
+  AliFemtoQinvCorrFctn *cqinvkt2pip = new AliFemtoQinvCorrFctn("qinvcfkt2pip", 100,0.0,1.0);
+  cqinvkt2pip->SetPairSelectionCut(ktpairkT2pip);
+  anpip->AddCorrFctn(cqinvkt2pip);
+
+  AliFemtoQinvCorrFctn *cqinvkt3pip = new AliFemtoQinvCorrFctn("qinvcfkt3pip", 100,0.0,1.0);
+  cqinvkt3pip->SetPairSelectionCut(ktpairkT3pip);
+  anpip->AddCorrFctn(cqinvkt3pip);
+
+  AliFemtoChi2CorrFctn *cchiqinvpip= new AliFemtoChi2CorrFctn("chicfpip",40,0.0,0.4);
+  AliFemtoCorrFctnTPCNcls *cqtpcnclspip = new AliFemtoCorrFctnTPCNcls("cqtpcnclspip",40,0.0,0.4);
+
+  AliFemtoModelBPLCMSCorrFctn *c3dsmallkt1pip;
+  AliFemtoModelBPLCMSCorrFctn *c3dsmallkt2pip;
+  AliFemtoModelBPLCMSCorrFctn *c3dsmallkt3pip;
+  AliFemtoModelCorrFctn *c1dpipip;
+  AliFemtoModelCorrFctn3DSpherical *c3dmsphpip;
+
+  // Setting up the model calculation
+  // First create the freeze-out generator
+  AliFemtoModelGausLCMSFreezeOutGenerator *tFreezepip = new AliFemtoModelGausLCMSFreezeOutGenerator();
+  tFreezepip->SetSizeOut(1.8*TMath::Sqrt(2.0));                                                
+  tFreezepip->SetSizeSide(1.3*TMath::Sqrt(2.0));                                               
+  tFreezepip->SetSizeLong(1.6*TMath::Sqrt(2.0));                                                
+
+  // And the weight generator                                                                    
+  AliFemtoModelWeightGeneratorBasic *tWeightpip = new AliFemtoModelWeightGeneratorBasic();
+  tWeightpip->SetPairType(AliFemtoModelWeightGenerator::PionPlusPionPlus());
+
+  // Create a manager that will connect it                                                                                                               
+  AliFemtoModelManager *tModelManagerpip = new AliFemtoModelManager();
+  tModelManagerpip->AcceptFreezeOutGenerator(tFreezepip);
+  tModelManagerpip->AcceptWeightGenerator(tWeightpip);
+  tModelManagerpip->CreateCopyHiddenInfo(kFALSE);
+
+  c3dsmallkt1pip = new AliFemtoModelBPLCMSCorrFctn("c3dsmallkt2pip",30, 0.0, 0.3);
+  c3dsmallkt1pip->SetSpecificPairCut(ktpairkT2pip);
+  c3dsmallkt1pip->ConnectToManager(tModelManagerpip);
+
+  c3dsmallkt2pip = new AliFemtoModelBPLCMSCorrFctn("c3dsmallkt1pip",30, 0.0, 0.3);
+  c3dsmallkt2pip->SetSpecificPairCut(ktpairkT1pip);
+  c3dsmallkt2pip->ConnectToManager(tModelManagerpip);
+
+  c3dsmallkt3pip = new AliFemtoModelBPLCMSCorrFctn("c3dsmallkt3pip",30, 0.0, 0.3);
+  c3dsmallkt3pip->SetSpecificPairCut(ktpairkT3pip);
+  c3dsmallkt3pip->ConnectToManager(tModelManagerpip);
+
+  c1dpipip = new AliFemtoModelCorrFctn("c1dpipip",100,0.0,1.0);
+  c1dpipip->ConnectToManager(tModelManagerpip);
+
+  c3dmsphpip = new AliFemtoModelCorrFctn3DSpherical("c3dmsphpip",60, 0.0, 0.3, 12,12);
+  c3dmsphpip->ConnectToManager(tModelManagerpip);
+
+  AliFemtoModelCorrFctnDirectYlm *cmylmkt1pip = new AliFemtoModelCorrFctnDirectYlm("mcylmkt1pip",3,60,0.0,0.3,1);
+  cmylmkt1pip->SetPairSelectionCut(ktpairkT1pip);
+  cmylmkt1pip->ConnectToManager(tModelManagerpip);
+  anpip->AddCorrFctn(cmylmkt1pip);
+
+  AliFemtoModelCorrFctnDirectYlm *cmylmkt2pip = new AliFemtoModelCorrFctnDirectYlm("mcylmkt2pip",3,60,0.0,0.3,1);
+  cmylmkt2pip->SetPairSelectionCut(ktpairkT2pip);
+  cmylmkt2pip->ConnectToManager(tModelManagerpip);
+  anpip->AddCorrFctn(cmylmkt2pip);
+
+  AliFemtoModelCorrFctnDirectYlm *cmylmkt3pip = new AliFemtoModelCorrFctnDirectYlm("mcylmkt3pip",3,60,0.0,0.3,1);
+  cmylmkt3pip->SetPairSelectionCut(ktpairkT3pip);
+  cmylmkt3pip->ConnectToManager(tModelManagerpip);
+  anpip->AddCorrFctn(cmylmkt3pip);
+
+  //###
+  anpip->AddCorrFctn(cqsphpip);
+  anpip->AddCorrFctn(csqqinvpip);
+  anpip->AddCorrFctn(cchiqinvpip);
+  anpip->AddCorrFctn(cqtpcnclspip);
+  anpip->AddCorrFctn(c3dsmallkt1pip);
+  anpip->AddCorrFctn(c3dsmallkt2pip);
+  anpip->AddCorrFctn(c3dsmallkt3pip);
+  anpip->AddCorrFctn(c1dpipip);
+  anpip->AddCorrFctn(c3dmsphpip);
+
+  Manager->AddAnalysis(anpip); 
+
+  // *** End pion-pion (positive) analysis
+
+  // *** Begin pion-pion (negative) analysis ***
+
+  AliFemtoVertexMultAnalysis *anpim = new AliFemtoVertexMultAnalysis(3, -15.6, 15.6, 5, 2, 200000);
+  anpim->SetNumEventsToMix(10);
+  anpim->SetMinSizePartCollection(2);
+
+  AliFemtoBasicEventCut* mecpim = new AliFemtoBasicEventCut();
+  mecpim->SetEventMult(2,100000);
+  mecpim->SetVertZPos(-1000,1000);
+       
+  AliFemtoESDTrackCut* dtcpim = new AliFemtoESDTrackCut();
+  dtcpim->SetPidProbPion(0.2,1.001);
+  dtcpim->SetPidProbMuon(0.0,1.0);
+  dtcpim->SetPidProbKaon(0.0,1.0);
+  dtcpim->SetPidProbProton(0.0,1.0);
+  dtcpim->SetCharge(-1.0);
+  dtcpim->SetPt(0.15,0.5);
+  dtcpim->SetMass(PionMass);
+  // Track quality cuts
+  dtcpim->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+  //  dtcpim->SetStatus(AliESDtrack::kTPCrefit);
+  dtcpim->SetminTPCncls(50);
+  dtcpim->SetRemoveKinks(kTRUE);
+  dtcpim->SetLabel(kFALSE);
+  dtcpim->SetMaxITSChiNdof(2.5);
+  dtcpim->SetMaxTPCChiNdof(3.0);
+  dtcpim->SetMaxImpactXY(3.0);
+  dtcpim->SetMaxImpactZ(3.0);
+
+  AliFemtoCutMonitorParticleYPt *cutPassYPtpim = new AliFemtoCutMonitorParticleYPt("cutPasspim", 0.13957);
+  AliFemtoCutMonitorParticleYPt *cutFailYPtpim = new AliFemtoCutMonitorParticleYPt("cutFailpim", 0.13957);
+  dtcpim->AddCutMonitor(cutPassYPtpim, cutFailYPtpim);
+
+  AliFemtoCutMonitorEventMult *cutPassEvMpim = new AliFemtoCutMonitorEventMult("cutPasspim");
+  AliFemtoCutMonitorEventMult *cutFailEvMpim = new AliFemtoCutMonitorEventMult("cutFailpim");
+  mecpim->AddCutMonitor(cutPassEvMpim, cutFailEvMpim);
+
+  AliFemtoCutMonitorEventVertex *cutPassEvVpim = new AliFemtoCutMonitorEventVertex("cutPasspim");
+  AliFemtoCutMonitorEventVertex *cutFailEvVpim = new AliFemtoCutMonitorEventVertex("cutFailpim");
+  mecpim->AddCutMonitor(cutPassEvVpim, cutFailEvVpim);
+
+  AliFemtoShareQualityTPCEntranceSepPairCut *sqpcpim = new AliFemtoShareQualityTPCEntranceSepPairCut();
+  sqpcpim->SetShareQualityMax(0.0);
+  sqpcpim->SetShareFractionMax(0.02);
+  sqpcpim->SetRemoveSameLabel(kFALSE);
+  sqpcpim->SetTPCEntranceSepMinimum(2.0);
+
+  anpim->SetEventCut(mecpim);
+  anpim->SetFirstParticleCut(dtcpim);
+  anpim->SetSecondParticleCut(dtcpim);
+  anpim->SetPairCut(sqpcpim);
+
+  AliFemtoCorrFctn3DSpherical *cqsphpim = new AliFemtoCorrFctn3DSpherical("cqsphpim",60,0.0,0.3, 12, 12);
+
+  AliFemtoShareQualityCorrFctn *csqqinvpim= new AliFemtoShareQualityCorrFctn("sqqinvcfpim",40,0.0,0.4);
+
+  // Intrdouce kT binning
+  AliFemtoKTPairCut *ktpairkT1pim = new AliFemtoKTPairCut(0.1,0.27);
+  AliFemtoKTPairCut *ktpairkT2pim = new AliFemtoKTPairCut(0.27,0.37);
+  AliFemtoKTPairCut *ktpairkT3pim = new AliFemtoKTPairCut(0.37,0.52);
+
+  AliFemtoCorrFctnDirectYlm *cylmkT1pim = new AliFemtoCorrFctnDirectYlm("cylmkT1pim",3,60,0.0,0.3,1);
+  cylmkT1pim->SetPairSelectionCut(ktpairkT1pim);
+  anpim->AddCorrFctn(cylmkT1pim);
+    
+  AliFemtoCorrFctnDirectYlm *cylmkT2pim = new AliFemtoCorrFctnDirectYlm("cylmkT2pim",3,60,0.0,0.3,1);
+  cylmkT2pim->SetPairSelectionCut(ktpairkT2pim);
+  anpim->AddCorrFctn(cylmkT2pim);
+    
+  AliFemtoCorrFctnDirectYlm *cylmkT3pim = new AliFemtoCorrFctnDirectYlm("cylmkT3pim",3,60,0.0,0.3,1);
+  cylmkT3pim->SetPairSelectionCut(ktpairkT3pim);
+  anpim->AddCorrFctn(cylmkT3pim);
+
+  AliFemtoQinvCorrFctn *cqinvkt1pim = new AliFemtoQinvCorrFctn("qinvcfkt1pim", 100,0.0,1.0);
+  cqinvkt1pim->SetPairSelectionCut(ktpairkT1pim);
+  anpim->AddCorrFctn(cqinvkt1pim);
+
+  AliFemtoQinvCorrFctn *cqinvkt2pim = new AliFemtoQinvCorrFctn("qinvcfkt2pim", 100,0.0,1.0);
+  cqinvkt2pim->SetPairSelectionCut(ktpairkT2pim);
+  anpim->AddCorrFctn(cqinvkt2pim);
+
+  AliFemtoQinvCorrFctn *cqinvkt3pim = new AliFemtoQinvCorrFctn("qinvcfkt3pim", 100,0.0,1.0);
+  cqinvkt3pim->SetPairSelectionCut(ktpairkT3pim);
+  anpim->AddCorrFctn(cqinvkt3pim);
+
+  AliFemtoChi2CorrFctn *cchiqinvpim= new AliFemtoChi2CorrFctn("chicfpim",40,0.0,0.4);
+  AliFemtoCorrFctnTPCNcls *cqtpcnclspim = new AliFemtoCorrFctnTPCNcls("cqtpcnclspim",40,0.0,0.4);
+
+  AliFemtoModelBPLCMSCorrFctn *c3dsmallkt1pim;
+  AliFemtoModelBPLCMSCorrFctn *c3dsmallkt2pim;
+  AliFemtoModelBPLCMSCorrFctn *c3dsmallkt3pim;
+  AliFemtoModelCorrFctn *c1dpimip;
+  AliFemtoModelCorrFctn3DSpherical *c3dmsphpim;
+
+  // Setting up the model calculation
+  // First create the freeze-out generator
+  AliFemtoModelGausLCMSFreezeOutGenerator *tFreezepim = new AliFemtoModelGausLCMSFreezeOutGenerator();
+  tFreezepim->SetSizeOut(1.8*TMath::Sqrt(2.0));                                                
+  tFreezepim->SetSizeSide(1.3*TMath::Sqrt(2.0));                                               
+  tFreezepim->SetSizeLong(1.6*TMath::Sqrt(2.0));                                                
+
+  // And the weight generator                                                                    
+  AliFemtoModelWeightGeneratorBasic *tWeightpim = new AliFemtoModelWeightGeneratorBasic();
+  tWeightpim->SetPairType(AliFemtoModelWeightGenerator::PionPlusPionPlus());
+
+  // Create a manager that will connect it                                                                                                               
+  AliFemtoModelManager *tModelManagerpim = new AliFemtoModelManager();
+  tModelManagerpim->AcceptFreezeOutGenerator(tFreezepim);
+  tModelManagerpim->AcceptWeightGenerator(tWeightpim);
+  tModelManagerpim->CreateCopyHiddenInfo(kFALSE);
+
+  c3dsmallkt1pim = new AliFemtoModelBPLCMSCorrFctn("c3dsmallkt2pim",30, 0.0, 0.3);
+  c3dsmallkt1pim->SetSpecificPairCut(ktpairkT2pim);
+  c3dsmallkt1pim->ConnectToManager(tModelManagerpim);
+
+  c3dsmallkt2pim = new AliFemtoModelBPLCMSCorrFctn("c3dsmallkt1pim",30, 0.0, 0.3);
+  c3dsmallkt2pim->SetSpecificPairCut(ktpairkT1pim);
+  c3dsmallkt2pim->ConnectToManager(tModelManagerpim);
+
+  c3dsmallkt3pim = new AliFemtoModelBPLCMSCorrFctn("c3dsmallkt3pim",30, 0.0, 0.3);
+  c3dsmallkt3pim->SetSpecificPairCut(ktpairkT3pim);
+  c3dsmallkt3pim->ConnectToManager(tModelManagerpim);
+
+  c1dpimip = new AliFemtoModelCorrFctn("c1dpimip",100,0.0,1.0);
+  c1dpimip->ConnectToManager(tModelManagerpim);
+
+  c3dmsphpim = new AliFemtoModelCorrFctn3DSpherical("c3dmsphpim",60, 0.0, 0.3, 12,12);
+  c3dmsphpim->ConnectToManager(tModelManagerpim);
+
+  AliFemtoModelCorrFctnDirectYlm *cmylmkt1pim = new AliFemtoModelCorrFctnDirectYlm("mcylmkt1pim",3,60,0.0,0.3,1);
+  cmylmkt1pim->SetPairSelectionCut(ktpairkT1pim);
+  cmylmkt1pim->ConnectToManager(tModelManagerpim);
+  anpim->AddCorrFctn(cmylmkt1pim);
+
+  AliFemtoModelCorrFctnDirectYlm *cmylmkt2pim = new AliFemtoModelCorrFctnDirectYlm("mcylmkt2pim",3,60,0.0,0.3,1);
+  cmylmkt2pim->SetPairSelectionCut(ktpairkT2pim);
+  cmylmkt2pim->ConnectToManager(tModelManagerpim);
+  anpim->AddCorrFctn(cmylmkt2pim);
+
+  AliFemtoModelCorrFctnDirectYlm *cmylmkt3pim = new AliFemtoModelCorrFctnDirectYlm("mcylmkt3pim",3,60,0.0,0.3,1);
+  cmylmkt3pim->SetPairSelectionCut(ktpairkT3pim);
+  cmylmkt3pim->ConnectToManager(tModelManagerpim);
+  anpim->AddCorrFctn(cmylmkt3pim);
+
+  //###
+  anpim->AddCorrFctn(cqsphpim);
+  anpim->AddCorrFctn(csqqinvpim);
+  anpim->AddCorrFctn(cchiqinvpim);
+  anpim->AddCorrFctn(cqtpcnclspim);
+  anpim->AddCorrFctn(c3dsmallkt1pim);
+  anpim->AddCorrFctn(c3dsmallkt2pim);
+  anpim->AddCorrFctn(c3dsmallkt3pim);
+  anpim->AddCorrFctn(c1dpimip);
+  anpim->AddCorrFctn(c3dmsphpim);
+
+  Manager->AddAnalysis(anpim); 
+
+  // *** End pion-pion (negative) analysis
+
+  // *** Begin Kaon-Kaon (positive) analysis
+  AliFemtoVertexMultAnalysis *ankp = new AliFemtoVertexMultAnalysis(18, -15.6, 15.6, 1, 2, 20000);
+  ankp->SetNumEventsToMix(5);
+  ankp->SetMinSizePartCollection(2);
+
+  AliFemtoBasicEventCut* meckp = new AliFemtoBasicEventCut();
+  meckp->SetEventMult(1,100000);
+  meckp->SetVertZPos(-1000,1000);
+       
+  AliFemtoESDTrackCut* dtckp = new AliFemtoESDTrackCut();
+  dtckp->SetPidProbKaon(0.7,1.001);
+  dtckp->SetPidProbMuon(0.0,0.5);
+  dtckp->SetPidProbPion(0.0,0.5);
+  dtckp->SetPidProbProton(0.0,0.5);
+  dtckp->SetCharge(1.0);
+  dtckp->SetMostProbableKaon();
+  dtckp->SetPt(0.15,2.0);
+  dtckp->SetMass(KaonMass);
+  // Track quality cuts
+  dtckp->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+  //dtckp->SetStatus(AliESDtrack::kTPCrefit);
+  //  dtckp->SetminTPCclsF(95);
+  dtckp->SetminTPCncls(50);
+  dtckp->SetRemoveKinks(kTRUE);
+  dtckp->SetLabel(kFALSE);
+  dtckp->SetMaxITSChiNdof(2.5);
+  dtckp->SetMaxTPCChiNdof(3.0);
+  //  dtckp->SetMaxSigmaToVertex(3.0);
+  dtckp->SetMaxImpactXY(3.0);
+  dtckp->SetMaxImpactZ(3.0);
+
+  AliFemtoCutMonitorParticleYPt *cutPassYPtkp = new AliFemtoCutMonitorParticleYPt("cutPasskp", 0.493677);
+  AliFemtoCutMonitorParticleYPt *cutFailYPtkp = new AliFemtoCutMonitorParticleYPt("cutFailkp", 0.493677);
+  dtckp->AddCutMonitor(cutPassYPtkp, cutFailYPtkp);
+
+  AliFemtoCutMonitorParticlePtPDG *cutPassPidkp = new AliFemtoCutMonitorParticlePtPDG("cutPasskp", 0.493677);
+  AliFemtoCutMonitorParticlePtPDG *cutFailPidkp = new AliFemtoCutMonitorParticlePtPDG("cutFailkp", 0.493677);
+  dtckp->AddCutMonitor(cutPassPidkp, cutFailPidkp);
+
+  AliFemtoCutMonitorParticleMomRes *cutPassMRkp = new AliFemtoCutMonitorParticleMomRes("cutPasskp");
+  AliFemtoCutMonitorParticleMomRes *cutFailMRkp = new AliFemtoCutMonitorParticleMomRes("cutFailkp");
+  dtckp->AddCutMonitor(cutPassMRkp, cutFailMRkp);
+
+  AliFemtoCutMonitorParticleVertPos *cutPassVPkp = new AliFemtoCutMonitorParticleVertPos("cutPasskp");
+  AliFemtoCutMonitorParticleVertPos *cutFailVPkp = new AliFemtoCutMonitorParticleVertPos("cutFailkp");
+  dtckp->AddCutMonitor(cutPassVPkp, cutFailVPkp);
+
+  AliFemtoCutMonitorEventMult *cutPassEvMkp = new AliFemtoCutMonitorEventMult("cutPasskp");
+  AliFemtoCutMonitorEventMult *cutFailEvMkp = new AliFemtoCutMonitorEventMult("cutFailkp");
+  meckp->AddCutMonitor(cutPassEvMkp, cutFailEvMkp);
+
+  AliFemtoCutMonitorEventVertex *cutPassEvVkp = new AliFemtoCutMonitorEventVertex("cutPasskp");
+  AliFemtoCutMonitorEventVertex *cutFailEvVkp = new AliFemtoCutMonitorEventVertex("cutFailkp");
+  meckp->AddCutMonitor(cutPassEvVkp, cutFailEvVkp);
+
+  AliFemtoShareQualityTPCEntranceSepPairCut *sqpckp = new AliFemtoShareQualityTPCEntranceSepPairCut();
+  sqpckp->SetShareQualityMax(0.0);
+  sqpckp->SetShareFractionMax(0.02);
+  sqpckp->SetRemoveSameLabel(kFALSE);
+  sqpckp->SetTPCEntranceSepMinimum(3.0);
+
+  ankp->SetEventCut(meckp);
+  ankp->SetFirstParticleCut(dtckp);
+  ankp->SetSecondParticleCut(dtckp);
+  ankp->SetPairCut(sqpckp);
+
+  AliFemtoQinvCorrFctn *cqinvkp= new AliFemtoQinvCorrFctn("qinvcf",100,0.0,1.0);
+
+  AliFemtoModelBPLCMSCorrFctn *c3dsmallkp;
+  AliFemtoModelCorrFctn *c1dpikp;
+
+  // Setting up the model calculation
+  // First create the freeze-out generator
+  AliFemtoModelGausRinvFreezeOutGenerator *tFreezekp = new AliFemtoModelGausRinvFreezeOutGenerator();
+  tFreezekp->SetSizeInv(1.8*TMath::Sqrt(2.0));
+  tFreezekp->SetSelectPrimaryFromHidden(false);
+
+  // And the weight generator                                                                    
+  AliFemtoModelWeightGeneratorBasic *tWeightkp = new AliFemtoModelWeightGeneratorBasic();
+  tWeightkp->SetPairType(AliFemtoModelWeightGenerator::KaonPlusKaonPlus());
+
+  // Create a manager that will connect it  
+  AliFemtoModelManager *tModelManagerkp = new AliFemtoModelManager();
+  tModelManagerkp->AcceptFreezeOutGenerator(tFreezekp);
+  tModelManagerkp->AcceptWeightGenerator(tWeightkp);
+  tModelManagerkp->CreateCopyHiddenInfo(kFALSE);
+
+  c3dsmallkp = new AliFemtoModelBPLCMSCorrFctn("c3dsmallkp",30, 0.0, 0.6);
+  c3dsmallkp->ConnectToManager(tModelManagerkp);
+
+  c1dpikp = new AliFemtoModelCorrFctn("c1dpikp",100,0.0,1.0);
+  c1dpikp->ConnectToManager(tModelManagerkp);
+
+  //###
+  ankp->AddCorrFctn(cqinvkp);
+  ankp->AddCorrFctn(c3dsmallkp);
+  ankp->AddCorrFctn(c1dpikp);
+
+  Manager->AddAnalysis(ankp);    
+
+  // *** End Kaon-Kaon (positive) analysis
+
+  return Manager;
+}                         
+                      
diff --git a/PWGCF/FEMTOSCOPY/macros/Train/PWG2TrainLHC10a6/ConfigFemtoAnalysis.C b/PWGCF/FEMTOSCOPY/macros/Train/PWG2TrainLHC10a6/ConfigFemtoAnalysis.C
new file mode 100644 (file)
index 0000000..960c8a6
--- /dev/null
@@ -0,0 +1,360 @@
+/*********************************************************************
+ *                                                                   *
+ * ConfigFemtoAnalysis.C - configuration macro for the femtoscopic   *
+ * analysis, meant as a QA process for two-particle effects          *
+ *                                                                   *
+ * Author: Adam Kisiel (Adam.Kisiel@cern.ch)                         *
+ *                                                                   *
+ *********************************************************************/
+
+#if !defined(__CINT__) || defined(__MAKECINT_)
+#include "AliFemtoManager.h"
+#include "AliFemtoEventReaderESDChain.h"
+#include "AliFemtoEventReaderESDChainKine.h"
+#include "AliFemtoSimpleAnalysis.h"
+#include "AliFemtoBasicEventCut.h"
+#include "AliFemtoESDTrackCut.h"
+#include "AliFemtoCorrFctn.h"
+#include "AliFemtoCutMonitorParticleYPt.h"
+#include "AliFemtoCutMonitorParticleVertPos.h"
+#include "AliFemtoCutMonitorParticleMomRes.h"
+#include "AliFemtoCutMonitorEventMult.h"
+#include "AliFemtoCutMonitorEventVertex.h"
+#include "AliFemtoShareQualityTPCEntranceSepPairCut.h"
+#include "AliFemtoQinvCorrFctn.h"
+#include "AliFemtoShareQualityCorrFctn.h"
+#include "AliFemtoTPCInnerCorrFctn.h"
+#include "AliFemtoVertexMultAnalysis.h"
+#include "AliFemtoCorrFctn3DSpherical.h"
+#include "AliFemtoChi2CorrFctn.h"
+#include "AliFemtoCorrFctnTPCNcls.h"
+#include "AliFemtoModelBPLCMSCorrFctn.h"
+#include "AliFemtoModelCorrFctn3DSpherical.h"
+#include "AliFemtoModelGausLCMSFreezeOutGenerator.h"
+#include "AliFemtoModelGausRinvFreezeOutGenerator.h"
+#include "AliFemtoModelManager.h"
+#include "AliFemtoModelWeightGeneratorBasic.h"
+#include "AliFemtoModelWeightGeneratorLednicky.h"
+#include "AliFemtoCorrFctnDirectYlm.h"
+#include "AliFemtoModelCorrFctnDirectYlm.h"
+#include "AliFemtoModelCorrFctnSource.h"
+#include "AliFemtoCutMonitorParticlePtPDG.h"
+#include "AliFemtoKTPairCut.h"
+#include "AliFemtoCorrFctnDEtaDPhi.h"
+#include "AliFemtoBPLCMS3DCorrFctn.h"
+#endif
+
+//________________________________________________________________________
+AliFemtoManager* ConfigFemtoAnalysis() {
+
+  double PionMass = 0.13956995;
+  double KaonMass = 0.493677;
+       
+  // Switches for QA analyses
+  int runPositiveTPCQA = 1;
+  int runNegativeTPCQA = 1;
+
+  int runktdep = 1;
+  int run3d = 0;
+  
+  int runtype = 0; // Types 0 - global, 1 - ITS only
+  int isrealdata = 0;
+
+  AliFemtoEventReaderESDChain* Reader=new AliFemtoEventReaderESDChain();
+  Reader->SetConstrained(true);
+  Reader->SetUseTPCOnly(false);
+  if (runtype == 0)
+    Reader->SetReadTrackType(AliFemtoEventReaderESDChain::kGlobal);
+  else if (runtype == 1)
+    Reader->SetReadTrackType(AliFemtoEventReaderESDChain::kITSOnly);
+  if (isrealdata)
+    Reader->SetUsePhysicsSelection(kTRUE);
+  else
+    Reader->SetUsePhysicsSelection(kFALSE);
+
+  AliFemtoManager* Manager=new AliFemtoManager();
+  Manager->SetEventReader(Reader);
+
+  // *** Third QA task - HBT analysis with all pair cuts off, TPC only ***
+  // *** Begin pion-pion (positive) analysis ***
+  if (runPositiveTPCQA) {
+    AliFemtoVertexMultAnalysis *anpiptpc = new AliFemtoVertexMultAnalysis(6, -10.0, 10.0, 1, 0, 10000);
+    anpiptpc->SetNumEventsToMix(10);
+    anpiptpc->SetMinSizePartCollection(2);
+
+    AliFemtoBasicEventCut* mecpiptpc = new AliFemtoBasicEventCut();
+    mecpiptpc->SetEventMult(0,100000);
+    mecpiptpc->SetVertZPos(-1000,1000);
+
+    AliFemtoCutMonitorEventMult *cutPassEvMpiptpc = new AliFemtoCutMonitorEventMult("cutPasspiptpc");
+    AliFemtoCutMonitorEventMult *cutFailEvMpiptpc = new AliFemtoCutMonitorEventMult("cutFailpiptpc");
+    mecpiptpc->AddCutMonitor(cutPassEvMpiptpc, cutFailEvMpiptpc);
+
+    AliFemtoCutMonitorEventVertex *cutPassEvVpiptpc = new AliFemtoCutMonitorEventVertex("cutPasspiptpc");
+    AliFemtoCutMonitorEventVertex *cutFailEvVpiptpc = new AliFemtoCutMonitorEventVertex("cutFailpiptpc");
+    mecpiptpc->AddCutMonitor(cutPassEvVpiptpc, cutFailEvVpiptpc);
+       
+    AliFemtoESDTrackCut* dtcpiptpc = new AliFemtoESDTrackCut();
+    //     dtcpiptpc->SetPidProbPion(0.0,1.001);
+    //     dtcpiptpc->SetPidProbMuon(0.0,1.0);
+    //     dtcpiptpc->SetPidProbKaon(0.0,1.0);
+    //     dtcpiptpc->SetPidProbProton(0.0,1.0);
+    dtcpiptpc->SetCharge(1.0);
+    dtcpiptpc->SetPt(0.05,10.0);
+    dtcpiptpc->SetMass(PionMass);
+    // Track quality cuts
+    if (runtype == 0) {
+      dtcpiptpc->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+      //    dtcpiptpc->SetStatus(AliESDtrack::kTPCrefit);
+      //    dtcpiptpc->SetStatus(AliESDtrack::kITSrefit);
+      dtcpiptpc->SetminTPCncls(50);
+      dtcpiptpc->SetRemoveKinks(kTRUE);
+      dtcpiptpc->SetLabel(kFALSE);
+      //    dtcpiptpc->SetMaxITSChiNdof(6.0);
+      dtcpiptpc->SetMaxTPCChiNdof(6.0);
+      dtcpiptpc->SetMaxImpactXY(0.2);
+      dtcpiptpc->SetMaxImpactZ(0.25);
+      dtcpiptpc->SetMaxSigmaToVertex(6.0);
+    }
+    else if (runtype == 1) {
+      //      dtcpiptpc->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+      //    dtcpiptpc->SetStatus(AliESDtrack::kTPCrefit);
+      dtcpiptpc->SetStatus(AliESDtrack::kITSrefit);
+      //      dtcpiptpc->SetminTPCncls(50);
+      dtcpiptpc->SetRemoveKinks(kTRUE);
+      dtcpiptpc->SetLabel(kFALSE);
+      //    dtcpiptpc->SetMaxITSChiNdof(6.0);
+      //      dtcpiptpc->SetMaxTPCChiNdof(6.0);
+      dtcpiptpc->SetMaxImpactXY(0.2);
+      dtcpiptpc->SetMaxImpactZ(0.25);
+      //      dtcpiptpc->SetMaxSigmaToVertex(6.0);
+    }
+
+    AliFemtoCutMonitorParticleYPt *cutPassYPtpiptpc = new AliFemtoCutMonitorParticleYPt("cutPasspiptpc", 0.13957);
+    AliFemtoCutMonitorParticleYPt *cutFailYPtpiptpc = new AliFemtoCutMonitorParticleYPt("cutFailpiptpc", 0.13957);
+    dtcpiptpc->AddCutMonitor(cutPassYPtpiptpc, cutFailYPtpiptpc);
+
+    AliFemtoShareQualityTPCEntranceSepPairCut *sqpcpiptpc = new AliFemtoShareQualityTPCEntranceSepPairCut();
+    if (runtype == 0) {
+      sqpcpiptpc->SetShareQualityMax(0.0);
+      sqpcpiptpc->SetShareFractionMax(0.05);
+      sqpcpiptpc->SetRemoveSameLabel(kFALSE);
+      sqpcpiptpc->SetTPCEntranceSepMinimum(0.0);
+    }
+    else if (runtype == 1) {
+      sqpcpiptpc->SetShareQualityMax(1.0);
+      sqpcpiptpc->SetShareFractionMax(1.05);
+      sqpcpiptpc->SetRemoveSameLabel(kFALSE);
+      sqpcpiptpc->SetTPCEntranceSepMinimum(0.0);
+    }
+
+    anpiptpc->SetEventCut(mecpiptpc);
+    anpiptpc->SetFirstParticleCut(dtcpiptpc);
+    anpiptpc->SetSecondParticleCut(dtcpiptpc);
+    anpiptpc->SetPairCut(sqpcpiptpc);
+    
+    //     AliFemtoShareQualityCorrFctn *csqqinvpiptpc= new AliFemtoShareQualityCorrFctn("sqqinvcfpiptpc",40,0.0,0.4);
+    //     anpiptpc->AddCorrFctn(csqqinvpiptpc);
+
+    AliFemtoCorrFctnDirectYlm *cylmpiptpc = new AliFemtoCorrFctnDirectYlm("cylmpiptpc",3,100,0.0,1.5,1);
+    anpiptpc->AddCorrFctn(cylmpiptpc);
+    
+    AliFemtoQinvCorrFctn *cqinvpiptpc = new AliFemtoQinvCorrFctn("qinvcfpiptpc", 100,0.0,1.5);
+    anpiptpc->AddCorrFctn(cqinvpiptpc);
+
+    AliFemtoChi2CorrFctn *cchiqinvpiptpc= new AliFemtoChi2CorrFctn("chicfpiptpc",40,0.0,0.4);
+    anpiptpc->AddCorrFctn(cchiqinvpiptpc);
+
+    if (run3d) {
+      AliFemtoBPLCMS3DCorrFctn *cq3dallpiptpc = new AliFemtoBPLCMS3DCorrFctn("cq3dallpiptpc",100,-1.5,1.5);
+      anpiptpc->AddCorrFctn(cq3dallpiptpc);
+    }
+
+    if (runktdep) {
+      // Intrdouce kT binning
+      AliFemtoKTPairCut *ktpairkT1piptpc = new AliFemtoKTPairCut(0.05,0.2);
+      AliFemtoKTPairCut *ktpairkT2piptpc = new AliFemtoKTPairCut(0.3,0.4);
+      AliFemtoKTPairCut *ktpairkT3piptpc = new AliFemtoKTPairCut(0.4,0.55);
+      AliFemtoKTPairCut *ktpairkT4piptpc = new AliFemtoKTPairCut(0.55,2.0);
+      
+      AliFemtoCorrFctnDirectYlm *cylmkT1piptpc = new AliFemtoCorrFctnDirectYlm("cylmkT1piptpc",3,100,0.0,1.5,1);
+      cylmkT1piptpc->SetPairSelectionCut(ktpairkT1piptpc);
+      anpiptpc->AddCorrFctn(cylmkT1piptpc);
+      
+      AliFemtoQinvCorrFctn *cqinvkT1piptpc = new AliFemtoQinvCorrFctn("qinvcfkT1piptpc", 100,0.0,1.5);
+      cqinvkT1piptpc->SetPairSelectionCut(ktpairkT1piptpc);
+      anpiptpc->AddCorrFctn(cqinvkT1piptpc);
+      
+      AliFemtoCorrFctnDirectYlm *cylmkT2piptpc = new AliFemtoCorrFctnDirectYlm("cylmkT2piptpc",3,100,0.0,1.5,1);
+      cylmkT2piptpc->SetPairSelectionCut(ktpairkT2piptpc);
+      anpiptpc->AddCorrFctn(cylmkT2piptpc);
+      
+      AliFemtoQinvCorrFctn *cqinvkT2piptpc = new AliFemtoQinvCorrFctn("qinvcfkT2piptpc", 100,0.0,1.5);
+      cqinvkT2piptpc->SetPairSelectionCut(ktpairkT2piptpc);
+      anpiptpc->AddCorrFctn(cqinvkT2piptpc);
+      
+      AliFemtoCorrFctnDirectYlm *cylmkT3piptpc = new AliFemtoCorrFctnDirectYlm("cylmkT3piptpc",3,100,0.0,1.5,1);
+      cylmkT3piptpc->SetPairSelectionCut(ktpairkT3piptpc);
+      anpiptpc->AddCorrFctn(cylmkT3piptpc);
+      
+      AliFemtoQinvCorrFctn *cqinvkT3piptpc = new AliFemtoQinvCorrFctn("qinvcfkT3piptpc", 100,0.0,1.5);
+      cqinvkT3piptpc->SetPairSelectionCut(ktpairkT3piptpc);
+      anpiptpc->AddCorrFctn(cqinvkT3piptpc);
+      
+      AliFemtoCorrFctnDirectYlm *cylmkT4piptpc = new AliFemtoCorrFctnDirectYlm("cylmkT4piptpc",3,100,0.0,1.5,1);
+      cylmkT4piptpc->SetPairSelectionCut(ktpairkT4piptpc);
+      anpiptpc->AddCorrFctn(cylmkT4piptpc);
+      
+      AliFemtoQinvCorrFctn *cqinvkT4piptpc = new AliFemtoQinvCorrFctn("qinvcfkT4piptpc", 100,0.0,1.5);
+      cqinvkT4piptpc->SetPairSelectionCut(ktpairkT4piptpc);
+      anpiptpc->AddCorrFctn(cqinvkT4piptpc);
+    }
+    //     AliFemtoCorrFctnTPCNcls *cqtpcnclspiptpc = new AliFemtoCorrFctnTPCNcls("cqtpcnclspiptpc",40,0.0,0.4);
+    //     anpiptpc->AddCorrFctn(cqtpcnclspiptpc);
+
+    //     AliFemtoCorrFctnDEtaDPhi *cdetadphipiptpc = new AliFemtoCorrFctnDEtaDPhi("cdetadphipiptpc", 18, 20);
+    //     anpiptpc->AddCorrFctn(cdetadphipiptpc);
+
+    Manager->AddAnalysis(anpiptpc);    
+  }
+  // *** End pion-pion (positive) analysis
+
+  // *** Begin pion-pion (negative) analysis ***
+  if (runNegativeTPCQA) {
+    AliFemtoVertexMultAnalysis *anpimtpc = new AliFemtoVertexMultAnalysis(6, -10.0, 10.0, 1, 0, 10000);
+    anpimtpc->SetNumEventsToMix(10);
+    anpimtpc->SetMinSizePartCollection(2);
+
+    AliFemtoBasicEventCut* mecpimtpc = new AliFemtoBasicEventCut();
+    mecpimtpc->SetEventMult(0,100000);
+    mecpimtpc->SetVertZPos(-1000,1000);
+       
+    AliFemtoESDTrackCut* dtcpimtpc = new AliFemtoESDTrackCut();
+    //     dtcpimtpc->SetPidProbPion(0.0,1.001);
+    //     dtcpimtpc->SetPidProbMuon(0.0,1.0);
+    //     dtcpimtpc->SetPidProbKaon(0.0,1.0);
+    //     dtcpimtpc->SetPidProbProton(0.0,1.0);
+    dtcpimtpc->SetCharge(-1.0);
+    dtcpimtpc->SetPt(0.05,10.0);
+    dtcpimtpc->SetMass(PionMass);
+    // Track quality cuts
+    if (runtype == 0) {
+      dtcpimtpc->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+      //    dtcpimtpc->SetStatus(AliESDtrack::kTPCrefit);
+      //dtcpimtpc->SetStatus(AliESDtrack::kITSrefit);
+      dtcpimtpc->SetminTPCncls(50);
+      dtcpimtpc->SetRemoveKinks(kTRUE);
+      dtcpimtpc->SetLabel(kFALSE);
+      //     dtcpimtpc->SetMaxITSChiNdof(6.0);
+      dtcpimtpc->SetMaxTPCChiNdof(6.0);
+      dtcpimtpc->SetMaxImpactXY(0.2);
+      dtcpimtpc->SetMaxImpactZ(0.25);
+      dtcpimtpc->SetMaxSigmaToVertex(6.0);
+    }
+    else if (runtype == 1) {
+      //      dtcpimtpc->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+      //    dtcpimtpc->SetStatus(AliESDtrack::kTPCrefit);
+      dtcpimtpc->SetStatus(AliESDtrack::kITSrefit);
+      //    dtcpimtpc->SetminTPCncls(50);
+      dtcpimtpc->SetRemoveKinks(kTRUE);
+      dtcpimtpc->SetLabel(kFALSE);
+      //     dtcpimtpc->SetMaxITSChiNdof(6.0);
+      //     dtcpimtpc->SetMaxTPCChiNdof(6.0);
+      dtcpimtpc->SetMaxImpactXY(0.2);
+      dtcpimtpc->SetMaxImpactZ(0.25);
+      //      dtcpimtpc->SetMaxSigmaToVertex(6.0);
+    }
+    
+    AliFemtoCutMonitorParticleYPt *cutPassYPtpimtpc = new AliFemtoCutMonitorParticleYPt("cutPasspimtpc", 0.13957);
+    AliFemtoCutMonitorParticleYPt *cutFailYPtpimtpc = new AliFemtoCutMonitorParticleYPt("cutFailpimtpc", 0.13957);
+    dtcpimtpc->AddCutMonitor(cutPassYPtpimtpc, cutFailYPtpimtpc);
+
+    AliFemtoShareQualityTPCEntranceSepPairCut *sqpcpimtpc = new AliFemtoShareQualityTPCEntranceSepPairCut();
+    if (runtype == 0) {
+      sqpcpimtpc->SetShareQualityMax(0.0);
+      sqpcpimtpc->SetShareFractionMax(0.05);
+      sqpcpimtpc->SetRemoveSameLabel(kFALSE);
+      sqpcpimtpc->SetTPCEntranceSepMinimum(0.0);
+    }
+    else if (runtype == 1) {
+      sqpcpimtpc->SetShareQualityMax(1.0);
+      sqpcpimtpc->SetShareFractionMax(1.05);
+      sqpcpimtpc->SetRemoveSameLabel(kFALSE);
+      sqpcpimtpc->SetTPCEntranceSepMinimum(0.0);
+    }
+    anpimtpc->SetEventCut(mecpimtpc);
+    anpimtpc->SetFirstParticleCut(dtcpimtpc);
+    anpimtpc->SetSecondParticleCut(dtcpimtpc);
+    anpimtpc->SetPairCut(sqpcpimtpc);
+    
+    //     AliFemtoShareQualityCorrFctn *csqqinvpimtpc= new AliFemtoShareQualityCorrFctn("sqqinvcfpimtpc",40,0.0,0.4);
+    //     anpimtpc->AddCorrFctn(csqqinvpimtpc);
+
+    AliFemtoCorrFctnDirectYlm *cylmpimtpc = new AliFemtoCorrFctnDirectYlm("cylmpimtpc",3,100,0.0,1.5,1);
+    anpimtpc->AddCorrFctn(cylmpimtpc);
+    
+    AliFemtoQinvCorrFctn *cqinvpimtpc = new AliFemtoQinvCorrFctn("qinvcfpimtpc", 100,0.0,1.5);
+    anpimtpc->AddCorrFctn(cqinvpimtpc);
+
+    AliFemtoChi2CorrFctn *cchiqinvpimtpc= new AliFemtoChi2CorrFctn("chicfpimtpc",40,0.0,0.4);
+    anpimtpc->AddCorrFctn(cchiqinvpimtpc);
+
+    if (run3d) {
+      AliFemtoBPLCMS3DCorrFctn *cq3dallpimtpc = new AliFemtoBPLCMS3DCorrFctn("cq3dallpimtpc",100,-1.5,1.5);
+      anpimtpc->AddCorrFctn(cq3dallpimtpc);
+    }
+
+    // Intrdouce kT binning
+    if (runktdep) {
+      // Intrdouce kT binning
+      AliFemtoKTPairCut *ktpairkT1pimtpc = new AliFemtoKTPairCut(0.05,0.3);
+      AliFemtoKTPairCut *ktpairkT2pimtpc = new AliFemtoKTPairCut(0.3,0.4);
+      AliFemtoKTPairCut *ktpairkT3pimtpc = new AliFemtoKTPairCut(0.4,0.55);
+      AliFemtoKTPairCut *ktpairkT4pimtpc = new AliFemtoKTPairCut(0.55,2.0);
+      
+      AliFemtoCorrFctnDirectYlm *cylmkT1pimtpc = new AliFemtoCorrFctnDirectYlm("cylmkT1pimtpc",3,100,0.0,1.5,1);
+      cylmkT1pimtpc->SetPairSelectionCut(ktpairkT1pimtpc);
+      anpimtpc->AddCorrFctn(cylmkT1pimtpc);
+      
+      AliFemtoQinvCorrFctn *cqinvkT1pimtpc = new AliFemtoQinvCorrFctn("qinvcfkT1pimtpc", 100,0.0,1.5);
+      cqinvkT1pimtpc->SetPairSelectionCut(ktpairkT1pimtpc);
+      anpimtpc->AddCorrFctn(cqinvkT1pimtpc);
+      
+      AliFemtoCorrFctnDirectYlm *cylmkT2pimtpc = new AliFemtoCorrFctnDirectYlm("cylmkT2pimtpc",3,100,0.0,1.5,1);
+      cylmkT2pimtpc->SetPairSelectionCut(ktpairkT2pimtpc);
+      anpimtpc->AddCorrFctn(cylmkT2pimtpc);
+      
+      AliFemtoQinvCorrFctn *cqinvkT2pimtpc = new AliFemtoQinvCorrFctn("qinvcfkT2pimtpc", 100,0.0,1.5);
+      cqinvkT2pimtpc->SetPairSelectionCut(ktpairkT2pimtpc);
+      anpimtpc->AddCorrFctn(cqinvkT2pimtpc);
+      
+      AliFemtoCorrFctnDirectYlm *cylmkT3pimtpc = new AliFemtoCorrFctnDirectYlm("cylmkT3pimtpc",3,100,0.0,1.5,1);
+      cylmkT3pimtpc->SetPairSelectionCut(ktpairkT3pimtpc);
+      anpimtpc->AddCorrFctn(cylmkT3pimtpc);
+      
+      AliFemtoQinvCorrFctn *cqinvkT3pimtpc = new AliFemtoQinvCorrFctn("qinvcfkT3pimtpc", 100,0.0,1.5);
+      cqinvkT3pimtpc->SetPairSelectionCut(ktpairkT3pimtpc);
+      anpimtpc->AddCorrFctn(cqinvkT3pimtpc);
+      
+      AliFemtoCorrFctnDirectYlm *cylmkT4pimtpc = new AliFemtoCorrFctnDirectYlm("cylmkT4pimtpc",3,100,0.0,1.5,1);
+      cylmkT4pimtpc->SetPairSelectionCut(ktpairkT4pimtpc);
+      anpimtpc->AddCorrFctn(cylmkT4pimtpc);
+      
+      AliFemtoQinvCorrFctn *cqinvkT4pimtpc = new AliFemtoQinvCorrFctn("qinvcfkT4pimtpc", 100,0.0,1.5);
+      cqinvkT4pimtpc->SetPairSelectionCut(ktpairkT4pimtpc);
+      anpimtpc->AddCorrFctn(cqinvkT4pimtpc);
+    }
+    //     AliFemtoCorrFctnTPCNcls *cqtpcnclspimtpc = new AliFemtoCorrFctnTPCNcls("cqtpcnclspimtpc",40,0.0,0.4);
+    //     anpimtpc->AddCorrFctn(cqtpcnclspimtpc);
+
+    //     AliFemtoCorrFctnDEtaDPhi *cdetadphipimtpc = new AliFemtoCorrFctnDEtaDPhi("cdetadphipimtpc", 18, 20);
+    //     anpimtpc->AddCorrFctn(cdetadphipimtpc);
+
+    Manager->AddAnalysis(anpimtpc);    
+  }
+  // *** End pion-pion (negative) analysis
+
+  return Manager;
+}                         
+                      
diff --git a/PWGCF/FEMTOSCOPY/macros/Train/PionsFemtoscopy/ConfigFemtoAnalysis.C b/PWGCF/FEMTOSCOPY/macros/Train/PionsFemtoscopy/ConfigFemtoAnalysis.C
new file mode 100644 (file)
index 0000000..95dedab
--- /dev/null
@@ -0,0 +1,356 @@
+/*********************************************************************
+ *                                                                   *
+ * Configfemtoanalysis.C - configuration macro for the femtoscopic   *
+ * analysis, meant as a QA process for two-particle effects          *
+ *                                                                   *
+ * Author: Adam Kisiel (Adam.Kisiel@cern.ch)                         *
+ *                                                                   *
+ *********************************************************************/
+
+#if !defined(__CINT__) || defined(__MAKECINT_)
+#include "AliFemtoManager.h"
+#include "AliFemtoEventReaderESDChain.h"
+#include "AliFemtoEventReaderESDChainKine.h"
+#include "AliFemtoEventReaderAODChain.h"
+#include "AliFemtoSimpleAnalysis.h"
+#include "AliFemtoBasicEventCut.h"
+#include "AliFemtoESDTrackCut.h"
+#include "AliFemtoCorrFctn.h"
+#include "AliFemtoCutMonitorParticleYPt.h"
+#include "AliFemtoCutMonitorParticleVertPos.h"
+#include "AliFemtoCutMonitorParticleMomRes.h"
+#include "AliFemtoCutMonitorParticlePID.h"
+#include "AliFemtoCutMonitorEventMult.h"
+#include "AliFemtoCutMonitorEventVertex.h"
+#include "AliFemtoShareQualityTPCEntranceSepPairCut.h"
+#include "AliFemtoPairCutAntiGamma.h"
+#include "AliFemtoPairCutRadialDistance.h"
+#include "AliFemtoQinvCorrFctn.h"
+#include "AliFemtoCorrFctnNonIdDR.h"
+#include "AliFemtoShareQualityCorrFctn.h"
+#include "AliFemtoTPCInnerCorrFctn.h"
+#include "AliFemtoVertexMultAnalysis.h"
+#include "AliFemtoCorrFctn3DSpherical.h"
+#include "AliFemtoChi2CorrFctn.h"
+#include "AliFemtoCorrFctnTPCNcls.h"
+#include "AliFemtoBPLCMS3DCorrFctn.h"
+#include "AliFemtoCorrFctn3DLCMSSym.h"
+#include "AliFemtoModelBPLCMSCorrFctn.h"
+#include "AliFemtoModelCorrFctn3DSpherical.h"
+#include "AliFemtoModelGausLCMSFreezeOutGenerator.h"
+#include "AliFemtoModelGausRinvFreezeOutGenerator.h"
+#include "AliFemtoModelManager.h"
+#include "AliFemtoModelWeightGeneratorBasic.h"
+#include "AliFemtoModelWeightGeneratorLednicky.h"
+#include "AliFemtoCorrFctnDirectYlm.h"
+#include "AliFemtoModelCorrFctnDirectYlm.h"
+#include "AliFemtoModelCorrFctnSource.h"
+#include "AliFemtoCutMonitorParticlePtPDG.h"
+#include "AliFemtoKTPairCut.h"
+#endif
+
+//________________________________________________________________________
+AliFemtoManager* ConfigFemtoAnalysis() {
+
+  double PionMass = 0.13956995;
+  double KaonMass = 0.493677;
+  double ProtonMass = 0.938272013;
+       
+
+  int runmults[10] = {1, 1, 1, 1, 1, 1, 1, 1, 1, 1};
+  int multbins[11] = {0.001, 50, 100, 200, 300, 400, 500, 600, 700, 800, 900};
+  
+  int runch[3] = {1, 1, 1};
+  const char *chrgs[3] = { "pip", "pim", "pimpip" };
+  
+
+  int runktdep = 1;
+  double ktrng[3] = {0.01, 0.7, 100.0};
+  //  double ktrng[8] = {0.2, 0.3, 0.4, 0.5, 0.6, 0.7, 0.8, 1.0};
+
+  int numOfMultBins = 10;  
+  int numOfChTypes = 3;
+  int numOfkTbins = 2;
+
+  int runqinv = 1;
+  int runshlcms = 1;// 0:PRF(PAP), 1:LCMS(PP,APAP)
+
+  int runtype = 2; // Types 0 - global, 1 - ITS only, 2 - TPC Inner
+  int isrealdata = 1;
+
+  int gammacut = 1;
+  
+  double shqmax = 1.2;
+  int nbinssh = 100;
+
+  AliFemtoEventReaderAODChain *Reader = new AliFemtoEventReaderAODChain();
+  Reader->SetFilterBit(7);
+  Reader->SetCentralityPreSelection(0.001, 910);
+
+  AliFemtoManager* Manager = new AliFemtoManager();
+  Manager->SetEventReader(Reader);
+
+  AliFemtoVertexMultAnalysis    *anetaphitpc[10*3];
+  AliFemtoBasicEventCut         *mecetaphitpc[10*3];
+  AliFemtoCutMonitorEventMult   *cutPassEvMetaphitpc[10*3];
+  AliFemtoCutMonitorEventMult   *cutFailEvMetaphitpc[10*3];
+  AliFemtoCutMonitorEventVertex *cutPassEvVetaphitpc[10*3];
+  AliFemtoCutMonitorEventVertex *cutFailEvVetaphitpc[10*3];
+  AliFemtoESDTrackCut           *dtc1etaphitpc[10*3];
+  AliFemtoESDTrackCut           *dtc2etaphitpc[10*3];
+  AliFemtoCutMonitorParticleYPt *cutPass1YPtetaphitpc[10*3];
+  AliFemtoCutMonitorParticleYPt *cutFail1YPtetaphitpc[10*3];
+  AliFemtoCutMonitorParticlePID *cutPass1PIDetaphitpc[10*3];
+  AliFemtoCutMonitorParticlePID *cutFail1PIDetaphitpc[10*3];
+  AliFemtoCutMonitorParticleYPt *cutPass2YPtetaphitpc[10*3];
+  AliFemtoCutMonitorParticleYPt *cutFail2YPtetaphitpc[10*3];
+  AliFemtoCutMonitorParticlePID *cutPass2PIDetaphitpc[10*3];
+  AliFemtoCutMonitorParticlePID *cutFail2PIDetaphitpc[10*3];
+  //   AliFemtoPairCutAntiGamma      *sqpcetaphitpcdiff[10*3];
+  //   AliFemtoShareQualityTPCEntranceSepPairCut      *sqpcetaphitpcsame[10*3];
+  AliFemtoPairCutAntiGamma      *sqpcetaphitpc[10*3];
+  //  AliFemtoPairCutRadialDistance      *sqpcetaphitpc[10*3];
+  //  AliFemtoChi2CorrFctn          *cchiqinvetaphitpc[20*2];
+  AliFemtoKTPairCut             *ktpcuts[10*3*2];
+  AliFemtoCorrFctnDirectYlm     *cylmkttpc[10*3];
+  //AliFemtoCorrFctnDirectYlm     *cylmetaphitpc[10*3];
+  AliFemtoQinvCorrFctn          *cqinvkttpc[10*3*2];
+  AliFemtoQinvCorrFctn          *cqinvtpc[10*3];
+  AliFemtoCorrFctnNonIdDR       *ckstartpc[10*3];
+  AliFemtoCorrFctnDEtaDPhi      *cdedpetaphi[10*3];
+
+  //   AliFemtoCorrFctn3DLCMSSym     *cq3dlcmskttpc[20*2];
+  //   AliFemtoCorrFctnTPCNcls       *cqinvnclstpc[20];
+  //   AliFemtoShareQualityCorrFctn  *cqinvsqtpc[20*10];
+  //   AliFemtoChi2CorrFctn          *cqinvchi2tpc[20];
+  //   AliFemtoTPCInnerCorrFctn      *cqinvinnertpc[20*10];
+  
+  // *** Third QA task - HBT analysis with all pair cuts off, TPC only ***
+  // *** Begin pion-pion (positive) analysis ***
+  int aniter = 0;  
+
+  for (int imult = 0; imult < numOfMultBins; imult++) {
+    if (runmults[imult]) {
+
+      for (int ichg = 0; ichg < numOfChTypes; ichg++) {
+       if (runch[ichg]) {
+
+         aniter = ichg * numOfMultBins + imult;
+         anetaphitpc[aniter] = new AliFemtoVertexMultAnalysis(8, -8.0, 8.0, 4, multbins[imult], multbins[imult+1]);
+         anetaphitpc[aniter]->SetNumEventsToMix(10);
+         anetaphitpc[aniter]->SetMinSizePartCollection(1);
+
+         mecetaphitpc[aniter] = new AliFemtoBasicEventCut();
+         mecetaphitpc[aniter]->SetEventMult(0.001,100000);
+         mecetaphitpc[aniter]->SetVertZPos(-8,8);
+
+         if (isrealdata)
+           mecetaphitpc[aniter]->SetAcceptOnlyPhysics(kTRUE);
+                 
+         cutPassEvMetaphitpc[aniter] = new AliFemtoCutMonitorEventMult(Form("cutPass%stpcM%i", chrgs[ichg], imult));
+         cutFailEvMetaphitpc[aniter] = new AliFemtoCutMonitorEventMult(Form("cutFail%stpcM%i", chrgs[ichg], imult));
+         mecetaphitpc[aniter]->AddCutMonitor(cutPassEvMetaphitpc[aniter], cutFailEvMetaphitpc[aniter]);
+         
+         cutPassEvVetaphitpc[aniter] = new AliFemtoCutMonitorEventVertex(Form("cutPass%stpcM%i", chrgs[ichg], imult));
+         cutFailEvVetaphitpc[aniter] = new AliFemtoCutMonitorEventVertex(Form("cutFail%stpcM%i", chrgs[ichg], imult));
+         mecetaphitpc[aniter]->AddCutMonitor(cutPassEvVetaphitpc[aniter], cutFailEvVetaphitpc[aniter]);
+         
+         dtc1etaphitpc[aniter] = new AliFemtoESDTrackCut();
+         dtc2etaphitpc[aniter] = new AliFemtoESDTrackCut();
+
+         if (ichg == 0)
+           dtc1etaphitpc[aniter]->SetCharge(1.0);
+         else if (ichg == 1)
+           dtc1etaphitpc[aniter]->SetCharge(-1.0);
+         else if (ichg == 2) {
+           dtc1etaphitpc[aniter]->SetCharge(-1.0);
+           dtc2etaphitpc[aniter]->SetCharge(1.0);
+         }
+         
+         dtc1etaphitpc[aniter]->SetEta(-0.8,0.8);
+         dtc1etaphitpc[aniter]->SetMass(PionMass);       
+         dtc1etaphitpc[aniter]->SetMostProbablePion();
+
+         if (ichg == 2) {          
+           dtc2etaphitpc[aniter]->SetEta(-0.8,0.8);
+           dtc2etaphitpc[aniter]->SetMass(PionMass);     
+           dtc2etaphitpc[aniter]->SetMostProbablePion();
+         }
+         
+         // Track quality cuts
+
+         if (runtype == 0) {
+           dtc1etaphitpc[aniter]->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+           //      dtc1etaphitpc[aniter]->SetStatus(AliESDtrack::kTPCrefit);
+           //    dtc1etaphitpc[aniter]->SetStatus(AliESDtrack::kITSrefit);
+           dtc1etaphitpc[aniter]->SetminTPCncls(80);
+           dtc1etaphitpc[aniter]->SetRemoveKinks(kTRUE);
+           dtc1etaphitpc[aniter]->SetLabel(kFALSE);
+           //    dtc1etaphitpc[aniter]->SetMaxITSChiNdof(6.0);
+           dtc1etaphitpc[aniter]->SetMaxTPCChiNdof(4.0);
+           dtc1etaphitpc[aniter]->SetMaxImpactXY(0.2);
+           //            dtc1etaphitpc[aniter]->SetMaxImpactXYPtDep(0.0182, 0.0350, -1.01);
+           dtc1etaphitpc[aniter]->SetMaxImpactZ(0.15);
+           //      dtc1etaphitpc[aniter]->SetMaxSigmaToVertex(6.0);
+         }
+         else if (runtype == 1) {
+           //      dtc1etaphitpc[aniter]->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+           //    dtc1etaphitpc[aniter]->SetStatus(AliESDtrack::kTPCrefit);
+           //      dtc1etaphitpc[aniter]->SetStatus(AliESDtrack::kITSrefit|AliESDtrack::kITSpureSA);
+           //      dtc1etaphitpc[aniter]->SetminTPCncls(70);
+           dtc1etaphitpc[aniter]->SetStatus(AliESDtrack::kITSrefit);
+           dtc1etaphitpc[aniter]->SetRemoveKinks(kTRUE);
+           dtc1etaphitpc[aniter]->SetLabel(kFALSE);
+           //    dtc1etaphitpc[aniter]->SetMaxITSChiNdof(6.0);
+           //      dtc1etaphitpc[aniter]->SetMaxTPCChiNdof(6.0);
+           dtc1etaphitpc[aniter]->SetMaxImpactXY(0.2);
+           dtc1etaphitpc[aniter]->SetMaxImpactZ(0.25);
+           //      dtc1etaphitpc[aniter]->SetMaxSigmaToVertex(6.0);
+         }
+         else if (runtype == 2) {
+           dtc1etaphitpc[aniter]->SetStatus(AliESDtrack::kTPCin);
+           dtc1etaphitpc[aniter]->SetminTPCncls(80);
+           dtc1etaphitpc[aniter]->SetRemoveKinks(kTRUE);
+           dtc1etaphitpc[aniter]->SetLabel(kFALSE);
+           dtc1etaphitpc[aniter]->SetMaxTPCChiNdof(4.0);
+           dtc1etaphitpc[aniter]->SetMaxImpactXY(2.4);
+           dtc1etaphitpc[aniter]->SetMaxImpactZ(3.0);
+
+           if (ichg == 2) {
+             dtc2etaphitpc[aniter]->SetStatus(AliESDtrack::kTPCin);
+             dtc2etaphitpc[aniter]->SetminTPCncls(80);
+             dtc2etaphitpc[aniter]->SetRemoveKinks(kTRUE);
+             dtc2etaphitpc[aniter]->SetLabel(kFALSE);
+             dtc2etaphitpc[aniter]->SetMaxTPCChiNdof(4.0);
+             dtc2etaphitpc[aniter]->SetMaxImpactXY(0.25);
+             dtc2etaphitpc[aniter]->SetMaxImpactZ(0.15);
+           }
+           
+         }
+         
+         cutPass1YPtetaphitpc[aniter] = new AliFemtoCutMonitorParticleYPt(Form("cutPass1%stpcM%i", chrgs[ichg], imult),PionMass);
+         cutFail1YPtetaphitpc[aniter] = new AliFemtoCutMonitorParticleYPt(Form("cutFail1%stpcM%i", chrgs[ichg], imult),PionMass);
+         dtc1etaphitpc[aniter]->AddCutMonitor(cutPass1YPtetaphitpc[aniter], cutFail1YPtetaphitpc[aniter]);
+         
+         cutPass1PIDetaphitpc[aniter] = new AliFemtoCutMonitorParticlePID(Form("cutPass1%stpcM%i", chrgs[ichg], imult),2);//0-pion,1-kaon,2-proton
+         cutFail1PIDetaphitpc[aniter] = new AliFemtoCutMonitorParticlePID(Form("cutFail1%stpcM%i", chrgs[ichg], imult),2);
+         dtc1etaphitpc[aniter]->AddCutMonitor(cutPass1PIDetaphitpc[aniter], cutFail1PIDetaphitpc[aniter]);
+
+         if (ichg == 2){
+           cutPass2PIDetaphitpc[aniter] = new AliFemtoCutMonitorParticlePID(Form("cutPass2%stpcM%i", chrgs[ichg], imult),2);//0-pion,1-kaon,2-proton
+           cutFail2PIDetaphitpc[aniter] = new AliFemtoCutMonitorParticlePID(Form("cutFail2%stpcM%i", chrgs[ichg], imult),2);
+           dtc2etaphitpc[aniter]->AddCutMonitor(cutPass2PIDetaphitpc[aniter], cutFail2PIDetaphitpc[aniter]);
+         }
+
+         sqpcetaphitpc[aniter] = new AliFemtoPairCutAntiGamma();
+
+         if (runtype == 0) {
+           sqpcetaphitpc[aniter]->SetShareQualityMax(1.0);
+           sqpcetaphitpc[aniter]->SetShareFractionMax(0.05);
+           sqpcetaphitpc[aniter]->SetRemoveSameLabel(kFALSE);
+           // sqpcetaphitpc[aniter]->SetMaxEEMinv(0.0);
+           // sqpcetaphitpc[aniter]->SetMaxThetaDiff(0.0);
+           //      sqpcetaphitpc[aniter]->SetTPCEntranceSepMinimum(1.5);
+           //sqpcetaphitpc[aniter]->SetRadialDistanceMinimum(0.12, 0.03);
+           //      sqpcetaphitpc[aniter]->SetEtaDifferenceMinimum(0.02);
+         }
+         else if (runtype == 1) {
+           sqpcetaphitpc[aniter]->SetShareQualityMax(1.0);
+           sqpcetaphitpc[aniter]->SetShareFractionMax(1.05);
+           sqpcetaphitpc[aniter]->SetRemoveSameLabel(kFALSE);
+           // sqpcetaphitpc[aniter]->SetMaxEEMinv(0.002);
+           // sqpcetaphitpc[aniter]->SetMaxThetaDiff(0.008);
+           //      sqpcetaphitpc[aniter]->SetTPCEntranceSepMinimum(5.0);
+           //sqpcetaphitpc[aniter]->SetRadialDistanceMinimum(1.2, 0.03);
+           //      sqpcetaphitpc[aniter]->SetEtaDifferenceMinimum(0.02);
+         }
+         else if (runtype == 2) {
+           sqpcetaphitpc[aniter]->SetUseAOD(kTRUE);
+           sqpcetaphitpc[aniter]->SetShareQualityMax(1.0);
+           sqpcetaphitpc[aniter]->SetShareFractionMax(0.05);
+           sqpcetaphitpc[aniter]->SetRemoveSameLabel(kFALSE);
+
+           if (gammacut == 0) {              
+             sqpcetaphitpc[aniter]->SetMaxEEMinv(0.0);
+             sqpcetaphitpc[aniter]->SetMaxThetaDiff(0.0);
+           }
+           else if (gammacut == 1) { 
+             sqpcetaphitpc[aniter]->SetMaxEEMinv(0.002);
+             sqpcetaphitpc[aniter]->SetMaxThetaDiff(0.008);
+           }
+
+           //phi-star cut - values from Johana
+           //      sqpcetaphitpc[aniter]->SetPhiStarDifferenceMinimum(0.012);
+           //      sqpcetaphitpc[aniter]->SetEtaDifferenceMinimum(0.017);
+
+         }
+         
+         anetaphitpc[aniter]->SetEventCut(mecetaphitpc[aniter]);
+
+         if (ichg == 2) {
+           anetaphitpc[aniter]->SetFirstParticleCut(dtc1etaphitpc[aniter]);
+           anetaphitpc[aniter]->SetSecondParticleCut(dtc2etaphitpc[aniter]);
+         }
+         else {
+           anetaphitpc[aniter]->SetFirstParticleCut(dtc1etaphitpc[aniter]);
+           anetaphitpc[aniter]->SetSecondParticleCut(dtc1etaphitpc[aniter]);
+         }
+           
+         anetaphitpc[aniter]->SetPairCut(sqpcetaphitpc[aniter]);
+         
+         if (ichg == 2) {
+           ckstartpc[aniter] = new AliFemtoCorrFctnNonIdDR(Form("ckstar%stpcM%i", chrgs[ichg], imult),nbinssh,0.0,shqmax);
+           anetaphitpc[aniter]->AddCorrFctn(ckstartpc[aniter]);
+         }
+         else {  
+           cqinvtpc[aniter] = new AliFemtoQinvCorrFctn(Form("cqinv%stpcM%i", chrgs[ichg], imult),nbinssh,0.0,shqmax);
+           anetaphitpc[aniter]->AddCorrFctn(cqinvtpc[aniter]);
+         }
+
+          cylmkttpc[aniter] = new AliFemtoCorrFctnDirectYlm(Form("cylm%stpcM%i", chrgs[ichg], imult),3,nbinssh, 0.0,shqmax,runshlcms);
+          anetaphitpc[aniter]->AddCorrFctn(cylmkttpc[aniter]);
+
+         if (runktdep) {
+           int ktm;
+           for (int ikt=0; ikt<numOfkTbins; ikt++) {
+
+             ktm = aniter * numOfkTbins + ikt;
+             ktpcuts[ktm] = new AliFemtoKTPairCut(ktrng[ikt], ktrng[ikt+1]);
+             
+             cylmkttpc[ktm] = new AliFemtoCorrFctnDirectYlm(Form("cylm%stpcM%ikT%i", chrgs[ichg], imult, ikt),3,nbinssh,0.0,shqmax,0);
+             cylmkttpc[ktm]->SetPairSelectionCut(ktpcuts[ktm]);
+             anetaphitpc[aniter]->AddCorrFctn(cylmkttpc[ktm]);
+             
+             cqinvkttpc[ktm] = new AliFemtoQinvCorrFctn(Form("cqinv%stpcM%ikT%i", chrgs[ichg], imult, ikt),nbinssh,0.0,(imult>6)?shqmax*2.5:shqmax);
+             cqinvkttpc[ktm]->SetPairSelectionCut(ktpcuts[ktm]);
+             anetaphitpc[aniter]->AddCorrFctn(cqinvkttpc[ktm]);
+
+             //              cqinvsqtpc[ktm] = new AliFemtoShareQualityCorrFctn(Form("cqinvsq%stpcM%ikT%i", chrgs[ichg], imult, ikt),nbinssh,0.0,shqmax);
+             //              cqinvsqtpc[ktm]->SetPairSelectionCut(ktpcuts[ktm]);
+             //              anetaphitpc[aniter]->AddCorrFctn(cqinvsqtpc[ktm]);
+
+             //              cqinvinnertpc[ktm] = new AliFemtoTPCInnerCorrFctn(Form("cqinvinner%stpcM%ikT%i", chrgs[ichg], imult, ikt),nbinssh,0.0,shqmax);
+             //              cqinvinnertpc[ktm]->SetPairSelectionCut(ktpcuts[ktm]);
+             //              cqinvinnertpc[ktm]->SetRadius(1.2);
+             //              anetaphitpc[aniter]->AddCorrFctn(cqinvinnertpc[ktm]);
+
+             //              if (run3d) {
+             //                cq3dlcmskttpc[ktm] = new AliFemtoCorrFctn3DLCMSSym(Form("cq3d%stpcM%ikT%i", chrgs[ichg], imult, ikt),60,(imult>3)?((imult>6)?((imult>7)?0.6:0.4):0.25):0.15);
+             //                cq3dlcmskttpc[ktm]->SetPairSelectionCut(ktpcuts[ktm]);
+             //                anetaphitpc[aniter]->AddCorrFctn(cq3dlcmskttpc[ktm]);
+             //              }
+           }
+         }
+         
+        // cdedpetaphi[aniter] = new AliFemtoCorrFctnDEtaDPhi(Form("cdedp%stpcM%i", chrgs[ichg], imult),24, 24);
+        // anetaphitpc[aniter]->AddCorrFctn(cdedpetaphi[aniter]);
+         
+         Manager->AddAnalysis(anetaphitpc[aniter]);
+       }
+      }
+    }
+  }
+  // *** End pion-pion (positive) analysis
+
+  return Manager;
+}                         
diff --git a/PWGCF/FEMTOSCOPY/macros/Train/ProtonFemtoscopy/ConfigFemtoAnalysis.C b/PWGCF/FEMTOSCOPY/macros/Train/ProtonFemtoscopy/ConfigFemtoAnalysis.C
new file mode 100644 (file)
index 0000000..2174613
--- /dev/null
@@ -0,0 +1,359 @@
+/*********************************************************************
+ *                                                                   *
+ * Configfemtoanalysis.C - configuration macro for the femtoscopic   *
+ * analysis, meant as a QA process for two-particle effects          *
+ *                                                                   *
+ * Author: Adam Kisiel (Adam.Kisiel@cern.ch)                         *
+ *                                                                   *
+ *********************************************************************/
+
+#if !defined(__CINT__) || defined(__MAKECINT_)
+#include "AliFemtoManager.h"
+#include "AliFemtoEventReaderESDChain.h"
+#include "AliFemtoEventReaderESDChainKine.h"
+#include "AliFemtoEventReaderAODChain.h"
+#include "AliFemtoSimpleAnalysis.h"
+#include "AliFemtoBasicEventCut.h"
+#include "AliFemtoESDTrackCut.h"
+#include "AliFemtoCorrFctn.h"
+#include "AliFemtoCutMonitorParticleYPt.h"
+#include "AliFemtoCutMonitorParticleVertPos.h"
+#include "AliFemtoCutMonitorParticleMomRes.h"
+#include "AliFemtoCutMonitorParticlePID.h"
+#include "AliFemtoCutMonitorEventMult.h"
+#include "AliFemtoCutMonitorEventVertex.h"
+#include "AliFemtoShareQualityTPCEntranceSepPairCut.h"
+#include "AliFemtoPairCutAntiGamma.h"
+#include "AliFemtoPairCutRadialDistance.h"
+#include "AliFemtoQinvCorrFctn.h"
+#include "AliFemtoCorrFctnNonIdDR.h"
+#include "AliFemtoShareQualityCorrFctn.h"
+#include "AliFemtoTPCInnerCorrFctn.h"
+#include "AliFemtoVertexMultAnalysis.h"
+#include "AliFemtoCorrFctn3DSpherical.h"
+#include "AliFemtoChi2CorrFctn.h"
+#include "AliFemtoCorrFctnTPCNcls.h"
+#include "AliFemtoBPLCMS3DCorrFctn.h"
+#include "AliFemtoCorrFctn3DLCMSSym.h"
+#include "AliFemtoModelBPLCMSCorrFctn.h"
+#include "AliFemtoModelCorrFctn3DSpherical.h"
+#include "AliFemtoModelGausLCMSFreezeOutGenerator.h"
+#include "AliFemtoModelGausRinvFreezeOutGenerator.h"
+#include "AliFemtoModelManager.h"
+#include "AliFemtoModelWeightGeneratorBasic.h"
+#include "AliFemtoModelWeightGeneratorLednicky.h"
+#include "AliFemtoCorrFctnDirectYlm.h"
+#include "AliFemtoModelCorrFctnDirectYlm.h"
+#include "AliFemtoModelCorrFctnSource.h"
+#include "AliFemtoCutMonitorParticlePtPDG.h"
+#include "AliFemtoKTPairCut.h"
+#endif
+
+//________________________________________________________________________
+AliFemtoManager* ConfigFemtoAnalysis() {
+
+  double PionMass = 0.13956995;
+  double KaonMass = 0.493677;
+  double ProtonMass = 0.938272013;
+       
+
+  int runmults[10] = {1, 1, 1, 1, 1, 1, 1, 1, 1, 1};
+  int multbins[11] = {0.001, 50, 100, 200, 300, 400, 500, 600, 700, 800, 900};
+  
+  int runch[3] = {1, 1, 1};
+  const char *chrgs[3] = { "PP", "APAP", "PAP" };
+  
+
+  int runktdep = 1;
+  double ktrng[3] = {0.01, 0.7, 100.0};
+  //  double ktrng[8] = {0.2, 0.3, 0.4, 0.5, 0.6, 0.7, 0.8, 1.0};
+
+  int numOfMultBins = 10;  
+  int numOfChTypes = 3;
+  int numOfkTbins = 2;
+
+  int runqinv = 1;
+  int runshlcms = 1;// 0:PRF(PAP), 1:LCMS(PP,APAP)
+
+  int runtype = 2; // Types 0 - global, 1 - ITS only, 2 - TPC Inner
+  int isrealdata = 1;
+
+  int gammacut = 1;
+  
+  double shqmax = 0.5;
+  int nbinssh = 100;
+
+  AliFemtoEventReaderAODChain *Reader = new AliFemtoEventReaderAODChain();
+  Reader->SetFilterBit(7);
+  Reader->SetCentralityPreSelection(0.001, 910);
+
+  AliFemtoManager* Manager = new AliFemtoManager();
+  Manager->SetEventReader(Reader);
+
+  AliFemtoVertexMultAnalysis    *anetaphitpc[10*3];
+  AliFemtoBasicEventCut         *mecetaphitpc[10*3];
+  AliFemtoCutMonitorEventMult   *cutPassEvMetaphitpc[10*3];
+  AliFemtoCutMonitorEventMult   *cutFailEvMetaphitpc[10*3];
+  AliFemtoCutMonitorEventVertex *cutPassEvVetaphitpc[10*3];
+  AliFemtoCutMonitorEventVertex *cutFailEvVetaphitpc[10*3];
+  AliFemtoESDTrackCut           *dtc1etaphitpc[10*3];
+  AliFemtoESDTrackCut           *dtc2etaphitpc[10*3];
+  AliFemtoCutMonitorParticleYPt *cutPass1YPtetaphitpc[10*3];
+  AliFemtoCutMonitorParticleYPt *cutFail1YPtetaphitpc[10*3];
+  AliFemtoCutMonitorParticlePID *cutPass1PIDetaphitpc[10*3];
+  AliFemtoCutMonitorParticlePID *cutFail1PIDetaphitpc[10*3];
+  AliFemtoCutMonitorParticleYPt *cutPass2YPtetaphitpc[10*3];
+  AliFemtoCutMonitorParticleYPt *cutFail2YPtetaphitpc[10*3];
+  AliFemtoCutMonitorParticlePID *cutPass2PIDetaphitpc[10*3];
+  AliFemtoCutMonitorParticlePID *cutFail2PIDetaphitpc[10*3];
+  //   AliFemtoPairCutAntiGamma      *sqpcetaphitpcdiff[10*3];
+  //   AliFemtoShareQualityTPCEntranceSepPairCut      *sqpcetaphitpcsame[10*3];
+  AliFemtoPairCutAntiGamma      *sqpcetaphitpc[10*3];
+  //  AliFemtoPairCutRadialDistance      *sqpcetaphitpc[10*3];
+  //  AliFemtoChi2CorrFctn          *cchiqinvetaphitpc[20*2];
+  AliFemtoKTPairCut             *ktpcuts[10*3*2];
+  AliFemtoCorrFctnDirectYlm     *cylmkttpc[10*3];
+  //AliFemtoCorrFctnDirectYlm     *cylmetaphitpc[10*3];
+  AliFemtoQinvCorrFctn          *cqinvkttpc[10*3*2];
+  AliFemtoQinvCorrFctn          *cqinvtpc[10*3];
+  AliFemtoCorrFctnNonIdDR       *ckstartpc[10*3];
+  AliFemtoCorrFctnDEtaDPhi      *cdedpetaphi[10*3];
+
+  //   AliFemtoCorrFctn3DLCMSSym     *cq3dlcmskttpc[20*2];
+  //   AliFemtoCorrFctnTPCNcls       *cqinvnclstpc[20];
+  //   AliFemtoShareQualityCorrFctn  *cqinvsqtpc[20*10];
+  //   AliFemtoChi2CorrFctn          *cqinvchi2tpc[20];
+  //   AliFemtoTPCInnerCorrFctn      *cqinvinnertpc[20*10];
+  
+  // *** Third QA task - HBT analysis with all pair cuts off, TPC only ***
+  // *** Begin pion-pion (positive) analysis ***
+  int aniter = 0;  
+
+  for (int imult = 0; imult < numOfMultBins; imult++) {
+    if (runmults[imult]) {
+
+      for (int ichg = 0; ichg < numOfChTypes; ichg++) {
+       if (runch[ichg]) {
+
+         aniter = ichg * numOfMultBins + imult;
+         anetaphitpc[aniter] = new AliFemtoVertexMultAnalysis(8, -8.0, 8.0, 4, multbins[imult], multbins[imult+1]);
+         anetaphitpc[aniter]->SetNumEventsToMix(10);
+         anetaphitpc[aniter]->SetMinSizePartCollection(1);
+
+         mecetaphitpc[aniter] = new AliFemtoBasicEventCut();
+         mecetaphitpc[aniter]->SetEventMult(0.001,100000);
+         mecetaphitpc[aniter]->SetVertZPos(-8,8);
+
+         if (isrealdata)
+           mecetaphitpc[aniter]->SetAcceptOnlyPhysics(kTRUE);
+                 
+         cutPassEvMetaphitpc[aniter] = new AliFemtoCutMonitorEventMult(Form("cutPass%stpcM%i", chrgs[ichg], imult));
+         cutFailEvMetaphitpc[aniter] = new AliFemtoCutMonitorEventMult(Form("cutFail%stpcM%i", chrgs[ichg], imult));
+         mecetaphitpc[aniter]->AddCutMonitor(cutPassEvMetaphitpc[aniter], cutFailEvMetaphitpc[aniter]);
+         
+         cutPassEvVetaphitpc[aniter] = new AliFemtoCutMonitorEventVertex(Form("cutPass%stpcM%i", chrgs[ichg], imult));
+         cutFailEvVetaphitpc[aniter] = new AliFemtoCutMonitorEventVertex(Form("cutFail%stpcM%i", chrgs[ichg], imult));
+         mecetaphitpc[aniter]->AddCutMonitor(cutPassEvVetaphitpc[aniter], cutFailEvVetaphitpc[aniter]);
+         
+         dtc1etaphitpc[aniter] = new AliFemtoESDTrackCut();
+         dtc2etaphitpc[aniter] = new AliFemtoESDTrackCut();
+
+         if (ichg == 0)
+           dtc1etaphitpc[aniter]->SetCharge(1.0);
+         else if (ichg == 1)
+           dtc1etaphitpc[aniter]->SetCharge(-1.0);
+         else if (ichg == 2) {
+           dtc1etaphitpc[aniter]->SetCharge(-1.0);
+           dtc2etaphitpc[aniter]->SetCharge(1.0);
+         }
+         
+         dtc1etaphitpc[aniter]->SetEta(-0.8,0.8);
+         dtc1etaphitpc[aniter]->SetMass(ProtonMass);     
+         dtc1etaphitpc[aniter]->SetMostProbableProton();
+
+         if (ichg == 2) {          
+           dtc2etaphitpc[aniter]->SetEta(-0.8,0.8);
+           dtc2etaphitpc[aniter]->SetMass(ProtonMass);   
+           dtc2etaphitpc[aniter]->SetMostProbableProton();
+         }
+         
+         // Track quality cuts
+
+         if (runtype == 0) {
+           dtc1etaphitpc[aniter]->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+           //      dtc1etaphitpc[aniter]->SetStatus(AliESDtrack::kTPCrefit);
+           //    dtc1etaphitpc[aniter]->SetStatus(AliESDtrack::kITSrefit);
+           dtc1etaphitpc[aniter]->SetminTPCncls(80);
+           dtc1etaphitpc[aniter]->SetRemoveKinks(kTRUE);
+           dtc1etaphitpc[aniter]->SetLabel(kFALSE);
+           //    dtc1etaphitpc[aniter]->SetMaxITSChiNdof(6.0);
+           dtc1etaphitpc[aniter]->SetMaxTPCChiNdof(4.0);
+           dtc1etaphitpc[aniter]->SetMaxImpactXY(0.2);
+           //            dtc1etaphitpc[aniter]->SetMaxImpactXYPtDep(0.0182, 0.0350, -1.01);
+           dtc1etaphitpc[aniter]->SetMaxImpactZ(0.15);
+           //      dtc1etaphitpc[aniter]->SetMaxSigmaToVertex(6.0);
+         }
+         else if (runtype == 1) {
+           //      dtc1etaphitpc[aniter]->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+           //    dtc1etaphitpc[aniter]->SetStatus(AliESDtrack::kTPCrefit);
+           //      dtc1etaphitpc[aniter]->SetStatus(AliESDtrack::kITSrefit|AliESDtrack::kITSpureSA);
+           //      dtc1etaphitpc[aniter]->SetminTPCncls(70);
+           dtc1etaphitpc[aniter]->SetStatus(AliESDtrack::kITSrefit);
+           dtc1etaphitpc[aniter]->SetRemoveKinks(kTRUE);
+           dtc1etaphitpc[aniter]->SetLabel(kFALSE);
+           //    dtc1etaphitpc[aniter]->SetMaxITSChiNdof(6.0);
+           //      dtc1etaphitpc[aniter]->SetMaxTPCChiNdof(6.0);
+           dtc1etaphitpc[aniter]->SetMaxImpactXY(0.2);
+           dtc1etaphitpc[aniter]->SetMaxImpactZ(0.25);
+           //      dtc1etaphitpc[aniter]->SetMaxSigmaToVertex(6.0);
+         }
+         else if (runtype == 2) {
+           dtc1etaphitpc[aniter]->SetStatus(AliESDtrack::kTPCin);
+           dtc1etaphitpc[aniter]->SetminTPCncls(80);
+           dtc1etaphitpc[aniter]->SetRemoveKinks(kTRUE);
+           dtc1etaphitpc[aniter]->SetLabel(kFALSE);
+           dtc1etaphitpc[aniter]->SetMaxTPCChiNdof(4.0);
+           dtc1etaphitpc[aniter]->SetMaxImpactXY(2.4);
+           dtc1etaphitpc[aniter]->SetMaxImpactZ(3.0);
+
+           if (ichg == 2) {
+             dtc2etaphitpc[aniter]->SetStatus(AliESDtrack::kTPCin);
+             dtc2etaphitpc[aniter]->SetminTPCncls(80);
+             dtc2etaphitpc[aniter]->SetRemoveKinks(kTRUE);
+             dtc2etaphitpc[aniter]->SetLabel(kFALSE);
+             dtc2etaphitpc[aniter]->SetMaxTPCChiNdof(4.0);
+             dtc2etaphitpc[aniter]->SetMaxImpactXY(2.4);
+             dtc2etaphitpc[aniter]->SetMaxImpactZ(3.0);
+           }
+           
+         }
+         
+         cutPass1YPtetaphitpc[aniter] = new AliFemtoCutMonitorParticleYPt(Form("cutPass1%stpcM%i", chrgs[ichg], imult),ProtonMass);
+         cutFail1YPtetaphitpc[aniter] = new AliFemtoCutMonitorParticleYPt(Form("cutFail1%stpcM%i", chrgs[ichg], imult),ProtonMass);
+         dtc1etaphitpc[aniter]->AddCutMonitor(cutPass1YPtetaphitpc[aniter], cutFail1YPtetaphitpc[aniter]);
+         
+         cutPass1PIDetaphitpc[aniter] = new AliFemtoCutMonitorParticlePID(Form("cutPass1%stpcM%i", chrgs[ichg], imult),2);//0-pion,1-kaon,2-proton
+         cutFail1PIDetaphitpc[aniter] = new AliFemtoCutMonitorParticlePID(Form("cutFail1%stpcM%i", chrgs[ichg], imult),2);
+         dtc1etaphitpc[aniter]->AddCutMonitor(cutPass1PIDetaphitpc[aniter], cutFail1PIDetaphitpc[aniter]);
+
+         if (ichg == 2){
+           cutPass2PIDetaphitpc[aniter] = new AliFemtoCutMonitorParticlePID(Form("cutPass2%stpcM%i", chrgs[ichg], imult),2);//0-pion,1-kaon,2-proton
+           cutFail2PIDetaphitpc[aniter] = new AliFemtoCutMonitorParticlePID(Form("cutFail2%stpcM%i", chrgs[ichg], imult),2);
+           dtc2etaphitpc[aniter]->AddCutMonitor(cutPass2PIDetaphitpc[aniter], cutFail2PIDetaphitpc[aniter]);
+         }
+
+         sqpcetaphitpc[aniter] = new AliFemtoPairCutAntiGamma();
+
+         if (runtype == 0) {
+           sqpcetaphitpc[aniter]->SetShareQualityMax(1.0);
+           sqpcetaphitpc[aniter]->SetShareFractionMax(0.05);
+           sqpcetaphitpc[aniter]->SetRemoveSameLabel(kFALSE);
+           // sqpcetaphitpc[aniter]->SetMaxEEMinv(0.0);
+           // sqpcetaphitpc[aniter]->SetMaxThetaDiff(0.0);
+           //      sqpcetaphitpc[aniter]->SetTPCEntranceSepMinimum(1.5);
+           //sqpcetaphitpc[aniter]->SetRadialDistanceMinimum(0.12, 0.03);
+           //      sqpcetaphitpc[aniter]->SetEtaDifferenceMinimum(0.02);
+         }
+         else if (runtype == 1) {
+           sqpcetaphitpc[aniter]->SetShareQualityMax(1.0);
+           sqpcetaphitpc[aniter]->SetShareFractionMax(1.05);
+           sqpcetaphitpc[aniter]->SetRemoveSameLabel(kFALSE);
+           // sqpcetaphitpc[aniter]->SetMaxEEMinv(0.002);
+           // sqpcetaphitpc[aniter]->SetMaxThetaDiff(0.008);
+           //      sqpcetaphitpc[aniter]->SetTPCEntranceSepMinimum(5.0);
+           //sqpcetaphitpc[aniter]->SetRadialDistanceMinimum(1.2, 0.03);
+           //      sqpcetaphitpc[aniter]->SetEtaDifferenceMinimum(0.02);
+         }
+         else if (runtype == 2) {
+           sqpcetaphitpc[aniter]->SetUseAOD(kTRUE);
+           sqpcetaphitpc[aniter]->SetShareQualityMax(1.0);
+           sqpcetaphitpc[aniter]->SetShareFractionMax(0.05);
+           sqpcetaphitpc[aniter]->SetRemoveSameLabel(kFALSE);
+
+           if (gammacut == 0) {              
+             sqpcetaphitpc[aniter]->SetMaxEEMinv(0.0);
+             sqpcetaphitpc[aniter]->SetMaxThetaDiff(0.0);
+           }
+           else if (gammacut == 1) { 
+             sqpcetaphitpc[aniter]->SetMaxEEMinv(0.002);
+             sqpcetaphitpc[aniter]->SetMaxThetaDiff(0.008);
+           }
+
+           //phi-star cut - values from Johana
+           //      sqpcetaphitpc[aniter]->SetPhiStarDifferenceMinimum(0.012);
+           //      sqpcetaphitpc[aniter]->SetEtaDifferenceMinimum(0.017);
+
+         }
+         
+         anetaphitpc[aniter]->SetEventCut(mecetaphitpc[aniter]);
+
+         if (ichg == 2) {
+           anetaphitpc[aniter]->SetFirstParticleCut(dtc1etaphitpc[aniter]);
+           anetaphitpc[aniter]->SetSecondParticleCut(dtc2etaphitpc[aniter]);
+         }
+         else {
+           anetaphitpc[aniter]->SetFirstParticleCut(dtc1etaphitpc[aniter]);
+           anetaphitpc[aniter]->SetSecondParticleCut(dtc1etaphitpc[aniter]);
+         }
+           
+         anetaphitpc[aniter]->SetPairCut(sqpcetaphitpc[aniter]);
+         
+
+         if (ichg == 2) {
+           ckstartpc[aniter] = new AliFemtoCorrFctnNonIdDR(Form("ckstar%stpcM%i", chrgs[ichg], imult),nbinssh,0.0,shqmax);
+           anetaphitpc[aniter]->AddCorrFctn(ckstartpc[aniter]);
+         }
+         else {  
+           cqinvtpc[aniter] = new AliFemtoQinvCorrFctn(Form("cqinv%stpcM%i", chrgs[ichg], imult),nbinssh,0.0,shqmax);
+           anetaphitpc[aniter]->AddCorrFctn(cqinvtpc[aniter]);
+         }
+
+          cylmkttpc[aniter] = new AliFemtoCorrFctnDirectYlm(Form("cylm%stpcM%i", chrgs[ichg], imult),2,nbinssh, 0.0,shqmax,runshlcms);
+          anetaphitpc[aniter]->AddCorrFctn(cylmkttpc[aniter]);
+
+         
+         if (runktdep) {
+           int ktm;
+           for (int ikt=0; ikt<numOfkTbins; ikt++) {
+
+             ktm = aniter * numOfkTbins + ikt;
+             ktpcuts[ktm] = new AliFemtoKTPairCut(ktrng[ikt], ktrng[ikt+1]);
+             
+
+             cylmkttpc[ktm] = new AliFemtoCorrFctnDirectYlm(Form("cylm%stpcM%ikT%i", chrgs[ichg], imult, ikt),3,nbinssh,0.0,shqmax,0);
+             cylmkttpc[ktm]->SetPairSelectionCut(ktpcuts[ktm]);
+             anetaphitpc[aniter]->AddCorrFctn(cylmkttpc[ktm]);
+             
+             cqinvkttpc[ktm] = new AliFemtoQinvCorrFctn(Form("cqinv%stpcM%ikT%i", chrgs[ichg], imult, ikt),nbinssh,0.0,shqmax);
+             cqinvkttpc[ktm]->SetPairSelectionCut(ktpcuts[ktm]);
+             anetaphitpc[aniter]->AddCorrFctn(cqinvkttpc[ktm]);
+
+             //              cqinvsqtpc[ktm] = new AliFemtoShareQualityCorrFctn(Form("cqinvsq%stpcM%ikT%i", chrgs[ichg], imult, ikt),nbinssh,0.0,shqmax);
+             //              cqinvsqtpc[ktm]->SetPairSelectionCut(ktpcuts[ktm]);
+             //              anetaphitpc[aniter]->AddCorrFctn(cqinvsqtpc[ktm]);
+
+             //              cqinvinnertpc[ktm] = new AliFemtoTPCInnerCorrFctn(Form("cqinvinner%stpcM%ikT%i", chrgs[ichg], imult, ikt),nbinssh,0.0,shqmax);
+             //              cqinvinnertpc[ktm]->SetPairSelectionCut(ktpcuts[ktm]);
+             //              cqinvinnertpc[ktm]->SetRadius(1.2);
+             //              anetaphitpc[aniter]->AddCorrFctn(cqinvinnertpc[ktm]);
+
+             //              if (run3d) {
+             //                cq3dlcmskttpc[ktm] = new AliFemtoCorrFctn3DLCMSSym(Form("cq3d%stpcM%ikT%i", chrgs[ichg], imult, ikt),60,(imult>3)?((imult>6)?((imult>7)?0.6:0.4):0.25):0.15);
+             //                cq3dlcmskttpc[ktm]->SetPairSelectionCut(ktpcuts[ktm]);
+             //                anetaphitpc[aniter]->AddCorrFctn(cq3dlcmskttpc[ktm]);
+             //              }
+           }
+         }
+         
+        // cdedpetaphi[aniter] = new AliFemtoCorrFctnDEtaDPhi(Form("cdedp%stpcM%i", chrgs[ichg], imult),24, 24);
+        // anetaphitpc[aniter]->AddCorrFctn(cdedpetaphi[aniter]);
+         
+         Manager->AddAnalysis(anetaphitpc[aniter]);    
+       }
+      }
+    }
+  }
+  // *** End pion-pion (positive) analysis
+
+  return Manager;
+}                         
diff --git a/PWGCF/FEMTOSCOPY/macros/Train/ProtonFemtoscopy/runBatch.C b/PWGCF/FEMTOSCOPY/macros/Train/ProtonFemtoscopy/runBatch.C
new file mode 100644 (file)
index 0000000..4031081
--- /dev/null
@@ -0,0 +1,257 @@
+void runBatch() {
+  TStopwatch timer;
+  timer.Start();
+
+  printf("*** Connect to AliEn ***\n");
+  TGrid::Connect("alien://");
+  gSystem->Load("libProofPlayer.so");
+  gSystem->Load("libVMC.so");
+  gSystem->Load("libPhysics.so");
+
+  // Use par files only for PWG2 code
+  int useParFiles = 0;
+  int usePWG2ParFiles = 1;
+
+  // Use precompiled libraries for the analysis framework
+  if (useParFiles)
+    setupPar("STEERBase");
+  if (gSystem->Load("libSTEERBase.so")<0) {
+    cout << "Cannot load libSTEERBase.so . Exiting" << endl;
+    exit(0);
+  }
+  gSystem->Load("libVMC.so");
+
+  if (useParFiles)
+    setupPar("ESD");
+  if (gSystem->Load("libESD.so")<0) {
+    cout << "Cannot load libESD.so . Exiting" << endl;
+    exit(0);
+  }
+
+  if (useParFiles)
+    setupPar("AOD");
+  if (gSystem->Load("libAOD.so")<0) {
+    cout << "Cannot load libAOD.so . Exiting" << endl;
+    exit(0);
+  }
+
+  if (useParFiles)
+    setupPar("ANALYSIS");
+  if (gSystem->Load("libANALYSIS.so")<0) {
+    cout << "Cannot load libANALYSIS.so . Exiting" << endl;
+    exit(0);
+  }
+
+  if (useParFiles)
+    setupPar("ANALYSISalice");
+  if (gSystem->Load("libANALYSISalice.so")<0) {
+    cout << "Cannot load libANALYSISalice.so . Exiting" << endl;
+    exit(0);
+  }
+
+  //____________________________________________________//
+  //_____________Setting up PWG2AOD.par_________________//
+  //____________________________________________________//
+  if (usePWG2ParFiles) {
+    // char dynpath[10000];
+    // sprintf(dynpath, ".:%s", gSystem->GetDynamicPath());
+    // gSystem->SetDynamicPath(dynpath);
+    TString dynpath;
+    dynpath = ".:";
+    dynpath += gSystem->GetDynamicPath();
+    gSystem->SetDynamicPath(dynpath.Data());
+  }
+
+  if (usePWG2ParFiles) {
+    setupPar("PWG2AOD");
+    if (gSystem->Load("./PWG2AOD/libPWG2AOD.so")<0) {
+      cout << "Cannot load local libPWG2AOD.so . Exiting" << endl;
+      exit(0);
+    }
+  }
+  else {
+    if (gSystem->Load("libPWG2AOD.so")<0) {
+      cout << "Cannot load libPWG2AOD.so . Exiting" << endl;
+      exit(0);
+    }
+  }
+  
+  //____________________________________________________//
+  //_____________Setting up PWG2femtoscopy.par__________//
+  //____________________________________________________//
+  if (usePWG2ParFiles) {
+    setupPar("PWG2femtoscopy");
+    if (gSystem->Load("./PWG2femtoscopy/libPWG2femtoscopy.so")<0) {
+      cout << "Cannot load local libPWG2femtoscopy.so . Exiting" << endl;
+      exit(0);
+    }
+  }
+  else {
+    if (gSystem->Load("libPWG2femtoscopy.so")<0) {
+      cout << "Cannot load libPWG2femtoscopy.so . Exiting" << endl;
+      exit(0);
+    }
+  }
+  
+  //____________________________________________________//
+  //_____________Setting up PWG2femtoscopyUser.par______//
+  //____________________________________________________//
+  if (usePWG2ParFiles) {
+    setupPar("PWG2femtoscopyUser");
+    if (gSystem->Load("./PWG2femtoscopyUser/libPWG2femtoscopyUser.so")<0) {
+      cout << "Cannot load libPWG2femtoscopyUser.so . Exiting" << endl;
+      exit(0);
+    }
+  }
+  else {
+    if (gSystem->Load("libPWG2femtoscopyUser.so")<0) {
+      cout << "Cannot load libPWG2femtoscopyUser.so . Exiting" << endl;
+      exit(0);
+    }
+  }
+  
+  //ANALYSIS PART
+  const char *collectionfile="wn.xml";
+  
+  //____________________________________________//
+  //Usage of event tags
+  // AliTagAnalysis *analysis = new AliTagAnalysis();
+  // TChain *chain = 0x0;
+  // chain = analysis->CreateChainFromCollection(collectionfile,"esdTree");
+
+  TChain *chain = new TChain("aodTree");;
+  //  gROOT->LoadMacro("CreateESDChain.C");
+//  const char *collectionfile="/home/akisiel/LHC10h.esds.txt";
+  
+  ifstream *istr = new ifstream(collectionfile);
+  
+  char fname[2000];
+  char pname[2000];
+  while (!istr->eof()) {
+    fname[0] = '\0';
+    (*istr) >> fname;
+    if (strlen(fname) > 10) {
+      sprintf(pname, "alien://%s", fname);
+      chain->Add(pname);
+      
+    }
+  }
+  
+//  chain->Add("data/AliAOD.root");
+
+  //  chain->Add("Data121040/AliESDs.root");
+  
+//   chain->Add("alien:///alice/sim/LHC10g1a/130844/001/AliESDs.root");
+//   chain->Add("alien:///alice/sim/LHC10g1a/130844/002/AliESDs.root");
+//   chain->Add("alien:///alice/sim/LHC10g1a/130844/003/AliESDs.root");
+//   chain->Add("alien:///alice/sim/LHC10g1a/130844/004/AliESDs.root");
+//   chain->Add("alien:///alice/sim/LHC10g1a/130844/005/AliESDs.root");
+//   chain->Add("alien:///alice/sim/LHC10g1a/130844/006/AliESDs.root");
+//   chain->Add("alien:///alice/sim/LHC10g1a/130844/007/AliESDs.root");
+//   chain->Add("alien:///alice/sim/LHC10g1a/130844/008/AliESDs.root");
+//   chain->Add("alien:///alice/sim/LHC10g1a/130844/009/AliESDs.root");
+//   chain->Add("alien:///alice/sim/LHC10g1a/130844/010/AliESDs.root");
+//   chain->Add("alien:///alice/sim/LHC10g1a/130844/011/AliESDs.root");
+//   chain->Add("alien:///alice/sim/LHC10g1a/130844/012/AliESDs.root");
+//   chain->Add("alien:///alice/sim/LHC10g1a/130844/013/AliESDs.root");
+//   chain->Add("alien:///alice/sim/LHC10g1a/130844/014/AliESDs.root");
+//   chain->Add("alien:///alice/sim/LHC10g1a/130844/015/AliESDs.root");
+//   chain->Add("alien:///alice/sim/LHC10g1a/130844/016/AliESDs.root");
+//   chain->Add("alien:///alice/sim/LHC10g1a/130844/017/AliESDs.root");
+//   chain->Add("alien:///alice/sim/LHC10g1a/130844/018/AliESDs.root");
+//   chain->Add("alien:///alice/sim/LHC10g1a/130844/019/AliESDs.root");
+//   chain->Add("alien:///alice/sim/LHC10g1a/130844/020/AliESDs.root");
+//  chain->Add("ESDs/AliESDs.101.root");
+
+  //____________________________________________//
+  // Make the analysis manager
+  AliAnalysisManager *mgr = new AliAnalysisManager("TestManager");
+//   AliESDInputHandler* esdH = new AliESDInputHandler;
+//  esdH->SetInactiveBranches("FMD CaloCluster");
+//   esdH->SetReadFriends(kFALSE);
+  AliAODInputHandler *aodH = new AliAODInputHandler;
+  //  mgr->SetInputEventHandler(esdH);  
+  mgr->SetInputEventHandler(aodH);
+
+//  AliMCEventHandler *mcH = new AliMCEventHandler;
+//  mgr->SetMCtruthEventHandler(mcH);
+
+//  gROOT->LoadMacro("AddTaskPhysicsSelection.C");
+//  AliPhysicsSelectionTask* physSelTask = AddTaskPhysicsSelection(0,  0);
+  //physSelTask->GetPhysicsSelection()->SetUseBXNumbers(kFALSE);
+
+  // AOD output handler
+//   AliAODHandler* aodHandler   = new AliAODHandler();
+//   aodHandler->SetOutputFileName("AliAOD.root");
+//   //aodHandler->SetFillAOD(kFALSE);
+//   aodHandler->SetFillAODforRun(kFALSE);
+//   mgr->SetOutputEventHandler(aodHandler);
+  
+//   AliCentralitySelectionTask *centralityTask = new AliCentralitySelectionTask("CentralitySelection");
+//   centralityTask->SetPass(2);
+//   mgr->AddTask(centralityTask);
+//   mgr->ConnectInput(centralityTask, 0, mgr->GetCommonInputContainer());
+  
+//   AliAnalysisDataContainer *outputCentrality =  mgr->CreateContainer("outputCentrality", TList::Class(),
+//   AliAnalysisManager::kOutputContainer, "CentralityOutput.root");
+//   mgr->ConnectOutput(centralityTask, 1, outputCentrality);
+
+  //  ESD filter task configuration.
+  //  gROOT->LoadMacro("AddTaskESDFilter.C");
+  // TODO usually requires muon filter libs
+  //  AliAnalysisTaskESDfilter *taskesdfilter = AddTaskESDFilter(kFALSE,  kFALSE, kFALSE, kTRUE, kTRUE);
+
+  //AddTaskPIDResponse
+  gROOT->LoadMacro("$ALICE_ROOT/ANALYSIS/macros/AddTaskPIDResponse.C");
+  AliAnalysisTaskSE *pidresponse = AddTaskPIDResponse();
+
+  //____________________________________________//
+  // 1st Pt task
+  gROOT->LoadMacro("AddTaskFemto.C");
+  AliAnalysisTaskFemto *taskfemto = AddTaskFemto("./ConfigFemtoAnalysis.C");
+
+  //____________________________________________//
+  // Run the analysis
+  if (!mgr->InitAnalysis()) return;
+  mgr->PrintStatus();
+  mgr->StartAnalysis("local",chain);
+
+  timer.Stop();
+  timer.Print();
+}
+
+Int_t setupPar(const char* pararchivename) {
+  ///////////////////
+  // Setup PAR File//
+  ///////////////////
+  if (pararchivename) {
+    char processline[1024];
+    sprintf(processline,".! tar xvzf %s.par",pararchivename);
+    gROOT->ProcessLine(processline);
+    const char* ocwd = gSystem->WorkingDirectory();
+    gSystem->ChangeDirectory(pararchivename);
+
+    // check for BUILD.sh and execute
+    if (!gSystem->AccessPathName("PROOF-INF/BUILD.sh")) {
+      printf("*******************************\n");
+      printf("*** Building PAR archive    ***\n");
+      printf("*******************************\n");
+
+      if (gSystem->Exec("PROOF-INF/BUILD.sh")) {
+        Error("runProcess","Cannot Build the PAR Archive! - Abort!");
+        return -1;
+      }
+    }
+    // check for SETUP.C and execute
+    if (!gSystem->AccessPathName("PROOF-INF/SETUP.C")) {
+      printf("*******************************\n");
+      printf("*** Setup PAR archive       ***\n");
+      printf("*******************************\n");
+      gROOT->Macro("PROOF-INF/SETUP.C");
+    }
+    
+    gSystem->ChangeDirectory("../");
+  }
+
+  return 1;
+}
diff --git a/PWGCF/FEMTOSCOPY/macros/Train/Train3/ConfigFemtoAnalysis.C b/PWGCF/FEMTOSCOPY/macros/Train/Train3/ConfigFemtoAnalysis.C
new file mode 100644 (file)
index 0000000..eac4d26
--- /dev/null
@@ -0,0 +1,970 @@
+/*********************************************************************
+ *                                                                   *
+ * ConfigFemtoAnalysis.C - configuration macro for the femtoscopic   *
+ * analysis, to be run in the analysis train.                        *
+ * Assumed input data: large (>10M) sample of MC pp events           *
+ * Inluded analysis:                                                 *
+ *    - positive pion HBT, 3 kt bins, 1D+3D functions                *
+ *    - negative pion HBT, 3 kt bins, 1D+3D functions                *
+ *    - positive kaon HBT, 1 kt bin,  1D+3D functions                *
+ *                                                                   *
+ * Author: Adam Kisiel (Adam.Kisiel@cern.ch)                         *
+ *                                                                   *
+ *********************************************************************/
+
+#if !defined(__CINT__) || defined(__MAKECINT_)
+#include "AliFemtoManager.h"
+#include "AliFemtoEventReaderESDChain.h"
+#include "AliFemtoEventReaderESDChainKine.h"
+#include "AliFemtoSimpleAnalysis.h"
+#include "AliFemtoBasicEventCut.h"
+#include "AliFemtoESDTrackCut.h"
+#include "AliFemtoCorrFctn.h"
+#include "AliFemtoCutMonitorParticleYPt.h"
+#include "AliFemtoCutMonitorParticleVertPos.h"
+#include "AliFemtoCutMonitorParticleMomRes.h"
+#include "AliFemtoCutMonitorEventMult.h"
+#include "AliFemtoCutMonitorEventVertex.h"
+#include "AliFemtoShareQualityTPCEntranceSepPairCut.h"
+#include "AliFemtoQinvCorrFctn.h"
+#include "AliFemtoShareQualityCorrFctn.h"
+#include "AliFemtoTPCInnerCorrFctn.h"
+#include "AliFemtoVertexMultAnalysis.h"
+#include "AliFemtoCorrFctn3DSpherical.h"
+#include "AliFemtoChi2CorrFctn.h"
+#include "AliFemtoCorrFctnTPCNcls.h"
+#include "AliFemtoModelBPLCMSCorrFctn.h"
+#include "AliFemtoModelCorrFctn3DSpherical.h"
+#include "AliFemtoModelGausLCMSFreezeOutGenerator.h"
+#include "AliFemtoModelGausRinvFreezeOutGenerator.h"
+#include "AliFemtoModelManager.h"
+#include "AliFemtoModelWeightGeneratorBasic.h"
+#include "AliFemtoModelWeightGeneratorLednicky.h"
+#include "AliFemtoCorrFctnDirectYlm.h"
+#include "AliFemtoModelCorrFctnDirectYlm.h"
+#include "AliFemtoModelCorrFctnSource.h"
+#include "AliFemtoCutMonitorParticlePtPDG.h"
+#include "AliFemtoKTPairCut.h"
+#endif
+
+//________________________________________________________________________
+AliFemtoManager* ConfigFemtoAnalysis() {
+
+  double PionMass = 0.13956995;
+  double KaonMass = 0.493677;
+  
+  AliFemtoEventReaderESDChainKine* Reader=new AliFemtoEventReaderESDChainKine();
+  Reader->SetConstrained(true);
+  Reader->SetUseTPCOnly(false);
+
+  AliFemtoManager* Manager=new AliFemtoManager();
+  Manager->SetEventReader(Reader);
+
+  int runPositivePions = 1;
+  int runNegativePions = 1;
+  int runPositiveKaons = 1;
+  int runNegativeKaons = 1;
+  int runPositiveNegativeKaons = 1;
+
+  if (runPositivePions) {
+    // *** Begin pion-pion (positive) analysis ***
+    AliFemtoVertexMultAnalysis *anpip = new AliFemtoVertexMultAnalysis(3, -15.6, 15.6, 1, 2, 200000);
+    anpip->SetNumEventsToMix(10);
+    anpip->SetMinSizePartCollection(2);
+
+    AliFemtoBasicEventCut* mecpip = new AliFemtoBasicEventCut();
+    mecpip->SetEventMult(2,100000);
+    mecpip->SetVertZPos(-1000,1000);
+       
+    AliFemtoESDTrackCut* dtcpip = new AliFemtoESDTrackCut();
+    dtcpip->SetPidProbPion(0.2,1.001);
+    dtcpip->SetPidProbMuon(0.0,1.0);
+    dtcpip->SetPidProbKaon(0.0,1.0);
+    dtcpip->SetPidProbProton(0.0,1.0);
+    dtcpip->SetCharge(1.0);
+    dtcpip->SetPt(0.15,0.5);
+    dtcpip->SetRapidity(-0.8,0.8);
+    dtcpip->SetMass(PionMass);
+    // Track quality cuts
+    dtcpip->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+    //  dtcpip->SetStatus(AliESDtrack::kTPCrefit);
+    dtcpip->SetminTPCncls(50);
+    dtcpip->SetRemoveKinks(kTRUE);
+    dtcpip->SetLabel(kFALSE);
+    dtcpip->SetMaxITSChiNdof(2.5);
+    dtcpip->SetMaxTPCChiNdof(3.0);
+    dtcpip->SetMaxImpactXY(3.0);
+    dtcpip->SetMaxImpactZ(3.0);
+
+    // Track monitors
+    AliFemtoCutMonitorParticleYPt *cutPassYPtpip = new AliFemtoCutMonitorParticleYPt("cutPasspip", 0.13957);
+    AliFemtoCutMonitorParticleYPt *cutFailYPtpip = new AliFemtoCutMonitorParticleYPt("cutFailpip", 0.13957);
+    dtcpip->AddCutMonitor(cutPassYPtpip, cutFailYPtpip);
+
+    AliFemtoCutMonitorEventMult *cutPassEvMpip = new AliFemtoCutMonitorEventMult("cutPasspip");
+    AliFemtoCutMonitorEventMult *cutFailEvMpip = new AliFemtoCutMonitorEventMult("cutFailpip");
+    mecpip->AddCutMonitor(cutPassEvMpip, cutFailEvMpip);
+
+    AliFemtoCutMonitorEventVertex *cutPassEvVpip = new AliFemtoCutMonitorEventVertex("cutPasspip");
+    AliFemtoCutMonitorEventVertex *cutFailEvVpip = new AliFemtoCutMonitorEventVertex("cutFailpip");
+    mecpip->AddCutMonitor(cutPassEvVpip, cutFailEvVpip);
+
+    // Pair cut
+    AliFemtoShareQualityTPCEntranceSepPairCut *sqpcpip = new AliFemtoShareQualityTPCEntranceSepPairCut();
+    sqpcpip->SetShareQualityMax(0.0);
+    sqpcpip->SetShareFractionMax(0.02);
+    sqpcpip->SetRemoveSameLabel(kFALSE);
+    sqpcpip->SetTPCEntranceSepMinimum(2.0);
+
+    anpip->SetEventCut(mecpip);
+    anpip->SetFirstParticleCut(dtcpip);
+    anpip->SetSecondParticleCut(dtcpip);
+    anpip->SetPairCut(sqpcpip);
+
+    // Two-track quality monitoring
+    AliFemtoShareQualityCorrFctn *csqqinvpip= new AliFemtoShareQualityCorrFctn("sqqinvcfpip",40,0.0,0.4);
+    AliFemtoChi2CorrFctn *cchiqinvpip= new AliFemtoChi2CorrFctn("chicfpip",40,0.0,0.4);
+    AliFemtoCorrFctnTPCNcls *cqtpcnclspip = new AliFemtoCorrFctnTPCNcls("cqtpcnclspip",40,0.0,0.4);
+
+    // Intrdouce kT binning
+    AliFemtoKTPairCut *ktpairkT1pip = new AliFemtoKTPairCut(0.1,0.27);
+    AliFemtoKTPairCut *ktpairkT2pip = new AliFemtoKTPairCut(0.27,0.37);
+    AliFemtoKTPairCut *ktpairkT3pip = new AliFemtoKTPairCut(0.37,0.52);
+
+    // Purely experimental correlation function
+    AliFemtoCorrFctnDirectYlm *cylmkT1pip = new AliFemtoCorrFctnDirectYlm("cylmkT1pip",3,80,0.0,0.8,1);
+    cylmkT1pip->SetPairSelectionCut(ktpairkT1pip);
+    anpip->AddCorrFctn(cylmkT1pip);
+    
+    AliFemtoCorrFctnDirectYlm *cylmkT2pip = new AliFemtoCorrFctnDirectYlm("cylmkT2pip",3,80,0.0,0.8,1);
+    cylmkT2pip->SetPairSelectionCut(ktpairkT2pip);
+    anpip->AddCorrFctn(cylmkT2pip);
+    
+    AliFemtoCorrFctnDirectYlm *cylmkT3pip = new AliFemtoCorrFctnDirectYlm("cylmkT3pip",3,80,0.0,0.8,1);
+    cylmkT3pip->SetPairSelectionCut(ktpairkT3pip);
+    anpip->AddCorrFctn(cylmkT3pip);
+
+    AliFemtoQinvCorrFctn *cqinvkt1pip = new AliFemtoQinvCorrFctn("qinvcfkt1pip", 100,0.0,1.0);
+    cqinvkt1pip->SetPairSelectionCut(ktpairkT1pip);
+    anpip->AddCorrFctn(cqinvkt1pip);
+
+    AliFemtoQinvCorrFctn *cqinvkt2pip = new AliFemtoQinvCorrFctn("qinvcfkt2pip", 100,0.0,1.0);
+    cqinvkt2pip->SetPairSelectionCut(ktpairkT2pip);
+    anpip->AddCorrFctn(cqinvkt2pip);
+
+    AliFemtoQinvCorrFctn *cqinvkt3pip = new AliFemtoQinvCorrFctn("qinvcfkt3pip", 100,0.0,1.0);
+    cqinvkt3pip->SetPairSelectionCut(ktpairkT3pip);
+    anpip->AddCorrFctn(cqinvkt3pip);
+
+    // Setting up the model calculation
+    // First create the freeze-out generator
+    AliFemtoModelGausLCMSFreezeOutGenerator *tFreezepip = new AliFemtoModelGausLCMSFreezeOutGenerator();
+    tFreezepip->SetSizeOut(1.8*TMath::Sqrt(2.0));                                                
+    tFreezepip->SetSizeSide(1.3*TMath::Sqrt(2.0));                                               
+    tFreezepip->SetSizeLong(1.6*TMath::Sqrt(2.0));                                                
+
+    // And the weight generator                                                                    
+    AliFemtoModelWeightGeneratorBasic *tWeightpip = new AliFemtoModelWeightGeneratorBasic();
+    tWeightpip->SetPairType(AliFemtoModelWeightGenerator::PionPlusPionPlus());
+
+    // Create a manager that will connect it                                                                                                               
+    AliFemtoModelManager *tModelManagerpip = new AliFemtoModelManager();
+    tModelManagerpip->AcceptFreezeOutGenerator(tFreezepip);
+    tModelManagerpip->AcceptWeightGenerator(tWeightpip);
+    tModelManagerpip->CreateCopyHiddenInfo(kFALSE);
+
+    // Model correlation functions
+    AliFemtoModelCorrFctn *c1dpipip;
+    AliFemtoModelBPLCMSCorrFctn *c3dsmallkt1pip;
+    AliFemtoModelBPLCMSCorrFctn *c3dsmallkt2pip;
+    AliFemtoModelBPLCMSCorrFctn *c3dsmallkt3pip;
+
+    c1dpipip = new AliFemtoModelCorrFctn("c1dpipip",100,0.0,1.0);
+    c1dpipip->ConnectToManager(tModelManagerpip);
+
+    c3dsmallkt1pip = new AliFemtoModelBPLCMSCorrFctn("c3dsmallkt1pip",40, -0.4, 0.4);
+    c3dsmallkt1pip->SetSpecificPairCut(ktpairkT1pip);
+    c3dsmallkt1pip->ConnectToManager(tModelManagerpip);
+
+    c3dsmallkt2pip = new AliFemtoModelBPLCMSCorrFctn("c3dsmallkt2pip",40, -0.4, 0.4);
+    c3dsmallkt2pip->SetSpecificPairCut(ktpairkT2pip);
+    c3dsmallkt2pip->ConnectToManager(tModelManagerpip);
+
+    c3dsmallkt3pip = new AliFemtoModelBPLCMSCorrFctn("c3dsmallkt3pip",40, -0.4, 0.4);
+    c3dsmallkt3pip->SetSpecificPairCut(ktpairkT3pip);
+    c3dsmallkt3pip->ConnectToManager(tModelManagerpip);
+
+    AliFemtoModelCorrFctnDirectYlm *cmylmkt1pip = new AliFemtoModelCorrFctnDirectYlm("mcylmkt1pip",3,80,0.0,0.8,1);
+    cmylmkt1pip->SetPairSelectionCut(ktpairkT1pip);
+    cmylmkt1pip->ConnectToManager(tModelManagerpip);
+
+    AliFemtoModelCorrFctnDirectYlm *cmylmkt2pip = new AliFemtoModelCorrFctnDirectYlm("mcylmkt2pip",3,80,0.0,0.8,1);
+    cmylmkt2pip->SetPairSelectionCut(ktpairkT2pip);
+    cmylmkt2pip->ConnectToManager(tModelManagerpip);
+
+    AliFemtoModelCorrFctnDirectYlm *cmylmkt3pip = new AliFemtoModelCorrFctnDirectYlm("mcylmkt3pip",3,80,0.0,0.8,1);
+    cmylmkt3pip->SetPairSelectionCut(ktpairkT3pip);
+    cmylmkt3pip->ConnectToManager(tModelManagerpip);
+
+    // Add correlation functions to the analysis 
+    anpip->AddCorrFctn(csqqinvpip);
+    anpip->AddCorrFctn(cchiqinvpip);
+    anpip->AddCorrFctn(cqtpcnclspip);
+    anpip->AddCorrFctn(c3dsmallkt1pip);
+    anpip->AddCorrFctn(c3dsmallkt2pip);
+    anpip->AddCorrFctn(c3dsmallkt3pip);
+    anpip->AddCorrFctn(c1dpipip);
+    anpip->AddCorrFctn(cmylmkt1pip);
+    anpip->AddCorrFctn(cmylmkt2pip);
+    anpip->AddCorrFctn(cmylmkt3pip);
+
+    Manager->AddAnalysis(anpip);       
+
+    // *** End pion-pion (positive) analysis
+  }
+
+  if (runNegativePions) {
+    // *** Begin pion-pion (negative) analysis ***
+    AliFemtoVertexMultAnalysis *anpim = new AliFemtoVertexMultAnalysis(3, -15.6, 15.6, 1, 2, 200000);
+    anpim->SetNumEventsToMix(10);
+    anpim->SetMinSizePartCollection(2);
+
+    AliFemtoBasicEventCut* mecpim = new AliFemtoBasicEventCut();
+    mecpim->SetEventMult(2,100000);
+    mecpim->SetVertZPos(-1000,1000);
+       
+    AliFemtoESDTrackCut* dtcpim = new AliFemtoESDTrackCut();
+    dtcpim->SetPidProbPion(0.2,1.001);
+    dtcpim->SetPidProbMuon(0.0,1.0);
+    dtcpim->SetPidProbKaon(0.0,1.0);
+    dtcpim->SetPidProbProton(0.0,1.0);
+    dtcpim->SetCharge(1.0);
+    dtcpim->SetPt(0.15,0.5);
+    dtcpim->SetRapidity(-0.8,0.8);
+    dtcpim->SetMass(PionMass);
+    // Track quality cuts
+    dtcpim->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+    //  dtcpim->SetStatus(AliESDtrack::kTPCrefit);
+    dtcpim->SetminTPCncls(50);
+    dtcpim->SetRemoveKinks(kTRUE);
+    dtcpim->SetLabel(kFALSE);
+    dtcpim->SetMaxITSChiNdof(2.5);
+    dtcpim->SetMaxTPCChiNdof(3.0);
+    dtcpim->SetMaxImpactXY(3.0);
+    dtcpim->SetMaxImpactZ(3.0);
+
+    // Track monitors
+    AliFemtoCutMonitorParticleYPt *cutPassYPtpim = new AliFemtoCutMonitorParticleYPt("cutPasspim", 0.13957);
+    AliFemtoCutMonitorParticleYPt *cutFailYPtpim = new AliFemtoCutMonitorParticleYPt("cutFailpim", 0.13957);
+    dtcpim->AddCutMonitor(cutPassYPtpim, cutFailYPtpim);
+
+    AliFemtoCutMonitorEventMult *cutPassEvMpim = new AliFemtoCutMonitorEventMult("cutPasspim");
+    AliFemtoCutMonitorEventMult *cutFailEvMpim = new AliFemtoCutMonitorEventMult("cutFailpim");
+    mecpim->AddCutMonitor(cutPassEvMpim, cutFailEvMpim);
+
+    AliFemtoCutMonitorEventVertex *cutPassEvVpim = new AliFemtoCutMonitorEventVertex("cutPasspim");
+    AliFemtoCutMonitorEventVertex *cutFailEvVpim = new AliFemtoCutMonitorEventVertex("cutFailpim");
+    mecpim->AddCutMonitor(cutPassEvVpim, cutFailEvVpim);
+
+    // Pair cut
+    AliFemtoShareQualityTPCEntranceSepPairCut *sqpcpim = new AliFemtoShareQualityTPCEntranceSepPairCut();
+    sqpcpim->SetShareQualityMax(0.0);
+    sqpcpim->SetShareFractionMax(0.02);
+    sqpcpim->SetRemoveSameLabel(kFALSE);
+    sqpcpim->SetTPCEntranceSepMinimum(2.0);
+
+    anpim->SetEventCut(mecpim);
+    anpim->SetFirstParticleCut(dtcpim);
+    anpim->SetSecondParticleCut(dtcpim);
+    anpim->SetPairCut(sqpcpim);
+
+    // Two-track quality monitoring
+    AliFemtoShareQualityCorrFctn *csqqinvpim= new AliFemtoShareQualityCorrFctn("sqqinvcfpim",40,0.0,0.4);
+    AliFemtoChi2CorrFctn *cchiqinvpim= new AliFemtoChi2CorrFctn("chicfpim",40,0.0,0.4);
+    AliFemtoCorrFctnTPCNcls *cqtpcnclspim = new AliFemtoCorrFctnTPCNcls("cqtpcnclspim",40,0.0,0.4);
+
+    // Intrdouce kT binning
+    AliFemtoKTPairCut *ktpairkT1pim = new AliFemtoKTPairCut(0.1,0.27);
+    AliFemtoKTPairCut *ktpairkT2pim = new AliFemtoKTPairCut(0.27,0.37);
+    AliFemtoKTPairCut *ktpairkT3pim = new AliFemtoKTPairCut(0.37,0.52);
+
+    // Purely experimental correlation function
+    AliFemtoCorrFctnDirectYlm *cylmkT1pim = new AliFemtoCorrFctnDirectYlm("cylmkT1pim",3,80,0.0,0.8,1);
+    cylmkT1pim->SetPairSelectionCut(ktpairkT1pim);
+    anpim->AddCorrFctn(cylmkT1pim);
+    
+    AliFemtoCorrFctnDirectYlm *cylmkT2pim = new AliFemtoCorrFctnDirectYlm("cylmkT2pim",3,80,0.0,0.8,1);
+    cylmkT2pim->SetPairSelectionCut(ktpairkT2pim);
+    anpim->AddCorrFctn(cylmkT2pim);
+    
+    AliFemtoCorrFctnDirectYlm *cylmkT3pim = new AliFemtoCorrFctnDirectYlm("cylmkT3pim",3,80,0.0,0.8,1);
+    cylmkT3pim->SetPairSelectionCut(ktpairkT3pim);
+    anpim->AddCorrFctn(cylmkT3pim);
+
+    AliFemtoQinvCorrFctn *cqinvkt1pim = new AliFemtoQinvCorrFctn("qinvcfkt1pim", 100,0.0,1.0);
+    cqinvkt1pim->SetPairSelectionCut(ktpairkT1pim);
+    anpim->AddCorrFctn(cqinvkt1pim);
+
+    AliFemtoQinvCorrFctn *cqinvkt2pim = new AliFemtoQinvCorrFctn("qinvcfkt2pim", 100,0.0,1.0);
+    cqinvkt2pim->SetPairSelectionCut(ktpairkT2pim);
+    anpim->AddCorrFctn(cqinvkt2pim);
+
+    AliFemtoQinvCorrFctn *cqinvkt3pim = new AliFemtoQinvCorrFctn("qinvcfkt3pim", 100,0.0,1.0);
+    cqinvkt3pim->SetPairSelectionCut(ktpairkT3pim);
+    anpim->AddCorrFctn(cqinvkt3pim);
+
+    // Setting up the model calculation
+    // First create the freeze-out generator
+    AliFemtoModelGausLCMSFreezeOutGenerator *tFreezepim = new AliFemtoModelGausLCMSFreezeOutGenerator();
+    tFreezepim->SetSizeOut(1.8*TMath::Sqrt(2.0));                                                
+    tFreezepim->SetSizeSide(1.3*TMath::Sqrt(2.0));                                               
+    tFreezepim->SetSizeLong(1.6*TMath::Sqrt(2.0));                                                
+
+    // And the weight generator                                                                    
+    AliFemtoModelWeightGeneratorBasic *tWeightpim = new AliFemtoModelWeightGeneratorBasic();
+    tWeightpim->SetPairType(AliFemtoModelWeightGenerator::PionPlusPionPlus());
+
+    // Create a manager that will connect it                                                                                                               
+    AliFemtoModelManager *tModelManagerpim = new AliFemtoModelManager();
+    tModelManagerpim->AcceptFreezeOutGenerator(tFreezepim);
+    tModelManagerpim->AcceptWeightGenerator(tWeightpim);
+    tModelManagerpim->CreateCopyHiddenInfo(kFALSE);
+
+    // Model correlation functions
+    AliFemtoModelCorrFctn *c1dpipim;
+    AliFemtoModelBPLCMSCorrFctn *c3dsmallkt1pim;
+    AliFemtoModelBPLCMSCorrFctn *c3dsmallkt2pim;
+    AliFemtoModelBPLCMSCorrFctn *c3dsmallkt3pim;
+
+    c1dpipim = new AliFemtoModelCorrFctn("c1dpipim",100,0.0,1.0);
+    c1dpipim->ConnectToManager(tModelManagerpim);
+
+    c3dsmallkt1pim = new AliFemtoModelBPLCMSCorrFctn("c3dsmallkt1pim",40, -0.4, 0.4);
+    c3dsmallkt1pim->SetSpecificPairCut(ktpairkT1pim);
+    c3dsmallkt1pim->ConnectToManager(tModelManagerpim);
+
+    c3dsmallkt2pim = new AliFemtoModelBPLCMSCorrFctn("c3dsmallkt2pim",40, -0.4, 0.4);
+    c3dsmallkt2pim->SetSpecificPairCut(ktpairkT2pim);
+    c3dsmallkt2pim->ConnectToManager(tModelManagerpim);
+
+    c3dsmallkt3pim = new AliFemtoModelBPLCMSCorrFctn("c3dsmallkt3pim",40, -0.4, 0.4);
+    c3dsmallkt3pim->SetSpecificPairCut(ktpairkT3pim);
+    c3dsmallkt3pim->ConnectToManager(tModelManagerpim);
+
+    AliFemtoModelCorrFctnDirectYlm *cmylmkt1pim = new AliFemtoModelCorrFctnDirectYlm("mcylmkt1pim",3,80,0.0,0.8,1);
+    cmylmkt1pim->SetPairSelectionCut(ktpairkT1pim);
+    cmylmkt1pim->ConnectToManager(tModelManagerpim);
+
+    AliFemtoModelCorrFctnDirectYlm *cmylmkt2pim = new AliFemtoModelCorrFctnDirectYlm("mcylmkt2pim",3,80,0.0,0.8,1);
+    cmylmkt2pim->SetPairSelectionCut(ktpairkT2pim);
+    cmylmkt2pim->ConnectToManager(tModelManagerpim);
+
+    AliFemtoModelCorrFctnDirectYlm *cmylmkt3pim = new AliFemtoModelCorrFctnDirectYlm("mcylmkt3pim",3,80,0.0,0.8,1);
+    cmylmkt3pim->SetPairSelectionCut(ktpairkT3pim);
+    cmylmkt3pim->ConnectToManager(tModelManagerpim);
+
+    // Add correlation functions to the analysis 
+    anpim->AddCorrFctn(csqqinvpim);
+    anpim->AddCorrFctn(cchiqinvpim);
+    anpim->AddCorrFctn(cqtpcnclspim);
+    anpim->AddCorrFctn(c3dsmallkt1pim);
+    anpim->AddCorrFctn(c3dsmallkt2pim);
+    anpim->AddCorrFctn(c3dsmallkt3pim);
+    anpim->AddCorrFctn(c1dpipim);
+    anpim->AddCorrFctn(cmylmkt1pim);
+    anpim->AddCorrFctn(cmylmkt2pim);
+    anpim->AddCorrFctn(cmylmkt3pim);
+
+    Manager->AddAnalysis(anpim);       
+
+    // *** End pion-pion (negative) analysis
+  }
+
+  if (runPositiveKaons) {
+    // *** Begin Kaon-Kaon (positive) analysis
+    AliFemtoVertexMultAnalysis *ankp = new AliFemtoVertexMultAnalysis(18, -15.6, 15.6, 1, 2, 20000);
+    ankp->SetNumEventsToMix(5);
+    ankp->SetMinSizePartCollection(2);
+
+    AliFemtoBasicEventCut* meckp = new AliFemtoBasicEventCut();
+    meckp->SetEventMult(1,100000);
+    meckp->SetVertZPos(-1000,1000);
+       
+    AliFemtoESDTrackCut* dtckp = new AliFemtoESDTrackCut();
+    dtckp->SetPidProbKaon(0.7,1.001);
+    dtckp->SetPidProbMuon(0.0,0.5);
+    dtckp->SetPidProbPion(0.0,0.5);
+    dtckp->SetPidProbProton(0.0,0.5);
+    dtckp->SetCharge(1.0);
+    dtckp->SetMostProbableKaon();
+    dtckp->SetMomRangeTOFpidIs(0.6,10000.);
+    dtckp->SetPt(0.15,2.0);
+    dtckp->SetMass(KaonMass);
+    // Track quality cuts
+    dtckp->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+    dtckp->SetminTPCncls(50);
+    dtckp->SetRemoveKinks(kTRUE);
+    dtckp->SetLabel(kFALSE);
+    dtckp->SetMaxITSChiNdof(2.5);
+    dtckp->SetMaxTPCChiNdof(3.0);
+    dtckp->SetMaxImpactXY(3.0);
+    dtckp->SetMaxImpactZ(3.0);
+
+    AliFemtoCutMonitorParticleYPt *cutPassYPtkp = new AliFemtoCutMonitorParticleYPt("cutPasskp", 0.493677);
+    AliFemtoCutMonitorParticleYPt *cutFailYPtkp = new AliFemtoCutMonitorParticleYPt("cutFailkp", 0.493677);
+    dtckp->AddCutMonitor(cutPassYPtkp, cutFailYPtkp);
+
+    AliFemtoCutMonitorParticlePtPDG *cutPassPidkp = new AliFemtoCutMonitorParticlePtPDG("cutPasskp", 0.493677);
+    AliFemtoCutMonitorParticlePtPDG *cutFailPidkp = new AliFemtoCutMonitorParticlePtPDG("cutFailkp", 0.493677);
+    dtckp->AddCutMonitor(cutPassPidkp, cutFailPidkp);
+
+    AliFemtoCutMonitorParticleMomRes *cutPassMRkp = new AliFemtoCutMonitorParticleMomRes("cutPasskp");
+    AliFemtoCutMonitorParticleMomRes *cutFailMRkp = new AliFemtoCutMonitorParticleMomRes("cutFailkp");
+    dtckp->AddCutMonitor(cutPassMRkp, cutFailMRkp);
+
+    AliFemtoCutMonitorParticleVertPos *cutPassVPkp = new AliFemtoCutMonitorParticleVertPos("cutPasskp");
+    AliFemtoCutMonitorParticleVertPos *cutFailVPkp = new AliFemtoCutMonitorParticleVertPos("cutFailkp");
+    dtckp->AddCutMonitor(cutPassVPkp, cutFailVPkp);
+
+    AliFemtoCutMonitorEventMult *cutPassEvMkp = new AliFemtoCutMonitorEventMult("cutPasskp");
+    AliFemtoCutMonitorEventMult *cutFailEvMkp = new AliFemtoCutMonitorEventMult("cutFailkp");
+    meckp->AddCutMonitor(cutPassEvMkp, cutFailEvMkp);
+
+    AliFemtoCutMonitorEventVertex *cutPassEvVkp = new AliFemtoCutMonitorEventVertex("cutPasskp");
+    AliFemtoCutMonitorEventVertex *cutFailEvVkp = new AliFemtoCutMonitorEventVertex("cutFailkp");
+    meckp->AddCutMonitor(cutPassEvVkp, cutFailEvVkp);
+
+    AliFemtoShareQualityTPCEntranceSepPairCut *sqpckp = new AliFemtoShareQualityTPCEntranceSepPairCut();
+    sqpckp->SetShareQualityMax(0.0);
+    sqpckp->SetShareFractionMax(0.02);
+    sqpckp->SetRemoveSameLabel(kFALSE);
+    sqpckp->SetTPCEntranceSepMinimum(3.0);
+
+    ankp->SetEventCut(meckp);
+    ankp->SetFirstParticleCut(dtckp);
+    ankp->SetSecondParticleCut(dtckp);
+    ankp->SetPairCut(sqpckp);
+
+    AliFemtoQinvCorrFctn *cqinvkp= new AliFemtoQinvCorrFctn("qinvcf",100,0.0,1.0);
+
+    AliFemtoModelBPLCMSCorrFctn *c3dsmallkp;
+    AliFemtoModelCorrFctn *c1dpikp;
+
+    // Setting up the model calculation
+    // First create the freeze-out generator
+    AliFemtoModelGausRinvFreezeOutGenerator *tFreezekp = new AliFemtoModelGausRinvFreezeOutGenerator();
+    tFreezekp->SetSizeInv(1.8*TMath::Sqrt(2.0));
+    tFreezekp->SetSelectPrimaryFromHidden(false);
+
+    // And the weight generator                                                                    
+    //   AliFemtoModelWeightGeneratorBasic *tWeightkp = new AliFemtoModelWeightGeneratorBasic();
+    //   tWeightkp->SetPairType(AliFemtoModelWeightGenerator::KaonPlusKaonPlus());
+    AliFemtoModelWeightGeneratorLednicky *tWeightkp = new AliFemtoModelWeightGeneratorLednicky();
+    tWeightkp->SetPairType(AliFemtoModelWeightGenerator::KaonPlusKaonPlus());
+    tWeightkp->SetCoulOn();
+    tWeightkp->SetQuantumOn();
+    tWeightkp->SetStrongOff();
+    tWeightkp->Set3BodyOff();
+
+    // Create a manager that will connect it  
+    AliFemtoModelManager *tModelManagerkp = new AliFemtoModelManager();
+    tModelManagerkp->AcceptFreezeOutGenerator(tFreezekp);
+    tModelManagerkp->AcceptWeightGenerator(tWeightkp);
+    tModelManagerkp->CreateCopyHiddenInfo(kFALSE);
+
+    c3dsmallkp = new AliFemtoModelBPLCMSCorrFctn("c3dsmallkp",30, 0.0, 0.6);
+    c3dsmallkp->ConnectToManager(tModelManagerkp);
+
+    c1dpikp = new AliFemtoModelCorrFctn("c1dpikp",100,0.0,1.0);
+    c1dpikp->ConnectToManager(tModelManagerkp);
+
+    //###
+    ankp->AddCorrFctn(cqinvkp);
+    ankp->AddCorrFctn(c3dsmallkp);
+    ankp->AddCorrFctn(c1dpikp);
+
+    Manager->AddAnalysis(ankp);          
+
+    // *** End Kaon-Kaon (positive) analysis
+  }
+
+  if (runNegativeKaons) {
+    // *** Begin Kaon-Kaon (negative) analysis
+    AliFemtoVertexMultAnalysis *ankm = new AliFemtoVertexMultAnalysis(18, -15.6, 15.6, 1, 2, 20000);
+    ankm->SetNumEventsToMix(5);
+    ankm->SetMinSizePartCollection(2);
+
+    AliFemtoBasicEventCut* meckm = new AliFemtoBasicEventCut();
+    meckm->SetEventMult(1,100000);
+    meckm->SetVertZPos(-1000,1000);
+       
+    AliFemtoESDTrackCut* dtckm = new AliFemtoESDTrackCut();
+    dtckm->SetPidProbKaon(0.7,1.001);
+    dtckm->SetPidProbMuon(0.0,0.5);
+    dtckm->SetPidProbPion(0.0,0.5);
+    dtckm->SetPidProbProton(0.0,0.5);
+    dtckp->SetMomRangeTOFpidIs(0.6,10000.);
+    dtckm->SetCharge(-1.0);
+    dtckm->SetMostProbableKaon();
+    dtckm->SetPt(0.15,2.0);
+    dtckm->SetMass(KaonMass);
+    // Track quality cuts
+    dtckm->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+    dtckm->SetminTPCncls(50);
+    dtckm->SetRemoveKinks(kTRUE);
+    dtckm->SetLabel(kFALSE);
+    dtckm->SetMaxITSChiNdof(2.5);
+    dtckm->SetMaxTPCChiNdof(3.0);
+    dtckm->SetMaxImpactXY(3.0);
+    dtckm->SetMaxImpactZ(3.0);
+
+    AliFemtoCutMonitorParticleYPt *cutPassYPtkm = new AliFemtoCutMonitorParticleYPt("cutPasskm", 0.493677);
+    AliFemtoCutMonitorParticleYPt *cutFailYPtkm = new AliFemtoCutMonitorParticleYPt("cutFailkm", 0.493677);
+    dtckm->AddCutMonitor(cutPassYPtkm, cutFailYPtkm);
+
+    AliFemtoCutMonitorParticlePtPDG *cutPassPidkm = new AliFemtoCutMonitorParticlePtPDG("cutPasskm", 0.493677);
+    AliFemtoCutMonitorParticlePtPDG *cutFailPidkm = new AliFemtoCutMonitorParticlePtPDG("cutFailkm", 0.493677);
+    dtckm->AddCutMonitor(cutPassPidkm, cutFailPidkm);
+
+    AliFemtoCutMonitorParticleMomRes *cutPassMRkm = new AliFemtoCutMonitorParticleMomRes("cutPasskm");
+    AliFemtoCutMonitorParticleMomRes *cutFailMRkm = new AliFemtoCutMonitorParticleMomRes("cutFailkm");
+    dtckm->AddCutMonitor(cutPassMRkm, cutFailMRkm);
+
+    AliFemtoCutMonitorParticleVertPos *cutPassVPkm = new AliFemtoCutMonitorParticleVertPos("cutPasskm");
+    AliFemtoCutMonitorParticleVertPos *cutFailVPkm = new AliFemtoCutMonitorParticleVertPos("cutFailkm");
+    dtckm->AddCutMonitor(cutPassVPkm, cutFailVPkm);
+
+    AliFemtoCutMonitorEventMult *cutPassEvMkm = new AliFemtoCutMonitorEventMult("cutPasskm");
+    AliFemtoCutMonitorEventMult *cutFailEvMkm = new AliFemtoCutMonitorEventMult("cutFailkm");
+    meckm->AddCutMonitor(cutPassEvMkm, cutFailEvMkm);
+
+    AliFemtoCutMonitorEventVertex *cutPassEvVkm = new AliFemtoCutMonitorEventVertex("cutPasskm");
+    AliFemtoCutMonitorEventVertex *cutFailEvVkm = new AliFemtoCutMonitorEventVertex("cutFailkm");
+    meckm->AddCutMonitor(cutPassEvVkm, cutFailEvVkm);
+
+    AliFemtoShareQualityTPCEntranceSepPairCut *sqpckm = new AliFemtoShareQualityTPCEntranceSepPairCut();
+    sqpckm->SetShareQualityMax(0.0);
+    sqpckm->SetShareFractionMax(0.02);
+    sqpckm->SetRemoveSameLabel(kFALSE);
+    sqpckm->SetTPCEntranceSepMinimum(3.0);
+
+    ankm->SetEventCut(meckm);
+    ankm->SetFirstParticleCut(dtckm);
+    ankm->SetSecondParticleCut(dtckm);
+    ankm->SetPairCut(sqpckm);
+
+    AliFemtoQinvCorrFctn *cqinvkm= new AliFemtoQinvCorrFctn("qinvcf",100,0.0,1.0);
+
+    AliFemtoModelBPLCMSCorrFctn *c3dsmallkm;
+    AliFemtoModelCorrFctn *c1dpikm;
+
+    // Setting up the model calculation
+    // First create the freeze-out generator
+    AliFemtoModelGausRinvFreezeOutGenerator *tFreezekm = new AliFemtoModelGausRinvFreezeOutGenerator();
+    tFreezekm->SetSizeInv(1.8*TMath::Sqrt(2.0));
+    tFreezekm->SetSelectPrimaryFromHidden(false);
+
+    // And the weight generator                                                                    
+    //   AliFemtoModelWeightGeneratorBasic *tWeightkp = new AliFemtoModelWeightGeneratorBasic();
+    //   tWeightkp->SetPairType(AliFemtoModelWeightGenerator::KaonPlusKaonPlus());
+    AliFemtoModelWeightGeneratorLednicky *tWeightkm = new AliFemtoModelWeightGeneratorLednicky();
+    tWeightkm->SetPairType(AliFemtoModelWeightGenerator::KaonPlusKaonPlus());
+    tWeightkm->SetCoulOn();
+    tWeightkm->SetQuantumOn();
+    tWeightkm->SetStrongOff();
+    tWeightkm->Set3BodyOff();
+
+    // Create a manager that will connect it  
+    AliFemtoModelManager *tModelManagerkm = new AliFemtoModelManager();
+    tModelManagerkm->AcceptFreezeOutGenerator(tFreezekp);
+    tModelManagerkm->AcceptWeightGenerator(tWeightkp);
+    tModelManagerkm->CreateCopyHiddenInfo(kFALSE);
+
+    c3dsmallkm = new AliFemtoModelBPLCMSCorrFctn("c3dsmallkm",30, 0.0, 0.6);
+    c3dsmallkm->ConnectToManager(tModelManagerkm);
+
+    c1dpikm = new AliFemtoModelCorrFctn("c1dpikm",100,0.0,1.0);
+    c1dpikm->ConnectToManager(tModelManagerkm);
+
+    //###
+    ankm->AddCorrFctn(cqinvkm);
+    ankm->AddCorrFctn(c3dsmallkm);
+    ankm->AddCorrFctn(c1dpikm);
+
+    Manager->AddAnalysis(ankm);          
+
+    // *** End Kaon-Kaon (negative) analysis
+  }
+
+  if (runPositiveNegativeKaons) {
+    // *** Begin Kaon+Kaon- analysis
+    AliFemtoVertexMultAnalysis *ankpkm = new AliFemtoVertexMultAnalysis(18, -15.6, 15.6, 1, 2, 20000);
+    ankpkm->SetNumEventsToMix(5);
+    ankpkm->SetMinSizePartCollection(2);
+
+    AliFemtoBasicEventCut* meckpkm = new AliFemtoBasicEventCut();
+    meckpkm->SetEventMult(1,100000);
+    meckpkm->SetVertZPos(-1000,1000);
+       
+    AliFemtoESDTrackCut* dtckp = new AliFemtoESDTrackCut();
+    dtckp->SetPidProbKaon(0.7,1.001);
+    dtckp->SetPidProbMuon(0.0,0.5);
+    dtckp->SetPidProbPion(0.0,0.5);
+    dtckp->SetPidProbProton(0.0,0.5);
+    dtckp->SetMomRangeTOFpidIs(0.6,10000.);
+    dtckp->SetCharge(1.0);
+    dtckp->SetMostProbableKaon();
+    dtckp->SetPt(0.15,2.0);
+    dtckp->SetMass(KaonMass);
+    // Track quality cuts
+    dtckp->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+    dtckp->SetminTPCncls(50);
+    dtckp->SetRemoveKinks(kTRUE);
+    dtckp->SetLabel(kFALSE);
+    dtckp->SetMaxITSChiNdof(2.5);
+    dtckp->SetMaxTPCChiNdof(3.0);
+    dtckp->SetMaxImpactXY(3.0);
+    dtckp->SetMaxImpactZ(3.0);
+
+    AliFemtoESDTrackCut* dtckm = new AliFemtoESDTrackCut();
+    dtckm->SetPidProbKaon(0.7,1.001);
+    dtckm->SetPidProbMuon(0.0,0.5);
+    dtckm->SetPidProbPion(0.0,0.5);
+    dtckm->SetPidProbProton(0.0,0.5);
+    dtckm->SetMomRangeTOFpidIs(0.6,10000.);
+    dtckm->SetCharge(-1.0);
+    dtckm->SetMostProbableKaon();
+    dtckm->SetPt(0.15,2.0);
+    dtckm->SetMass(KaonMass);
+    // Track quality cuts
+    dtckm->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+    dtckm->SetminTPCncls(50);
+    dtckm->SetRemoveKinks(kTRUE);
+    dtckm->SetLabel(kFALSE);
+    dtckm->SetMaxITSChiNdof(2.5);
+    dtckm->SetMaxTPCChiNdof(3.0);
+    dtckm->SetMaxImpactXY(3.0);
+    dtckm->SetMaxImpactZ(3.0);
+
+
+    AliFemtoCutMonitorParticleYPt *cutPassYPtkp = new AliFemtoCutMonitorParticleYPt("cutPasskp", 0.493677);
+    AliFemtoCutMonitorParticleYPt *cutFailYPtkp = new AliFemtoCutMonitorParticleYPt("cutFailkp", 0.493677);
+    dtckp->AddCutMonitor(cutPassYPtkp, cutFailYPtkp);
+
+    AliFemtoCutMonitorParticleYPt *cutPassYPtkm = new AliFemtoCutMonitorParticleYPt("cutPasskm", 0.493677);
+    AliFemtoCutMonitorParticleYPt *cutFailYPtkm = new AliFemtoCutMonitorParticleYPt("cutFailkm", 0.493677);
+    dtckm->AddCutMonitor(cutPassYPtkm, cutFailYPtkm);
+
+    AliFemtoCutMonitorParticlePtPDG *cutPassPidkp = new AliFemtoCutMonitorParticlePtPDG("cutPasskp", 0.493677);
+    AliFemtoCutMonitorParticlePtPDG *cutFailPidkp = new AliFemtoCutMonitorParticlePtPDG("cutFailkp", 0.493677);
+    dtckp->AddCutMonitor(cutPassPidkp, cutFailPidkp);
+
+    AliFemtoCutMonitorParticlePtPDG *cutPassPidkm = new AliFemtoCutMonitorParticlePtPDG("cutPasskm", 0.493677);
+    AliFemtoCutMonitorParticlePtPDG *cutFailPidkm = new AliFemtoCutMonitorParticlePtPDG("cutFailkm", 0.493677);
+    dtckm->AddCutMonitor(cutPassPidkm, cutFailPidkm);
+  
+    AliFemtoCutMonitorParticleMomRes *cutPassMRkp = new AliFemtoCutMonitorParticleMomRes("cutPasskp");
+    AliFemtoCutMonitorParticleMomRes *cutFailMRkp = new AliFemtoCutMonitorParticleMomRes("cutFailkp");
+    dtckp->AddCutMonitor(cutPassMRkp, cutFailMRkp);
+
+    AliFemtoCutMonitorParticleMomRes *cutPassMRkm = new AliFemtoCutMonitorParticleMomRes("cutPasskm");
+    AliFemtoCutMonitorParticleMomRes *cutFailMRkm = new AliFemtoCutMonitorParticleMomRes("cutFailkm");
+    dtckm->AddCutMonitor(cutPassMRkm, cutFailMRkm);
+
+    AliFemtoCutMonitorParticleVertPos *cutPassVPkp = new AliFemtoCutMonitorParticleVertPos("cutPasskp");
+    AliFemtoCutMonitorParticleVertPos *cutFailVPkp = new AliFemtoCutMonitorParticleVertPos("cutFailkp");
+    dtckp->AddCutMonitor(cutPassVPkp, cutFailVPkp);
+
+    AliFemtoCutMonitorParticleVertPos *cutPassVPkm = new AliFemtoCutMonitorParticleVertPos("cutPasskm");
+    AliFemtoCutMonitorParticleVertPos *cutFailVPkm = new AliFemtoCutMonitorParticleVertPos("cutFailkm");
+    dtckm->AddCutMonitor(cutPassVPkm, cutFailVPkm);
+
+    AliFemtoCutMonitorEventMult *cutPassEvMkpkm = new AliFemtoCutMonitorEventMult("cutPasskpkm");
+    AliFemtoCutMonitorEventMult *cutFailEvMkpkm = new AliFemtoCutMonitorEventMult("cutFailkpkm");
+    meckpkm->AddCutMonitor(cutPassEvMkpkm, cutFailEvMkpkm);
+    AliFemtoCutMonitorEventVertex *cutPassEvVkpkm = new AliFemtoCutMonitorEventVertex("cutPasskpkm");
+    AliFemtoCutMonitorEventVertex *cutFailEvVkpkm = new AliFemtoCutMonitorEventVertex("cutFailkpkm");
+    meckpkm->AddCutMonitor(cutPassEvVkpkm, cutFailEvVkpkm);
+
+    AliFemtoShareQualityTPCEntranceSepPairCut *sqpckpkm = new AliFemtoShareQualityTPCEntranceSepPairCut();
+    sqpckpkm->SetShareQualityMax(0.0);
+    sqpckpkm->SetShareFractionMax(0.02);
+    sqpckpkm->SetRemoveSameLabel(kFALSE);
+    sqpckpkm->SetTPCEntranceSepMinimum(3.0);
+
+    ankpkm->SetEventCut(meckpkm);
+    ankpkm->SetFirstParticleCut(dtckp);
+    ankpkm->SetSecondParticleCut(dtckm);
+    ankpkm->SetPairCut(sqpckpkm);
+
+    AliFemtoQinvCorrFctn *cqinvkpkm= new AliFemtoQinvCorrFctn("qinvcf",100,0.0,1.0);
+
+    AliFemtoModelBPLCMSCorrFctn *c3dsmallkpkm;
+    AliFemtoModelCorrFctn *c1dpikpkm;
+
+    // Setting up the model calculation
+    // First create the freeze-out generator
+    AliFemtoModelGausRinvFreezeOutGenerator *tFreezekpkm = new AliFemtoModelGausRinvFreezeOutGenerator();
+    tFreezekpkm->SetSizeInv(1.8*TMath::Sqrt(2.0));
+    tFreezekpkm->SetSelectPrimaryFromHidden(false);
+
+    // And the weight generator                                                                    
+    AliFemtoModelWeightGeneratorLednicky *tWeightkpkm = new AliFemtoModelWeightGeneratorLednicky();
+    tWeightkpkm->SetPairType(AliFemtoModelWeightGenerator::KaonPlusKaonMinus());
+    tWeightkpkm->SetCoulOn();
+    tWeightkpkm->SetQuantumOn();
+    tWeightkpkm->SetStrongOff();
+    tWeightkpkm->Set3BodyOff();
+
+    // Create a manager that will connect it  
+    AliFemtoModelManager *tModelManagerkpkm = new AliFemtoModelManager();
+    tModelManagerkpkm->AcceptFreezeOutGenerator(tFreezekpkm);
+    tModelManagerkpkm->AcceptWeightGenerator(tWeightkpkm);
+    tModelManagerkpkm->CreateCopyHiddenInfo(kFALSE);
+
+    c3dsmallkpkm = new AliFemtoModelBPLCMSCorrFctn("c3dsmallkpkm",30, 0.0, 0.6);
+    c3dsmallkpkm->ConnectToManager(tModelManagerkpkm);
+
+    c1dpikpkm = new AliFemtoModelCorrFctn("c1dpikpkm",100,0.0,1.0);
+    c1dpikpkm->ConnectToManager(tModelManagerkpkm);
+
+    //###
+    ankpkm->AddCorrFctn(cqinvkpkm);
+    ankpkm->AddCorrFctn(c3dsmallkpkm);
+    ankpkm->AddCorrFctn(c1dpikpkm);
+
+    Manager->AddAnalysis(ankpkm);        
+
+    // *** End Kaon+Kaon-  analysis
+  }
+  //   if (runPositiveKaons) {
+  //     // *** Begin Kaon-Kaon (positive) analysis
+  //     AliFemtoVertexMultAnalysis *ankp = new AliFemtoVertexMultAnalysis(10, -15.6, 15.6, 1, 2, 20000);
+  //     ankp->SetNumEventsToMix(10);
+  //     ankp->SetMinSizePartCollection(2);
+
+  //     AliFemtoBasicEventCut* meckp = new AliFemtoBasicEventCut();
+  //     meckp->SetEventMult(1,100000);
+  //     meckp->SetVertZPos(-1000,1000);
+       
+  //     AliFemtoESDTrackCut* dtckp = new AliFemtoESDTrackCut();
+  //     dtckp->SetPidProbKaon(0.7,1.001);
+  //     dtckp->SetPidProbMuon(0.0,0.5);
+  //     dtckp->SetPidProbPion(0.0,0.5);
+  //     dtckp->SetPidProbProton(0.0,0.5);
+  //     dtckp->SetCharge(1.0);
+  //     dtckp->SetMostProbableKaon();
+  //     dtckp->SetPt(0.15,2.0);
+  //     dtckp->SetMass(KaonMass);
+  //     dtckp->SetRapidity(-0.8,0.8);
+  //     // Track quality cuts
+  //     dtckp->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+  //     //dtckp->SetStatus(AliESDtrack::kTPCrefit);
+  //     //  dtckp->SetminTPCclsF(95);
+  //     dtckp->SetminTPCncls(50);
+  //     dtckp->SetRemoveKinks(kTRUE);
+  //     dtckp->SetLabel(kFALSE);
+  //     dtckp->SetMaxITSChiNdof(2.5);
+  //     dtckp->SetMaxTPCChiNdof(3.0);
+  //     //  dtckp->SetMaxSigmaToVertex(3.0);
+  //     dtckp->SetMaxImpactXY(3.0);
+  //     dtckp->SetMaxImpactZ(3.0);
+
+  //     AliFemtoCutMonitorParticleYPt *cutPassYPtkp = new AliFemtoCutMonitorParticleYPt("cutPasskp", 0.493677);
+  //     AliFemtoCutMonitorParticleYPt *cutFailYPtkp = new AliFemtoCutMonitorParticleYPt("cutFailkp", 0.493677);
+  //     dtckp->AddCutMonitor(cutPassYPtkp, cutFailYPtkp);
+
+  //     AliFemtoCutMonitorParticlePtPDG *cutPassPidkp = new AliFemtoCutMonitorParticlePtPDG("cutPasskp", 0.493677);
+  //     AliFemtoCutMonitorParticlePtPDG *cutFailPidkp = new AliFemtoCutMonitorParticlePtPDG("cutFailkp", 0.493677);
+  //     dtckp->AddCutMonitor(cutPassPidkp, cutFailPidkp);
+
+  //     AliFemtoCutMonitorParticleMomRes *cutPassMRkp = new AliFemtoCutMonitorParticleMomRes("cutPasskp");
+  //     AliFemtoCutMonitorParticleMomRes *cutFailMRkp = new AliFemtoCutMonitorParticleMomRes("cutFailkp");
+  //     dtckp->AddCutMonitor(cutPassMRkp, cutFailMRkp);
+
+  //     AliFemtoCutMonitorParticleVertPos *cutPassVPkp = new AliFemtoCutMonitorParticleVertPos("cutPasskp");
+  //     AliFemtoCutMonitorParticleVertPos *cutFailVPkp = new AliFemtoCutMonitorParticleVertPos("cutFailkp");
+  //     dtckp->AddCutMonitor(cutPassVPkp, cutFailVPkp);
+
+  //     AliFemtoCutMonitorEventMult *cutPassEvMkp = new AliFemtoCutMonitorEventMult("cutPasskp");
+  //     AliFemtoCutMonitorEventMult *cutFailEvMkp = new AliFemtoCutMonitorEventMult("cutFailkp");
+  //     meckp->AddCutMonitor(cutPassEvMkp, cutFailEvMkp);
+
+  //     AliFemtoCutMonitorEventVertex *cutPassEvVkp = new AliFemtoCutMonitorEventVertex("cutPasskp");
+  //     AliFemtoCutMonitorEventVertex *cutFailEvVkp = new AliFemtoCutMonitorEventVertex("cutFailkp");
+  //     meckp->AddCutMonitor(cutPassEvVkp, cutFailEvVkp);
+
+  //     AliFemtoShareQualityTPCEntranceSepPairCut *sqpckp = new AliFemtoShareQualityTPCEntranceSepPairCut();
+  //     sqpckp->SetShareQualityMax(0.0);
+  //     sqpckp->SetShareFractionMax(0.02);
+  //     sqpckp->SetRemoveSameLabel(kFALSE);
+  //     sqpckp->SetTPCEntranceSepMinimum(3.0);
+
+  //     ankp->SetEventCut(meckp);
+  //     ankp->SetFirstParticleCut(dtckp);
+  //     ankp->SetSecondParticleCut(dtckp);
+  //     ankp->SetPairCut(sqpckp);
+
+  //     AliFemtoQinvCorrFctn *cqinvkp= new AliFemtoQinvCorrFctn("qinvcf",100,0.0,1.0);
+
+  //     AliFemtoModelBPLCMSCorrFctn *c3dsmallkp;
+  //     AliFemtoModelCorrFctn *c1dpikp;
+
+  //     // Setting up the model calculation
+  //     // First create the freeze-out generator
+  //     AliFemtoModelGausRinvFreezeOutGenerator *tFreezekp = new AliFemtoModelGausRinvFreezeOutGenerator();
+  //     tFreezekp->SetSizeInv(1.8*TMath::Sqrt(2.0));
+  //     tFreezekp->SetSelectPrimaryFromHidden(false);
+
+  //     // And the weight generator                                                                    
+  //     //   AliFemtoModelWeightGeneratorBasic *tWeightkp = new AliFemtoModelWeightGeneratorBasic();
+  //     //   tWeightkp->SetPairType(AliFemtoModelWeightGenerator::KaonPlusKaonPlus());
+  //     AliFemtoModelWeightGeneratorLednicky *tWeightkp = new AliFemtoModelWeightGeneratorLednicky();
+  //     tWeightkp->SetPairType(AliFemtoModelWeightGenerator::KaonPlusKaonPlus());
+  //     tWeightkp->SetCoulOn();
+  //     tWeightkp->SetQuantumOn();
+  //     tWeightkp->SetStrongOff();
+  //     tWeightkp->Set3BodyOff();
+
+  //     // Create a manager that will connect it  
+  //     AliFemtoModelManager *tModelManagerkp = new AliFemtoModelManager();
+  //     tModelManagerkp->AcceptFreezeOutGenerator(tFreezekp);
+  //     tModelManagerkp->AcceptWeightGenerator(tWeightkp);
+  //     tModelManagerkp->CreateCopyHiddenInfo(kFALSE);
+
+  //     c3dsmallkp = new AliFemtoModelBPLCMSCorrFctn("c3dsmallkp",30, 0.0, 0.6);
+  //     c3dsmallkp->ConnectToManager(tModelManagerkp);
+
+  //     c1dpikp = new AliFemtoModelCorrFctn("c1dpikp",100,0.0,1.0);
+  //     c1dpikp->ConnectToManager(tModelManagerkp);
+
+  //     //###
+  //     ankp->AddCorrFctn(cqinvkp);
+  //     ankp->AddCorrFctn(c3dsmallkp);
+  //     ankp->AddCorrFctn(c1dpikp);
+
+  //     Manager->AddAnalysis(ankp);     
+
+  //     // *** End Kaon-Kaon (positive) analysis
+  //   }
+
+  //   if (runNegativeKaons) {
+  //     // *** Begin Kaon-Kaon (negative) analysis
+  //     AliFemtoVertexMultAnalysis *ankm = new AliFemtoVertexMultAnalysis(10, -15.6, 15.6, 1, 2, 20000);
+  //     ankm->SetNumEventsToMix(10);
+  //     ankm->SetMinSizePartCollection(2);
+
+  //     AliFemtoBasicEventCut* meckm = new AliFemtoBasicEventCut();
+  //     meckm->SetEventMult(1,100000);
+  //     meckm->SetVertZPos(-1000,1000);
+       
+  //     AliFemtoESDTrackCut* dtckm = new AliFemtoESDTrackCut();
+  //     dtckm->SetPidProbKaon(0.7,1.001);
+  //     dtckm->SetPidProbMuon(0.0,0.5);
+  //     dtckm->SetPidProbPion(0.0,0.5);
+  //     dtckm->SetPidProbProton(0.0,0.5);
+  //     dtckm->SetCharge(1.0);
+  //     dtckm->SetMostProbableKaon();
+  //     dtckm->SetPt(0.15,2.0);
+  //     dtckm->SetMass(KaonMass);
+  //     dtckm->SetRapidity(-0.8,0.8);
+  //     // Track quality cuts
+  //     dtckm->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+  //     //dtckm->SetStatus(AliESDtrack::kTPCrefit);
+  //     //  dtckm->SetminTPCclsF(95);
+  //     dtckm->SetminTPCncls(50);
+  //     dtckm->SetRemoveKinks(kTRUE);
+  //     dtckm->SetLabel(kFALSE);
+  //     dtckm->SetMaxITSChiNdof(2.5);
+  //     dtckm->SetMaxTPCChiNdof(3.0);
+  //     //  dtckm->SetMaxSigmaToVertex(3.0);
+  //     dtckm->SetMaxImpactXY(3.0);
+  //     dtckm->SetMaxImpactZ(3.0);
+
+  //     AliFemtoCutMonitorParticleYPt *cutPassYPtkm = new AliFemtoCutMonitorParticleYPt("cutPasskm", 0.493677);
+  //     AliFemtoCutMonitorParticleYPt *cutFailYPtkm = new AliFemtoCutMonitorParticleYPt("cutFailkm", 0.493677);
+  //     dtckm->AddCutMonitor(cutPassYPtkm, cutFailYPtkm);
+
+  //     AliFemtoCutMonitorParticlePtPDG *cutPassPidkm = new AliFemtoCutMonitorParticlePtPDG("cutPasskm", 0.493677);
+  //     AliFemtoCutMonitorParticlePtPDG *cutFailPidkm = new AliFemtoCutMonitorParticlePtPDG("cutFailkm", 0.493677);
+  //     dtckm->AddCutMonitor(cutPassPidkm, cutFailPidkm);
+
+  //     AliFemtoCutMonitorParticleMomRes *cutPassMRkm = new AliFemtoCutMonitorParticleMomRes("cutPasskm");
+  //     AliFemtoCutMonitorParticleMomRes *cutFailMRkm = new AliFemtoCutMonitorParticleMomRes("cutFailkm");
+  //     dtckm->AddCutMonitor(cutPassMRkm, cutFailMRkm);
+
+  //     AliFemtoCutMonitorParticleVertPos *cutPassVPkm = new AliFemtoCutMonitorParticleVertPos("cutPasskm");
+  //     AliFemtoCutMonitorParticleVertPos *cutFailVPkm = new AliFemtoCutMonitorParticleVertPos("cutFailkm");
+  //     dtckm->AddCutMonitor(cutPassVPkm, cutFailVPkm);
+
+  //     AliFemtoCutMonitorEventMult *cutPassEvMkm = new AliFemtoCutMonitorEventMult("cutPasskm");
+  //     AliFemtoCutMonitorEventMult *cutFailEvMkm = new AliFemtoCutMonitorEventMult("cutFailkm");
+  //     meckm->AddCutMonitor(cutPassEvMkm, cutFailEvMkm);
+
+  //     AliFemtoCutMonitorEventVertex *cutPassEvVkm = new AliFemtoCutMonitorEventVertex("cutPasskm");
+  //     AliFemtoCutMonitorEventVertex *cutFailEvVkm = new AliFemtoCutMonitorEventVertex("cutFailkm");
+  //     meckm->AddCutMonitor(cutPassEvVkm, cutFailEvVkm);
+
+  //     AliFemtoShareQualityTPCEntranceSepPairCut *sqpckm = new AliFemtoShareQualityTPCEntranceSepPairCut();
+  //     sqpckm->SetShareQualityMax(0.0);
+  //     sqpckm->SetShareFractionMax(0.02);
+  //     sqpckm->SetRemoveSameLabel(kFALSE);
+  //     sqpckm->SetTPCEntranceSepMinimum(3.0);
+
+  //     ankm->SetEventCut(meckm);
+  //     ankm->SetFirstParticleCut(dtckm);
+  //     ankm->SetSecondParticleCut(dtckm);
+  //     ankm->SetPairCut(sqpckm);
+
+  //     AliFemtoQinvCorrFctn *cqinvkm= new AliFemtoQinvCorrFctn("qinvcf",100,0.0,1.0);
+
+  //     AliFemtoModelBPLCMSCorrFctn *c3dsmallkm;
+  //     AliFemtoModelCorrFctn *c1dpikm;
+
+  //     // Setting up the model calculation
+  //     // First create the freeze-out generator
+  //     AliFemtoModelGausRinvFreezeOutGenerator *tFreezekm = new AliFemtoModelGausRinvFreezeOutGenerator();
+  //     tFreezekm->SetSizeInv(1.8*TMath::Sqrt(2.0));
+  //     tFreezekm->SetSelectPrimaryFromHidden(false);
+
+  //     // And the weight generator                                                                    
+  //     //   AliFemtoModelWeightGeneratorBasic *tWeightkm = new AliFemtoModelWeightGeneratorBasic();
+  //     //   tWeightkm->SetPairType(AliFemtoModelWeightGenerator::KaonPlusKaonPlus());
+  //     AliFemtoModelWeightGeneratorLednicky *tWeightkm = new AliFemtoModelWeightGeneratorLednicky();
+  //     tWeightkm->SetPairType(AliFemtoModelWeightGenerator::KaonPlusKaonPlus());
+  //     tWeightkm->SetCoulOn();
+  //     tWeightkm->SetQuantumOn();
+  //     tWeightkm->SetStrongOff();
+  //     tWeightkm->Set3BodyOff();
+
+  //     // Create a manager that will connect it  
+  //     AliFemtoModelManager *tModelManagerkm = new AliFemtoModelManager();
+  //     tModelManagerkm->AcceptFreezeOutGenerator(tFreezekm);
+  //     tModelManagerkm->AcceptWeightGenerator(tWeightkm);
+  //     tModelManagerkm->CreateCopyHiddenInfo(kFALSE);
+
+  //     c3dsmallkm = new AliFemtoModelBPLCMSCorrFctn("c3dsmallkm",30, 0.0, 0.6);
+  //     c3dsmallkm->ConnectToManager(tModelManagerkm);
+
+  //     c1dpikm = new AliFemtoModelCorrFctn("c1dpikm",100,0.0,1.0);
+  //     c1dpikm->ConnectToManager(tModelManagerkm);
+
+  //     //###
+  //     ankm->AddCorrFctn(cqinvkm);
+  //     ankm->AddCorrFctn(c3dsmallkm);
+  //     ankm->AddCorrFctn(c1dpikm);
+
+  //     Manager->AddAnalysis(ankm);     
+
+  //     // *** End Kaon-Kaon (positive) analysis
+  //   }
+
+  return Manager;
+}                         
+                      
diff --git a/PWGCF/FEMTOSCOPY/macros/Train/TwoTrackQA/ConfigFemtoAnalysis.C b/PWGCF/FEMTOSCOPY/macros/Train/TwoTrackQA/ConfigFemtoAnalysis.C
new file mode 100644 (file)
index 0000000..103c884
--- /dev/null
@@ -0,0 +1,456 @@
+/*********************************************************************
+ *                                                                   *
+ * ConfigFemtoAnalysis.C - configuration macro for the femtoscopic   *
+ * analysis, meant as a QA process for two-particle effects          *
+ *                                                                   *
+ * Author: Adam Kisiel (Adam.Kisiel@cern.ch)                         *
+ *                                                                   *
+ *********************************************************************/
+
+#if !defined(__CINT__) || defined(__MAKECINT_)
+#include "AliFemtoManager.h"
+#include "AliFemtoEventReaderESDChain.h"
+#include "AliFemtoEventReaderESDChainKine.h"
+#include "AliFemtoSimpleAnalysis.h"
+#include "AliFemtoBasicEventCut.h"
+#include "AliFemtoESDTrackCut.h"
+#include "AliFemtoCorrFctn.h"
+#include "AliFemtoCutMonitorParticleYPt.h"
+#include "AliFemtoCutMonitorParticleVertPos.h"
+#include "AliFemtoCutMonitorParticleMomRes.h"
+#include "AliFemtoCutMonitorEventMult.h"
+#include "AliFemtoCutMonitorEventVertex.h"
+#include "AliFemtoShareQualityTPCEntranceSepPairCut.h"
+#include "AliFemtoQinvCorrFctn.h"
+#include "AliFemtoShareQualityCorrFctn.h"
+#include "AliFemtoTPCInnerCorrFctn.h"
+#include "AliFemtoVertexMultAnalysis.h"
+#include "AliFemtoCorrFctn3DSpherical.h"
+#include "AliFemtoChi2CorrFctn.h"
+#include "AliFemtoCorrFctnTPCNcls.h"
+#include "AliFemtoModelBPLCMSCorrFctn.h"
+#include "AliFemtoModelCorrFctn3DSpherical.h"
+#include "AliFemtoModelGausLCMSFreezeOutGenerator.h"
+#include "AliFemtoModelGausRinvFreezeOutGenerator.h"
+#include "AliFemtoModelManager.h"
+#include "AliFemtoModelWeightGeneratorBasic.h"
+#include "AliFemtoModelWeightGeneratorLednicky.h"
+#include "AliFemtoCorrFctnDirectYlm.h"
+#include "AliFemtoModelCorrFctnDirectYlm.h"
+#include "AliFemtoModelCorrFctnSource.h"
+#include "AliFemtoCutMonitorParticlePtPDG.h"
+#include "AliFemtoKTPairCut.h"
+#endif
+
+//________________________________________________________________________
+AliFemtoManager* ConfigFemtoAnalysis() {
+
+  double PionMass = 0.13956995;
+  double KaonMass = 0.493677;
+  
+//   AliFemtoEventReaderESDChainKine* Reader=new AliFemtoEventReaderESDChainKine();
+//   Reader->SetConstrained(true);
+//   Reader->SetUseTPCOnly(false);
+
+  AliFemtoEventReaderESDChain* Reader=new AliFemtoEventReaderESDChain();
+  Reader->SetConstrained(true);
+  Reader->SetUseTPCOnly(false);
+
+  AliFemtoManager* Manager=new AliFemtoManager();
+  Manager->SetEventReader(Reader);
+       
+  // Switches for QA analyses
+  int runPiPlusStandard = 1;
+  int runPiMinusStandard = 1;
+  int runPositiveQA = 1;
+  int runNegativeQA = 1;
+  int runPositiveTPCQA = 1;
+  int runNegativeTPCQA = 1;
+
+  // *** First QA task - standard HBT analysis with all the cut on ***
+
+  // *** Begin pion-pion (positive) analysis ***
+  if (runPiPlusStandard) {
+    AliFemtoVertexMultAnalysis *anpipstd = new AliFemtoVertexMultAnalysis(3, -15.6, 15.6, 5, 2, 200);
+    anpipstd->SetNumEventsToMix(10);
+    anpipstd->SetMinSizePartCollection(2);
+
+    AliFemtoBasicEventCut* mecpipstd = new AliFemtoBasicEventCut();
+    mecpipstd->SetEventMult(2,100000);
+    mecpipstd->SetVertZPos(-1000,1000);
+       
+    AliFemtoESDTrackCut* dtcpipstd = new AliFemtoESDTrackCut();
+    dtcpipstd->SetPidProbPion(0.2,1.001);
+    dtcpipstd->SetPidProbMuon(0.0,1.0);
+    dtcpipstd->SetPidProbKaon(0.0,1.0);
+    dtcpipstd->SetPidProbProton(0.0,1.0);
+    dtcpipstd->SetCharge(1.0);
+    dtcpipstd->SetPt(0.15,0.5);
+    dtcpipstd->SetMass(PionMass);
+    // Track quality cuts
+    dtcpipstd->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+    //  dtcpipstd->SetStatus(AliESDtrack::kTPCrefit);
+    dtcpipstd->SetminTPCncls(50);
+    dtcpipstd->SetRemoveKinks(kTRUE);
+    dtcpipstd->SetLabel(kFALSE);
+    dtcpipstd->SetMaxITSChiNdof(2.5);
+    dtcpipstd->SetMaxTPCChiNdof(3.0);
+    dtcpipstd->SetMaxImpactXY(3.0);
+    dtcpipstd->SetMaxImpactZ(3.0);
+
+    AliFemtoCutMonitorParticleYPt *cutPassYPtpipstd = new AliFemtoCutMonitorParticleYPt("cutPasspipstd", 0.13957);
+    AliFemtoCutMonitorParticleYPt *cutFailYPtpipstd = new AliFemtoCutMonitorParticleYPt("cutFailpipstd", 0.13957);
+    dtcpipstd->AddCutMonitor(cutPassYPtpipstd, cutFailYPtpipstd);
+
+    AliFemtoShareQualityTPCEntranceSepPairCut *sqpcpipstd = new AliFemtoShareQualityTPCEntranceSepPairCut();
+    sqpcpipstd->SetShareQualityMax(0.0);
+    sqpcpipstd->SetShareFractionMax(0.02);
+    sqpcpipstd->SetRemoveSameLabel(kFALSE);
+    sqpcpipstd->SetTPCEntranceSepMinimum(2.0);
+
+    anpipstd->SetEventCut(mecpipstd);
+    anpipstd->SetFirstParticleCut(dtcpipstd);
+    anpipstd->SetSecondParticleCut(dtcpipstd);
+    anpipstd->SetPairCut(sqpcpipstd);
+    
+    AliFemtoShareQualityCorrFctn *csqqinvpipstd= new AliFemtoShareQualityCorrFctn("sqqinvcfpipstd",40,0.0,0.4);
+    anpipstd->AddCorrFctn(csqqinvpipstd);
+
+    AliFemtoCorrFctnDirectYlm *cylmpipstd = new AliFemtoCorrFctnDirectYlm("cylmpipstd",3,60,0.0,0.3,1);
+    anpipstd->AddCorrFctn(cylmpipstd);
+    
+    AliFemtoQinvCorrFctn *cqinvpipstd = new AliFemtoQinvCorrFctn("qinvcfpipstd", 100,0.0,1.0);
+    anpipstd->AddCorrFctn(cqinvpipstd);
+
+    AliFemtoChi2CorrFctn *cchiqinvpipstd= new AliFemtoChi2CorrFctn("chicfpipstd",40,0.0,0.4);
+    anpipstd->AddCorrFctn(cchiqinvpipstd);
+
+    AliFemtoCorrFctnTPCNcls *cqtpcnclspipstd = new AliFemtoCorrFctnTPCNcls("cqtpcnclspipstd",40,0.0,0.4);
+    anpipstd->AddCorrFctn(cqtpcnclspipstd);
+
+    Manager->AddAnalysis(anpipstd);    
+  }
+  // *** End pion-pion (positive) analysis
+
+  // *** Begin pion-pion (negative) analysis ***
+  if (runPiMinusStandard) {
+    AliFemtoVertexMultAnalysis *anpimstd = new AliFemtoVertexMultAnalysis(3, -15.6, 15.6, 5, 2, 200);
+    anpimstd->SetNumEventsToMix(10);
+    anpimstd->SetMinSizePartCollection(2);
+
+    AliFemtoBasicEventCut* mecpimstd = new AliFemtoBasicEventCut();
+    mecpimstd->SetEventMult(2,100000);
+    mecpimstd->SetVertZPos(-1000,1000);
+       
+    AliFemtoESDTrackCut* dtcpimstd = new AliFemtoESDTrackCut();
+    dtcpimstd->SetPidProbPion(0.2,1.001);
+    dtcpimstd->SetPidProbMuon(0.0,1.0);
+    dtcpimstd->SetPidProbKaon(0.0,1.0);
+    dtcpimstd->SetPidProbProton(0.0,1.0);
+    dtcpimstd->SetCharge(-1.0);
+    dtcpimstd->SetPt(0.15,0.5);
+    dtcpimstd->SetMass(PionMass);
+    // Track quality cuts
+    dtcpimstd->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+    //  dtcpimstd->SetStatus(AliESDtrack::kTPCrefit);
+    dtcpimstd->SetminTPCncls(50);
+    dtcpimstd->SetRemoveKinks(kTRUE);
+    dtcpimstd->SetLabel(kFALSE);
+    dtcpimstd->SetMaxITSChiNdof(2.5);
+    dtcpimstd->SetMaxTPCChiNdof(3.0);
+    dtcpimstd->SetMaxImpactXY(3.0);
+    dtcpimstd->SetMaxImpactZ(3.0);
+
+    AliFemtoCutMonitorParticleYPt *cutPassYPtpimstd = new AliFemtoCutMonitorParticleYPt("cutPasspimstd", 0.13957);
+    AliFemtoCutMonitorParticleYPt *cutFailYPtpimstd = new AliFemtoCutMonitorParticleYPt("cutFailpimstd", 0.13957);
+    dtcpimstd->AddCutMonitor(cutPassYPtpimstd, cutFailYPtpimstd);
+
+    AliFemtoShareQualityTPCEntranceSepPairCut *sqpcpimstd = new AliFemtoShareQualityTPCEntranceSepPairCut();
+    sqpcpimstd->SetShareQualityMax(0.0);
+    sqpcpimstd->SetShareFractionMax(0.02);
+    sqpcpimstd->SetRemoveSameLabel(kFALSE);
+    sqpcpimstd->SetTPCEntranceSepMinimum(2.0);
+
+    anpimstd->SetEventCut(mecpimstd);
+    anpimstd->SetFirstParticleCut(dtcpimstd);
+    anpimstd->SetSecondParticleCut(dtcpimstd);
+    anpimstd->SetPairCut(sqpcpimstd);
+    
+    AliFemtoShareQualityCorrFctn *csqqinvpimstd= new AliFemtoShareQualityCorrFctn("sqqinvcfpimstd",40,0.0,0.4);
+    anpimstd->AddCorrFctn(csqqinvpimstd);
+
+    AliFemtoCorrFctnDirectYlm *cylmpimstd = new AliFemtoCorrFctnDirectYlm("cylmpimstd",3,60,0.0,0.3,1);
+    anpimstd->AddCorrFctn(cylmpimstd);
+    
+    AliFemtoQinvCorrFctn *cqinvpimstd = new AliFemtoQinvCorrFctn("qinvcfpimstd", 100,0.0,1.0);
+    anpimstd->AddCorrFctn(cqinvpimstd);
+
+    AliFemtoChi2CorrFctn *cchiqinvpimstd= new AliFemtoChi2CorrFctn("chicfpimstd",40,0.0,0.4);
+    anpimstd->AddCorrFctn(cchiqinvpimstd);
+
+    AliFemtoCorrFctnTPCNcls *cqtpcnclspimstd = new AliFemtoCorrFctnTPCNcls("cqtpcnclspimstd",40,0.0,0.4);
+    anpimstd->AddCorrFctn(cqtpcnclspimstd);
+
+    Manager->AddAnalysis(anpimstd);    
+  }
+  // *** End pion-pion (negative) analysis
+
+  // *** Second QA task - HBT analysis with all pair cuts off ***
+  // *** Begin pion-pion (positive) analysis ***
+  if (runPositiveQA) {
+    AliFemtoVertexMultAnalysis *anpipnct = new AliFemtoVertexMultAnalysis(3, -15.6, 15.6, 5, 2, 200);
+    anpipnct->SetNumEventsToMix(10);
+    anpipnct->SetMinSizePartCollection(2);
+
+    AliFemtoBasicEventCut* mecpipnct = new AliFemtoBasicEventCut();
+    mecpipnct->SetEventMult(2,100000);
+    mecpipnct->SetVertZPos(-1000,1000);
+       
+    AliFemtoESDTrackCut* dtcpipnct = new AliFemtoESDTrackCut();
+    dtcpipnct->SetPidProbPion(0.0,1.001);
+    dtcpipnct->SetPidProbMuon(0.0,1.0);
+    dtcpipnct->SetPidProbKaon(0.0,1.0);
+    dtcpipnct->SetPidProbProton(0.0,1.0);
+    dtcpipnct->SetCharge(1.0);
+    dtcpipnct->SetPt(0.1,1.0);
+    dtcpipnct->SetMass(PionMass);
+    // Track quality cuts
+    dtcpipnct->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+    //  dtcpipnct->SetStatus(AliESDtrack::kTPCrefit);
+    dtcpipnct->SetminTPCncls(50);
+    dtcpipnct->SetRemoveKinks(kTRUE);
+    dtcpipnct->SetLabel(kFALSE);
+    dtcpipnct->SetMaxITSChiNdof(6.0);
+    dtcpipnct->SetMaxTPCChiNdof(6.0);
+    dtcpipnct->SetMaxImpactXY(3.0);
+    dtcpipnct->SetMaxImpactZ(3.0);
+
+    AliFemtoCutMonitorParticleYPt *cutPassYPtpipnct = new AliFemtoCutMonitorParticleYPt("cutPasspipnct", 0.13957);
+    AliFemtoCutMonitorParticleYPt *cutFailYPtpipnct = new AliFemtoCutMonitorParticleYPt("cutFailpipnct", 0.13957);
+    dtcpipnct->AddCutMonitor(cutPassYPtpipnct, cutFailYPtpipnct);
+
+    AliFemtoShareQualityTPCEntranceSepPairCut *sqpcpipnct = new AliFemtoShareQualityTPCEntranceSepPairCut();
+    sqpcpipnct->SetShareQualityMax(1.0);
+    sqpcpipnct->SetShareFractionMax(1.0);
+    sqpcpipnct->SetRemoveSameLabel(kFALSE);
+    sqpcpipnct->SetTPCEntranceSepMinimum(0.0);
+
+    anpipnct->SetEventCut(mecpipnct);
+    anpipnct->SetFirstParticleCut(dtcpipnct);
+    anpipnct->SetSecondParticleCut(dtcpipnct);
+    anpipnct->SetPairCut(sqpcpipnct);
+    
+    AliFemtoShareQualityCorrFctn *csqqinvpipnct= new AliFemtoShareQualityCorrFctn("sqqinvcfpipnct",40,0.0,0.4);
+    anpipnct->AddCorrFctn(csqqinvpipnct);
+
+    AliFemtoCorrFctnDirectYlm *cylmpipnct = new AliFemtoCorrFctnDirectYlm("cylmpipnct",3,60,0.0,0.3,1);
+    anpipnct->AddCorrFctn(cylmpipnct);
+    
+    AliFemtoQinvCorrFctn *cqinvpipnct = new AliFemtoQinvCorrFctn("qinvcfpipnct", 100,0.0,1.0);
+    anpipnct->AddCorrFctn(cqinvpipnct);
+
+    AliFemtoChi2CorrFctn *cchiqinvpipnct= new AliFemtoChi2CorrFctn("chicfpipnct",40,0.0,0.4);
+    anpipnct->AddCorrFctn(cchiqinvpipnct);
+
+    AliFemtoCorrFctnTPCNcls *cqtpcnclspipnct = new AliFemtoCorrFctnTPCNcls("cqtpcnclspipnct",40,0.0,0.4);
+    anpipnct->AddCorrFctn(cqtpcnclspipnct);
+
+    Manager->AddAnalysis(anpipnct);    
+  }
+  // *** End pion-pion (positive) analysis
+
+  // *** Begin pion-pion (negative) analysis ***
+  if (runNegativeQA) {
+    AliFemtoVertexMultAnalysis *anpimnct = new AliFemtoVertexMultAnalysis(3, -15.6, 15.6, 5, 2, 200);
+    anpimnct->SetNumEventsToMix(10);
+    anpimnct->SetMinSizePartCollection(2);
+
+    AliFemtoBasicEventCut* mecpimnct = new AliFemtoBasicEventCut();
+    mecpimnct->SetEventMult(2,100000);
+    mecpimnct->SetVertZPos(-1000,1000);
+       
+    AliFemtoESDTrackCut* dtcpimnct = new AliFemtoESDTrackCut();
+    dtcpimnct->SetPidProbPion(0.0,1.001);
+    dtcpimnct->SetPidProbMuon(0.0,1.0);
+    dtcpimnct->SetPidProbKaon(0.0,1.0);
+    dtcpimnct->SetPidProbProton(0.0,1.0);
+    dtcpimnct->SetCharge(-1.0);
+    dtcpimnct->SetPt(0.1,1.0);
+    dtcpimnct->SetMass(PionMass);
+    // Track quality cuts
+    dtcpimnct->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+    //  dtcpimnct->SetStatus(AliESDtrack::kTPCrefit);
+    dtcpimnct->SetminTPCncls(50);
+    dtcpimnct->SetRemoveKinks(kTRUE);
+    dtcpimnct->SetLabel(kFALSE);
+    dtcpimnct->SetMaxITSChiNdof(6.0);
+    dtcpimnct->SetMaxTPCChiNdof(6.0);
+    dtcpimnct->SetMaxImpactXY(3.0);
+    dtcpimnct->SetMaxImpactZ(3.0);
+
+    AliFemtoCutMonitorParticleYPt *cutPassYPtpimnct = new AliFemtoCutMonitorParticleYPt("cutPasspimnct", 0.13957);
+    AliFemtoCutMonitorParticleYPt *cutFailYPtpimnct = new AliFemtoCutMonitorParticleYPt("cutFailpimnct", 0.13957);
+    dtcpimnct->AddCutMonitor(cutPassYPtpimnct, cutFailYPtpimnct);
+
+    AliFemtoShareQualityTPCEntranceSepPairCut *sqpcpimnct = new AliFemtoShareQualityTPCEntranceSepPairCut();
+    sqpcpimnct->SetShareQualityMax(1.0);
+    sqpcpimnct->SetShareFractionMax(1.0);
+    sqpcpimnct->SetRemoveSameLabel(kFALSE);
+    sqpcpimnct->SetTPCEntranceSepMinimum(0.0);
+
+    anpimnct->SetEventCut(mecpimnct);
+    anpimnct->SetFirstParticleCut(dtcpimnct);
+    anpimnct->SetSecondParticleCut(dtcpimnct);
+    anpimnct->SetPairCut(sqpcpimnct);
+    
+    AliFemtoShareQualityCorrFctn *csqqinvpimnct= new AliFemtoShareQualityCorrFctn("sqqinvcfpimnct",40,0.0,0.4);
+    anpimnct->AddCorrFctn(csqqinvpimnct);
+
+    AliFemtoCorrFctnDirectYlm *cylmpimnct = new AliFemtoCorrFctnDirectYlm("cylmpimnct",3,60,0.0,0.3,1);
+    anpimnct->AddCorrFctn(cylmpimnct);
+    
+    AliFemtoQinvCorrFctn *cqinvpimnct = new AliFemtoQinvCorrFctn("qinvcfpimnct", 100,0.0,1.0);
+    anpimnct->AddCorrFctn(cqinvpimnct);
+
+    AliFemtoChi2CorrFctn *cchiqinvpimnct= new AliFemtoChi2CorrFctn("chicfpimnct",40,0.0,0.4);
+    anpimnct->AddCorrFctn(cchiqinvpimnct);
+
+    AliFemtoCorrFctnTPCNcls *cqtpcnclspimnct = new AliFemtoCorrFctnTPCNcls("cqtpcnclspimnct",40,0.0,0.4);
+    anpimnct->AddCorrFctn(cqtpcnclspimnct);
+
+    Manager->AddAnalysis(anpimnct);    
+  }
+  // *** End pion-pion (negative) analysis
+
+  // *** Third QA task - HBT analysis with all pair cuts off, TPC only ***
+  // *** Begin pion-pion (positive) analysis ***
+  if (runPositiveTPCQA) {
+    AliFemtoVertexMultAnalysis *anpiptpc = new AliFemtoVertexMultAnalysis(3, -15.6, 15.6, 5, 2, 200);
+    anpiptpc->SetNumEventsToMix(10);
+    anpiptpc->SetMinSizePartCollection(2);
+
+    AliFemtoBasicEventCut* mecpiptpc = new AliFemtoBasicEventCut();
+    mecpiptpc->SetEventMult(2,100000);
+    mecpiptpc->SetVertZPos(-1000,1000);
+       
+    AliFemtoESDTrackCut* dtcpiptpc = new AliFemtoESDTrackCut();
+    dtcpiptpc->SetPidProbPion(0.0,1.001);
+    dtcpiptpc->SetPidProbMuon(0.0,1.0);
+    dtcpiptpc->SetPidProbKaon(0.0,1.0);
+    dtcpiptpc->SetPidProbProton(0.0,1.0);
+    dtcpiptpc->SetCharge(1.0);
+    dtcpiptpc->SetPt(0.1,1.0);
+    dtcpiptpc->SetMass(PionMass);
+    // Track quality cuts
+    //dtcpiptpc->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+    dtcpiptpc->SetStatus(AliESDtrack::kTPCrefit);
+    dtcpiptpc->SetminTPCncls(50);
+    dtcpiptpc->SetRemoveKinks(kTRUE);
+    dtcpiptpc->SetLabel(kFALSE);
+    dtcpiptpc->SetMaxITSChiNdof(6.0);
+    dtcpiptpc->SetMaxTPCChiNdof(6.0);
+    dtcpiptpc->SetMaxImpactXY(3.0);
+    dtcpiptpc->SetMaxImpactZ(3.0);
+
+    AliFemtoCutMonitorParticleYPt *cutPassYPtpiptpc = new AliFemtoCutMonitorParticleYPt("cutPasspiptpc", 0.13957);
+    AliFemtoCutMonitorParticleYPt *cutFailYPtpiptpc = new AliFemtoCutMonitorParticleYPt("cutFailpiptpc", 0.13957);
+    dtcpiptpc->AddCutMonitor(cutPassYPtpiptpc, cutFailYPtpiptpc);
+
+    AliFemtoShareQualityTPCEntranceSepPairCut *sqpcpiptpc = new AliFemtoShareQualityTPCEntranceSepPairCut();
+    sqpcpiptpc->SetShareQualityMax(1.0);
+    sqpcpiptpc->SetShareFractionMax(1.0);
+    sqpcpiptpc->SetRemoveSameLabel(kFALSE);
+    sqpcpiptpc->SetTPCEntranceSepMinimum(0.0);
+
+    anpiptpc->SetEventCut(mecpiptpc);
+    anpiptpc->SetFirstParticleCut(dtcpiptpc);
+    anpiptpc->SetSecondParticleCut(dtcpiptpc);
+    anpiptpc->SetPairCut(sqpcpiptpc);
+    
+    AliFemtoShareQualityCorrFctn *csqqinvpiptpc= new AliFemtoShareQualityCorrFctn("sqqinvcfpiptpc",40,0.0,0.4);
+    anpiptpc->AddCorrFctn(csqqinvpiptpc);
+
+    AliFemtoCorrFctnDirectYlm *cylmpiptpc = new AliFemtoCorrFctnDirectYlm("cylmpiptpc",3,60,0.0,0.3,1);
+    anpiptpc->AddCorrFctn(cylmpiptpc);
+    
+    AliFemtoQinvCorrFctn *cqinvpiptpc = new AliFemtoQinvCorrFctn("qinvcfpiptpc", 100,0.0,1.0);
+    anpiptpc->AddCorrFctn(cqinvpiptpc);
+
+    AliFemtoChi2CorrFctn *cchiqinvpiptpc= new AliFemtoChi2CorrFctn("chicfpiptpc",40,0.0,0.4);
+    anpiptpc->AddCorrFctn(cchiqinvpiptpc);
+
+    AliFemtoCorrFctnTPCNcls *cqtpcnclspiptpc = new AliFemtoCorrFctnTPCNcls("cqtpcnclspiptpc",40,0.0,0.4);
+    anpiptpc->AddCorrFctn(cqtpcnclspiptpc);
+
+    Manager->AddAnalysis(anpiptpc);    
+  }
+  // *** End pion-pion (positive) analysis
+
+  // *** Begin pion-pion (negative) analysis ***
+  if (runNegativeTPCQA) {
+    AliFemtoVertexMultAnalysis *anpimtpc = new AliFemtoVertexMultAnalysis(3, -15.6, 15.6, 5, 2, 200);
+    anpimtpc->SetNumEventsToMix(10);
+    anpimtpc->SetMinSizePartCollection(2);
+
+    AliFemtoBasicEventCut* mecpimtpc = new AliFemtoBasicEventCut();
+    mecpimtpc->SetEventMult(2,100000);
+    mecpimtpc->SetVertZPos(-1000,1000);
+       
+    AliFemtoESDTrackCut* dtcpimtpc = new AliFemtoESDTrackCut();
+    dtcpimtpc->SetPidProbPion(0.0,1.001);
+    dtcpimtpc->SetPidProbMuon(0.0,1.0);
+    dtcpimtpc->SetPidProbKaon(0.0,1.0);
+    dtcpimtpc->SetPidProbProton(0.0,1.0);
+    dtcpimtpc->SetCharge(-1.0);
+    dtcpimtpc->SetPt(0.1,1.0);
+    dtcpimtpc->SetMass(PionMass);
+    // Track quality cuts
+    //dtcpimtpc->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+    dtcpimtpc->SetStatus(AliESDtrack::kTPCrefit);
+    dtcpimtpc->SetminTPCncls(50);
+    dtcpimtpc->SetRemoveKinks(kTRUE);
+    dtcpimtpc->SetLabel(kFALSE);
+    dtcpimtpc->SetMaxITSChiNdof(6.0);
+    dtcpimtpc->SetMaxTPCChiNdof(6.0);
+    dtcpimtpc->SetMaxImpactXY(3.0);
+    dtcpimtpc->SetMaxImpactZ(3.0);
+
+    AliFemtoCutMonitorParticleYPt *cutPassYPtpimtpc = new AliFemtoCutMonitorParticleYPt("cutPasspimtpc", 0.13957);
+    AliFemtoCutMonitorParticleYPt *cutFailYPtpimtpc = new AliFemtoCutMonitorParticleYPt("cutFailpimtpc", 0.13957);
+    dtcpimtpc->AddCutMonitor(cutPassYPtpimtpc, cutFailYPtpimtpc);
+
+    AliFemtoShareQualityTPCEntranceSepPairCut *sqpcpimtpc = new AliFemtoShareQualityTPCEntranceSepPairCut();
+    sqpcpimtpc->SetShareQualityMax(1.0);
+    sqpcpimtpc->SetShareFractionMax(1.0);
+    sqpcpimtpc->SetRemoveSameLabel(kFALSE);
+    sqpcpimtpc->SetTPCEntranceSepMinimum(0.0);
+
+    anpimtpc->SetEventCut(mecpimtpc);
+    anpimtpc->SetFirstParticleCut(dtcpimtpc);
+    anpimtpc->SetSecondParticleCut(dtcpimtpc);
+    anpimtpc->SetPairCut(sqpcpimtpc);
+    
+    AliFemtoShareQualityCorrFctn *csqqinvpimtpc= new AliFemtoShareQualityCorrFctn("sqqinvcfpimtpc",40,0.0,0.4);
+    anpimtpc->AddCorrFctn(csqqinvpimtpc);
+
+    AliFemtoCorrFctnDirectYlm *cylmpimtpc = new AliFemtoCorrFctnDirectYlm("cylmpimtpc",3,60,0.0,0.3,1);
+    anpimtpc->AddCorrFctn(cylmpimtpc);
+    
+    AliFemtoQinvCorrFctn *cqinvpimtpc = new AliFemtoQinvCorrFctn("qinvcfpimtpc", 100,0.0,1.0);
+    anpimtpc->AddCorrFctn(cqinvpimtpc);
+
+    AliFemtoChi2CorrFctn *cchiqinvpimtpc= new AliFemtoChi2CorrFctn("chicfpimtpc",40,0.0,0.4);
+    anpimtpc->AddCorrFctn(cchiqinvpimtpc);
+
+    AliFemtoCorrFctnTPCNcls *cqtpcnclspimtpc = new AliFemtoCorrFctnTPCNcls("cqtpcnclspimtpc",40,0.0,0.4);
+    anpimtpc->AddCorrFctn(cqtpcnclspimtpc);
+
+    Manager->AddAnalysis(anpimtpc);    
+  }
+  // *** End pion-pion (negative) analysis
+
+
+
+  return Manager;
+}                         
+                      
diff --git a/PWGCF/FEMTOSCOPY/macros/Train/TwoTrackQA/ConfigFemtoAnalysisCentral.C b/PWGCF/FEMTOSCOPY/macros/Train/TwoTrackQA/ConfigFemtoAnalysisCentral.C
new file mode 100644 (file)
index 0000000..8ad15ba
--- /dev/null
@@ -0,0 +1,499 @@
+/*********************************************************************
+ *                                                                   *
+ * ConfigFemtoAnalysis.C - configuration macro for the femtoscopic   *
+ * analysis, meant as a QA process for two-particle effects          *
+ *                                                                   *
+ * Author: Adam Kisiel (Adam.Kisiel@cern.ch)                         *
+ *                                                                   *
+ *********************************************************************/
+
+#if !defined(__CINT__) || defined(__MAKECINT_)
+#include "AliFemtoManager.h"
+#include "AliFemtoEventReaderESDChain.h"
+#include "AliFemtoEventReaderESDChainKine.h"
+#include "AliFemtoSimpleAnalysis.h"
+#include "AliFemtoBasicEventCut.h"
+#include "AliFemtoESDTrackCut.h"
+#include "AliFemtoCorrFctn.h"
+#include "AliFemtoCutMonitorParticleYPt.h"
+#include "AliFemtoCutMonitorParticleVertPos.h"
+#include "AliFemtoCutMonitorParticleMomRes.h"
+#include "AliFemtoCutMonitorEventMult.h"
+#include "AliFemtoCutMonitorEventVertex.h"
+#include "AliFemtoShareQualityTPCEntranceSepPairCut.h"
+#include "AliFemtoQinvCorrFctn.h"
+#include "AliFemtoShareQualityCorrFctn.h"
+#include "AliFemtoTPCInnerCorrFctn.h"
+#include "AliFemtoVertexMultAnalysis.h"
+#include "AliFemtoCorrFctn3DSpherical.h"
+#include "AliFemtoChi2CorrFctn.h"
+#include "AliFemtoCorrFctnTPCNcls.h"
+#include "AliFemtoModelBPLCMSCorrFctn.h"
+#include "AliFemtoModelCorrFctn3DLCMSSym.h"
+#include "AliFemtoModelCorrFctn3DSpherical.h"
+#include "AliFemtoModelGausLCMSFreezeOutGenerator.h"
+#include "AliFemtoModelGausRinvFreezeOutGenerator.h"
+#include "AliFemtoModelManager.h"
+#include "AliFemtoModelWeightGeneratorBasic.h"
+#include "AliFemtoModelWeightGeneratorLednicky.h"
+#include "AliFemtoCorrFctnDirectYlm.h"
+#include "AliFemtoModelCorrFctnDirectYlm.h"
+#include "AliFemtoModelCorrFctnSource.h"
+#include "AliFemtoCutMonitorParticlePtPDG.h"
+#include "AliFemtoKTPairCut.h"
+#endif
+
+//________________________________________________________________________
+AliFemtoManager* ConfigFemtoAnalysis(int doESD=1, int iCollision=1, int iCent=0) {
+
+  double PionMass = 0.13956995;
+  double KaonMass = 0.493677;
+  
+//   AliFemtoEventReaderESDChainKine* Reader=new AliFemtoEventReaderESDChainKine();
+//   Reader->SetConstrained(true);
+//   Reader->SetUseTPCOnly(false);
+
+  int multmin=0, multmax=0;
+  double zmin, zmax;
+
+  int ppranges[9] = { 1, 12, 17, 23, 30, 37, 45, 58, 150 };
+  int aaranges[11] = { 0, 50, 100, 200, 300, 400, 500, 600, 700, 800, 900 };
+
+  if (iCollision == 0) { // pp setup
+    if ((iCent >=0) && (iCent<8)) {
+      multmin = ppranges[iCent];
+      multmax = ppranges[iCent+1];
+    }
+    zmin = -12.0;
+    zmax = 12.0;
+  }
+  if (iCollision == 1) { // PbPb setup
+    if ((iCent >=0) && (iCent<10)) {
+      multmin = aaranges[iCent];
+      multmax = aaranges[iCent+1];
+    }
+    zmin = -8.0;
+    zmax = 8.0;
+  }
+
+  AliFemtoEventReaderESDChain* Reader=new AliFemtoEventReaderESDChain();
+  Reader->SetConstrained(true);
+  Reader->SetUseTPCOnly(false);
+
+  if (iCollision == 0) 
+    Reader->SetUseMultiplicity(AliFemtoEventReaderESDChain::kGlobalCount);
+  if (iCollision == 1) 
+    Reader->SetUseMultiplicity(AliFemtoEventReaderESDChain::kV0Centrality);
+
+  AliFemtoManager* Manager=new AliFemtoManager();
+  Manager->SetEventReader(Reader);
+       
+  // Switches for QA analyses
+  int runPiPlusStandard = 1;
+  int runPiMinusStandard = 1;
+  int runPositiveQA = 1;
+  int runNegativeQA = 1;
+  int runPositiveTPCQA = 1;
+  int runNegativeTPCQA = 0;
+
+  // *** First QA task - standard HBT analysis with all the cut on ***
+
+  // *** Begin pion-pion (positive) analysis ***
+  if (runPiPlusStandard) {
+    AliFemtoVertexMultAnalysis *anpipstd = new AliFemtoVertexMultAnalysis(1, zmin, zmax, 5, multmin, multmax);
+    anpipstd->SetNumEventsToMix(iCollision?3:10);
+    anpipstd->SetMinSizePartCollection(2);
+
+    AliFemtoBasicEventCut* mecpipstd = new AliFemtoBasicEventCut();
+    mecpipstd->SetEventMult(0,100000);
+    mecpipstd->SetVertZPos(-1000,1000);
+       
+    AliFemtoESDTrackCut* dtcpipstd = new AliFemtoESDTrackCut();
+    dtcpipstd->SetPidProbPion(0.2,1.001);
+    dtcpipstd->SetPidProbMuon(0.0,1.0);
+    dtcpipstd->SetPidProbKaon(0.0,1.0);
+    dtcpipstd->SetPidProbProton(0.0,1.0);
+    dtcpipstd->SetCharge(1.0);
+    dtcpipstd->SetPt(0.15,0.5);
+    dtcpipstd->SetMass(PionMass);
+    // Track quality cuts
+    dtcpipstd->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+    //  dtcpipstd->SetStatus(AliESDtrack::kTPCrefit);
+    dtcpipstd->SetminTPCncls(50);
+    dtcpipstd->SetRemoveKinks(kTRUE);
+    dtcpipstd->SetLabel(kFALSE);
+    dtcpipstd->SetMaxITSChiNdof(2.5);
+    dtcpipstd->SetMaxTPCChiNdof(3.0);
+    dtcpipstd->SetMaxImpactXY(3.0);
+    dtcpipstd->SetMaxImpactZ(3.0);
+
+    AliFemtoCutMonitorParticleYPt *cutPassYPtpipstd = new AliFemtoCutMonitorParticleYPt("cutPasspipstd", 0.13957);
+    AliFemtoCutMonitorParticleYPt *cutFailYPtpipstd = new AliFemtoCutMonitorParticleYPt("cutFailpipstd", 0.13957);
+    dtcpipstd->AddCutMonitor(cutPassYPtpipstd, cutFailYPtpipstd);
+
+    AliFemtoShareQualityTPCEntranceSepPairCut *sqpcpipstd = new AliFemtoShareQualityTPCEntranceSepPairCut();
+    sqpcpipstd->SetShareQualityMax(0.0);
+    sqpcpipstd->SetShareFractionMax(0.02);
+    sqpcpipstd->SetRemoveSameLabel(kFALSE);
+    sqpcpipstd->SetTPCEntranceSepMinimum(2.0);
+
+    anpipstd->SetEventCut(mecpipstd);
+    anpipstd->SetFirstParticleCut(dtcpipstd);
+    anpipstd->SetSecondParticleCut(dtcpipstd);
+    anpipstd->SetPairCut(sqpcpipstd);
+    
+    AliFemtoShareQualityCorrFctn *csqqinvpipstd= new AliFemtoShareQualityCorrFctn("sqqinvcfpipstd",40,0.0,0.4);
+    anpipstd->AddCorrFctn(csqqinvpipstd);
+
+    AliFemtoCorrFctnDirectYlm *cylmpipstd = new AliFemtoCorrFctnDirectYlm("cylmpipstd",3,60,0.0,0.3,1);
+    anpipstd->AddCorrFctn(cylmpipstd);
+    
+    AliFemtoQinvCorrFctn *cqinvpipstd = new AliFemtoQinvCorrFctn("qinvcfpipstd", 100,0.0,1.0);
+    anpipstd->AddCorrFctn(cqinvpipstd);
+
+    AliFemtoChi2CorrFctn *cchiqinvpipstd= new AliFemtoChi2CorrFctn("chicfpipstd",40,0.0,0.4);
+    anpipstd->AddCorrFctn(cchiqinvpipstd);
+
+    AliFemtoCorrFctnTPCNcls *cqtpcnclspipstd = new AliFemtoCorrFctnTPCNcls("cqtpcnclspipstd",40,0.0,0.4);
+    anpipstd->AddCorrFctn(cqtpcnclspipstd);
+
+    AliFemtoCorrFctn3DLCMSSym *cq3dlcmspipstd = new AliFemtoCorrFctn3DLCMSSym("cq3dlcmspipstd",60,0.3);
+    anpipstd->AddCorrFctn(cq3dlcmspipstd);
+
+    Manager->AddAnalysis(anpipstd);    
+  }
+  // *** End pion-pion (positive) analysis
+
+  // *** Begin pion-pion (negative) analysis ***
+  if (runPiMinusStandard) {
+    AliFemtoVertexMultAnalysis *anpimstd = new AliFemtoVertexMultAnalysis(1, zmin, zmax, 5, multmin, multmax);
+    anpimstd->SetNumEventsToMix(iCollision?3:10);
+    anpimstd->SetMinSizePartCollection(2);
+
+    AliFemtoBasicEventCut* mecpimstd = new AliFemtoBasicEventCut();
+    mecpimstd->SetEventMult(0,100000);
+    mecpimstd->SetVertZPos(-1000,1000);
+       
+    AliFemtoESDTrackCut* dtcpimstd = new AliFemtoESDTrackCut();
+    dtcpimstd->SetPidProbPion(0.2,1.001);
+    dtcpimstd->SetPidProbMuon(0.0,1.0);
+    dtcpimstd->SetPidProbKaon(0.0,1.0);
+    dtcpimstd->SetPidProbProton(0.0,1.0);
+    dtcpimstd->SetCharge(-1.0);
+    dtcpimstd->SetPt(0.15,0.5);
+    dtcpimstd->SetMass(PionMass);
+    // Track quality cuts
+    dtcpimstd->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+    //  dtcpimstd->SetStatus(AliESDtrack::kTPCrefit);
+    dtcpimstd->SetminTPCncls(50);
+    dtcpimstd->SetRemoveKinks(kTRUE);
+    dtcpimstd->SetLabel(kFALSE);
+    dtcpimstd->SetMaxITSChiNdof(2.5);
+    dtcpimstd->SetMaxTPCChiNdof(3.0);
+    dtcpimstd->SetMaxImpactXY(3.0);
+    dtcpimstd->SetMaxImpactZ(3.0);
+
+    AliFemtoCutMonitorParticleYPt *cutPassYPtpimstd = new AliFemtoCutMonitorParticleYPt("cutPasspimstd", 0.13957);
+    AliFemtoCutMonitorParticleYPt *cutFailYPtpimstd = new AliFemtoCutMonitorParticleYPt("cutFailpimstd", 0.13957);
+    dtcpimstd->AddCutMonitor(cutPassYPtpimstd, cutFailYPtpimstd);
+
+    AliFemtoShareQualityTPCEntranceSepPairCut *sqpcpimstd = new AliFemtoShareQualityTPCEntranceSepPairCut();
+    sqpcpimstd->SetShareQualityMax(0.0);
+    sqpcpimstd->SetShareFractionMax(0.02);
+    sqpcpimstd->SetRemoveSameLabel(kFALSE);
+    sqpcpimstd->SetTPCEntranceSepMinimum(2.0);
+
+    anpimstd->SetEventCut(mecpimstd);
+    anpimstd->SetFirstParticleCut(dtcpimstd);
+    anpimstd->SetSecondParticleCut(dtcpimstd);
+    anpimstd->SetPairCut(sqpcpimstd);
+    
+    AliFemtoShareQualityCorrFctn *csqqinvpimstd= new AliFemtoShareQualityCorrFctn("sqqinvcfpimstd",40,0.0,0.4);
+    anpimstd->AddCorrFctn(csqqinvpimstd);
+
+    AliFemtoCorrFctnDirectYlm *cylmpimstd = new AliFemtoCorrFctnDirectYlm("cylmpimstd",3,60,0.0,0.3,1);
+    anpimstd->AddCorrFctn(cylmpimstd);
+    
+    AliFemtoQinvCorrFctn *cqinvpimstd = new AliFemtoQinvCorrFctn("qinvcfpimstd", 100,0.0,1.0);
+    anpimstd->AddCorrFctn(cqinvpimstd);
+
+    AliFemtoChi2CorrFctn *cchiqinvpimstd= new AliFemtoChi2CorrFctn("chicfpimstd",40,0.0,0.4);
+    anpimstd->AddCorrFctn(cchiqinvpimstd);
+
+    AliFemtoCorrFctnTPCNcls *cqtpcnclspimstd = new AliFemtoCorrFctnTPCNcls("cqtpcnclspimstd",40,0.0,0.4);
+    anpimstd->AddCorrFctn(cqtpcnclspimstd);
+
+    AliFemtoCorrFctn3DLCMSSym *cq3dlcmspimstd = new AliFemtoCorrFctn3DLCMSSym("cq3dlcmspimstd",60,0.3);
+    anpimstd->AddCorrFctn(cq3dlcmspimstd);
+
+    Manager->AddAnalysis(anpimstd);    
+  }
+  // *** End pion-pion (negative) analysis
+
+  // *** Second QA task - HBT analysis with all pair cuts off ***
+  // *** Begin pion-pion (positive) analysis ***
+  if (runPositiveQA) {
+    AliFemtoVertexMultAnalysis *anpipnct = new AliFemtoVertexMultAnalysis(1, zmin, zmax, 5, multmin, multmax);
+    anpipnct->SetNumEventsToMix(iCollision?3:10);
+    anpipnct->SetMinSizePartCollection(2);
+
+    AliFemtoBasicEventCut* mecpipnct = new AliFemtoBasicEventCut();
+    mecpipnct->SetEventMult(0,100000);
+    mecpipnct->SetVertZPos(-1000,1000);
+       
+    AliFemtoESDTrackCut* dtcpipnct = new AliFemtoESDTrackCut();
+    dtcpipnct->SetPidProbPion(0.0,1.001);
+    dtcpipnct->SetPidProbMuon(0.0,1.0);
+    dtcpipnct->SetPidProbKaon(0.0,1.0);
+    dtcpipnct->SetPidProbProton(0.0,1.0);
+    dtcpipnct->SetCharge(1.0);
+    dtcpipnct->SetPt(0.1,1.0);
+    dtcpipnct->SetMass(PionMass);
+    // Track quality cuts
+    dtcpipnct->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+    //  dtcpipnct->SetStatus(AliESDtrack::kTPCrefit);
+    dtcpipnct->SetminTPCncls(50);
+    dtcpipnct->SetRemoveKinks(kTRUE);
+    dtcpipnct->SetLabel(kFALSE);
+    dtcpipnct->SetMaxITSChiNdof(6.0);
+    dtcpipnct->SetMaxTPCChiNdof(6.0);
+    dtcpipnct->SetMaxImpactXY(3.0);
+    dtcpipnct->SetMaxImpactZ(3.0);
+
+    AliFemtoCutMonitorParticleYPt *cutPassYPtpipnct = new AliFemtoCutMonitorParticleYPt("cutPasspipnct", 0.13957);
+    AliFemtoCutMonitorParticleYPt *cutFailYPtpipnct = new AliFemtoCutMonitorParticleYPt("cutFailpipnct", 0.13957);
+    dtcpipnct->AddCutMonitor(cutPassYPtpipnct, cutFailYPtpipnct);
+
+    AliFemtoShareQualityTPCEntranceSepPairCut *sqpcpipnct = new AliFemtoShareQualityTPCEntranceSepPairCut();
+    sqpcpipnct->SetShareQualityMax(1.0);
+    sqpcpipnct->SetShareFractionMax(1.0);
+    sqpcpipnct->SetRemoveSameLabel(kFALSE);
+    sqpcpipnct->SetTPCEntranceSepMinimum(0.0);
+
+    anpipnct->SetEventCut(mecpipnct);
+    anpipnct->SetFirstParticleCut(dtcpipnct);
+    anpipnct->SetSecondParticleCut(dtcpipnct);
+    anpipnct->SetPairCut(sqpcpipnct);
+    
+    AliFemtoShareQualityCorrFctn *csqqinvpipnct= new AliFemtoShareQualityCorrFctn("sqqinvcfpipnct",40,0.0,0.4);
+    anpipnct->AddCorrFctn(csqqinvpipnct);
+
+    AliFemtoCorrFctnDirectYlm *cylmpipnct = new AliFemtoCorrFctnDirectYlm("cylmpipnct",3,60,0.0,0.3,1);
+    anpipnct->AddCorrFctn(cylmpipnct);
+    
+    AliFemtoQinvCorrFctn *cqinvpipnct = new AliFemtoQinvCorrFctn("qinvcfpipnct", 100,0.0,1.0);
+    anpipnct->AddCorrFctn(cqinvpipnct);
+
+    AliFemtoChi2CorrFctn *cchiqinvpipnct= new AliFemtoChi2CorrFctn("chicfpipnct",40,0.0,0.4);
+    anpipnct->AddCorrFctn(cchiqinvpipnct);
+
+    AliFemtoCorrFctnTPCNcls *cqtpcnclspipnct = new AliFemtoCorrFctnTPCNcls("cqtpcnclspipnct",40,0.0,0.4);
+    anpipnct->AddCorrFctn(cqtpcnclspipnct);
+
+    Manager->AddAnalysis(anpipnct);    
+  }
+  // *** End pion-pion (positive) analysis
+
+  // *** Begin pion-pion (negative) analysis ***
+  if (runNegativeQA) {
+    AliFemtoVertexMultAnalysis *anpimnct = new AliFemtoVertexMultAnalysis(1, zmin, zmax, 5, multmin, multmax);
+    anpimnct->SetNumEventsToMix(iCollision?3:10);
+    anpimnct->SetMinSizePartCollection(2);
+
+    AliFemtoBasicEventCut* mecpimnct = new AliFemtoBasicEventCut();
+    mecpimnct->SetEventMult(0,100000);
+    mecpimnct->SetVertZPos(-1000,1000);
+       
+    AliFemtoESDTrackCut* dtcpimnct = new AliFemtoESDTrackCut();
+    dtcpimnct->SetPidProbPion(0.0,1.001);
+    dtcpimnct->SetPidProbMuon(0.0,1.0);
+    dtcpimnct->SetPidProbKaon(0.0,1.0);
+    dtcpimnct->SetPidProbProton(0.0,1.0);
+    dtcpimnct->SetCharge(-1.0);
+    dtcpimnct->SetPt(0.1,1.0);
+    dtcpimnct->SetMass(PionMass);
+    // Track quality cuts
+    dtcpimnct->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+    //  dtcpimnct->SetStatus(AliESDtrack::kTPCrefit);
+    dtcpimnct->SetminTPCncls(50);
+    dtcpimnct->SetRemoveKinks(kTRUE);
+    dtcpimnct->SetLabel(kFALSE);
+    dtcpimnct->SetMaxITSChiNdof(6.0);
+    dtcpimnct->SetMaxTPCChiNdof(6.0);
+    dtcpimnct->SetMaxImpactXY(3.0);
+    dtcpimnct->SetMaxImpactZ(3.0);
+
+    AliFemtoCutMonitorParticleYPt *cutPassYPtpimnct = new AliFemtoCutMonitorParticleYPt("cutPasspimnct", 0.13957);
+    AliFemtoCutMonitorParticleYPt *cutFailYPtpimnct = new AliFemtoCutMonitorParticleYPt("cutFailpimnct", 0.13957);
+    dtcpimnct->AddCutMonitor(cutPassYPtpimnct, cutFailYPtpimnct);
+
+    AliFemtoShareQualityTPCEntranceSepPairCut *sqpcpimnct = new AliFemtoShareQualityTPCEntranceSepPairCut();
+    sqpcpimnct->SetShareQualityMax(1.0);
+    sqpcpimnct->SetShareFractionMax(1.0);
+    sqpcpimnct->SetRemoveSameLabel(kFALSE);
+    sqpcpimnct->SetTPCEntranceSepMinimum(0.0);
+
+    anpimnct->SetEventCut(mecpimnct);
+    anpimnct->SetFirstParticleCut(dtcpimnct);
+    anpimnct->SetSecondParticleCut(dtcpimnct);
+    anpimnct->SetPairCut(sqpcpimnct);
+    
+    AliFemtoShareQualityCorrFctn *csqqinvpimnct= new AliFemtoShareQualityCorrFctn("sqqinvcfpimnct",40,0.0,0.4);
+    anpimnct->AddCorrFctn(csqqinvpimnct);
+
+    AliFemtoCorrFctnDirectYlm *cylmpimnct = new AliFemtoCorrFctnDirectYlm("cylmpimnct",3,60,0.0,0.3,1);
+    anpimnct->AddCorrFctn(cylmpimnct);
+    
+    AliFemtoQinvCorrFctn *cqinvpimnct = new AliFemtoQinvCorrFctn("qinvcfpimnct", 100,0.0,1.0);
+    anpimnct->AddCorrFctn(cqinvpimnct);
+
+    AliFemtoChi2CorrFctn *cchiqinvpimnct= new AliFemtoChi2CorrFctn("chicfpimnct",40,0.0,0.4);
+    anpimnct->AddCorrFctn(cchiqinvpimnct);
+
+    AliFemtoCorrFctnTPCNcls *cqtpcnclspimnct = new AliFemtoCorrFctnTPCNcls("cqtpcnclspimnct",40,0.0,0.4);
+    anpimnct->AddCorrFctn(cqtpcnclspimnct);
+
+    Manager->AddAnalysis(anpimnct);    
+  }
+  // *** End pion-pion (negative) analysis
+
+  // *** Third QA task - HBT analysis with all pair cuts off, TPC only ***
+  // *** Begin pion-pion (positive) analysis ***
+  if (runPositiveTPCQA) {
+    AliFemtoVertexMultAnalysis *anpiptpc = new AliFemtoVertexMultAnalysis(1, zmin, zmax, 5, multmin, multmax);
+    anpiptpc->SetNumEventsToMix(iCollision?3:10);
+    anpiptpc->SetMinSizePartCollection(2);
+
+    AliFemtoBasicEventCut* mecpiptpc = new AliFemtoBasicEventCut();
+    mecpiptpc->SetEventMult(0,100000);
+    mecpiptpc->SetVertZPos(-1000,1000);
+
+    AliFemtoCutMonitorEventMult *cutPassEvMpiptpc = new AliFemtoCutMonitorEventMult("cutPasspiptpc");
+    AliFemtoCutMonitorEventMult *cutFailEvMpiptpc = new AliFemtoCutMonitorEventMult("cutFailpiptpc");
+    mecpiptpc->AddCutMonitor(cutPassEvMpiptpc, cutFailEvMpiptpc);
+
+    AliFemtoCutMonitorEventVertex *cutPassEvVpiptpc = new AliFemtoCutMonitorEventVertex("cutPasspiptpc");
+    AliFemtoCutMonitorEventVertex *cutFailEvVpiptpc = new AliFemtoCutMonitorEventVertex("cutFailpiptpc");
+    mecpiptpc->AddCutMonitor(cutPassEvVpiptpc, cutFailEvVpiptpc);
+       
+    AliFemtoESDTrackCut* dtcpiptpc = new AliFemtoESDTrackCut();
+//     dtcpiptpc->SetPidProbPion(0.0,1.001);
+//     dtcpiptpc->SetPidProbMuon(0.0,1.0);
+//     dtcpiptpc->SetPidProbKaon(0.0,1.0);
+//     dtcpiptpc->SetPidProbProton(0.0,1.0);
+    dtcpiptpc->SetCharge(0.0);
+    dtcpiptpc->SetPt(0.01,1000.0);
+    dtcpiptpc->SetMass(PionMass);
+    // Track quality cuts
+    //dtcpiptpc->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+    dtcpiptpc->SetStatus(AliESDtrack::kTPCrefit);
+    dtcpiptpc->SetminTPCncls(50);
+    dtcpiptpc->SetRemoveKinks(kTRUE);
+    dtcpiptpc->SetLabel(kFALSE);
+//     dtcpiptpc->SetMaxITSChiNdof(6.0);
+    dtcpiptpc->SetMaxTPCChiNdof(4.0);
+//     dtcpiptpc->SetMaxImpactXY(3.0);
+//     dtcpiptpc->SetMaxImpactZ(3.0);
+
+    AliFemtoCutMonitorParticleYPt *cutPassYPtpiptpc = new AliFemtoCutMonitorParticleYPt("cutPasspiptpc", 0.13957);
+    AliFemtoCutMonitorParticleYPt *cutFailYPtpiptpc = new AliFemtoCutMonitorParticleYPt("cutFailpiptpc", 0.13957);
+    dtcpiptpc->AddCutMonitor(cutPassYPtpiptpc, cutFailYPtpiptpc);
+
+    AliFemtoShareQualityTPCEntranceSepPairCut *sqpcpiptpc = new AliFemtoShareQualityTPCEntranceSepPairCut();
+    sqpcpiptpc->SetShareQualityMax(1.0);
+    sqpcpiptpc->SetShareFractionMax(1.0);
+    sqpcpiptpc->SetRemoveSameLabel(kFALSE);
+    sqpcpiptpc->SetTPCEntranceSepMinimum(0.0);
+
+    anpiptpc->SetEventCut(mecpiptpc);
+    anpiptpc->SetFirstParticleCut(dtcpiptpc);
+    anpiptpc->SetSecondParticleCut(dtcpiptpc);
+    anpiptpc->SetPairCut(sqpcpiptpc);
+    
+    AliFemtoShareQualityCorrFctn *csqqinvpiptpc= new AliFemtoShareQualityCorrFctn("sqqinvcfpiptpc",40,0.0,0.4);
+    anpiptpc->AddCorrFctn(csqqinvpiptpc);
+
+//     AliFemtoCorrFctnDirectYlm *cylmpiptpc = new AliFemtoCorrFctnDirectYlm("cylmpiptpc",3,60,0.0,0.3,1);
+//     anpiptpc->AddCorrFctn(cylmpiptpc);
+    
+    AliFemtoQinvCorrFctn *cqinvpiptpc = new AliFemtoQinvCorrFctn("qinvcfpiptpc", 100,0.0,1.0);
+    anpiptpc->AddCorrFctn(cqinvpiptpc);
+
+    AliFemtoChi2CorrFctn *cchiqinvpiptpc= new AliFemtoChi2CorrFctn("chicfpiptpc",40,0.0,0.4);
+    anpiptpc->AddCorrFctn(cchiqinvpiptpc);
+
+    AliFemtoCorrFctnTPCNcls *cqtpcnclspiptpc = new AliFemtoCorrFctnTPCNcls("cqtpcnclspiptpc",40,0.0,0.4);
+    anpiptpc->AddCorrFctn(cqtpcnclspiptpc);
+
+    Manager->AddAnalysis(anpiptpc);    
+  }
+  // *** End pion-pion (positive) analysis
+
+  // *** Begin pion-pion (negative) analysis ***
+  if (runNegativeTPCQA) {
+    AliFemtoVertexMultAnalysis *anpimtpc = new AliFemtoVertexMultAnalysis(1, zmin, zmax, 5, multmin, multmax);
+    anpimtpc->SetNumEventsToMix(iCollision?3:10);
+    anpimtpc->SetMinSizePartCollection(2);
+
+    AliFemtoBasicEventCut* mecpimtpc = new AliFemtoBasicEventCut();
+    mecpimtpc->SetEventMult(0,100000);
+    mecpimtpc->SetVertZPos(-1000,1000);
+       
+    AliFemtoESDTrackCut* dtcpimtpc = new AliFemtoESDTrackCut();
+//     dtcpimtpc->SetPidProbPion(0.0,1.001);
+//     dtcpimtpc->SetPidProbMuon(0.0,1.0);
+//     dtcpimtpc->SetPidProbKaon(0.0,1.0);
+//     dtcpimtpc->SetPidProbProton(0.0,1.0);
+    dtcpimtpc->SetCharge(0.0);
+    dtcpimtpc->SetPt(0.001,100.0);
+    dtcpimtpc->SetMass(PionMass);
+    // Track quality cuts
+    //dtcpimtpc->SetStatus(AliESDtrack::kTPCrefit|AliESDtrack::kITSrefit);
+    //    dtcpimtpc->SetStatus(AliESDtrack::kTPCrefit);
+//     dtcpimtpc->SetminTPCncls(50);
+    dtcpimtpc->SetRemoveKinks(kTRUE);
+    dtcpimtpc->SetLabel(kFALSE);
+//     dtcpimtpc->SetMaxITSChiNdof(6.0);
+//     dtcpimtpc->SetMaxTPCChiNdof(6.0);
+    dtcpimtpc->SetMaxImpactXY(1.0);
+    dtcpimtpc->SetMaxImpactZ(1.0);
+
+    AliFemtoCutMonitorParticleYPt *cutPassYPtpimtpc = new AliFemtoCutMonitorParticleYPt("cutPasspimtpc", 0.13957);
+    AliFemtoCutMonitorParticleYPt *cutFailYPtpimtpc = new AliFemtoCutMonitorParticleYPt("cutFailpimtpc", 0.13957);
+    dtcpimtpc->AddCutMonitor(cutPassYPtpimtpc, cutFailYPtpimtpc);
+
+    AliFemtoShareQualityTPCEntranceSepPairCut *sqpcpimtpc = new AliFemtoShareQualityTPCEntranceSepPairCut();
+    sqpcpimtpc->SetShareQualityMax(1.0);
+    sqpcpimtpc->SetShareFractionMax(1.0);
+    sqpcpimtpc->SetRemoveSameLabel(kFALSE);
+    sqpcpimtpc->SetTPCEntranceSepMinimum(0.0);
+
+    anpimtpc->SetEventCut(mecpimtpc);
+    anpimtpc->SetFirstParticleCut(dtcpimtpc);
+    anpimtpc->SetSecondParticleCut(dtcpimtpc);
+    anpimtpc->SetPairCut(sqpcpimtpc);
+    
+    AliFemtoShareQualityCorrFctn *csqqinvpimtpc= new AliFemtoShareQualityCorrFctn("sqqinvcfpimtpc",40,0.0,0.4);
+    anpimtpc->AddCorrFctn(csqqinvpimtpc);
+
+    AliFemtoCorrFctnDirectYlm *cylmpimtpc = new AliFemtoCorrFctnDirectYlm("cylmpimtpc",3,60,0.0,0.3,1);
+    anpimtpc->AddCorrFctn(cylmpimtpc);
+    
+    AliFemtoQinvCorrFctn *cqinvpimtpc = new AliFemtoQinvCorrFctn("qinvcfpimtpc", 100,0.0,1.0);
+    anpimtpc->AddCorrFctn(cqinvpimtpc);
+
+    AliFemtoChi2CorrFctn *cchiqinvpimtpc= new AliFemtoChi2CorrFctn("chicfpimtpc",40,0.0,0.4);
+    anpimtpc->AddCorrFctn(cchiqinvpimtpc);
+
+    AliFemtoCorrFctnTPCNcls *cqtpcnclspimtpc = new AliFemtoCorrFctnTPCNcls("cqtpcnclspimtpc",40,0.0,0.4);
+    anpimtpc->AddCorrFctn(cqtpcnclspimtpc);
+
+    Manager->AddAnalysis(anpimtpc);    
+  }
+  // *** End pion-pion (negative) analysis
+
+
+
+  return Manager;
+}                         
+                      
diff --git a/PWGCF/FEMTOSCOPY/macros/Train/TwoTrackQA/FemtoQAPlots.C b/PWGCF/FEMTOSCOPY/macros/Train/TwoTrackQA/FemtoQAPlots.C
new file mode 100644 (file)
index 0000000..7ac92f9
--- /dev/null
@@ -0,0 +1,423 @@
+void preparepad()
+{
+  gPad->SetFillColor(0);
+  gPad->SetFillStyle(4000);
+
+  gPad->SetTopMargin(0.02);
+  //  gPad->SetRightMargin(0.02);
+}
+
+void preparehist(TH1D *hist)
+{
+  hist->SetMarkerSize(0.8);
+  hist->SetMarkerStyle(8);
+  hist->SetMarkerColor(2);
+}
+
+TH2D *plot2ddtpc(TH2D *numdtpc, TH2D *dendtpc, const char *suff)
+{
+  // Create a 2D CF vs minimum separation distance in the TPC
+
+
+
+  int nslices = numdtpc->GetNbinsY();
+  int nrange = numdtpc->GetNbinsX();
+  char hname[200];
+  
+  sprintf(hname,"numdtpc%s",suff);
+  TH2D *nums = new TH2D(hname, ";q_{inv} [GeV/c];nominal TPC entrance sep - lower cut-off [cm]", 
+                       numdtpc->GetNbinsX(), numdtpc->GetXaxis()->GetXmin(), numdtpc->GetXaxis()->GetXmax(), 
+                       numdtpc->GetNbinsY(), numdtpc->GetYaxis()->GetXmin(), numdtpc->GetYaxis()->GetXmax());
+  sprintf(hname,"dendtpc%s",suff);
+  TH2D *dens = new TH2D(hname, ";q_{inv} [GeV/c];nominal TPC entrance sep - lower cut-off [cm]", 
+                       numdtpc->GetNbinsX(), numdtpc->GetXaxis()->GetXmin(), numdtpc->GetXaxis()->GetXmax(), 
+                       numdtpc->GetNbinsY(), numdtpc->GetYaxis()->GetXmin(), numdtpc->GetYaxis()->GetXmax());
+  sprintf(hname,"ratdtpc%s",suff);
+  TH2D *rats = new TH2D(hname,  ";q_{inv} [GeV/c];nominal TPC entrance sep - lower cut-off [cm]", 
+                       numdtpc->GetNbinsX(), numdtpc->GetXaxis()->GetXmin(), numdtpc->GetXaxis()->GetXmax(), 
+                       numdtpc->GetNbinsY(), numdtpc->GetYaxis()->GetXmin(), numdtpc->GetYaxis()->GetXmax());
+  
+  sprintf(hname,"chi2toone%s",suff);
+  TH1D *chi2toone = new TH1D(hname,";nominal TPC entrance sep - lower cut-off [cm];\\chi^2",
+                            numdtpc->GetNbinsY(), numdtpc->GetYaxis()->GetXmin(), numdtpc->GetYaxis()->GetXmax());
+
+  char bufname[100];
+  for (int iter=0; iter<nslices; iter++) {
+    sprintf(bufname, "numbuf%i", iter);
+    TH1D *numbuf = numdtpc->ProjectionX(bufname, (iter+1),  nslices, "e");
+    sprintf(bufname, "denbuf%i", iter);
+    TH1D *denbuf = dendtpc->ProjectionX(bufname, (iter+1),  nslices, "e");
+    
+    TH1D *ratbuf = new TH1D(*numbuf);
+    ratbuf->Divide(denbuf);
+    Double_t scale = ratbuf->Integral(nrange-9,nrange)/10.0;
+
+    if (scale > 0.0)
+      ratbuf->Scale(1.0/scale);
+    
+    double chi2 = 0.0;
+    for (int ibin = 1; ibin<=ratbuf->GetNbinsX(); ibin++) {
+      rats->SetBinContent(ibin, iter+1, ratbuf->GetBinContent(ibin));
+      if (ratbuf->GetBinError(ibin) > 0.0) {
+       chi2 += (TMath::Power(ratbuf->GetBinContent(ibin)-1.0,2)/
+                TMath::Power(ratbuf->GetBinError(ibin),2));
+      }
+    }
+    chi2toone->SetBinContent(iter+1, chi2);
+  }
+
+  rats->GetXaxis()->SetTitleOffset(0.9);
+  rats->GetYaxis()->SetTitleOffset(0.95);
+
+  return rats;
+}
+
+TH2D * plot2dshare(TH2D *numshare, TH2D *denshare, const char *suff)
+{
+  // Create a 2D CF vs minimum separation distance in the TPC
+  int nrange = numshare->GetNbinsX();
+  char hname[200];
+    
+  sprintf(hname,"numshare%s",suff);
+  TH2D *nums = new TH2D(hname, ";q_{inv} [GeV/c];fraction of shared hits - upper cut-off", 
+                       numshare->GetNbinsX(), numshare->GetXaxis()->GetXmin(), numshare->GetXaxis()->GetXmax(),
+                       numshare->GetNbinsY(), numshare->GetYaxis()->GetXmin(), numshare->GetYaxis()->GetXmax());
+
+  sprintf(hname,"denshare%s",suff);
+  TH2D *dens = new TH2D(hname, ";q_{inv} [GeV/c];fraction of shared hits - upper cut-off", 
+                       numshare->GetNbinsX(), numshare->GetXaxis()->GetXmin(), numshare->GetXaxis()->GetXmax(),
+                       numshare->GetNbinsY(), numshare->GetYaxis()->GetXmin(), numshare->GetYaxis()->GetXmax());
+
+  sprintf(hname,"ratshare%s",suff);
+  TH2D *rats = new TH2D(hname, ";q_{inv} [GeV/c];fraction of shared hits - upper cut-off", 
+                       numshare->GetNbinsX(), numshare->GetXaxis()->GetXmin(), numshare->GetXaxis()->GetXmax(),
+                       numshare->GetNbinsY(), numshare->GetYaxis()->GetXmin(), numshare->GetYaxis()->GetXmax());
+  
+  char bufname[100];
+  for (int iter=0; iter<numshare->GetNbinsY(); iter++) {
+    sprintf(bufname, "numbuf%i", iter);
+    TH1D *numbuf = numshare->ProjectionX(bufname, 1, iter+1, "e");
+    sprintf(bufname, "denbuf%i", iter);
+    TH1D *denbuf = denshare->ProjectionX(bufname, 1, iter+1, "e");
+    
+    ratbuf = new TH1D(*numbuf);
+    ratbuf->Divide(denbuf);
+    Double_t scale = ratbuf->Integral(nrange-24,nrange)/25.0;
+    ratbuf->Scale(1.0/scale);
+
+    for (int ibin = 1; ibin<=ratbuf->GetNbinsX(); ibin++) {
+      rats->SetBinContent(ibin, iter+1, ratbuf->GetBinContent(ibin));
+    }
+  }
+  
+  rats->GetXaxis()->SetTitleOffset(0.95);
+  rats->GetYaxis()->SetTitleOffset(0.9);
+
+  return rats;
+}
+
+TH2D *plot2dquality(TH2D *numqual, TH2D *denqual, const char *suff)
+{
+  // Create a 2D CF vs pair quality 
+  int nrange = numqual->GetNbinsX();
+  char hname[200];
+    
+  sprintf(hname,"numqual%s",suff);
+  TH2D *nums = new TH2D(hname, ";q_{inv} [GeV/c];pair quality - upper cut-off", 
+                       numqual->GetNbinsX(), numqual->GetXaxis()->GetXmin(), numqual->GetXaxis()->GetXmax(),
+                       numqual->GetNbinsY(), numqual->GetYaxis()->GetXmin(), numqual->GetYaxis()->GetXmax());
+  sprintf(hname,"denqual%s",suff);
+  TH2D *dens = new TH2D(hname, ";q_{inv} [GeV/c];pair quality - upper cut-off", 
+                       numqual->GetNbinsX(), numqual->GetXaxis()->GetXmin(), numqual->GetXaxis()->GetXmax(),
+                       numqual->GetNbinsY(), numqual->GetYaxis()->GetXmin(), numqual->GetYaxis()->GetXmax());
+  sprintf(hname,"ratqual%s",suff);
+  TH2D *rats = new TH2D(hname, ";q_{inv} [GeV/c];pair quality - upper cut-off", 
+                       numqual->GetNbinsX(), numqual->GetXaxis()->GetXmin(), numqual->GetXaxis()->GetXmax(),
+                       numqual->GetNbinsY(), numqual->GetYaxis()->GetXmin(), numqual->GetYaxis()->GetXmax());
+  
+  char bufname[100];
+  for (int iter=0; iter<numqual->GetNbinsY(); iter++) {
+    sprintf(bufname, "numbuf%i", iter);
+    TH1D *numbuf = numqual->ProjectionX(bufname, 1, iter+1, "e");
+    sprintf(bufname, "denbuf%i", iter);
+    TH1D *denbuf = denqual->ProjectionX(bufname, 1, iter+1, "e");
+    
+    ratbuf = new TH1D(*numbuf);
+    ratbuf->Divide(denbuf);
+    Double_t scale = ratbuf->Integral(nrange-24,nrange)/25.0;
+    if (scale > 0.0)
+      ratbuf->Scale(1.0/scale);
+
+    for (int ibin = 1; ibin<=ratbuf->GetNbinsX(); ibin++) {
+      rats->SetBinContent(ibin, iter+1, ratbuf->GetBinContent(ibin));
+    }
+  }
+  
+  rats->GetXaxis()->SetTitleOffset(0.95);
+  rats->GetYaxis()->SetTitleOffset(0.9);
+
+  return rats;
+}
+
+TH1D *getcf(TH1D *numq, TH1D *denq, const char *suff)
+{
+  char hname[200];
+
+  TH1D *rats = new TH1D(*numq);
+  rats->Reset("ICE");
+  rats->Divide(numq, denq, 1.0*denq->Integral()/numq->Integral(), 1.0);
+
+  sprintf(hname, "ratqinv%s", suff);
+  rats->SetName(hname);
+  rats->SetTitle(";q_{inv} [GeV/c];C(q_{inv})");
+  preparehist(rats);
+
+  return rats;
+}
+
+void FemtoQAPlots(const char *infname)
+{
+  gStyle->SetStatX(0.8);
+  gStyle->SetStatW(0.25);
+  gStyle->SetOptStat(11);
+
+  TFile *ifile = new TFile(infname);
+  
+  gStyle->SetPalette(1,0);
+
+  // Make plot for TPC entrance separation - positive
+
+  TCanvas *candtpcp = new TCanvas("candtpcp","candtpcp",1200,300);
+  preparepad();
+  candtpcp->Divide(3,1,0.0001,0.0001);
+  
+  candtpcp->cd(1);  preparepad();
+  TH2D *ratdtpcpipstd = plot2ddtpc((TH2D *) gDirectory->Get("NumTPCSepsqqinvcfpipstd"), (TH2D *) gDirectory->Get("DenTPCSepsqqinvcfpipstd"), "pipstd");
+  ratdtpcpipstd->Draw("COLZ");
+
+  candtpcp->cd(2);  preparepad();
+  TH2D *ratdtpcpipnct = plot2ddtpc((TH2D *) gDirectory->Get("NumTPCSepsqqinvcfpipnct"), (TH2D *) gDirectory->Get("DenTPCSepsqqinvcfpipnct"), "pipnct");
+  ratdtpcpipnct->Draw("COLZ");
+
+  candtpcp->cd(3);  preparepad();
+  TH2D *ratdtpcpiptpc = plot2ddtpc((TH2D *) gDirectory->Get("NumTPCSepsqqinvcfpiptpc"), (TH2D *) gDirectory->Get("DenTPCSepsqqinvcfpiptpc"), "piptpc");
+  ratdtpcpiptpc->Draw("COLZ");
+
+  // Make plot for TPC entrance separation - negative
+
+  TCanvas *candtpcm = new TCanvas("candtpcm","candtpcm",1200,300);
+  preparepad();
+  candtpcm->Divide(3,1,0.0001,0.0001);
+  
+  candtpcm->cd(1);  preparepad();
+  TH2D *ratdtpcpimstd = plot2ddtpc((TH2D *) gDirectory->Get("NumTPCSepsqqinvcfpimstd"), (TH2D *) gDirectory->Get("DenTPCSepsqqinvcfpimstd"), "pimstd");
+  ratdtpcpimstd->Draw("COLZ");
+
+  candtpcm->cd(2);  preparepad();
+  TH2D *ratdtpcpimnct = plot2ddtpc((TH2D *) gDirectory->Get("NumTPCSepsqqinvcfpimnct"), (TH2D *) gDirectory->Get("DenTPCSepsqqinvcfpimnct"), "pimnct");
+  ratdtpcpimnct->Draw("COLZ");
+
+  candtpcm->cd(3);  preparepad();
+  TH2D *ratdtpcpimtpc = plot2ddtpc((TH2D *) gDirectory->Get("NumTPCSepsqqinvcfpimtpc"), (TH2D *) gDirectory->Get("DenTPCSepsqqinvcfpimtpc"), "pimtpc");
+  ratdtpcpimtpc->Draw("COLZ");
+
+  // Make plot for pair fraction of shared hits - positive
+
+  TCanvas *cansharep = new TCanvas("cansharep","cansharep",1200,300);
+  preparepad();
+  cansharep->Divide(3,1,0.0001,0.0001);
+  
+  cansharep->cd(1);  preparepad();
+  TH2D *ratsharepipstd = plot2dshare((TH2D *) gDirectory->Get("NumSharesqqinvcfpipstd"), (TH2D *) gDirectory->Get("DenSharesqqinvcfpipstd"), "pipstd");
+  ratsharepipstd->Draw("COLZ");
+
+  cansharep->cd(2);  preparepad();
+  TH2D *ratsharepipnct = plot2dshare((TH2D *) gDirectory->Get("NumSharesqqinvcfpipnct"), (TH2D *) gDirectory->Get("DenSharesqqinvcfpipnct"), "pipnct");
+  ratsharepipnct->Draw("COLZ");
+
+  cansharep->cd(3);  preparepad();
+  TH2D *ratsharepiptpc = plot2dshare((TH2D *) gDirectory->Get("NumSharesqqinvcfpiptpc"), (TH2D *) gDirectory->Get("DenSharesqqinvcfpiptpc"), "piptpc");
+  ratsharepiptpc->Draw("COLZ");
+
+  // Make plot for pair fraction of shared hits - negative
+
+  TCanvas *cansharem = new TCanvas("cansharem","cansharem",1200,300);
+  preparepad();
+  cansharem->Divide(3,1,0.0001,0.0001);
+  
+  cansharem->cd(1);  preparepad();
+  TH2D *ratsharepimstd = plot2dshare((TH2D *) gDirectory->Get("NumSharesqqinvcfpimstd"), (TH2D *) gDirectory->Get("DenSharesqqinvcfpimstd"), "pimstd");
+  ratsharepimstd->Draw("COLZ");
+
+  cansharem->cd(2);  preparepad();
+  TH2D *ratsharepimnct = plot2dshare((TH2D *) gDirectory->Get("NumSharesqqinvcfpimnct"), (TH2D *) gDirectory->Get("DenSharesqqinvcfpimnct"), "pimnct");
+  ratsharepimnct->Draw("COLZ");
+
+  cansharem->cd(3);  preparepad();
+  TH2D *ratsharepimtpc = plot2dshare((TH2D *) gDirectory->Get("NumSharesqqinvcfpimtpc"), (TH2D *) gDirectory->Get("DenSharesqqinvcfpimtpc"), "pimtpc");
+  ratsharepimtpc->Draw("COLZ");
+
+  // Make signal pair fraction of shared hits - positive
+
+  TCanvas *cansharesignalp = new TCanvas("cansharesignalp","cansharesignalp",1200,300);
+  preparepad();
+  cansharesignalp->Divide(3,1,0.0001,0.0001);
+  
+  cansharesignalp->cd(1);  preparepad();
+  ((TH2D *) gDirectory->Get("NumSharesqqinvcfpipstd"))->Draw("COLZ");
+
+  cansharesignalp->cd(2);  preparepad();
+  ((TH2D *) gDirectory->Get("NumSharesqqinvcfpipnct"))->Draw("COLZ");
+
+  cansharesignalp->cd(3);  preparepad();
+  ((TH2D *) gDirectory->Get("NumSharesqqinvcfpiptpc"))->Draw("COLZ");
+
+  // Make signal pair fraction of shared hits - negative
+
+  TCanvas *cansharesignalm = new TCanvas("cansharesignalm","cansharesignalm",1200,300);
+  preparepad();
+  cansharesignalm->Divide(3,1,0.0001,0.0001);
+  
+  cansharesignalm->cd(1);  preparepad();
+  ((TH2D *) gDirectory->Get("NumSharesqqinvcfpimstd"))->Draw("COLZ");
+
+  cansharesignalm->cd(2);  preparepad();
+  ((TH2D *) gDirectory->Get("NumSharesqqinvcfpimnct"))->Draw("COLZ");
+
+  cansharesignalm->cd(3);  preparepad();
+  ((TH2D *) gDirectory->Get("NumSharesqqinvcfpimtpc"))->Draw("COLZ");
+
+  // Make background pair fraction of shared hits - positive
+
+  TCanvas *cansharebackp = new TCanvas("cansharebackp","cansharebackp",1200,300);
+  preparepad();
+  cansharebackp->Divide(3,1,0.0001,0.0001);
+  
+  cansharebackp->cd(1);  preparepad();
+  ((TH2D *) gDirectory->Get("DenSharesqqinvcfpipstd"))->Draw("COLZ");
+
+  cansharebackp->cd(2);  preparepad();
+  ((TH2D *) gDirectory->Get("DenSharesqqinvcfpipnct"))->Draw("COLZ");
+
+  cansharebackp->cd(3);  preparepad();
+  ((TH2D *) gDirectory->Get("DenSharesqqinvcfpiptpc"))->Draw("COLZ");
+
+  // Make background pair fraction of shared hits - negative
+
+  TCanvas *cansharebackm = new TCanvas("cansharebackm","cansharebackm",1200,300);
+  preparepad();
+  cansharebackm->Divide(3,1,0.0001,0.0001);
+  
+  cansharebackm->cd(1);  preparepad();
+  ((TH2D *) gDirectory->Get("DenSharesqqinvcfpimstd"))->Draw("COLZ");
+
+  cansharebackm->cd(2);  preparepad();
+  ((TH2D *) gDirectory->Get("DenSharesqqinvcfpimnct"))->Draw("COLZ");
+
+  cansharebackm->cd(3);  preparepad();
+  ((TH2D *) gDirectory->Get("DenSharesqqinvcfpimtpc"))->Draw("COLZ");
+
+  // Make plot for pair quality - positive
+
+  TCanvas *canqualp = new TCanvas("canqualp","canqualp",1200,300);
+  preparepad();
+  canqualp->Divide(3,1,0.0001,0.0001);
+  
+  canqualp->cd(1);  preparepad();
+  TH2D *ratqualpipstd = plot2dquality((TH2D *) gDirectory->Get("NumQualitysqqinvcfpipstd"), (TH2D *) gDirectory->Get("DenQualitysqqinvcfpipstd"), "pipstd");
+  ratqualpipstd->Draw("COLZ");
+
+  canqualp->cd(2);  preparepad();
+  TH2D *ratqualpipnct = plot2dquality((TH2D *) gDirectory->Get("NumQualitysqqinvcfpipnct"), (TH2D *) gDirectory->Get("DenQualitysqqinvcfpipnct"), "pipnct");
+  ratqualpipnct->Draw("COLZ");
+
+  canqualp->cd(3);  preparepad();
+  TH2D *ratqualpiptpc = plot2dquality((TH2D *) gDirectory->Get("NumQualitysqqinvcfpiptpc"), (TH2D *) gDirectory->Get("DenQualitysqqinvcfpiptpc"), "piptpc");
+  ratqualpiptpc->Draw("COLZ");
+
+  // Make plot for pair quality - negative
+
+  TCanvas *canqualm = new TCanvas("canqualm","canqualm",1200,300);
+  preparepad();
+  canqualm->Divide(3,1,0.0001,0.0001);
+  
+  canqualm->cd(1);  preparepad();
+  TH2D *ratqualpimstd = plot2dquality((TH2D *) gDirectory->Get("NumQualitysqqinvcfpimstd"), (TH2D *) gDirectory->Get("DenQualitysqqinvcfpimstd"), "pimstd");
+  ratqualpimstd->Draw("COLZ");
+
+  canqualm->cd(2);  preparepad();
+  TH2D *ratqualpimnct = plot2dquality((TH2D *) gDirectory->Get("NumQualitysqqinvcfpimnct"), (TH2D *) gDirectory->Get("DenQualitysqqinvcfpimnct"), "pimnct");
+  ratqualpimnct->Draw("COLZ");
+
+  canqualm->cd(3);  preparepad();
+  TH2D *ratqualpimtpc = plot2dquality((TH2D *) gDirectory->Get("NumQualitysqqinvcfpimtpc"), (TH2D *) gDirectory->Get("DenQualitysqqinvcfpimtpc"), "pimtpc");
+  ratqualpimtpc->Draw("COLZ");
+
+  // Make signal pair quality - positive
+
+  TCanvas *canqualitysignalp = new TCanvas("canqualitysignalp","canqualitysignalp",1200,300);
+  preparepad();
+  canqualitysignalp->Divide(3,1,0.0001,0.0001);
+  
+  canqualitysignalp->cd(1);  preparepad();
+  ((TH2D *) gDirectory->Get("NumQualitysqqinvcfpipstd"))->Draw("COLZ");
+
+  canqualitysignalp->cd(2);  preparepad();
+  ((TH2D *) gDirectory->Get("NumQualitysqqinvcfpipnct"))->Draw("COLZ");
+
+  canqualitysignalp->cd(3);  preparepad();
+  ((TH2D *) gDirectory->Get("NumQualitysqqinvcfpiptpc"))->Draw("COLZ");
+
+  // Make signal pair quality - negative
+
+  TCanvas *canqualitysignalm = new TCanvas("canqualitysignalm","canqualitysignalm",1200,300);
+  preparepad();
+  canqualitysignalm->Divide(3,1,0.0001,0.0001);
+  
+  canqualitysignalm->cd(1);  preparepad();
+  ((TH2D *) gDirectory->Get("NumQualitysqqinvcfpimstd"))->Draw("COLZ");
+
+  canqualitysignalm->cd(2);  preparepad();
+  ((TH2D *) gDirectory->Get("NumQualitysqqinvcfpimnct"))->Draw("COLZ");
+
+  canqualitysignalm->cd(3);  preparepad();
+  ((TH2D *) gDirectory->Get("NumQualitysqqinvcfpimtpc"))->Draw("COLZ");
+
+  // Make plot for pair quality - positive
+
+  TCanvas *canqinvp = new TCanvas("canqinvp","canqinvp",1200,300);
+  preparepad();
+  canqinvp->Divide(3,1,0.0001,0.0001);
+  
+  canqinvp->cd(1); preparepad();
+  TH1D *ratqinvpipstd = getcf((TH1D *) gDirectory->Get("Numqinvcfpipstd"), (TH1D *) gDirectory->Get("Denqinvcfpipstd"), "pipstd");
+  ratqinvpipstd->Draw();
+
+  canqinvp->cd(2); preparepad();
+  TH1D *ratqinvpipnct = getcf((TH1D *) gDirectory->Get("Numqinvcfpipnct"), (TH1D *) gDirectory->Get("Denqinvcfpipnct"), "pipnct");
+  ratqinvpipnct->Draw("");
+
+  canqinvp->cd(3); preparepad();
+  TH1D *ratqinvpiptpc = getcf((TH1D *) gDirectory->Get("Numqinvcfpiptpc"), (TH1D *) gDirectory->Get("Denqinvcfpiptpc"), "piptpc");
+  ratqinvpiptpc->Draw("");
+
+  // Make plot for pair quality - negative
+
+  TCanvas *canqinvm = new TCanvas("canqinvm","canqinvm",1200,300);
+  preparepad();
+  canqinvm->Divide(3,1,0.0001,0.0001);
+  
+  canqinvm->cd(1); preparepad();
+  TH1D *ratqinvpimstd = getcf((TH1D *) gDirectory->Get("Numqinvcfpimstd"), (TH1D *) gDirectory->Get("Denqinvcfpimstd"), "pimstd");
+  ratqinvpimstd->Draw("");
+
+  canqinvm->cd(2); preparepad();
+  TH1D *ratqinvpimnct = getcf((TH1D *) gDirectory->Get("Numqinvcfpimnct"), (TH1D *) gDirectory->Get("Denqinvcfpimnct"), "pimnct");
+  ratqinvpimnct->Draw("");
+
+  canqinvm->cd(3); preparepad();
+  TH1D *ratqinvpimtpc = getcf((TH1D *) gDirectory->Get("Numqinvcfpimtpc"), (TH1D *) gDirectory->Get("Denqinvcfpimtpc"), "pimtpc");
+  ratqinvpimtpc->Draw("");
+
+  
+}
diff --git a/PWGCF/PWGCFFEMTOSCOPYAODLinkDef.h b/PWGCF/PWGCFFEMTOSCOPYAODLinkDef.h
new file mode 100644 (file)
index 0000000..199d90f
--- /dev/null
@@ -0,0 +1,11 @@
+#ifdef __CINT__
+
+#pragma link off all glols;
+#pragma link off all classes;
+#pragma link off all functions;
+
+#pragma link C++ class  AliPWG2AODTrack+;
+#pragma link C++ class  AliAnalysisTaskPWG2ESDfilter+;
+#pragma link C++ class  AliAnalysisTaskPWG2AODUpdate+;
+
+#endif
diff --git a/PWGCF/PWGCFfemtoscopyLinkDef.h b/PWGCF/PWGCFfemtoscopyLinkDef.h
new file mode 100644 (file)
index 0000000..49306d5
--- /dev/null
@@ -0,0 +1,68 @@
+#ifdef __CINT__
+
+#pragma link off all glols;
+#pragma link off all classes;
+#pragma link off all functions;
+
+#pragma link C++ class AliFemtoAnalysis+;
+#pragma link C++ class AliFemtoLikeSignAnalysis+;
+#pragma link C++ class AliFemtoVertexAnalysis+;
+#pragma link C++ class AliFemtoVertexMultAnalysis+;
+#pragma link C++ class AliFemtoAnalysisAzimuthal+;
+#pragma link C++ class AliFemtoSimpleAnalysis+;
+#pragma link C++ class AliFemtoAnalysisReactionPlane+;
+#pragma link C++ class AliFemtoEventCut+;
+#pragma link C++ class AliFemtoEventReader+;
+#pragma link C++ class AliFemtoEventReaderStandard+;
+#pragma link C++ class AliFemtoKinkCut+;
+#pragma link C++ class AliFemtoPairCut+;
+#pragma link C++ class AliFemtoKTPairCut+;
+#pragma link C++ class AliFemtoParticleCut+;
+#pragma link C++ class AliFemtoTrackCut+;
+#pragma link C++ class AliFemtoV0Cut+;
+#pragma link C++ class AliFemtoXiCut+;
+#pragma link C++ class AliFemtoBPLCMS3DCorrFctn+;
+#pragma link C++ class AliFemtoCorrFctn3DLCMSSym+;
+#pragma link C++ class AliFemtoQinvCorrFctn+;
+#pragma link C++ class AliFemtoCorrFctnNonIdDR+;
+#pragma link C++ class AliFemtoCorrFctn3DSpherical+;
+#pragma link C++ class AliFemtoCorrFctn+;
+#pragma link C++ class AliFemtoBasicEventCut+;
+#pragma link C++ class AliFemtoEventCutEstimators+;
+#pragma link C++ class AliFemtoBasicTrackCut+;
+#pragma link C++ class AliFemtoDummyPairCut+;
+#pragma link C++ class AliFemtoCoulomb+;
+#pragma link C++ class AliFemtoCutMonitorHandler+;
+#pragma link C++ class AliFemtoLorentzVector+;
+#pragma link C++ class AliFemtoManager+;
+#pragma link C++ class AliFmHelixD+;
+#pragma link C++ class AliFmLorentzVectorD+;
+#pragma link C++ class AliFmPhysicalHelixD+;
+#pragma link C++ class AliFmThreeVectorD+;
+#pragma link C++ class AliFmThreeVectorF+;
+#pragma link C++ class AliFemtoEventReaderESD+;
+#pragma link C++ class AliFemtoEventReaderESDChain+;
+#pragma link C++ class AliFemtoEventReaderESDChainKine+;
+#pragma link C++ class AliFemtoModelManager+;
+#pragma link C++ class AliFemtoModelWeightGenerator+;
+#pragma link C++ class AliFemtoModelWeightGeneratorBasic+;
+#pragma link C++ class AliFemtoModelFreezeOutGenerator+;
+#pragma link C++ class AliFemtoModelGausLCMSFreezeOutGenerator+;
+#pragma link C++ class AliFemtoModelHiddenInfo+;
+#pragma link C++ class AliFemtoModelGlobalHiddenInfo+;
+#pragma link C++ class AliFemtoModelCorrFctn+;
+#pragma link C++ class AliFemtoModelWeightGeneratorLednicky+;
+#pragma link C++ class AliFemtoCutMonitorParticleYPt+;
+#pragma link C++ class AliFemtoCutMonitorParticleVertPos+;
+#pragma link C++ class AliFemtoCutMonitorParticlePID+;
+#pragma link C++ class AliFemtoCutMonitorEventMult+;
+#pragma link C++ class AliFemtoCutMonitorEventVertex+;
+#pragma link C++ class AliFemtoEventReaderAOD+;
+#pragma link C++ class AliFemtoEventReaderAODChain+;
+#pragma link C++ class AliFemtoAODTrackCut+;
+#pragma link C++ class AliAnalysisTaskFemto+;
+#pragma link C++ class AliTwoTrackRes+;
+#pragma link C++ class AliFemtoMCTrackCut+;
+#pragma link C++ class AliFemtoEventReaderKinematicsChain+;
+
+#endif
diff --git a/PWGCF/PWGCFfemtoscopyUserLinkDef.h b/PWGCF/PWGCFfemtoscopyUserLinkDef.h
new file mode 100644 (file)
index 0000000..72f0949
--- /dev/null
@@ -0,0 +1,44 @@
+#pragma link off all globals;
+#pragma link off all classes;
+#pragma link off all functions;
+
+#pragma link C++ class AliFemtoShareQualityPairCut;
+#pragma link C++ class AliFemtoShareQualityKTPairCut;
+#pragma link C++ class AliFemtoShareQualityTPCEntranceSepPairCut;
+#pragma link C++ class AliFemtoPairCutRadialDistance;
+#pragma link C++ class AliFemtoESDTrackCut;
+#pragma link C++ class AliFemtoShareQualityCorrFctn;
+#pragma link C++ class AliFemtoTPCInnerCorrFctn;
+#pragma link C++ class AliFemtoChi2CorrFctn;
+#pragma link C++ class AliFemtoModelCorrFctnSource;
+#pragma link C++ class AliFemtoModelCorrFctnDEtaDPhi;
+#pragma link C++ class AliFemtoModelBPLCMSCorrFctn;
+#pragma link C++ class AliFemtoModelGausRinvFreezeOutGenerator;
+#pragma link C++ class AliFemtoModelCorrFctnTrueQ;
+#pragma link C++ class AliFemtoModelCorrFctnNonIdDR;
+#pragma link C++ class AliFemtoModelCorrFctn3DSpherical;
+#pragma link C++ class AliFemtoModelCorrFctn3DLCMSSpherical;
+#pragma link C++ class AliFemtoCutMonitorParticleMomRes;
+#pragma link C++ class AliFemtoModelAllHiddenInfo;
+#pragma link C++ class AliFemtoCutMonitorTrackTPCchiNdof;
+#pragma link C++ class AliFemtoQATrackCut;
+#pragma link C++ class AliFemtoQAEventCut;
+#pragma link C++ class AliFemtoCutMonitorTrackTPCncls;
+#pragma link C++ class AliFemtoShareQualityTPCEntranceSepQAPairCut;
+#pragma link C++ class AliFemtoShareQualityQAPairCut;
+//#pragma link C++ class AliFemtoEventReaderESDKine;
+//#pragma link C++ class AliFemtoEventReaderAllESDKine;
+#pragma link C++ class AliFemtoYlm;
+#pragma link C++ class AliFemtoCorrFctnDirectYlm;
+#pragma link C++ class AliFemtoModelCorrFctnDirectYlm;
+#pragma link C++ class AliFemtoCorrFctnTPCNcls;
+#pragma link C++ class AliFemtoCorrFctnDEtaDPhi;
+#pragma link C++ class AliFemtoCutMonitorParticlePtPDG;
+#pragma link C++ class AliFemtoCutMonitorParticleEtCorr;
+#pragma link C++ class AliFemtoCorrFctnGammaMonitor;
+#pragma link C++ class AliFemtoPairCutAntiGamma;
+//#pragma link C++ class AliFemtoPhiPairCut;
+#pragma link C++ class AliFemtoQinvCorrFctnEMCIC;
+#pragma link C++ class AliFemtoCorrFctn3DSphericalEMCIC;
+#pragma link C++ class AliFemtoBPLCMS3DCorrFctnEMCIC;
+#pragma link C++ class AliFemtoPairCutPt;