]> git.uio.no Git - u/mrichter/AliRoot.git/blob - PWG/muon/AliVAnalysisMuon.cxx
Merge branch 'feature-movesplit'
[u/mrichter/AliRoot.git] / PWG / muon / AliVAnalysisMuon.cxx
1 /**************************************************************************
2  * Copyright(c) 1998-2007, 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 /* $Id: AliVAnalysisMuon.cxx 47782 2011-02-24 18:37:31Z martinez $ */
17
18 //-----------------------------------------------------------------------------
19 /// \class AliVAnalysisMuon
20 /// Base class with utilities for muon analysis
21 ///
22 /// \author Diego Stocco
23 //-----------------------------------------------------------------------------
24
25 #include "AliVAnalysisMuon.h"
26
27 // ROOT includes
28 #include "TROOT.h"
29 #include "TH1.h"
30 #include "TH2.h"
31 #include "TAxis.h"
32 #include "TCanvas.h"
33 #include "TLegend.h"
34 #include "TMath.h"
35 #include "TObjString.h"
36 #include "TObjArray.h"
37 #include "THashList.h"
38 #include "TStyle.h"
39 //#include "TMCProcess.h"
40 #include "TLorentzVector.h"
41 #include "TRegexp.h"
42
43 // STEER includes
44 #include "AliInputEventHandler.h"
45 #include "AliCentrality.h"
46
47 #include "AliAODEvent.h"
48 #include "AliAODTrack.h"
49 #include "AliAODMCParticle.h"
50 #include "AliMCEvent.h"
51 #include "AliMCParticle.h"
52 //#include "AliStack.h"
53 #include "AliESDEvent.h"
54 #include "AliESDMuonTrack.h"
55 #include "AliCounterCollection.h"
56 #include "AliVVertex.h"
57
58 // ANALYSIS includes
59 #include "AliAnalysisManager.h"
60 #include "AliAnalysisTaskSE.h"
61 #include "AliAnalysisDataSlot.h"
62 #include "AliAnalysisDataContainer.h"
63
64 // CORRFW includes
65 #include "AliCFGridSparse.h"
66
67 // PWG includes
68 #include "AliMergeableCollection.h"
69 #include "AliMuonEventCuts.h"
70 #include "AliMuonTrackCuts.h"
71 #include "AliMuonPairCuts.h"
72 #include "AliAnalysisMuonUtility.h"
73 #include "AliUtilityMuonAncestor.h"
74
75 /// \cond CLASSIMP
76 ClassImp(AliVAnalysisMuon) // Class implementation in ROOT context
77 /// \endcond
78
79
80 //________________________________________________________________________
81 AliVAnalysisMuon::AliVAnalysisMuon() :
82   AliAnalysisTaskSE(),
83   fMuonEventCuts(0x0),
84   fMuonTrackCuts(0x0),
85   fMuonPairCuts(0x0),
86   fESDEvent(0x0),
87   fAODEvent(0x0),
88   fTerminateOptions(0x0),
89   fChargeKeys(0x0),
90   fSrcKeys(0x0),
91   fPhysSelKeys(0x0),
92   fWeights(0x0),
93   fUtilityMuonAncestor(0x0),
94   fEventCounters(0x0),
95   fMergeableCollection(0x0),
96   fOutputList(0x0),
97   fOutputPrototypeList(0x0)
98 {
99   /// Default ctor.
100 }
101
102 //________________________________________________________________________
103 AliVAnalysisMuon::AliVAnalysisMuon(const char *name, const AliMuonTrackCuts& trackCuts, const AliMuonPairCuts& pairCuts) :
104   AliAnalysisTaskSE(name),
105   fMuonEventCuts(new AliMuonEventCuts("stdEventCuts","stdEventCuts")),
106   fMuonTrackCuts(new AliMuonTrackCuts(trackCuts)),
107   fMuonPairCuts(new AliMuonPairCuts(pairCuts)),
108   fESDEvent(0x0),
109   fAODEvent(0x0),
110   fTerminateOptions(0x0),
111   fChargeKeys(0x0),
112   fSrcKeys(0x0),
113   fPhysSelKeys(0x0),
114   fWeights(new THashList()),
115   fUtilityMuonAncestor(0x0),
116   fEventCounters(0x0),
117   fMergeableCollection(0x0),
118   fOutputList(0x0),
119   fOutputPrototypeList(0x0)
120 {
121   //
122   /// Constructor.
123   //
124   
125   InitKeys();
126   SetTrigClassPatterns("");
127   SetCentralityClasses();
128   fWeights->SetOwner();
129
130   DefineOutput(1, TObjArray::Class());
131 }
132
133 //________________________________________________________________________
134 AliVAnalysisMuon::AliVAnalysisMuon(const char *name, const AliMuonTrackCuts& trackCuts) :
135   AliAnalysisTaskSE(name),
136   fMuonEventCuts(new AliMuonEventCuts("stdEventCuts","stdEventCuts")),
137   fMuonTrackCuts(new AliMuonTrackCuts(trackCuts)),
138   fMuonPairCuts(0x0),
139   fESDEvent(0x0),
140   fAODEvent(0x0),
141   fTerminateOptions(0x0),
142   fChargeKeys(0x0),
143   fSrcKeys(0x0),
144   fPhysSelKeys(0x0),
145   fWeights(new THashList()),
146   fUtilityMuonAncestor(0x0),
147   fEventCounters(0x0),
148   fMergeableCollection(0x0),
149   fOutputList(0x0),
150   fOutputPrototypeList(0x0)
151 {
152   //
153   /// Constructor.
154   //
155   
156   InitKeys();
157   SetTrigClassPatterns("");
158   SetCentralityClasses();
159   fWeights->SetOwner();
160   
161   DefineOutput(1, TObjArray::Class());
162 }
163
164
165 //________________________________________________________________________
166 AliVAnalysisMuon::AliVAnalysisMuon(const char *name, const AliMuonPairCuts& pairCuts) :
167   AliAnalysisTaskSE(name),
168   fMuonEventCuts(new AliMuonEventCuts("stdEventCuts","stdEventCuts")),
169   fMuonTrackCuts(0x0),
170   fMuonPairCuts(new AliMuonPairCuts(pairCuts)),
171   fESDEvent(0x0),
172   fAODEvent(0x0),
173   fTerminateOptions(0x0),
174   fChargeKeys(0x0),
175   fSrcKeys(0x0),
176   fPhysSelKeys(0x0),
177   fWeights(new THashList()),
178   fUtilityMuonAncestor(0x0),
179   fEventCounters(0x0),
180   fMergeableCollection(0x0),
181   fOutputList(0x0),
182   fOutputPrototypeList(0x0)
183 {
184   //
185   /// Constructor.
186   //
187   InitKeys();
188   SetTrigClassPatterns("");
189   SetCentralityClasses();
190   fWeights->SetOwner();
191     
192   DefineOutput(1, TObjArray::Class());
193 }
194
195
196 //________________________________________________________________________
197 AliVAnalysisMuon::~AliVAnalysisMuon()
198 {
199   //
200   /// Destructor
201   //
202
203   delete fMuonEventCuts;
204   delete fMuonTrackCuts;
205   delete fMuonPairCuts;
206   delete fTerminateOptions;
207   delete fChargeKeys;
208   delete fSrcKeys;
209   delete fPhysSelKeys;
210   delete fWeights;
211   delete fUtilityMuonAncestor;
212   delete fOutputPrototypeList;
213
214
215   // For proof: do not delete output containers
216   if ( ! AliAnalysisManager::GetAnalysisManager() || ! AliAnalysisManager::GetAnalysisManager()->IsProofMode() ) {
217     delete fOutputList;
218   }
219 }
220
221 //___________________________________________________________________________
222 void AliVAnalysisMuon::FinishTaskOutput()
223 {
224   //
225   /// Remove empty histograms to reduce the number of histos to be merged
226   //
227
228
229   fMergeableCollection->PruneEmptyObjects();
230   
231   // Add stat. info from physics selection
232   // (usefull when running on AODs)
233   if ( fInputHandler ) {
234     for ( Int_t istat=0; istat<2; istat++ ) {
235       TString statType = ( istat == 0 ) ? "ALL" : "BIN0";
236       TH2* hStat = dynamic_cast<TH2*>(fInputHandler->GetStatistics(statType.Data()));
237       if ( hStat ) {
238         TString objectName = Form("%s_%s", hStat->GetName(), GetName());
239         TH2* cloneStat = static_cast<TH2*>(hStat->Clone(objectName.Data()));
240         cloneStat->SetDirectory(0);
241         fOutputList->Add(cloneStat);
242       }
243       else {
244         AliWarning("Stat histogram not available");
245         break;
246       }
247     } // loop on stat type
248   }
249 }
250
251
252 //___________________________________________________________________________
253 void AliVAnalysisMuon::NotifyRun()
254 {
255   /// Set run number for cuts
256   if ( fMuonTrackCuts ) fMuonTrackCuts->SetRun(fInputHandler);
257   if ( fMuonPairCuts ) fMuonPairCuts->SetRun(fInputHandler);
258 }
259
260 //___________________________________________________________________________
261 void AliVAnalysisMuon::UserCreateOutputObjects() 
262 {
263   //
264   /// Create output objects
265   //
266   AliInfo(Form("   CreateOutputObjects of task %s\n", GetName()));
267   
268   fOutputList = new TObjArray();
269   fOutputList->SetOwner();
270
271   fEventCounters = new AliCounterCollection("eventCounters");
272
273   if ( ! GetCentralityClasses() ) SetCentralityClasses();
274   TString centralityClasses = "";
275   for ( Int_t icent=1; icent<=GetCentralityClasses()->GetNbins(); ++icent ) {
276     if ( ! centralityClasses.IsNull() ) centralityClasses += "/";
277     centralityClasses += GetCentralityClasses()->GetBinLabel(icent);
278   }
279   fEventCounters->AddRubric("selected", "yes/no");
280   fEventCounters->AddRubric("trigger", 100);
281   fEventCounters->AddRubric("centrality", centralityClasses);
282   fEventCounters->AddRubric("run", 10000);
283   fEventCounters->Init();
284   fOutputList->Add(fEventCounters);
285  
286   fMergeableCollection = new AliMergeableCollection("outputObjects");
287   fOutputList->Add(fMergeableCollection);
288
289   PostData(1, fOutputList);
290   
291   fMuonEventCuts->Print();
292   
293   MyUserCreateOutputObjects();
294   
295   fUtilityMuonAncestor = new AliUtilityMuonAncestor();
296 }
297
298
299 //________________________________________________________________________
300 void AliVAnalysisMuon::UserExec(Option_t * /*option*/) 
301 {
302   //
303   /// Main loop
304   /// Called for each event
305   //
306
307   fAODEvent = dynamic_cast<AliAODEvent*> (InputEvent());
308   if ( ! fAODEvent ) 
309     fESDEvent = dynamic_cast<AliESDEvent*> (InputEvent());
310
311   if ( ! fAODEvent && ! fESDEvent ) {
312     AliError ("AOD or ESD event not found. Nothing done!");
313     return;
314   }
315   
316   if ( ! fMuonEventCuts->IsSelected(fInputHandler) ) return;
317
318   Int_t physSel = ( fInputHandler->IsEventSelected() & AliVEvent::kAny ) ? kPhysSelPass : kPhysSelReject;
319
320   //
321   // Global event info
322   //
323   const TObjArray* selectTrigClasses = fMuonEventCuts->GetSelectedTrigClassesInEvent(InputEvent());
324
325   Double_t centrality = fMuonEventCuts->GetCentrality(InputEvent());
326   Int_t centralityBin = GetCentralityClasses()->FindBin(centrality);
327   TString centralityBinLabel = GetCentralityClasses()->GetBinLabel(centralityBin);
328
329   TString selKey = ( physSel == kPhysSelPass ) ? "yes" : "no";
330   for ( Int_t itrig=0; itrig<selectTrigClasses->GetEntries(); ++itrig ) {
331     TString trigName = selectTrigClasses->At(itrig)->GetName();
332     fEventCounters->Count(Form("trigger:%s/selected:%s/centrality:%s/run:%i", trigName.Data(), selKey.Data(), centralityBinLabel.Data(),fCurrentRunNumber));
333   }
334
335   ProcessEvent(fPhysSelKeys->At(physSel)->GetName(), *selectTrigClasses, centralityBinLabel);
336
337   // Post final data. It will be written to a file with option "RECREATE"
338   PostData(1, fOutputList);
339 }
340
341 //________________________________________________________________________
342 void AliVAnalysisMuon::Terminate(Option_t *)
343 {
344   //
345   /// Draw some histogram at the end.
346   //
347   
348   if ( ! fTerminateOptions ) SetTerminateOptions();
349   
350   TString furtherOpt = ((TObjString*)fTerminateOptions->At(3))->GetString();
351   furtherOpt.ToUpper();
352   if ( gROOT->IsBatch() && ! furtherOpt.Contains("FORCEBATCH") ) return;
353     
354   fOutputList = dynamic_cast<TObjArray*>(GetOutputData(1));
355   if ( ! fOutputList ) return;
356   fEventCounters = static_cast<AliCounterCollection*>(fOutputList->FindObject("eventCounters"));
357   fMergeableCollection = static_cast<AliMergeableCollection*>(fOutputList->FindObject("outputObjects"));
358   
359   if ( ! fMergeableCollection ) return;
360   AliInfo(Form("Mergeable collection size %g MB", fMergeableCollection->EstimateSize()/1024.0/1024.0));
361   if ( fTerminateOptions->At(3) ) {
362     TString sopt = fTerminateOptions->At(3)->GetName();
363     if ( sopt.Contains("verbose") ) fMergeableCollection->Print("*"); 
364   }
365   SetCentralityClassesFromOutput();
366 }
367
368
369 //________________________________________________________________________
370 Int_t AliVAnalysisMuon::GetParticleType ( AliVParticle* track )
371 {
372   //
373   /// Get particle type from mathced MC track
374   //
375   
376   if ( fUtilityMuonAncestor->IsUnidentified(track,MCEvent()) ) return kUnidentified;
377   if ( fUtilityMuonAncestor->IsBeautyMu(track,MCEvent()) ) return kBeautyMu;
378   if ( fUtilityMuonAncestor->IsCharmMu(track,MCEvent()) ) return kCharmMu;
379   if ( fUtilityMuonAncestor->IsWBosonMu(track,MCEvent()) ) return kWbosonMu;
380   if ( fUtilityMuonAncestor->IsZBosonMu(track,MCEvent()) ) return kZbosonMu;
381   if ( fUtilityMuonAncestor->IsDecayMu(track,MCEvent()) ) return kDecayMu;
382   if ( fUtilityMuonAncestor->IsQuarkoniumMu(track,MCEvent()) ) return kQuarkoniumMu;
383   if ( fUtilityMuonAncestor->IsHadron(track,MCEvent()) ) return kRecoHadron;
384   if ( fUtilityMuonAncestor->IsSecondaryMu(track,MCEvent()) ) return kSecondaryMu;
385   return kDecayMu;
386 }
387
388
389 //________________________________________________________________________
390 Bool_t AliVAnalysisMuon::AddObjectToCollection(TObject* object, Int_t index)
391 {
392   //
393   /// Add object to collection
394   //
395   
396   if ( ! fOutputPrototypeList ) {
397     fOutputPrototypeList = new TObjArray();
398     fOutputPrototypeList->SetOwner();
399   }
400   if ( fOutputPrototypeList->FindObject(object->GetName() ) ) {
401     AliWarning(Form("Object with name %s already in the list", object->GetName()));
402     return kFALSE;
403   }
404   if ( index < 0 ) fOutputPrototypeList->Add(object);
405   else fOutputPrototypeList->AddAtAndExpand(object, index);
406   
407   return kTRUE;
408 }
409
410 //________________________________________________________________________
411 TObject* AliVAnalysisMuon::GetMergeableObject(TString physSel, TString trigClassName, TString centrality, TString objectName)
412 {
413   //
414   /// Get mergeable object
415   /// (create collection if necessary)
416   //
417   
418   TString identifier = Form("/%s/%s/%s/", physSel.Data(), trigClassName.Data(), centrality.Data());
419   
420   TObject* obj = fMergeableCollection->GetObject(identifier.Data(), objectName.Data());
421   if ( ! obj ) {
422     CreateMergeableObjects(physSel, trigClassName, centrality);
423     obj = fMergeableCollection->GetObject(identifier.Data(), objectName.Data());
424     AliInfo(Form("Mergeable object collection size %g MB", fMergeableCollection->EstimateSize()/1024.0/1024.0));
425   }
426   return obj;
427 }
428
429 //________________________________________________________________________
430 TObject* AliVAnalysisMuon::GetSum(TString physSel, TString trigClassNames, TString centrality, TString objectPattern)
431 {
432   //
433   /// Sum objects
434   /// - physSel, trigClassNames must be in the form: key1,key2
435   /// - centrality must be in the form minValue_maxValue
436   /// - objectPattern must be in the form match1,match2
437   ///   meaning that the object name must contain match1 or match2
438   ///   wildcard * is allowed
439   
440   if ( ! fMergeableCollection ) return 0x0;
441   
442   // Get centrality range
443   Int_t firstCentrality = 1;
444   Int_t lastCentrality = GetCentralityClasses()->GetNbins();
445   
446   TObjArray* centralityRange = centrality.Tokenize("_");
447   Float_t range[2] = {0., 100.};
448   if ( centralityRange->GetEntries() >= 2 ) {
449     for ( Int_t irange=0; irange<2; ++irange ) {
450       range[irange] = ((TObjString*)centralityRange->At(irange))->GetString().Atof();
451     }
452     firstCentrality = GetCentralityClasses()->FindBin(range[0]+0.0001);
453     lastCentrality = GetCentralityClasses()->FindBin(range[1]-0.0001);
454   }
455   delete centralityRange;
456   
457   TString sumCentralityString = "";
458   for ( Int_t icent=firstCentrality; icent<=lastCentrality; ++icent ) {
459     if ( ! sumCentralityString.IsNull() ) sumCentralityString += ",";
460     sumCentralityString += GetCentralityClasses()->GetBinLabel(icent);
461   }
462   
463 //  objectPattern.ReplaceAll(" ","");
464 //  TObjArray* objPatternList = objectPattern.Tokenize("&");
465 //  TObjArray objPatternMatrix(objPatternList->GetEntries());
466 //  objPatternMatrix.SetOwner();
467 //  for ( Int_t ikey=0; ikey<objPatternList->GetEntries(); ikey++ ) {
468 //    TObjArray* subKeyList = ((TObjString*)objPatternList->At(ikey))->GetString().Tokenize(",");
469 //    objPatternMatrix.AddAt(subKeyList, ikey);
470 //  }
471 //  delete objPatternList;
472   
473
474   TObjArray objectNameInCollection;
475   objectNameInCollection.SetOwner();
476   TObjArray* physSelList = physSel.Tokenize(",");
477   TObjArray* trigClassList = trigClassNames.Tokenize(",");
478   TObjArray* centralityList = sumCentralityString.Tokenize(",");
479   for ( Int_t isel=0; isel<physSelList->GetEntries(); isel++ ) {
480     for ( Int_t itrig = 0; itrig<trigClassList->GetEntries(); itrig++ ) {
481       for ( Int_t icent=0; icent<centralityList->GetEntries(); icent++ ) {
482         TString currId = Form("/%s/%s/%s/", physSelList->At(isel)->GetName(), trigClassList->At(itrig)->GetName(),centralityList->At(icent)->GetName());
483         TList* objNameList = fMergeableCollection->CreateListOfObjectNames(currId.Data());
484         for ( Int_t iobj=0; iobj<objNameList->GetEntries(); iobj++ ) {
485           TString objName = objNameList->At(iobj)->GetName();
486           if ( ! objectNameInCollection.FindObject(objName.Data()) ) objectNameInCollection.Add(new TObjString(objName.Data()));
487         }
488         delete objNameList;
489       }
490     }
491   }
492   delete physSelList;
493   delete trigClassList;
494   delete centralityList;
495   
496   TObjArray* objPatternList = objectPattern.Tokenize(",");
497
498   TString matchingObjectNames = "";
499   for ( Int_t iobj=0; iobj<objectNameInCollection.GetEntries(); iobj++ ) {
500     TString objName = objectNameInCollection.At(iobj)->GetName();
501     for ( Int_t ipat=0; ipat<objPatternList->GetEntries(); ipat++ ) {
502       TString currPattern = ((TObjString*)objPatternList->At(ipat))->GetString();
503       if ( currPattern.Contains("*") ) {
504         if ( ! objName.Contains(TRegexp(currPattern.Data(),kTRUE)) ) continue;
505       }
506       else if ( objName != currPattern ) continue;
507
508       if ( ! matchingObjectNames.IsNull() ) matchingObjectNames.Append(",");
509       matchingObjectNames += objName;
510     }
511   }
512   delete objPatternList;
513   
514 //  for ( Int_t iobj=0; iobj<objectNameInCollection.GetEntries(); iobj++ ) {
515 //    TString objName = objectNameInCollection.At(iobj)->GetName();
516 //    Bool_t matchAnd = kTRUE;
517 //    for ( Int_t ikey=0; ikey<objPatternMatrix.GetEntries(); ikey++ ) {
518 //      TObjArray*  subKeyList = (TObjArray*)objPatternMatrix.At(ikey);
519 //      Bool_t matchOr = kFALSE;
520 //      for ( Int_t isub=0; isub<subKeyList->GetEntries(); isub++ ) {
521 //        TString subKeyString = ((TObjString*)subKeyList->At(isub))->GetString();
522 //        if ( subKeyString.Contains("*") ) {
523 //          if ( objName.Contains(TRegexp(subKeyString.Data())) ) {
524 //            matchOr = kTRUE;
525 //            break;
526 //          }
527 //        }
528 //        else if ( objName == subKeyString ) {
529 //          matchOr = kTRUE;
530 //          break;
531 //        }
532 //      }
533 //      if ( ! matchOr ) {
534 //        matchAnd = kFALSE;
535 //        break;
536 //      }
537 //    }
538 //    if ( ! matchAnd ) continue;
539 //    if ( ! matchingObjectNames.IsNull() ) matchingObjectNames.Append(",");
540 //    matchingObjectNames += objName;
541 //  }
542
543   TString idPattern = Form("/%s/%s/%s/%s", physSel.Data(), trigClassNames.Data(), sumCentralityString.Data(), matchingObjectNames.Data());
544   idPattern.ReplaceAll(" ","");
545   
546   AliDebug(1,Form("Sum pattern %s", idPattern.Data()));
547   
548   return fMergeableCollection->GetSum(idPattern.Data());
549 }
550
551 //___________________________________________________________________________
552 void AliVAnalysisMuon::CreateMergeableObjects(TString physSel, TString trigClassName, TString centrality)
553 {
554   TObject* obj = 0x0;
555   TString objectName = "";
556   TString identifier = Form("/%s/%s/%s/", physSel.Data(), trigClassName.Data(), centrality.Data());
557   for ( Int_t iobj=0; iobj<fOutputPrototypeList->GetEntries(); ++iobj ) {
558     objectName = fOutputPrototypeList->At(iobj)->GetName();
559     obj = fOutputPrototypeList->At(iobj)->Clone(objectName.Data());
560     fMergeableCollection->Adopt(identifier, obj);
561   } // loop on histos
562 }
563
564
565 //_______________________________________________________________________
566 Bool_t AliVAnalysisMuon::SetSparseRange(AliCFGridSparse* gridSparse,
567                                         Int_t ivar, TString labelName,
568                                         Double_t varMin, Double_t varMax,
569                                         TString option)
570 {
571   //
572   /// Set range in a smart way.
573   /// Allows to select a bin from the label.
574   /// Check the bin limits.
575   //
576   
577   // Keep for backward compatibility
578   
579   return AliAnalysisMuonUtility::SetSparseRange(gridSparse,ivar,labelName,varMin, varMax,option);
580 }
581
582 //________________________________________________________________________
583 TString AliVAnalysisMuon::GetDefaultTrigClassPatterns() const
584 {
585   /// Get default trigger class patterns
586   return fMuonEventCuts->GetDefaultTrigClassPatterns();
587 }
588
589 //________________________________________________________________________
590 void AliVAnalysisMuon::SetTrigClassPatterns(const TString pattern)
591 {
592   /// Set trigger classes
593   TString currPattern = pattern;
594   if ( currPattern.IsNull() ) { 
595     currPattern = GetDefaultTrigClassPatterns();
596     currPattern.Append(",!CMUP*"); // by default do not account for UltraPeripheral events
597   }
598   fMuonEventCuts->SetTrigClassPatterns(currPattern);
599 }
600
601 //________________________________________________________________________
602 TList* AliVAnalysisMuon::GetAllSelectedTrigClasses() const
603 {
604   /// Get trigger classes
605   return fMuonEventCuts->GetAllSelectedTrigClasses();
606 }
607
608 //________________________________________________________________________
609 void AliVAnalysisMuon::SetCentralityClasses(Int_t nCentralityBins, Double_t* centralityBins)
610 {
611   //
612   /// Set centrality classes
613   //
614   fMuonEventCuts->SetCentralityClasses(nCentralityBins, centralityBins);
615 }
616
617 //________________________________________________________________________
618 TAxis* AliVAnalysisMuon::GetCentralityClasses() const
619 {
620   //
621   /// Set centrality classes
622   //
623   return fMuonEventCuts->GetCentralityClasses();
624 }
625
626 //________________________________________________________________________
627 Bool_t AliVAnalysisMuon::SetCentralityClassesFromOutput()
628 {
629   //
630   /// Get axis of centrality classes from output key
631   //
632   if ( ! fMergeableCollection ) return kFALSE;
633   TList* centrKeyList = fMergeableCollection->CreateListOfKeys(2);
634   TObjArray centrLimitsList;
635   centrLimitsList.SetOwner();
636   if ( ! centrKeyList ) return kFALSE;
637   for ( Int_t ikey=0; ikey<centrKeyList->GetEntries(); ikey++ ) {
638     TString centr = static_cast<TObjString*>(centrKeyList->At(ikey))->GetString();
639     TObjArray* array = centr.Tokenize("_");
640     for ( Int_t ilim=0; ilim<array->GetEntries(); ilim++ ) {
641       TString currLim = static_cast<TObjString*>(array->At(ilim))->GetString();
642       if ( ! centrLimitsList.FindObject(currLim.Data()) ) centrLimitsList.Add(new TObjString(currLim));
643     }
644     delete array;
645   }
646   delete centrKeyList;
647   
648   // Get unsorted array
649   TArrayD bins(centrLimitsList.GetEntries());
650   for ( Int_t ibin=0; ibin<centrLimitsList.GetEntries(); ibin++ ) {
651     bins[ibin] = static_cast<TObjString*>(centrLimitsList.At(ibin))->GetString().Atof();
652   }
653   
654   // Sort it
655   Int_t index[bins.GetSize()];
656   TMath::Sort(bins.GetSize(),bins.GetArray(),index, kFALSE);
657   
658   TArrayD sortedBins(bins.GetSize());
659   for ( Int_t ibin=0; ibin<centrLimitsList.GetEntries(); ibin++ ) {
660     sortedBins[ibin] = bins[index[ibin]];
661   }
662   
663   SetCentralityClasses(sortedBins.GetSize()-1, sortedBins.GetArray());
664   return kTRUE;
665 }
666
667 //________________________________________________________________________
668 void AliVAnalysisMuon::SetTerminateOptions(TString physSel, TString trigClass, TString centralityRange, TString furtherOpts)
669 {
670   //
671   /// Set terminate options
672   //
673   if ( ! fTerminateOptions ) {
674     fTerminateOptions = new TObjArray(4);
675     fTerminateOptions->SetOwner();
676   }
677   fTerminateOptions->AddAt(new TObjString(physSel), 0);
678   fTerminateOptions->AddAt(new TObjString(trigClass), 1);
679   fTerminateOptions->AddAt(new TObjString(centralityRange),2);
680   fTerminateOptions->AddLast(new TObjString(furtherOpts));
681 }
682
683 //________________________________________________________________________
684 void AliVAnalysisMuon::InitKeys()
685 {
686   //
687   /// Init keys
688   //
689   TString chargeKeys = "MuMinus MuPlus";
690   fChargeKeys = chargeKeys.Tokenize(" ");
691   
692   TString srcKeys = "CharmMu BeautyMu QuarkoniumMu WbosonMu ZbosonMu DecayMu SecondaryMu Hadron Unidentified";
693   fSrcKeys = srcKeys.Tokenize(" ");
694   
695   TString physSelKeys = "PhysSelPass PhysSelReject";
696   fPhysSelKeys = physSelKeys.Tokenize(" ");
697 }
698
699
700 //________________________________________________________________________
701 void AliVAnalysisMuon::SetWeight ( TObject* wgtObj )
702 {
703   /// Set weight
704   if ( fWeights->FindObject(wgtObj->GetName()) ) {
705     AliWarning(Form("Weight object %s is already in the list",wgtObj->GetName()));
706     return;
707   }
708   fWeights->Add(wgtObj);
709 }
710
711 //________________________________________________________________________
712 TObject* AliVAnalysisMuon::GetWeight ( const Char_t* wgtName )
713 {
714   /// Get weight
715   return fWeights->FindObject(wgtName);
716 }
717
718