Major update (Davide, ChiaraZ)
[u/mrichter/AliRoot.git] / PWG3 / vertexingHF / AliCFVertexingHF.cxx
1 /**************************************************************************
2  * Copyright(c) 1998-2009, ALICE Experiment at CERN, All rights reserved. *
3  *                                                                        *
4  * Author: The ALICE Off-line Project.                                    *
5  * Contributors are mentioned in the code where appropriate.              *
6  *                                                                        *
7  * Permission to use, copy, modify and distribute this software and its   *
8  * documentation strictly for non-commercial purposes is hereby granted   *
9  * without fee, provided that the above copyright notice appears in all   *
10  * copies and that both the copyright notice and this permission notice   *
11  * appear in the supporting documentation. The authors make no claims     *
12  * about the suitability of this software for any purpose. It is          *
13  * provided "as is" without express or implied warranty.                  *
14  **************************************************************************/
15
16 //-----------------------------------------------------------------------
17 // Class for HF corrections as a function of many variables and step 
18 // Author : C. Zampolli, CERN
19 // D. Caffarri, Univ & INFN Padova caffarri@pd.infn.it
20 // Base class for HF Unfolding - agrelli@uu.nl
21 //-----------------------------------------------------------------------
22
23 #include "TParticle.h"
24 #include "TClonesArray.h"
25 #include "AliAODMCParticle.h"
26 #include "AliAODRecoDecayHF.h"
27 #include "AliAODRecoDecayHF2Prong.h"
28 #include "AliAODRecoDecayHF3Prong.h"
29 #include "AliAODRecoDecayHF4Prong.h"
30 #include "AliAODMCHeader.h"
31 #include "AliAODEvent.h"
32 #include "AliLog.h"
33 #include "AliESDtrackCuts.h"
34 #include "AliESDtrack.h"
35
36 #include "AliCFVertexingHF.h"
37
38 //___________________________________________________________
39 AliCFVertexingHF::AliCFVertexingHF() :
40         fmcArray(0x0),
41         fRecoCandidate(0),
42         fmcPartCandidate(0x0),
43         fNDaughters(0),
44         fNVar(0),
45         fzPrimVertex(0),
46         fzMCVertex(0),
47         fFillFromGenerated(0),
48         fOriginDselection(0),
49         fKeepDfromB(kFALSE),
50         fKeepDfromBOnly(kFALSE),
51         fmcLabel(0),
52         fProngs(-1)
53 {
54         //
55         // constructor
56         //
57
58         return;
59 }
60
61
62
63 //_____________________________________________________
64 AliCFVertexingHF::AliCFVertexingHF(TClonesArray *mcArray, UShort_t originDselection) :
65         fmcArray(mcArray),
66         fRecoCandidate(0),
67         fmcPartCandidate(0x0),
68         fNDaughters(0),
69         fNVar(0),
70         fzPrimVertex(0),
71         fzMCVertex(0),
72         fFillFromGenerated(0),
73         fOriginDselection(0),
74         fKeepDfromB(kFALSE),
75         fKeepDfromBOnly(kFALSE),
76         fmcLabel(0),
77         fProngs(-1)
78 {
79         //
80         // constructor with mcArray
81         //
82         
83         SetDselection(originDselection);
84         return;
85 }
86
87 //_______________________________________________________
88 AliCFVertexingHF::~AliCFVertexingHF()
89 {
90         //
91         // destructor
92         //
93
94         if (fmcArray) fmcArray = 0x0;
95         if (fRecoCandidate) fRecoCandidate = 0x0;
96         if (fmcPartCandidate) fmcPartCandidate = 0x0;
97 }
98
99 //_____________________________________________________
100 AliCFVertexingHF& AliCFVertexingHF::operator=(const AliCFVertexingHF& c)
101 {       
102         //
103         // assigment operator
104         //
105
106         if (this!= &c){
107                 TObject::operator=(c);
108                 fmcArray = c.fmcArray;
109                 fRecoCandidate = c.fRecoCandidate;
110                 fmcPartCandidate = c.fmcPartCandidate;
111                 fNDaughters = c.fNDaughters;
112                 fNVar = c.fNVar;
113                 fzPrimVertex = c.fzPrimVertex;
114                 fzMCVertex = c.fzMCVertex;
115                 fFillFromGenerated = c.fFillFromGenerated;
116                 fOriginDselection = c.fOriginDselection;
117                 fKeepDfromB = c.fKeepDfromB;
118                 fKeepDfromBOnly = c.fKeepDfromBOnly;
119                 fmcLabel = c.fmcLabel;
120                 
121         }
122         
123         return *this;
124 }
125
126 //____________________________________________________
127 AliCFVertexingHF::AliCFVertexingHF(const AliCFVertexingHF &c) :
128         TObject(c),
129         fmcArray(c.fmcArray),
130         fRecoCandidate(c.fRecoCandidate),
131         fmcPartCandidate(c.fmcPartCandidate),
132         fNDaughters(c.fNDaughters),
133         fNVar(c.fNVar),
134         fzPrimVertex(c.fzPrimVertex),
135         fzMCVertex(c.fzMCVertex),
136         fFillFromGenerated(c.fFillFromGenerated),
137         fOriginDselection (c.fOriginDselection),
138         fKeepDfromB (c.fKeepDfromB),
139         fKeepDfromBOnly (c.fKeepDfromBOnly),
140         fmcLabel(c.fmcLabel),
141         fProngs(c.fProngs)
142 {  
143         //
144         //copy constructor
145         //
146 }
147
148 //___________________________________________________________
149 void AliCFVertexingHF::SetDselection(UShort_t originDselection)
150 {
151         // setting the way the D0 will be selected
152         // 0 --> only from c quarks
153         // 1 --> only from b quarks
154         // 2 --> from both c quarks and b quarks
155                 
156         fOriginDselection = originDselection;
157         
158         if (fOriginDselection == 0) {
159                 fKeepDfromB = kFALSE;
160                 fKeepDfromBOnly = kFALSE;
161         }
162         
163         if (fOriginDselection == 1) {
164                 fKeepDfromB = kTRUE;
165                 fKeepDfromBOnly = kTRUE;
166         }
167         
168         if (fOriginDselection == 2) {
169                 fKeepDfromB = kTRUE;
170                 fKeepDfromBOnly = kFALSE;
171         }
172         
173         return; 
174 }
175
176 //______________________________________________________
177 void AliCFVertexingHF::SetMCCandidateParam(Int_t label)
178 {
179         //
180         // setting the parameters (candidate and n. daughters)
181         //      
182         
183         fmcPartCandidate = dynamic_cast <AliAODMCParticle*> (fmcArray->At(label));
184         fNDaughters = fmcPartCandidate->GetNDaughters();
185         return;
186 }
187
188 //____________________________________________________________
189 Int_t AliCFVertexingHF::MCcquarkCounting(AliAODMCParticle* mcPart) const
190 {
191         //
192         // counting the c-quarks
193         // 
194
195         Int_t cquarks = 0;
196         if (mcPart->GetPdgCode() == 4) cquarks++; 
197         if (mcPart->GetPdgCode() == -4) cquarks++; 
198         if (!mcPart) {
199                 AliWarning("Particle not found in tree, skipping\n"); 
200                 return cquarks;
201         } 
202         
203         return cquarks;
204 }
205
206 //________________________________________________________
207 Bool_t AliCFVertexingHF::CheckMCPartFamily(AliAODMCParticle */*mcPart*/, TClonesArray */*mcArray*/) const 
208 {
209         // 
210         //checking the family
211         //
212
213         Int_t pdgGranma = CheckOrigin();
214         if (pdgGranma == -9999){
215                 AliDebug(2,"This particle come from a B decay channel but according to the settings of the task, we keep only the prompt charm particles\n");   
216                 AliInfo("This particle come from a B decay channel but according to the settings of the task, we keep only the prompt charm particles\n");      
217                 return kFALSE;
218         }       
219         
220         if (pdgGranma == -999){
221                 AliDebug(2,"This particle come from a prompt charm particles but according to the settings of the task, we want only the ones coming from B\n");        
222                 AliInfo("This particle come from a prompt charm particles but according to the settings of the task, we want only the ones coming from B\n");   
223                 return kFALSE;
224         }       
225         
226         if (!CheckMCDaughters()) {
227                 Printf("CheckMCDaughters false");
228                 return kFALSE;
229         }
230         if (!CheckMCChannelDecay()) {
231                 Printf("CheckMCChannelDecay false");
232                 return kFALSE;
233         }
234         return kTRUE;
235 }
236
237 //_________________________________________________________________________________________________
238 Int_t AliCFVertexingHF::CheckOrigin() const 
239 {               
240         //
241         // checking whether the mother of the particles come from a charm or a bottom quark
242         //
243         
244         Int_t pdgGranma = 0;
245         Int_t mother = 0;
246         mother = fmcPartCandidate->GetMother();
247         Int_t istep = 0;
248         while (mother >0 ){
249                 istep++;
250                 AliDebug(2,Form("mother at step %d = %d", istep, mother));
251                 AliAODMCParticle* mcGranma = dynamic_cast<AliAODMCParticle*>(fmcArray->At(mother));
252                 pdgGranma = mcGranma->GetPdgCode();
253                 AliDebug(2,Form("Pdg mother at step %d = %d", istep, pdgGranma));
254                 Int_t abspdgGranma = TMath::Abs(pdgGranma);
255                 if ((abspdgGranma > 500 && abspdgGranma < 600) || (abspdgGranma > 5000 && abspdgGranma < 6000)) {
256                         if (!fKeepDfromB) return -9999; //skip particle if come from a B meson.
257                         
258                         else{
259                                 return pdgGranma;
260                         }
261                 }
262                 else {
263                         if (fKeepDfromBOnly) return -999;
264                 }
265                 
266                 mother = mcGranma->GetMother();
267         }
268         
269         return pdgGranma;
270 }
271
272
273 //___________________________________________
274 Bool_t AliCFVertexingHF::CheckMCDaughters()const 
275 {
276         //
277         // checking the daughters
278         // at MC level
279
280         Printf("CheckMCDaughters");
281         
282         AliAODMCParticle *mcPartDaughter;
283         Bool_t checkDaughters = kFALSE;
284         
285         Int_t label0 = fmcPartCandidate->GetDaughter(0);
286         Int_t label1 = fmcPartCandidate->GetDaughter(1);
287         Printf("label0 = %d, label1 = %d",label0,label1);
288         if (label1==0 || label0 == 0){
289                 AliDebug(2, Form("The MC particle doesn't jave correct daughters, skipping!!"));
290                 AliInfo(Form("The MC particle doesn't jave correct daughters, skipping!!"));
291                 return checkDaughters;  
292         }
293         
294         if (label1 - label0 != fProngs-1){
295                 AliDebug(2, Form("The MC particle doesn't come from a %d-prong decay, skipping!!", fProngs));
296                 AliInfo(Form("The MC particle doesn't come from a %d-prong decay, skipping!!", fProngs));
297                 return checkDaughters;  
298         }
299         
300         for (Int_t iProng = 0; iProng<fProngs; iProng++){
301                 mcPartDaughter = dynamic_cast<AliAODMCParticle*>(fmcArray->At(label0+iProng));    
302                 if (!mcPartDaughter) {
303                         AliWarning("At least one Daughter Particle not found in tree, skipping"); 
304                         return checkDaughters;  
305                 }
306         }
307         
308         checkDaughters = kTRUE;
309         return checkDaughters;
310 }
311
312 //______________________________________________________
313 Bool_t AliCFVertexingHF::FillMCContainer(Double_t *containerInputMC)
314 {
315         //
316         // fill the container for Generator level selection
317         //
318
319         Bool_t mcContainerFilled = kFALSE;  
320         
321         Double_t* vectorMC = new Double_t[fNVar];
322         for (Int_t iVar = 0; iVar<fNVar; iVar++) vectorMC[iVar]= 9999.;
323         
324         if (GetGeneratedValuesFromMCParticle(&vectorMC[0])){
325                 for (Int_t iVar = 0; iVar<fNVar; iVar++){                       
326                         containerInputMC[iVar] = vectorMC[iVar];
327                 }               
328                 mcContainerFilled = kTRUE;              
329         }
330         delete [] vectorMC;
331         vectorMC = 0x0;
332         return mcContainerFilled;       
333 }
334
335 //______________________________________________________
336 Bool_t AliCFVertexingHF::FillRecoContainer(Double_t *containerInput) 
337 {  
338         //      
339         // fill the container for Reconstrucred level selection
340         //
341
342         Bool_t recoContainerFilled = kFALSE;
343         Double_t* vectorValues = new Double_t[fNVar];
344         Double_t* vectorReco = new Double_t[fNVar];  
345         
346         for (Int_t iVar = 0; iVar<fNVar; iVar++) {
347                 vectorValues[iVar]= 9999.;
348                 vectorReco[iVar]=9999.;
349         }
350         
351         if(fFillFromGenerated){
352                 //filled with MC values
353                 if (GetGeneratedValuesFromMCParticle(&vectorValues[0])){
354                         for (Int_t iVar = 0; iVar<fNVar; iVar++){
355                                 containerInput[iVar] = vectorValues[iVar];
356                         }
357                         recoContainerFilled = kTRUE;            
358                 }
359         }
360         else{
361                 //filled with Reco values
362                 
363                 if (GetRecoValuesFromCandidate(&vectorReco[0])){
364                         for (Int_t iVar = 0; iVar<fNVar; iVar++){
365                                 containerInput[iVar] = vectorReco[iVar];
366                         }
367                         recoContainerFilled = kTRUE;            
368                 }
369         }
370         
371         delete [] vectorValues;
372         delete [] vectorReco;
373         vectorValues = 0x0;
374         vectorReco = 0x0;
375         return recoContainerFilled;     
376 }
377
378 //_____________________________________________________
379 Bool_t AliCFVertexingHF::MCAcceptanceStep() const
380 {
381         //
382         // checking the MC acceptance step
383         //
384
385         Bool_t bMCAccStep = kFALSE;
386         
387         AliAODMCParticle *mcPartDaughter;
388         Int_t label0 = fmcPartCandidate->GetDaughter(0);
389         Int_t label1 = fmcPartCandidate->GetDaughter(1);
390         if (label1==0 || label0 == 0){
391                 AliDebug(2, Form("The MC particle doesn't have correct daughters, skipping!!"));
392                 return bMCAccStep;  
393         }
394         
395         if (label1 - label0 != fProngs-1){
396                 AliDebug(2, Form("The MC particle doesn't come from a %d-prong decay, skipping!!", fProngs));
397                 return bMCAccStep;  
398         }
399         
400         for (Int_t iProng = 0; iProng<fProngs; iProng++){
401                 mcPartDaughter = dynamic_cast<AliAODMCParticle*>(fmcArray->At(label0+iProng));    
402                 if (!mcPartDaughter) {
403                         AliWarning("At least one Daughter Particle not found in tree, skipping"); 
404                         return bMCAccStep;  
405                 }
406                 Double_t eta = mcPartDaughter->Eta();
407                 Double_t pt = mcPartDaughter->Pt();
408                 
409                 //set values of eta and pt in the constructor.
410                 if (TMath::Abs(eta) > 0.9 || pt < 0.1){
411                         AliDebug(3,"At least one daughter has eta>0.9 or pt < 0.1 \n"); 
412                         return bMCAccStep;
413                 }
414         }  
415         bMCAccStep = kTRUE;
416         return bMCAccStep; 
417         
418 }
419
420 //_____________________________________________________
421 /*
422   Bool_t AliCFVertexingHF::MCRefitStep(AliAODEvent *aodEvent, AliESDtrackCuts *trackCuts) const
423   {             
424   // check on the kTPCrefit and kITSrefit conditions of the daughters
425   Bool_t bRefitStep = kTRUE;
426   
427   Int_t label0 = fmcPartCandidate->GetDaughter(0);
428   Int_t label1 = fmcPartCandidate->GetDaughter(1);
429   
430   if (label1==0 || label0 == 0){
431   AliDebug(2, Form("The MC particle doesn't have correct daughters, skipping!!"));
432   AliInfo(Form("The MC particle doesn't have correct daughters, skipping!! **** THIS SHOULD NOT HAPPEN 1"));
433   return kFALSE;  
434   }
435   
436   if (label1 - label0 != fProngs-1){
437   AliDebug(2, Form("The MC particle doesn't come from a %d-prong decay, skipping!!", fProngs));
438   AliInfo(Form("The MC particle doesn't come from a %d-prong decay, skipping!! **** THIS SHOULD NOT HAPPEN 1", fProngs));
439   return kFALSE;  
440   }
441   
442   Int_t foundDaughters = 0;
443   
444   if (trackCuts->GetRequireTPCRefit() || trackCuts->GetRequireITSRefit()){
445   
446   for(Int_t iaod =0; iaod<aodEvent->GetNumberOfTracks(); iaod++){
447   AliAODTrack *track = (AliAODTrack*)aodEvent->GetTrack(iaod);
448   if (track->GetLabel()>= label0 && track->GetLabel()<=label1){
449   foundDaughters++;
450   printf("daughter %d \n",foundDaughters);
451   if(trackCuts->GetRequireTPCRefit()){
452   if(!(track->GetStatus()&AliESDtrack::kTPCrefit)) {
453   bRefitStep = kFALSE;
454   AliDebug(3, "Refit cut not passed , missing TPC refit\n");
455   AliInfo( "Refit cut not passed , missing TPC refit\n");
456   break;
457   }
458   else {
459   AliDebug(3, "TPC Refit cut passed\n");
460   AliInfo( "TPC Refit cut passed\n");
461   }
462   }
463   
464   if (trackCuts->GetRequireITSRefit()) {
465   if(!(track->GetStatus()&AliESDtrack::kITSrefit)){
466   bRefitStep = kFALSE;
467   AliDebug(3, "Refit cut not passed , missing ITS refit\n");
468   AliInfo("Refit cut not passed , missing ITS refit\n");
469   break;
470   }
471   else {
472   AliDebug(3, "ITS Refit cut passed\n");
473   AliInfo("ITS Refit cut passed\n");
474   }
475   }
476   }             
477   if (foundDaughters == fProngs){       
478   break;
479   }
480   
481   }
482   
483   } 
484   if (foundDaughters==fProng) return bRefitStep;
485   else return kFALSE;
486   }
487 */
488
489  //_____________________________________________________
490 Bool_t AliCFVertexingHF::MCRefitStep(AliAODEvent *aodEvent, AliESDtrackCuts *trackCuts) const
491 {               
492         //
493         // check on the kTPCrefit and kITSrefit conditions of the daughters
494         //
495         Bool_t bRefitStep = kFALSE;
496         
497         Int_t label0 = fmcPartCandidate->GetDaughter(0);
498         Int_t label1 = fmcPartCandidate->GetDaughter(1);
499         
500         if (label1==0 || label0 == 0){
501                 AliDebug(2, Form("The MC particle doesn't have correct daughters, skipping!!"));
502                 return bRefitStep;  
503         }
504         
505         if (label1 - label0 != fProngs-1){
506                 AliDebug(2, Form("The MC particle doesn't come from a %d-prong decay, skipping!!", fProngs));
507                 //AliInfo(Form("The MC particle doesn't come from a %d-prong decay, skipping!!", fProngs));
508                 return bRefitStep;  
509         }
510         
511         Int_t foundDaughters = 0;
512         
513         if (trackCuts->GetRequireTPCRefit() || trackCuts->GetRequireITSRefit()){
514                 
515                 for(Int_t iaod =0; iaod<aodEvent->GetNumberOfTracks(); iaod++){
516                         AliAODTrack *track = (AliAODTrack*)aodEvent->GetTrack(iaod);
517                         if (track->GetLabel()>= label0 && track->GetLabel()<=label1){
518                                 foundDaughters++;
519                                 AliDebug(4,Form("daughter %d \n",foundDaughters));
520                                 if(trackCuts->GetRequireTPCRefit()){
521                                         if(track->GetStatus()&AliESDtrack::kTPCrefit) {
522                                                 bRefitStep = kTRUE;
523                                         }
524                                         else {
525                                                 AliDebug(3, "Refit cut not passed , missing TPC refit\n");
526                                                 return kFALSE;
527                                         }
528                                 }
529                                 
530                                 if (trackCuts->GetRequireITSRefit()) {
531                                         if(track->GetStatus()&AliESDtrack::kITSrefit){
532                                                 bRefitStep = kTRUE;
533                                         }
534                                         else {
535                                                 AliDebug(3, "Refit cut not passed , missing ITS refit\n");
536             return kFALSE;
537                                         }
538                                 }
539                         }       
540                         if (foundDaughters == fProngs){                         
541                                 break;
542                         }                       
543                 }    
544         } 
545         if (foundDaughters== fProngs)  return bRefitStep;
546         else return kFALSE;
547 }
548
549 //____________________________________________________________________________
550
551 Bool_t AliCFVertexingHF::RecoStep() 
552
553         //
554         //check also vertex and ITS Refit and TPC Refit
555         //
556
557         Bool_t bRecoStep = kFALSE;
558         Int_t mcLabel = GetMCLabel();
559         
560         if (mcLabel == -1) {
561                 AliDebug(2,"No MC particle found");
562                 return bRecoStep;
563         }
564         else{
565                 fmcPartCandidate = (AliAODMCParticle*)fmcArray->At(mcLabel);
566                 if (!fmcPartCandidate){
567                         AliWarning("Could not find associated MC in AOD MC tree");
568                         return bRecoStep;
569                 }    
570         }
571         
572         Int_t pdgGranma = CheckOrigin();
573         
574         if (pdgGranma == -9999){
575                 AliDebug(2,"This particle come from a B decay channel but according to the settings of the task, we keep only prompt charm particles\n");
576                 return bRecoStep;
577         }
578
579         if (pdgGranma == -999){
580                 AliDebug(2,"This particle come from a  prompt charm particle but according to the settings of the task, we want only the ones coming from B\n");
581                 return bRecoStep;
582         }
583    
584         bRecoStep=kTRUE;
585         return bRecoStep;  
586 }       
587 //____________________________________________
588 Double_t AliCFVertexingHF::GetEtaProng(Int_t iProng) const 
589 {
590         //
591         // getting eta of the prong
592         //
593         
594         if (fRecoCandidate){
595                 Double_t etaProng = fRecoCandidate->EtaProng(iProng);  
596                 return etaProng;
597         }
598         return 999999;  
599 }
600 //______________________________________________________
601 Double_t AliCFVertexingHF::GetPtProng(Int_t iProng) const 
602 {
603         //
604         // getting pt of the prong
605         //
606
607         if (fRecoCandidate){
608                 Double_t ptProng = fRecoCandidate->PtProng(iProng);  
609                 return ptProng;
610         }
611         return 999999;  
612         
613 }
614
615 //____________________________________________________________________
616
617 Bool_t AliCFVertexingHF::RecoAcceptStep(AliESDtrackCuts *trackCuts) const
618 {
619         //
620         // reco Acceptance step
621         //
622         
623         Bool_t bRecoAccStep = kFALSE;
624         
625         Float_t etaCutMin, ptCutMin, etaCutMax, ptCutMax;
626         trackCuts->GetEtaRange(etaCutMin, etaCutMax);
627         trackCuts->GetPtRange(ptCutMin, ptCutMax);
628         
629         Float_t etaProng=0., ptProng=0.; 
630         
631         for (Int_t iProng =0; iProng<fProngs; iProng++){
632                 
633                 etaProng = GetEtaProng(iProng);
634                 ptProng = GetPtProng(iProng);
635                 
636                 Bool_t acceptanceProng = (etaProng>etaCutMin && etaProng<etaCutMax && ptProng>ptCutMin && ptProng<ptCutMax);
637                 if (!acceptanceProng) {
638                         AliDebug(2,"At least one reconstructed prong isn't in the acceptance\n");
639                         return bRecoAccStep;
640                 }
641         }
642         
643         bRecoAccStep=kTRUE;
644         return bRecoAccStep;
645 }
646 //___________________________________________________________
647
648 Bool_t AliCFVertexingHF::FillUnfoldingMatrix(Double_t *fill) const
649 {
650         //
651         // filling the unfolding matrix
652         //
653         
654         fill = new Double_t[4];
655         
656         if(fmcPartCandidate){
657                 
658                 fill[0] = GetPtCand();
659                 fill[1] = GetYCand();
660                 
661                 fill[2] =  fmcPartCandidate->Pt(); 
662                 fill[3] =  fmcPartCandidate->Y(); 
663                 
664                 return kTRUE;
665         }
666         
667         delete [] fill;
668         fill = 0x0;
669         return kFALSE;
670 }
671 //___________________________________________________________
672
673 Int_t AliCFVertexingHF::CheckReflexion()
674 {
675         //
676         // check for reflexion (particle/antiparticle)
677         //
678
679         Int_t mcLabel = GetMCLabel();
680         
681         if (mcLabel == -1) {
682                 AliDebug(2,"No MC particle found");
683                 return 0;
684         }
685         else{
686                 fmcPartCandidate = (AliAODMCParticle*)fmcArray->At(mcLabel);
687                 if (!fmcPartCandidate){
688                         AliWarning("Could not find associated MC in AOD MC tree");
689                         return 0;
690                 }    
691         }
692         
693         if(fmcPartCandidate->GetPdgCode()>0) return 1;  // particle
694         else if(fmcPartCandidate->GetPdgCode()<0) return 2;  // antiparticle
695         else return 0;  // ....shouldn't be...
696 }