]> git.uio.no Git - u/mrichter/AliRoot.git/blame - PWGLF/RESONANCES/AliRsnMiniAnalysisTask.cxx
Fixed typo in macros/lego_train/AddRsnTaskTrain.C (mvala)
[u/mrichter/AliRoot.git] / PWGLF / RESONANCES / AliRsnMiniAnalysisTask.cxx
CommitLineData
03d23846 1//
2// Analysis task for 'mini' sub-package
3// Contains all definitions needed for running an analysis:
4// -- global event cut
5// -- a list of track cuts (any number)
6// -- definitions of output histograms
7// -- values to be computed.
8// Each one must be defined using the "CREATE" methods, which
9// add directly a new element in the task collections, and don't
10// need an external object to be passed to the task itself.
11//
12
13#include <Riostream.h>
14
03d23846 15#include <TH1.h>
6aaeb33c 16#include <TList.h>
17#include <TTree.h>
52e6652d 18#include <TStopwatch.h>
03d23846 19
20#include "AliLog.h"
6aaeb33c 21#include "AliEventplane.h"
22#include "AliMultiplicity.h"
23#include "AliTriggerAnalysis.h"
03d23846 24#include "AliAnalysisManager.h"
6aaeb33c 25#include "AliInputEventHandler.h"
26
03d23846 27#include "AliESDtrackCuts.h"
28#include "AliESDUtils.h"
6aaeb33c 29
03d23846 30#include "AliAODEvent.h"
03d23846 31#include "AliAODMCParticle.h"
32
33#include "AliRsnCutSet.h"
6aaeb33c 34#include "AliRsnMiniPair.h"
03d23846 35#include "AliRsnMiniEvent.h"
36#include "AliRsnMiniParticle.h"
03d23846 37
38#include "AliRsnMiniAnalysisTask.h"
39
52e6652d 40
03d23846 41ClassImp(AliRsnMiniAnalysisTask)
42
43//__________________________________________________________________________________________________
44AliRsnMiniAnalysisTask::AliRsnMiniAnalysisTask() :
45 AliAnalysisTaskSE(),
c80938f5 46 fUseMC(kFALSE),
03d23846 47 fEvNum(0),
48 fUseCentrality(kFALSE),
49 fCentralityType("QUALITY"),
1cdc3671 50 fUseAOD049CentralityPatch(kFALSE),
caef2e3c 51 fContinuousMix(kTRUE),
03d23846 52 fNMix(0),
53 fMaxDiffMult(10),
54 fMaxDiffVz(1.0),
55 fMaxDiffAngle(1E20),
56 fOutput(0x0),
57 fHistograms("AliRsnMiniOutput", 0),
58 fValues("AliRsnMiniValue", 0),
59 fHEventStat(0x0),
955ca046 60 fHAEventsVsMulti(0x0),
5654276f 61 fHAEventVz(0x0),
62 fHAEventMultiCent(0x0),
63 fHAEventPlane(0x0),
03d23846 64 fEventCuts(0x0),
65 fTrackCuts(0),
66 fRsnEvent(),
c80938f5 67 fEvBuffer(0x0),
c80938f5 68 fTriggerAna(0x0),
6aaeb33c 69 fESDtrackCuts(0x0),
caef2e3c 70 fMiniEvent(0x0),
61f275d1 71 fBigOutput(kFALSE),
72 fMixPrintRefresh(-1)
03d23846 73{
74//
75// Dummy constructor ALWAYS needed for I/O.
76//
77}
78
79//__________________________________________________________________________________________________
c80938f5 80AliRsnMiniAnalysisTask::AliRsnMiniAnalysisTask(const char *name, Bool_t useMC) :
03d23846 81 AliAnalysisTaskSE(name),
c80938f5 82 fUseMC(useMC),
03d23846 83 fEvNum(0),
84 fUseCentrality(kFALSE),
85 fCentralityType("QUALITY"),
1cdc3671 86 fUseAOD049CentralityPatch(kFALSE),
caef2e3c 87 fContinuousMix(kTRUE),
03d23846 88 fNMix(0),
89 fMaxDiffMult(10),
90 fMaxDiffVz(1.0),
91 fMaxDiffAngle(1E20),
92 fOutput(0x0),
93 fHistograms("AliRsnMiniOutput", 0),
94 fValues("AliRsnMiniValue", 0),
95 fHEventStat(0x0),
955ca046 96 fHAEventsVsMulti(0x0),
5654276f 97 fHAEventVz(0x0),
98 fHAEventMultiCent(0x0),
99 fHAEventPlane(0x0),
03d23846 100 fEventCuts(0x0),
101 fTrackCuts(0),
102 fRsnEvent(),
c80938f5 103 fEvBuffer(0x0),
c80938f5 104 fTriggerAna(0x0),
6aaeb33c 105 fESDtrackCuts(0x0),
caef2e3c 106 fMiniEvent(0x0),
61f275d1 107 fBigOutput(kFALSE),
108 fMixPrintRefresh(-1)
03d23846 109{
110//
111// Default constructor.
112// Define input and output slots here (never in the dummy constructor)
113// Input slot #0 works with a TChain - it is connected to the default input container
114// Output slot #1 writes into a TH1 container
115//
116
117 DefineOutput(1, TList::Class());
118}
119
120//__________________________________________________________________________________________________
52e6652d 121AliRsnMiniAnalysisTask::AliRsnMiniAnalysisTask(const AliRsnMiniAnalysisTask &copy) :
03d23846 122 AliAnalysisTaskSE(copy),
c80938f5 123 fUseMC(copy.fUseMC),
03d23846 124 fEvNum(0),
125 fUseCentrality(copy.fUseCentrality),
126 fCentralityType(copy.fCentralityType),
1cdc3671 127 fUseAOD049CentralityPatch(copy.fUseAOD049CentralityPatch),
caef2e3c 128 fContinuousMix(copy.fContinuousMix),
03d23846 129 fNMix(copy.fNMix),
130 fMaxDiffMult(copy.fMaxDiffMult),
131 fMaxDiffVz(copy.fMaxDiffVz),
132 fMaxDiffAngle(copy.fMaxDiffAngle),
133 fOutput(0x0),
134 fHistograms(copy.fHistograms),
135 fValues(copy.fValues),
136 fHEventStat(0x0),
955ca046 137 fHAEventsVsMulti(0x0),
5654276f 138 fHAEventVz(0x0),
139 fHAEventMultiCent(0x0),
140 fHAEventPlane(0x0),
03d23846 141 fEventCuts(copy.fEventCuts),
142 fTrackCuts(copy.fTrackCuts),
143 fRsnEvent(),
c80938f5 144 fEvBuffer(0x0),
c80938f5 145 fTriggerAna(copy.fTriggerAna),
6aaeb33c 146 fESDtrackCuts(copy.fESDtrackCuts),
caef2e3c 147 fMiniEvent(0x0),
61f275d1 148 fBigOutput(copy.fBigOutput),
149 fMixPrintRefresh(copy.fMixPrintRefresh)
03d23846 150{
151//
152// Copy constructor.
153// Implemented as requested by C++ standards.
154// Can be used in PROOF and by plugins.
155//
156}
157
158//__________________________________________________________________________________________________
52e6652d 159AliRsnMiniAnalysisTask &AliRsnMiniAnalysisTask::operator=(const AliRsnMiniAnalysisTask &copy)
03d23846 160{
161//
162// Assignment operator.
163// Implemented as requested by C++ standards.
164// Can be used in PROOF and by plugins.
165//
166
167 AliAnalysisTaskSE::operator=(copy);
e6f3a909 168 if (this == &copy)
61f275d1 169 return *this;
c80938f5 170 fUseMC = copy.fUseMC;
03d23846 171 fUseCentrality = copy.fUseCentrality;
172 fCentralityType = copy.fCentralityType;
1cdc3671 173 fUseAOD049CentralityPatch = copy.fUseAOD049CentralityPatch;
caef2e3c 174 fContinuousMix = copy.fContinuousMix;
03d23846 175 fNMix = copy.fNMix;
176 fMaxDiffMult = copy.fMaxDiffMult;
177 fMaxDiffVz = copy.fMaxDiffVz;
178 fMaxDiffAngle = copy.fMaxDiffAngle;
179 fHistograms = copy.fHistograms;
180 fValues = copy.fValues;
955ca046 181 fHEventStat = copy.fHEventStat;
182 fHAEventsVsMulti = copy.fHAEventsVsMulti;
5654276f 183 fHAEventVz = copy.fHAEventVz;
184 fHAEventMultiCent = copy.fHAEventMultiCent;
185 fHAEventPlane = copy.fHAEventPlane;
03d23846 186 fEventCuts = copy.fEventCuts;
187 fTrackCuts = copy.fTrackCuts;
188 fTriggerAna = copy.fTriggerAna;
c80938f5 189 fESDtrackCuts = copy.fESDtrackCuts;
caef2e3c 190 fBigOutput = copy.fBigOutput;
61f275d1 191 fMixPrintRefresh = copy.fMixPrintRefresh;
03d23846 192 return (*this);
193}
194
195//__________________________________________________________________________________________________
196AliRsnMiniAnalysisTask::~AliRsnMiniAnalysisTask()
197{
198//
52e6652d 199// Destructor.
03d23846 200// Clean-up the output list, but not the histograms that are put inside
201// (the list is owner and will clean-up these histograms). Protect in PROOF case.
202//
203
d573d2fb 204
03d23846 205 if (fOutput && !AliAnalysisManager::GetAnalysisManager()->IsProofMode()) {
206 delete fOutput;
d573d2fb 207 delete fEvBuffer;
03d23846 208 }
209}
210
211//__________________________________________________________________________________________________
212Int_t AliRsnMiniAnalysisTask::AddTrackCuts(AliRsnCutSet *cuts)
213{
214//
215// Add a new cut set for a new criterion for track selection.
216// A user can add as many as he wants, and each one corresponds
217// to one of the available bits in the AliRsnMiniParticle mask.
218// The only check is the following: if a cut set with the same name
219// as the argument is there, this is not added.
220// Return value is the array position of this set.
221//
222
223 TObject *obj = fTrackCuts.FindObject(cuts->GetName());
52e6652d 224
03d23846 225 if (obj) {
226 AliInfo(Form("A cut set named '%s' already exists", cuts->GetName()));
227 return fTrackCuts.IndexOf(obj);
228 } else {
229 fTrackCuts.AddLast(cuts);
230 return fTrackCuts.IndexOf(cuts);
231 }
232}
233
234//__________________________________________________________________________________________________
235void AliRsnMiniAnalysisTask::UserCreateOutputObjects()
236{
237//
238// Initialization of outputs.
239// This is called once per worker node.
240//
241
242 // reset counter
9e7b94f5 243 fEvNum = -1;
52e6652d 244
d573d2fb 245 // message
246 AliInfo(Form("Selected event characterization: %s (%s)", (fUseCentrality ? "centrality" : "multiplicity"), fCentralityType.Data()));
03d23846 247
248 // initialize trigger analysis
c80938f5 249 if (fTriggerAna) delete fTriggerAna;
03d23846 250 fTriggerAna = new AliTriggerAnalysis;
52e6652d 251
c80938f5 252 // initialize ESD quality cuts
253 if (fESDtrackCuts) delete fESDtrackCuts;
254 fESDtrackCuts = AliESDtrackCuts::GetStandardITSTPCTrackCuts2010();
03d23846 255
256 // create list and set it as owner of its content (MANDATORY)
caef2e3c 257 if (fBigOutput) OpenFile(1);
03d23846 258 fOutput = new TList();
259 fOutput->SetOwner();
52e6652d 260
03d23846 261 // initialize event statistics counter
262 fHEventStat = new TH1F("hEventStat", "Event statistics", 4, 0.0, 4.0);
263 fHEventStat->GetXaxis()->SetBinLabel(1, "CINT1B");
264 fHEventStat->GetXaxis()->SetBinLabel(2, "V0AND");
265 fHEventStat->GetXaxis()->SetBinLabel(3, "Candle");
266 fHEventStat->GetXaxis()->SetBinLabel(4, "Accepted");
267 fOutput->Add(fHEventStat);
52e6652d 268
955ca046 269 if (fUseCentrality)
270 fHAEventsVsMulti = new TH1F("hAEventsVsMulti", "Accepted events vs Centrality", 100, 0, 100.0);
271 else
5654276f 272 fHAEventsVsMulti = new TH1F("hAEventsVsMulti", "Accepted events vs Multiplicity",1000, 0, 1000.0);
955ca046 273 fOutput->Add(fHAEventsVsMulti);
274
5654276f 275 if(fHAEventVz) fOutput->Add(fHAEventVz);
276 if(fHAEventMultiCent) fOutput->Add(fHAEventMultiCent);
277 if(fHAEventPlane) fOutput->Add(fHAEventPlane);
278
61f275d1 279 TIter next(&fTrackCuts);
280 AliRsnCutSet *cs;
281 while ((cs = (AliRsnCutSet *) next())) {
282 cs->Init(fOutput);
283 }
284
03d23846 285 // create temporary tree for filtered events
6aaeb33c 286 if (fMiniEvent) delete fMiniEvent;
c80938f5 287 fEvBuffer = new TTree("EventBuffer", "Temporary buffer for mini events");
6aaeb33c 288 fEvBuffer->Branch("events", "AliRsnMiniEvent", &fMiniEvent);
52e6652d 289
03d23846 290 // create one histogram per each stored definition (event histograms)
291 Int_t i, ndef = fHistograms.GetEntries();
292 AliRsnMiniOutput *def = 0x0;
293 for (i = 0; i < ndef; i++) {
52e6652d 294 def = (AliRsnMiniOutput *)fHistograms[i];
03d23846 295 if (!def) continue;
296 if (!def->Init(GetName(), fOutput)) {
297 AliError(Form("Def '%s': failed initialization", def->GetName()));
298 continue;
299 }
300 }
52e6652d 301
03d23846 302 // post data for ALL output slots >0 here, to get at least an empty histogram
303 PostData(1, fOutput);
304}
305
306//__________________________________________________________________________________________________
307void AliRsnMiniAnalysisTask::UserExec(Option_t *)
308{
309//
6aaeb33c 310// Computation loop.
311// In this case, it checks if the event is acceptable, and eventually
312// creates the corresponding mini-event and stores it in the buffer.
313// The real histogram filling is done at the end, in "FinishTaskOutput".
03d23846 314//
315
9e7b94f5 316 // increment event counter
03d23846 317 fEvNum++;
9e7b94f5 318
03d23846 319 // check current event
320 Char_t check = CheckCurrentEvent();
321 if (!check) return;
52e6652d 322
d573d2fb 323 // setup PID response
52e6652d 324 AliAnalysisManager *man = AliAnalysisManager::GetAnalysisManager();
325 AliInputEventHandler *inputHandler = (AliInputEventHandler *)man->GetInputEventHandler();
326 fRsnEvent.SetPIDResponse(inputHandler->GetPIDResponse());
327
6aaeb33c 328 // fill a mini-event from current
329 // and skip this event if no tracks were accepted
45aa62b9 330 FillMiniEvent(check);
52e6652d 331
6aaeb33c 332 // fill MC based histograms on mothers,
333 // which do need the original event
c80938f5 334 if (fUseMC) {
335 if (fRsnEvent.IsESD() && fMCEvent)
6aaeb33c 336 FillTrueMotherESD(fMiniEvent);
c80938f5 337 else if (fRsnEvent.IsAOD() && fRsnEvent.GetAODList())
6aaeb33c 338 FillTrueMotherAOD(fMiniEvent);
03d23846 339 }
52e6652d 340
9e7b94f5 341 // if the event is not empty, store it
342 if (fMiniEvent->IsEmpty()) {
343 AliDebugClass(2, Form("Rejecting empty event #%d", fEvNum));
344 } else {
345 Int_t id = fEvBuffer->GetEntries();
346 AliDebugClass(2, Form("Adding event #%d with ID = %d", fEvNum, id));
347 fMiniEvent->ID() = id;
348 fEvBuffer->Fill();
349 }
52e6652d 350
6aaeb33c 351 // post data for computed stuff
03d23846 352 PostData(1, fOutput);
353}
354
355//__________________________________________________________________________________________________
356void AliRsnMiniAnalysisTask::FinishTaskOutput()
357{
358//
6aaeb33c 359// This function is called at the end of the loop on available events,
360// and then the buffer will be full with all the corresponding mini-events,
361// each one containing all tracks selected by each of the available track cuts.
362// Here a loop is done on each of these events, and both single-event and mixing are computed
03d23846 363//
364
6aaeb33c 365 // security code: reassign the buffer to the mini-event cursor
366 fEvBuffer->SetBranchAddress("events", &fMiniEvent);
52e6652d 367 TStopwatch timer;
0efb7042 368 // prepare variables
6aaeb33c 369 Int_t ievt, nEvents = (Int_t)fEvBuffer->GetEntries();
370 Int_t idef, nDefs = fHistograms.GetEntries();
45aa62b9 371 Int_t imix, iloop, ifill;
6aaeb33c 372 AliRsnMiniOutput *def = 0x0;
373 AliRsnMiniOutput::EComputation compType;
52e6652d 374
61f275d1 375 Int_t printNum = fMixPrintRefresh;
376 if (printNum < 0) {
377 if (nEvents>1e5) printNum=nEvents/100;
378 else if (nEvents>1e4) printNum=nEvents/10;
379 else printNum = 0;
380 }
381
6aaeb33c 382 // loop on events, and for each one fill all outputs
383 // using the appropriate procedure depending on its type
384 // only mother-related histograms are filled in UserExec,
385 // since they require direct access to MC event
52e6652d 386 timer.Start();
6aaeb33c 387 for (ievt = 0; ievt < nEvents; ievt++) {
388 // get next entry
389 fEvBuffer->GetEntry(ievt);
52e6652d 390 if (printNum&&(ievt%printNum==0)) {
391 AliInfo(Form("[%s] Std.Event %d/%d",GetName(), ievt,nEvents));
61f275d1 392 timer.Stop(); timer.Print(); fflush(stdout); timer.Start(kFALSE);
52e6652d 393 }
45aa62b9 394 // fill
6aaeb33c 395 for (idef = 0; idef < nDefs; idef++) {
52e6652d 396 def = (AliRsnMiniOutput *)fHistograms[idef];
6aaeb33c 397 if (!def) continue;
398 compType = def->GetComputation();
399 // execute computation in the appropriate way
400 switch (compType) {
401 case AliRsnMiniOutput::kEventOnly:
9e7b94f5 402 //AliDebugClass(1, Form("Event %d, def '%s': event-value histogram filling", ievt, def->GetName()));
45aa62b9 403 ifill = 1;
0efb7042 404 def->FillEvent(fMiniEvent, &fValues);
6aaeb33c 405 break;
406 case AliRsnMiniOutput::kTruePair:
9e7b94f5 407 //AliDebugClass(1, Form("Event %d, def '%s': true-pair histogram filling", ievt, def->GetName()));
0efb7042 408 ifill = def->FillPair(fMiniEvent, fMiniEvent, &fValues);
6aaeb33c 409 break;
410 case AliRsnMiniOutput::kTrackPair:
9e7b94f5 411 //AliDebugClass(1, Form("Event %d, def '%s': pair-value histogram filling", ievt, def->GetName()));
0efb7042 412 ifill = def->FillPair(fMiniEvent, fMiniEvent, &fValues);
6aaeb33c 413 break;
414 case AliRsnMiniOutput::kTrackPairRotated1:
9e7b94f5 415 //AliDebugClass(1, Form("Event %d, def '%s': rotated (1) background histogram filling", ievt, def->GetName()));
0efb7042 416 ifill = def->FillPair(fMiniEvent, fMiniEvent, &fValues);
6aaeb33c 417 break;
418 case AliRsnMiniOutput::kTrackPairRotated2:
9e7b94f5 419 //AliDebugClass(1, Form("Event %d, def '%s': rotated (2) background histogram filling", ievt, def->GetName()));
0efb7042 420 ifill = def->FillPair(fMiniEvent, fMiniEvent, &fValues);
6aaeb33c 421 break;
422 default:
423 // other kinds are processed elsewhere
45aa62b9 424 ifill = 0;
6aaeb33c 425 AliDebugClass(2, Form("Computation = %d", (Int_t)compType));
426 }
45aa62b9 427 // message
428 AliDebugClass(1, Form("Event %6d: def = '%15s' -- fills = %5d", ievt, def->GetName(), ifill));
03d23846 429 }
430 }
52e6652d 431
0efb7042 432 // if no mixing is required, stop here and post the output
433 if (fNMix < 1) {
434 AliDebugClass(2, "Stopping here, since no mixing is required");
435 PostData(1, fOutput);
436 return;
437 }
52e6652d 438
0efb7042 439 // initialize mixing counter
9e7b94f5 440 Int_t nmatched[nEvents];
441 TString *smatched = new TString[nEvents];
0efb7042 442 for (ievt = 0; ievt < nEvents; ievt++) {
9e7b94f5 443 smatched[ievt] = "|";
444 nmatched[ievt] = 0;
0efb7042 445 }
61f275d1 446
447
52e6652d 448 AliInfo(Form("[%s] Std.Event %d/%d",GetName(), nEvents,nEvents));
61f275d1 449 timer.Stop(); timer.Print(); timer.Start(); fflush(stdout);
52e6652d 450
0efb7042 451 // search for good matchings
452 for (ievt = 0; ievt < nEvents; ievt++) {
52e6652d 453 if (printNum&&(ievt%printNum==0)) {
454 AliInfo(Form("[%s] EventMixing searching %d/%d",GetName(),ievt,nEvents));
455 timer.Stop(); timer.Print(); timer.Start(kFALSE); fflush(stdout);
456 }
9e7b94f5 457 if (nmatched[ievt] >= fNMix) continue;
0efb7042 458 fEvBuffer->GetEntry(ievt);
459 AliRsnMiniEvent evMain(*fMiniEvent);
460 for (iloop = 1; iloop < nEvents; iloop++) {
461 imix = ievt + iloop;
462 if (imix >= nEvents) imix -= nEvents;
463 if (imix == ievt) continue;
464 // text next entry
465 fEvBuffer->GetEntry(imix);
466 // skip if events are not matched
caef2e3c 467 if (!EventsMatch(&evMain, fMiniEvent)) continue;
0efb7042 468 // check that the array of good matches for mixed does not already contain main event
9e7b94f5 469 if (smatched[imix].Contains(Form("|%d|", ievt))) continue;
470 // check that the found good events has not enough matches already
471 if (nmatched[imix] >= fNMix) continue;
0efb7042 472 // add new mixing candidate
9e7b94f5 473 smatched[ievt].Append(Form("%d|", imix));
474 nmatched[ievt]++;
475 nmatched[imix]++;
476 if (nmatched[ievt] >= fNMix) break;
0efb7042 477 }
9e7b94f5 478 AliDebugClass(1, Form("Matches for event %5d = %d [%s] (missing are declared above)", evMain.ID(), nmatched[ievt], smatched[ievt].Data()));
0efb7042 479 }
61f275d1 480
52e6652d 481 AliInfo(Form("[%s] EventMixing searching %d/%d",GetName(),nEvents,nEvents));
61f275d1 482 timer.Stop(); timer.Print(); fflush(stdout); timer.Start();
52e6652d 483
0efb7042 484 // perform mixing
485 TObjArray *list = 0x0;
486 TObjString *os = 0x0;
487 for (ievt = 0; ievt < nEvents; ievt++) {
52e6652d 488 if (printNum&&(ievt%printNum==0)) {
489 AliInfo(Form("[%s] EventMixing %d/%d",GetName(),ievt,nEvents));
490 timer.Stop(); timer.Print(); timer.Start(kFALSE); fflush(stdout);
491 }
0efb7042 492 ifill = 0;
493 fEvBuffer->GetEntry(ievt);
494 AliRsnMiniEvent evMain(*fMiniEvent);
9e7b94f5 495 list = smatched[ievt].Tokenize("|");
0efb7042 496 TObjArrayIter next(list);
52e6652d 497 while ( (os = (TObjString *)next()) ) {
0efb7042 498 imix = os->GetString().Atoi();
0efb7042 499 fEvBuffer->GetEntry(imix);
500 for (idef = 0; idef < nDefs; idef++) {
52e6652d 501 def = (AliRsnMiniOutput *)fHistograms[idef];
0efb7042 502 if (!def) continue;
503 if (!def->IsTrackPairMix()) continue;
d573d2fb 504 ifill += def->FillPair(&evMain, fMiniEvent, &fValues, kTRUE);
9e7b94f5 505 if (!def->IsSymmetric()) {
506 AliDebugClass(2, "Reflecting non symmetric pair");
507 ifill += def->FillPair(fMiniEvent, &evMain, &fValues, kFALSE);
508 }
0efb7042 509 }
510 }
511 delete list;
512 }
52e6652d 513
9e7b94f5 514 delete [] smatched;
52e6652d 515
516 AliInfo(Form("[%s] EventMixing %d/%d",GetName(),nEvents,nEvents));
61f275d1 517 timer.Stop(); timer.Print(); fflush(stdout);
52e6652d 518
0efb7042 519 /*
52e6652d 520 OLD
0efb7042 521 ifill = 0;
522 for (iloop = 1; iloop < nEvents; iloop++) {
523 imix = ievt + iloop;
524 // restart from beginning if reached last event
525 if (imix >= nEvents) imix -= nEvents;
526 // avoid to mix an event with itself
527 if (imix == ievt) continue;
528 // skip all events already mixed enough times
529 if (fNMixed[ievt] >= fNMix) break;
530 if (fNMixed[imix] >= fNMix) continue;
531 fEvBuffer->GetEntry(imix);
532 // skip if events are not matched
533 if (TMath::Abs(evMain.Vz() - fMiniEvent->Vz() ) > fMaxDiffVz ) continue;
534 if (TMath::Abs(evMain.Mult() - fMiniEvent->Mult() ) > fMaxDiffMult ) continue;
535 if (TMath::Abs(evMain.Angle() - fMiniEvent->Angle()) > fMaxDiffAngle) continue;
536 // found a match: increment counter for both events
537 AliDebugClass(1, Form("Event %d, def '%s': event mixing (%d with %d)", ievt, def->GetName(), ievt, imix));
538 fNMixed[ievt]++;
539 fNMixed[imix]++;
540 // process mixing
541 ifill += def->FillPair(&evMain, fMiniEvent, &fValues);
542 // stop if mixed enough times
543 if (fNMixed[ievt] >= fNMix) break;
544 }
52e6652d 545 break;
6aaeb33c 546 // print number of mixings done with each event
45aa62b9 547 for (ievt = 0; ievt < nEvents; ievt++) {
548 AliDebugClass(2, Form("Event %6d: mixed %2d times", ievt, fNMixed[ievt]));
549 }
0efb7042 550 */
52e6652d 551
6aaeb33c 552 // post computed data
03d23846 553 PostData(1, fOutput);
554}
555
556//__________________________________________________________________________________________________
557void AliRsnMiniAnalysisTask::Terminate(Option_t *)
558{
559//
560// Draw result to screen, or perform fitting, normalizations
561// Called once at the end of the query
562//
563
52e6652d 564 fOutput = dynamic_cast<TList *>(GetOutputData(1));
565 if (!fOutput) {
566 AliError("Could not retrieve TList fOutput");
567 return;
03d23846 568 }
569}
570
571//__________________________________________________________________________________________________
572Char_t AliRsnMiniAnalysisTask::CheckCurrentEvent()
573{
574//
c80938f5 575// This method checks if current event is OK for analysis.
576// In case it is, the pointers of the local AliRsnEvent data member
577// will point to it, in order to allow cut checking, otherwise the
578// function exits with a failure message.
579// ---
580// ESD events must pass the physics selection, AOD are supposed to do.
581// ---
582// While checking the event, a histogram is filled to count the number
583// of CINT1B, V0AND and CANDLE events, which are needed for normalization
584// ---
585// Return values can be:
03d23846 586// -- 'E' if the event is accepted and is ESD
587// -- 'A' if the event is accepted and is AOD
588// -- 0 if the event is not accepted
589//
590
591 // string to sum messages
592 TString msg("");
52e6652d 593
03d23846 594 // check input type
c80938f5 595 // exit points are provided in all cases an event is bad
596 // if this block is passed, an event can be rejected only
597 // if it does not pass the set of event cuts defined in the task
03d23846 598 Char_t output = 0;
c80938f5 599 Bool_t isSelected;
600 if (fInputEvent->InheritsFrom(AliESDEvent::Class())) {
601 // type ESD
03d23846 602 output = 'E';
c80938f5 603 // ESD specific check: Physics Selection
604 // --> if this is failed, the event is rejected
52e6652d 605 isSelected = (((AliInputEventHandler *)(AliAnalysisManager::GetAnalysisManager()->GetInputEventHandler()))->IsEventSelected() & AliVEvent::kMB);
c80938f5 606 if (!isSelected) {
45aa62b9 607 AliDebugClass(2, "Event does not pass physics selections");
c80938f5 608 fRsnEvent.SetRef(0x0);
609 fRsnEvent.SetRefMC(0x0);
610 return 0;
611 }
612 // set reference to input
613 fRsnEvent.SetRef(fInputEvent);
614 // add MC if requested and available
615 if (fUseMC) {
52e6652d 616 if (fMCEvent)
c80938f5 617 fRsnEvent.SetRefMC(fMCEvent);
618 else {
619 AliWarning("MC event requested but not available");
620 fRsnEvent.SetRefMC(0x0);
621 }
622 }
623 } else if (fInputEvent->InheritsFrom(AliAODEvent::Class())) {
624 // type AOD
03d23846 625 output = 'A';
c80938f5 626 // set reference to input
627 fRsnEvent.SetRef(fInputEvent);
628 // add MC if requested and available (it is in the same object)
629 if (fUseMC) {
630 fRsnEvent.SetRefMC(fInputEvent);
631 if (!fRsnEvent.GetAODList()) {
632 AliWarning("MC event requested but not available");
633 fRsnEvent.SetRefMC(0x0);
634 }
635 }
636 } else {
03d23846 637 AliError(Form("Bad input event class: %s", fInputEvent->ClassName()));
c80938f5 638 // reset pointers in local AliRsnEvent object
639 fRsnEvent.SetRef(0x0);
640 fRsnEvent.SetRefMC(0x0);
03d23846 641 return 0;
642 }
52e6652d 643
c80938f5 644 // fill counter of accepted events
645 fHEventStat->Fill(0.1);
52e6652d 646
03d23846 647 // check if it is V0AND
c80938f5 648 // --> uses a cast to AliESDEvent even if the input is an AliAODEvent
52e6652d 649 Bool_t v0A = fTriggerAna->IsOfflineTriggerFired((AliESDEvent *)fInputEvent, AliTriggerAnalysis::kV0A);
650 Bool_t v0C = fTriggerAna->IsOfflineTriggerFired((AliESDEvent *)fInputEvent, AliTriggerAnalysis::kV0C);
03d23846 651 if (v0A && v0C) {
652 msg += " -- VOAND = YES";
653 fHEventStat->Fill(1.1);
654 } else {
655 msg += " -- VOAND = NO ";
656 }
52e6652d 657
03d23846 658 // check candle
c80938f5 659 // --> requires at least one good quality track with Pt > 0.5 and |eta| <= 0.8
660 Int_t iTrack, ntracksLoop = fInputEvent->GetNumberOfTracks();
03d23846 661 Bool_t candle = kFALSE;
52e6652d 662 for (iTrack = 0; iTrack < ntracksLoop; iTrack++) {
663 AliVTrack *track = (AliVTrack *)fInputEvent->GetTrack(iTrack);
664 AliESDtrack *esdt = dynamic_cast<AliESDtrack *>(track);
665 AliAODTrack *aodt = dynamic_cast<AliAODTrack *>(track);
03d23846 666 if (track->Pt() < 0.5) continue;
667 if(TMath::Abs(track->Eta()) > 0.8) continue;
c80938f5 668 if (esdt) if (!fESDtrackCuts->AcceptTrack(esdt)) continue;
669 if (aodt) if (!aodt->TestFilterBit(5)) continue;
03d23846 670 candle = kTRUE;
671 break;
672 }
673 if (candle) {
52e6652d 674 msg += " -- CANDLE = YES";
03d23846 675 fHEventStat->Fill(2.1);
676 } else {
52e6652d 677 msg += " -- CANDLE = NO ";
03d23846 678 }
52e6652d 679
c80938f5 680 // if event cuts are defined, they are checked here
681 // final decision on the event depends on this
682 isSelected = kTRUE;
03d23846 683 if (fEventCuts) {
684 if (!fEventCuts->IsSelected(&fRsnEvent)) {
685 msg += " -- Local cuts = REJECTED";
c80938f5 686 isSelected = kFALSE;
03d23846 687 } else {
688 msg += " -- Local cuts = ACCEPTED";
c80938f5 689 isSelected = kTRUE;
03d23846 690 }
691 } else {
692 msg += " -- Local cuts = NONE";
c80938f5 693 isSelected = kTRUE;
03d23846 694 }
52e6652d 695
03d23846 696 // if the above exit point is not taken, the event is accepted
9e7b94f5 697 AliDebugClass(2, Form("Stats: %s", msg.Data()));
c80938f5 698 if (isSelected) {
699 fHEventStat->Fill(3.1);
955ca046 700 Double_t multi = ComputeCentrality((output == 'E'));
701 fHAEventsVsMulti->Fill(multi);
5654276f 702 if(fHAEventVz) fHAEventVz->Fill(multi,fInputEvent->GetPrimaryVertex()->GetZ());
703 if(fHAEventMultiCent) fHAEventMultiCent->Fill(multi,ComputeMultiplicity(output == 'E',fHAEventMultiCent->GetYaxis()->GetTitle()));
704 if(fHAEventPlane) fHAEventPlane->Fill(multi,ComputeAngle());
c80938f5 705 return output;
706 } else {
707 return 0;
708 }
03d23846 709}
710
6aaeb33c 711//__________________________________________________________________________________________________
45aa62b9 712void AliRsnMiniAnalysisTask::FillMiniEvent(Char_t evType)
6aaeb33c 713{
714//
715// Refresh cursor mini-event data member to fill with current event.
716// Returns the total number of tracks selected.
717//
718
719 // assign event-related values
45aa62b9 720 if (fMiniEvent) delete fMiniEvent;
6aaeb33c 721 fMiniEvent = new AliRsnMiniEvent;
722 fMiniEvent->Vz() = fInputEvent->GetPrimaryVertex()->GetZ();
723 fMiniEvent->Angle() = ComputeAngle();
724 fMiniEvent->Mult() = ComputeCentrality((evType == 'E'));
45aa62b9 725 AliDebugClass(2, Form("Event %d: type = %c -- vz = %f -- mult = %f -- angle = %f", fEvNum, evType, fMiniEvent->Vz(), fMiniEvent->Mult(), fMiniEvent->Angle()));
52e6652d 726
6aaeb33c 727 // loop on daughters and assign track-related values
728 Int_t ic, ncuts = fTrackCuts.GetEntries();
729 Int_t ip, npart = fRsnEvent.GetAbsoluteSum();
45aa62b9 730 Int_t npos = 0, nneg = 0, nneu = 0;
6aaeb33c 731 AliRsnDaughter cursor;
732 AliRsnMiniParticle miniParticle;
733 for (ip = 0; ip < npart; ip++) {
734 // point cursor to next particle
735 fRsnEvent.SetDaughter(cursor, ip);
736 // copy momentum and MC info if present
737 miniParticle.CopyDaughter(&cursor);
45aa62b9 738 miniParticle.Index() = ip;
6aaeb33c 739 // switch on the bits corresponding to passed cuts
740 for (ic = 0; ic < ncuts; ic++) {
52e6652d 741 AliRsnCutSet *cuts = (AliRsnCutSet *)fTrackCuts[ic];
6aaeb33c 742 if (cuts->IsSelected(&cursor)) miniParticle.SetCutBit(ic);
743 }
744 // if a track passes at least one track cut, it is added to the pool
45aa62b9 745 if (miniParticle.CutBits()) {
746 fMiniEvent->AddParticle(miniParticle);
747 if (miniParticle.Charge() == '+') npos++;
748 else if (miniParticle.Charge() == '-') nneg++;
749 else nneu++;
750 }
6aaeb33c 751 }
52e6652d 752
6aaeb33c 753 // get number of accepted tracks
45aa62b9 754 AliDebugClass(1, Form("Event %6d: total = %5d, accepted = %4d (pos %4d, neg %4d, neu %4d)", fEvNum, npart, (Int_t)fMiniEvent->Particles().GetEntriesFast(), npos, nneg, nneu));
6aaeb33c 755}
756
3dced4f8 757//__________________________________________________________________________________________________
758Double_t AliRsnMiniAnalysisTask::ComputeAngle()
759{
760//
761// Get the plane angle
762//
763
cd273d20 764 AliEventplane *plane = 0x0;
52e6652d 765
cd273d20 766 if (fInputEvent->InheritsFrom(AliESDEvent::Class()))
767 plane = fInputEvent->GetEventplane();
768 else if (fInputEvent->InheritsFrom(AliAODEvent::Class())) {
52e6652d 769 AliAODEvent *aodEvent = (AliAODEvent *)fInputEvent;
cd273d20 770 plane = aodEvent->GetHeader()->GetEventplaneP();
771 }
772
52e6652d 773 if (plane)
3dced4f8 774 return plane->GetEventplane("Q");
775 else {
776 AliWarning("No event plane defined");
777 return 1E20;
778 }
779}
780
03d23846 781//__________________________________________________________________________________________________
782Double_t AliRsnMiniAnalysisTask::ComputeCentrality(Bool_t isESD)
783{
784//
785// Computes event centrality/multiplicity according to the criterion defined
786// by two elements: (1) choice between multiplicity and centrality and
787// (2) the string defining what criterion must be used for specific computation.
788//
789
790 if (fUseCentrality) {
3da8cef7 791
792 if ((!fUseMC) && (!isESD) && (fUseAOD049CentralityPatch)) {
793 return ApplyCentralityPatchAOD049();
794 } else {
795 AliCentrality *centrality = fInputEvent->GetCentrality();
796 if (!centrality) {
797 AliError("Cannot compute centrality!");
798 return -1.0;
799 }
800 return centrality->GetCentralityPercentile(fCentralityType.Data());
801 }
03d23846 802 } else {
03d23846 803 if (!fCentralityType.CompareTo("TRACKS"))
804 return fInputEvent->GetNumberOfTracks();
805 else if (!fCentralityType.CompareTo("QUALITY"))
c80938f5 806 if (isESD)
52e6652d 807 return AliESDtrackCuts::GetReferenceMultiplicity((AliESDEvent *)fInputEvent, kTRUE);
c80938f5 808 else {
809 Double_t count = 0.;
810 Int_t iTrack, ntracksLoop = fInputEvent->GetNumberOfTracks();
52e6652d 811 for (iTrack = 0; iTrack < ntracksLoop; iTrack++) {
812 AliVTrack *track = (AliVTrack *)fInputEvent->GetTrack(iTrack);
813 AliAODTrack *aodt = dynamic_cast<AliAODTrack *>(track);
c80938f5 814 if (!aodt) continue;
815 if (!aodt->TestFilterBit(5)) continue;
816 count++;
817 }
818 return count;
819 }
03d23846 820 else if (!fCentralityType.CompareTo("TRACKLETS")) {
c80938f5 821 if (isESD) {
52e6652d 822 const AliMultiplicity *mult = ((AliESDEvent *)fInputEvent)->GetMultiplicity();
c80938f5 823 Float_t nClusters[6] = {0.0,0.0,0.0,0.0,0.0,0.0};
824 for(Int_t ilay = 0; ilay < 6; ilay++) nClusters[ilay] = (Float_t)mult->GetNumberOfITSClusters(ilay);
825 return AliESDUtils::GetCorrSPD2(nClusters[1], fInputEvent->GetPrimaryVertex()->GetZ());
826 } else {
827 AliWarning("Cannot compute multiplicity with SPD tracklets from AOD");
828 return 1E20;
829 }
03d23846 830 } else {
831 AliError(Form("String '%s' does not define a possible multiplicity/centrality computation", fCentralityType.Data()));
832 return -1.0;
833 }
834 }
835}
836
5654276f 837//__________________________________________________________________________________________________
838Double_t AliRsnMiniAnalysisTask::ComputeMultiplicity(Bool_t isESD,TString type)
839{
840//
841// Computes event multiplicity according to the string defining
842// what criterion must be used for specific computation.
843//
844
845 type.ToUpper();
846
847 if (!type.CompareTo("TRACKS"))
848 return fInputEvent->GetNumberOfTracks();
849 else if (!type.CompareTo("QUALITY"))
850 if (isESD)
851 return AliESDtrackCuts::GetReferenceMultiplicity((AliESDEvent *)fInputEvent, kTRUE);
852 else {
853 Double_t count = 0.;
854 Int_t iTrack, ntracksLoop = fInputEvent->GetNumberOfTracks();
855 for (iTrack = 0; iTrack < ntracksLoop; iTrack++) {
856 AliVTrack *track = (AliVTrack *)fInputEvent->GetTrack(iTrack);
857 AliAODTrack *aodt = dynamic_cast<AliAODTrack *>(track);
858 if (!aodt) continue;
859 if (!aodt->TestFilterBit(5)) continue;
860 count++;
861 }
862 return count;
863 }
864 else if (!type.CompareTo("TRACKLETS")) {
865 if (isESD) {
866 const AliMultiplicity *mult = ((AliESDEvent *)fInputEvent)->GetMultiplicity();
867 Float_t nClusters[6] = {0.0,0.0,0.0,0.0,0.0,0.0};
868 for(Int_t ilay = 0; ilay < 6; ilay++) nClusters[ilay] = (Float_t)mult->GetNumberOfITSClusters(ilay);
869 return AliESDUtils::GetCorrSPD2(nClusters[1], fInputEvent->GetPrimaryVertex()->GetZ());
870 } else {
871 AliWarning("Cannot compute multiplicity with SPD tracklets from AOD");
872 return 1E20;
873 }
874 } else {
875 AliError(Form("String '%s' does not define a possible multiplicity/centrality computation", type.Data()));
876 return -1.0;
877 }
878
879 return 1E20;
880}
881
03d23846 882//__________________________________________________________________________________________________
883void AliRsnMiniAnalysisTask::FillTrueMotherESD(AliRsnMiniEvent *miniEvent)
884{
885//
886// Fills the histograms with true mother (ESD version)
887//
888
889 Bool_t okMatch;
890 Int_t id, ndef = fHistograms.GetEntries();
891 Int_t ip, label1, label2, npart = fMCEvent->GetNumberOfTracks();
892 static AliRsnMiniPair miniPair;
893 AliMCParticle *daughter1, *daughter2;
894 TLorentzVector p1, p2;
895 AliRsnMiniOutput *def = 0x0;
52e6652d 896
03d23846 897 for (id = 0; id < ndef; id++) {
52e6652d 898 def = (AliRsnMiniOutput *)fHistograms[id];
03d23846 899 if (!def) continue;
900 if (!def->IsMother()) continue;
901 for (ip = 0; ip < npart; ip++) {
52e6652d 902 AliMCParticle *part = (AliMCParticle *)fMCEvent->GetTrack(ip);
64129b35 903 if (part->Particle()->GetPdgCode() != def->GetMotherPDG()) continue;
03d23846 904 // check that daughters match expected species
905 if (part->Particle()->GetNDaughters() < 2) continue;
906 label1 = part->Particle()->GetDaughter(0);
907 label2 = part->Particle()->GetDaughter(1);
52e6652d 908 daughter1 = (AliMCParticle *)fMCEvent->GetTrack(label1);
909 daughter2 = (AliMCParticle *)fMCEvent->GetTrack(label2);
03d23846 910 okMatch = kFALSE;
911 if (TMath::Abs(daughter1->Particle()->GetPdgCode()) == def->GetPDG(0) && TMath::Abs(daughter2->Particle()->GetPdgCode()) == def->GetPDG(1)) {
912 okMatch = kTRUE;
913 p1.SetXYZM(daughter1->Px(), daughter1->Py(), daughter1->Pz(), def->GetMass(0));
914 p2.SetXYZM(daughter2->Px(), daughter2->Py(), daughter2->Pz(), def->GetMass(1));
915 } else if (TMath::Abs(daughter1->Particle()->GetPdgCode()) == def->GetPDG(1) && TMath::Abs(daughter2->Particle()->GetPdgCode()) == def->GetPDG(0)) {
916 okMatch = kTRUE;
917 p1.SetXYZM(daughter1->Px(), daughter1->Py(), daughter1->Pz(), def->GetMass(1));
918 p2.SetXYZM(daughter2->Px(), daughter2->Py(), daughter2->Pz(), def->GetMass(0));
919 }
920 if (!okMatch) continue;
921 // assign momenta to computation object
922 miniPair.Sum(0) = miniPair.Sum(1) = (p1 + p2);
923 miniPair.FillRef(def->GetMotherMass());
924 // do computations
45aa62b9 925 def->FillMother(&miniPair, miniEvent, &fValues);
03d23846 926 }
927 }
928}
929
930//__________________________________________________________________________________________________
931void AliRsnMiniAnalysisTask::FillTrueMotherAOD(AliRsnMiniEvent *miniEvent)
932{
933//
934// Fills the histograms with true mother (AOD version)
935//
936
937 Bool_t okMatch;
938 TClonesArray *list = fRsnEvent.GetAODList();
939 Int_t id, ndef = fHistograms.GetEntries();
940 Int_t ip, label1, label2, npart = list->GetEntries();
941 static AliRsnMiniPair miniPair;
942 AliAODMCParticle *daughter1, *daughter2;
943 TLorentzVector p1, p2;
944 AliRsnMiniOutput *def = 0x0;
52e6652d 945
03d23846 946 for (id = 0; id < ndef; id++) {
52e6652d 947 def = (AliRsnMiniOutput *)fHistograms[id];
03d23846 948 if (!def) continue;
949 if (!def->IsMother()) continue;
950 for (ip = 0; ip < npart; ip++) {
52e6652d 951 AliAODMCParticle *part = (AliAODMCParticle *)list->At(ip);
64129b35 952 if (part->GetPdgCode() != def->GetMotherPDG()) continue;
03d23846 953 // check that daughters match expected species
954 if (part->GetNDaughters() < 2) continue;
955 label1 = part->GetDaughter(0);
956 label2 = part->GetDaughter(1);
52e6652d 957 daughter1 = (AliAODMCParticle *)list->At(label1);
958 daughter2 = (AliAODMCParticle *)list->At(label2);
03d23846 959 okMatch = kFALSE;
960 if (TMath::Abs(daughter1->GetPdgCode()) == def->GetPDG(0) && TMath::Abs(daughter2->GetPdgCode()) == def->GetPDG(1)) {
961 okMatch = kTRUE;
962 p1.SetXYZM(daughter1->Px(), daughter1->Py(), daughter1->Pz(), def->GetMass(0));
963 p2.SetXYZM(daughter2->Px(), daughter2->Py(), daughter2->Pz(), def->GetMass(1));
964 } else if (TMath::Abs(daughter1->GetPdgCode()) == def->GetPDG(1) && TMath::Abs(daughter2->GetPdgCode()) == def->GetPDG(0)) {
965 okMatch = kTRUE;
966 p1.SetXYZM(daughter1->Px(), daughter1->Py(), daughter1->Pz(), def->GetMass(1));
967 p2.SetXYZM(daughter2->Px(), daughter2->Py(), daughter2->Pz(), def->GetMass(0));
968 }
969 if (!okMatch) continue;
970 // assign momenta to computation object
971 miniPair.Sum(0) = miniPair.Sum(1) = (p1 + p2);
972 miniPair.FillRef(def->GetMotherMass());
973 // do computations
45aa62b9 974 def->FillMother(&miniPair, miniEvent, &fValues);
03d23846 975 }
976 }
977}
caef2e3c 978
979//__________________________________________________________________________________________________
980Bool_t AliRsnMiniAnalysisTask::EventsMatch(AliRsnMiniEvent *event1, AliRsnMiniEvent *event2)
981{
982//
983// Check if two events are compatible.
984// If the mixing is continuous, this is true if differences in vz, mult and angle are smaller than
52e6652d 985// the specified values.
caef2e3c 986// If the mixing is binned, this is true if the events are in the same bin.
987//
988
989 if (!event1 || !event2) return kFALSE;
990 Int_t ivz1, ivz2, imult1, imult2, iangle1, iangle2;
9e7b94f5 991 Double_t dv, dm, da;
52e6652d 992
caef2e3c 993 if (fContinuousMix) {
9e7b94f5 994 dv = TMath::Abs(event1->Vz() - event2->Vz() );
995 dm = TMath::Abs(event1->Mult() - event2->Mult() );
996 da = TMath::Abs(event1->Angle() - event2->Angle());
997 if (dv > fMaxDiffVz) {
998 //AliDebugClass(2, Form("Events #%4d and #%4d don't match due to a too large diff in Vz = %f", event1->ID(), event2->ID(), dv));
999 return kFALSE;
1000 }
1001 if (dm > fMaxDiffMult ) {
1002 //AliDebugClass(2, Form("Events #%4d and #%4d don't match due to a too large diff in Mult = %f", event1->ID(), event2->ID(), dm));
1003 return kFALSE;
1004 }
1005 if (da > fMaxDiffAngle) {
1006 //AliDebugClass(2, Form("Events #%4d and #%4d don't match due to a too large diff in Angle = %f", event1->ID(), event2->ID(), da));
1007 return kFALSE;
1008 }
caef2e3c 1009 return kTRUE;
1010 } else {
1011 ivz1 = (Int_t)(event1->Vz() / fMaxDiffVz);
1012 ivz2 = (Int_t)(event2->Vz() / fMaxDiffVz);
1013 imult1 = (Int_t)(event1->Mult() / fMaxDiffMult);
1014 imult2 = (Int_t)(event2->Mult() / fMaxDiffMult);
1015 iangle1 = (Int_t)(event1->Angle() / fMaxDiffAngle);
1016 iangle2 = (Int_t)(event2->Angle() / fMaxDiffAngle);
1017 if (ivz1 != ivz2) return kFALSE;
1018 if (imult1 != imult2) return kFALSE;
1019 if (iangle1 != iangle2) return kFALSE;
1020 return kTRUE;
1021 }
1022}
1023
52e6652d 1024
1cdc3671 1025//---------------------------------------------------------------------
1026Double_t AliRsnMiniAnalysisTask::ApplyCentralityPatchAOD049()
1027{
3da8cef7 1028 //
1029 //Apply centrality patch for AOD049 outliers
1030 //
1031 if (fInputEvent->InheritsFrom(AliESDEvent::Class())) {
1032 AliWarning("Requested patch for AOD049 for ESD. ");
1cdc3671 1033 return -999.0;
3da8cef7 1034 }
1035
1036 if (fCentralityType!="V0M") {
1037 AliWarning("Requested patch forAOD049 for wrong value (not centrality from V0).");
1cdc3671 1038 return -999.0;
3da8cef7 1039 }
1040
1041 AliCentrality *centrality = fInputEvent->GetCentrality();
1042 if (!centrality) {
1043 AliWarning("Cannot get centrality from AOD event.");
1044 return -999.0;
1045 }
1046
1047 Float_t cent = (Float_t)(centrality->GetCentralityPercentile("V0M"));
1048 /*
1049 Bool_t isSelRun = kFALSE;
1050 Int_t selRun[5] = {138364, 138826, 138828, 138836, 138871};
1051 if(cent<0){
1052 Int_t quality = centrality->GetQuality();
1053 if(quality<=1){
1054 cent=(Float_t)centrality->GetCentralityPercentileUnchecked("V0M");
1055 } else {
1056 Int_t runnum=aodEvent->GetRunNumber();
1057 for(Int_t ir=0;ir<5;ir++){
1058 if(runnum==selRun[ir]){
1059 isSelRun=kTRUE;
1060 break;
1061 }
1062 }
1063 if((quality==8||quality==9)&&isSelRun) cent=(Float_t)centrality->GetCentralityPercentileUnchecked("V0M");
1064 }
1065 }
1066 */
1067
1068 if(cent>=0.0) {
1069 Float_t v0 = 0.0;
1070 AliAODEvent *aodEvent = (AliAODEvent *)fInputEvent;
1071 AliAODVZERO *aodV0 = (AliAODVZERO *) aodEvent->GetVZEROData();
1072 v0+=aodV0->GetMTotV0A();
1073 v0+=aodV0->GetMTotV0C();
1074 if ( (cent==0) && (v0<19500) ) {
1075 AliDebug(3, Form("Filtering issue in centrality -> cent = %5.2f",cent));
1076 return -999.0;
1077 }
1078 Float_t tkl = (Float_t)(aodEvent->GetTracklets()->GetNumberOfTracklets());
1079 Float_t val = 1.30552 + 0.147931 * v0;
1080
1081 Float_t tklSigma[101] = {176.644, 156.401, 153.789, 153.015, 142.476, 137.951, 136.127, 129.852, 127.436, 124.86,
1082 120.788, 115.611, 113.172, 110.496, 109.127, 104.421, 102.479, 99.9766, 97.5152, 94.0654,
1083 92.4602, 89.3364, 87.1342, 83.3497, 82.6216, 81.1084, 78.0793, 76.1234, 72.9434, 72.1334,
1084 68.0056, 68.2755, 66.0376, 62.9666, 62.4274, 59.65, 58.3776, 56.6361, 54.5184, 53.4224,
1085 51.932, 50.8922, 48.2848, 47.912, 46.5717, 43.4114, 43.2083, 41.3065, 40.1863, 38.5255,
1086 37.2851, 37.5396, 34.4949, 33.8366, 31.8043, 31.7412, 30.8392, 30.0274, 28.8793, 27.6398,
1087 26.6488, 25.0183, 25.1489, 24.4185, 22.9107, 21.2002, 21.6977, 20.1242, 20.4963, 19.0235,
1088 19.298, 17.4103, 16.868, 15.2939, 15.2939, 16.0295, 14.186, 14.186, 15.2173, 12.9504, 12.9504,
1089 12.9504, 15.264, 12.3674, 12.3674, 12.3674, 12.3674, 12.3674, 18.3811, 13.7544, 13.7544,
1090 13.7544, 13.7544, 13.7544, 13.7544, 13.7544, 13.7544, 13.7544, 13.7544, 13.7544, 13.7544
1091 };
1092
1093 if ( TMath::Abs(tkl-val) > 6.*tklSigma[(Int_t)cent] ) {
1094 AliDebug(3, Form("Outlier event in centrality -> cent = %5.2f",cent));
1095 return -999.0;
1096 }
1097 } else {
1098 //force it to be -999. whatever the negative value was
1099 cent = -999.;
1100 }
1101 return cent;
1cdc3671 1102}
5654276f 1103
1104//----------------------------------------------------------------------------------
1105void AliRsnMiniAnalysisTask::SetEventQAHist(TString type,TH2F* histo)
1106{
1107 if(!histo){
1108 AliWarning(Form("event QA histogram pointer not defined for slot %s",type.Data()));
1109 return;
1110 }
1111
1112 type.ToLower();
1113
1114 if(!type.CompareTo("vz")) fHAEventVz = histo;
1115 else if(!type.CompareTo("multicent")){
1116 TString mtype(histo->GetYaxis()->GetTitle());
1117 mtype.ToUpper();
1118 if(mtype.CompareTo("QUALITY") && mtype.CompareTo("TRACKS") && mtype.CompareTo("TRACKLETS")){
1119 AliWarning(Form("multiplicity vs. centrality histogram y-axis %s unknown, setting to TRACKS",mtype.Data()));
1120 histo->GetYaxis()->SetTitle("TRACKS");
1121 }
1122 fHAEventMultiCent = histo;
1123 }
1124 else if(!type.CompareTo("eventplane")) fHAEventPlane = histo;
1125 else AliWarning(Form("event QA histogram slot %s undefined",type.Data()));
1126
1127 return;
1128}