]> git.uio.no Git - u/mrichter/AliRoot.git/blame - PWG4/JetTasks/AliUEHist.cxx
disabling vtx bins by default
[u/mrichter/AliRoot.git] / PWG4 / JetTasks / AliUEHist.cxx
CommitLineData
a75aacd6 1/**************************************************************************
2 * Copyright(c) 1998-1999, 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: AliUEHist.cxx 20164 2007-08-14 15:31:50Z morsch $ */
17
18//
19//
20// encapsulate histogram and corrections for one underlying event histogram
21//
22//
23// Author: Jan Fiete Grosse-Oetringhaus, Sara Vallero
24
25#include "AliUEHist.h"
26#include "AliCFContainer.h"
27#include "THnSparse.h"
28#include "TMath.h"
29#include "TList.h"
30#include "TCollection.h"
31#include "TH1D.h"
32#include "TH2D.h"
33#include "TH3D.h"
34#include "AliLog.h"
35#include "TCanvas.h"
144bd037 36#include "TF1.h"
85bfac17 37#include "AliTHn.h"
a75aacd6 38
39ClassImp(AliUEHist)
40
41const Int_t AliUEHist::fgkCFSteps = 10;
42
43AliUEHist::AliUEHist(const char* reqHist) :
d1c75d06 44 TObject(),
a75aacd6 45 fkRegions(4),
46 fEventHist(0),
b1831bcb 47 fTrackHistEfficiency(0),
a75aacd6 48 fEtaMin(0),
49 fEtaMax(0),
50 fPtMin(0),
51 fPtMax(0),
2a910c25 52 fCentralityMin(0),
53 fCentralityMax(0),
85bfac17 54 fZVtxMin(0),
55 fZVtxMax(0),
144bd037 56 fContaminationEnhancement(0),
a75aacd6 57 fCombineMinMax(0),
c7245604 58 fCache(0),
59 fHistogramType(reqHist)
a75aacd6 60{
61 // Constructor
62
ff458f69 63 for (UInt_t i=0; i<fkRegions; i++)
a75aacd6 64 fTrackHist[i] = 0;
65
66 if (strlen(reqHist) == 0)
67 return;
68
df269636 69 AliLog::SetClassDebugLevel("AliCFContainer", -1);
e741fadd 70 AliLog::SetClassDebugLevel("AliCFGridSparse", -3);
df269636 71
a75aacd6 72 const char* title = "";
73
74 // track level
75 Int_t nTrackVars = 4; // eta vs pT vs pT,lead (vs delta phi) vs multiplicity
85bfac17 76 Int_t iTrackBin[6];
77 Double_t* trackBins[6];
78 const char* trackAxisTitle[6];
a75aacd6 79
80 // eta
81 iTrackBin[0] = 20;
82 Double_t etaBins[20+1];
83 for (Int_t i=0; i<=iTrackBin[0]; i++)
84 etaBins[i] = -1.0 + 0.1 * i;
85 trackBins[0] = etaBins;
86 trackAxisTitle[0] = "#eta";
87
e0331fd9 88 // delta eta
85bfac17 89 const Int_t kNDeltaEtaBins = 40;
e0331fd9 90 Double_t deltaEtaBins[kNDeltaEtaBins+1];
91 for (Int_t i=0; i<=kNDeltaEtaBins; i++)
85bfac17 92 deltaEtaBins[i] = -2.0 + 0.1 * i;
e0331fd9 93
a75aacd6 94 // pT
85bfac17 95 iTrackBin[1] = 22;
96 Double_t pTBins[] = {0.15, 0.2, 0.3, 0.4, 0.5, 0.75, 1.0, 1.5, 2.0, 2.5, 3.0, 3.5, 4.0, 4.5, 5.0, 6.0, 7.0, 8.0, 9.0, 10.0, 12.0, 15.0, 20.0};
a75aacd6 97 trackBins[1] = pTBins;
98 trackAxisTitle[1] = "p_{T} (GeV/c)";
99
100 // pT,lead binning 1
101 const Int_t kNLeadingpTBins = 100;
102 Double_t leadingpTBins[kNLeadingpTBins+1];
103 for (Int_t i=0; i<=kNLeadingpTBins; i++)
104 leadingpTBins[i] = 0.5 * i;
105
106 // pT,lead binning 2
85bfac17 107 const Int_t kNLeadingpTBins2 = 9;
108 Double_t leadingpTBins2[] = { 0.5, 1.0, 2.0, 3.0, 4.0, 6.0, 8.0, 10.0, 15.0, 20.0 };
a75aacd6 109
c7245604 110 // phi,lead; this binning starts at -pi/2 and is modulo 3
85bfac17 111 const Int_t kNLeadingPhiBins = 72;
a75aacd6 112 Double_t leadingPhiBins[kNLeadingPhiBins+1];
113 for (Int_t i=0; i<=kNLeadingPhiBins; i++)
c7245604 114 leadingPhiBins[i] = -TMath::Pi() / 2 + 1.0 / kNLeadingPhiBins * i * TMath::TwoPi();
a75aacd6 115
116 // multiplicity
117 const Int_t kNMultiplicityBins = 15;
118 Double_t multiplicityBins[kNMultiplicityBins+1];
119 for (Int_t i=0; i<=kNMultiplicityBins; i++)
120 multiplicityBins[i] = -0.5 + i;
121 multiplicityBins[kNMultiplicityBins] = 200;
bf58cbde 122
85bfac17 123 trackBins[3] = multiplicityBins;
124 iTrackBin[3] = kNMultiplicityBins;
125 trackAxisTitle[3] = "multiplicity";
126
c7245604 127 // centrality (in %)
85bfac17 128 const Int_t kNCentralityBins = 5 + 1 + 9;
129 Double_t centralityBins[] = { 0, 1, 2, 3, 4, 5, 10, 20, 30, 40, 50, 60, 70, 80, 90, 100.1 };
bf58cbde 130
b1831bcb 131 // particle species
132 const Int_t kNSpeciesBins = 4; // pi, K, p, rest
133 Double_t speciesBins[] = { -0.5, 0.5, 1.5, 2.5, 3.5 };
a75aacd6 134
85bfac17 135 // vtx-z axis
136 const Int_t kNVertexBins = 7;
137 Double_t vertexBins[] = { -7, -5, -3, -1, 1, 3, 5, 7 };
a75aacd6 138
139 // selection depending on requested histogram
140 Int_t axis = -1; // 0 = pT,lead, 1 = phi,lead
141 if (strcmp(reqHist, "NumberDensitypT") == 0)
142 {
143 axis = 0;
144 title = "d^{2}N_{ch}/d#phid#eta";
145 }
146 else if (strcmp(reqHist, "NumberDensityPhi") == 0)
147 {
148 axis = 1;
149 title = "d^{2}N_{ch}/d#phid#eta";
150 }
bf58cbde 151 else if (strcmp(reqHist, "NumberDensityPhiCentrality") == 0)
152 {
153 axis = 2;
154 title = "d^{2}N_{ch}/d#phid#eta";
155 }
a75aacd6 156 else if (strcmp(reqHist, "SumpT") == 0)
157 {
158 axis = 0;
159 title = "d^{2}#Sigma p_{T}/d#phid#eta";
160 }
161 else
162 AliFatal(Form("Invalid histogram requested: %s", reqHist));
163
ff458f69 164 UInt_t initRegions = fkRegions;
a75aacd6 165
eb88bdfe 166 Bool_t useVtxAxis = kFALSE;
167
a75aacd6 168 if (axis == 0)
169 {
170 trackBins[2] = leadingpTBins;
171 iTrackBin[2] = kNLeadingpTBins;
172 trackAxisTitle[2] = "leading p_{T} (GeV/c)";
173
174 }
175 else if (axis == 1)
176 {
177 nTrackVars = 5;
178 initRegions = 1;
179
180 iTrackBin[2] = kNLeadingpTBins2;
181 trackBins[2] = leadingpTBins2;
182 trackAxisTitle[2] = "leading p_{T} (GeV/c)";
183
184 iTrackBin[4] = kNLeadingPhiBins;
185 trackBins[4] = leadingPhiBins;
bf58cbde 186 trackAxisTitle[4] = "#Delta #phi w.r.t. leading track";
187 }
188 else if (axis == 2)
189 {
eb88bdfe 190 nTrackVars = 5;
bf58cbde 191 initRegions = 1;
192
e0331fd9 193 iTrackBin[0] = kNDeltaEtaBins;
194 trackBins[0] = deltaEtaBins;
195 trackAxisTitle[0] = "#Delta#eta";
196
bf58cbde 197 iTrackBin[2] = kNLeadingpTBins2;
198 trackBins[2] = leadingpTBins2;
199 trackAxisTitle[2] = "leading p_{T} (GeV/c)";
200
201 trackBins[3] = centralityBins;
202 iTrackBin[3] = kNCentralityBins;
203 trackAxisTitle[3] = "centrality";
204
205 iTrackBin[4] = kNLeadingPhiBins;
206 trackBins[4] = leadingPhiBins;
2a910c25 207 trackAxisTitle[4] = "#Delta#phi (rad.)";
85bfac17 208
eb88bdfe 209 if (useVtxAxis)
210 {
211 nTrackVars = 6;
212 iTrackBin[5] = kNVertexBins;
213 trackBins[5] = vertexBins;
214 trackAxisTitle[5] = "z-vtx (cm)";
215 }
a75aacd6 216 }
217
ff458f69 218 for (UInt_t i=0; i<initRegions; i++)
a75aacd6 219 {
85bfac17 220 if (strcmp(reqHist, "NumberDensityPhiCentrality") == 0)
221 fTrackHist[i] = new AliTHn(Form("fTrackHist_%d", i), title, fgkCFSteps, nTrackVars, iTrackBin);
222 else
223 fTrackHist[i] = new AliCFContainer(Form("fTrackHist_%d", i), title, fgkCFSteps, nTrackVars, iTrackBin);
a75aacd6 224
225 for (Int_t j=0; j<nTrackVars; j++)
226 {
227 fTrackHist[i]->SetBinLimits(j, trackBins[j]);
228 fTrackHist[i]->SetVarTitle(j, trackAxisTitle[j]);
229 }
230
231 SetStepNames(fTrackHist[i]);
232 }
233
85bfac17 234 // event level
235 Int_t nEventVars = 2;
236 Int_t iEventBin[3];
237
a75aacd6 238 // track 3rd and 4th axis --> event 1st and 2nd axis
85bfac17 239 iEventBin[0] = iTrackBin[2];
240 iEventBin[1] = iTrackBin[3];
241
242 // plus track 5th axis (in certain cases)
eb88bdfe 243 if (axis == 2 && useVtxAxis)
85bfac17 244 {
245 nEventVars = 3;
246 iEventBin[2] = iTrackBin[5];
247 }
248
249 fEventHist = new AliCFContainer("fEventHist", title, fgkCFSteps, nEventVars, iEventBin);
a75aacd6 250
251 fEventHist->SetBinLimits(0, trackBins[2]);
252 fEventHist->SetVarTitle(0, trackAxisTitle[2]);
253
254 fEventHist->SetBinLimits(1, trackBins[3]);
255 fEventHist->SetVarTitle(1, trackAxisTitle[3]);
256
eb88bdfe 257 if (axis == 2 && useVtxAxis)
85bfac17 258 {
259 fEventHist->SetBinLimits(2, trackBins[5]);
260 fEventHist->SetVarTitle(2, trackAxisTitle[5]);
261 }
262
a75aacd6 263 SetStepNames(fEventHist);
b1831bcb 264
265 iTrackBin[2] = kNSpeciesBins;
266
c7245604 267 fTrackHistEfficiency = new AliCFContainer("fTrackHistEfficiency", "Tracking efficiency", 3, 4, iTrackBin);
b1831bcb 268 fTrackHistEfficiency->SetBinLimits(0, trackBins[0]);
269 fTrackHistEfficiency->SetVarTitle(0, trackAxisTitle[0]);
270 fTrackHistEfficiency->SetBinLimits(1, trackBins[1]);
271 fTrackHistEfficiency->SetVarTitle(1, trackAxisTitle[1]);
272 fTrackHistEfficiency->SetBinLimits(2, speciesBins);
273 fTrackHistEfficiency->SetVarTitle(2, "particle species");
c7245604 274 fTrackHistEfficiency->SetBinLimits(3, trackBins[3]);
275 fTrackHistEfficiency->SetVarTitle(3, trackAxisTitle[3]);
a75aacd6 276}
277
d1c75d06 278//_____________________________________________________________________________
279AliUEHist::AliUEHist(const AliUEHist &c) :
280 TObject(),
281 fkRegions(4),
282 fEventHist(0),
b1831bcb 283 fTrackHistEfficiency(0),
d1c75d06 284 fEtaMin(0),
285 fEtaMax(0),
286 fPtMin(0),
287 fPtMax(0),
2a910c25 288 fCentralityMin(0),
289 fCentralityMax(0),
85bfac17 290 fZVtxMin(0),
291 fZVtxMax(0),
144bd037 292 fContaminationEnhancement(0),
d1c75d06 293 fCombineMinMax(0),
c7245604 294 fCache(0),
295 fHistogramType()
d1c75d06 296{
297 //
298 // AliUEHist copy constructor
299 //
300
301 ((AliUEHist &) c).Copy(*this);
302}
303
a75aacd6 304//____________________________________________________________________
305void AliUEHist::SetStepNames(AliCFContainer* container)
306{
307 // sets the names of the correction steps
308
309 for (Int_t i=0; i<fgkCFSteps; i++)
310 container->SetStepTitle(i, GetStepTitle((CFStep) i));
311}
312
313//____________________________________________________________________
314AliUEHist::~AliUEHist()
315{
316 // Destructor
317
ff458f69 318 for (UInt_t i=0; i<fkRegions; i++)
a75aacd6 319 {
320 if (fTrackHist[i])
321 {
322 delete fTrackHist[i];
323 fTrackHist[i] = 0;
324 }
325 }
326
327 if (fEventHist)
328 {
329 delete fEventHist;
330 fEventHist = 0;
331 }
332
b1831bcb 333 if (fTrackHistEfficiency)
334 {
335 delete fTrackHistEfficiency;
336 fTrackHistEfficiency = 0;
337 }
338
a75aacd6 339 if (fCache)
340 {
341 delete fCache;
342 fCache = 0;
343 }
344}
345
346//____________________________________________________________________
347AliUEHist &AliUEHist::operator=(const AliUEHist &c)
348{
349 // assigment operator
350
351 if (this != &c)
352 ((AliUEHist &) c).Copy(*this);
353
354 return *this;
355}
356
357//____________________________________________________________________
358void AliUEHist::Copy(TObject& c) const
359{
360 // copy function
361
362 AliUEHist& target = (AliUEHist &) c;
363
ff458f69 364 for (UInt_t i=0; i<fkRegions; i++)
a75aacd6 365 if (fTrackHist[i])
366 target.fTrackHist[i] = dynamic_cast<AliCFContainer*> (fTrackHist[i]->Clone());
367
368 if (fEventHist)
369 target.fEventHist = dynamic_cast<AliCFContainer*> (fEventHist->Clone());
b1831bcb 370
371 if (fTrackHistEfficiency)
372 target.fTrackHistEfficiency = dynamic_cast<AliCFContainer*> (fTrackHistEfficiency->Clone());
c7245604 373
374 target.fEtaMin = fEtaMin;
375 target.fEtaMax = fEtaMax;
376 target.fPtMin = fPtMin;
377 target.fPtMax = fPtMax;
2a910c25 378 target.fCentralityMin = fCentralityMin;
379 target.fCentralityMax = fCentralityMax;
85bfac17 380 target.fZVtxMin = fZVtxMin;
381 target.fZVtxMax = fZVtxMax;
c7245604 382
383 if (fContaminationEnhancement)
384 target.fContaminationEnhancement = dynamic_cast<TH1F*> (fContaminationEnhancement->Clone());
385
386 target.fCombineMinMax = fCombineMinMax;
387 target.fHistogramType = fHistogramType;
a75aacd6 388}
389
390//____________________________________________________________________
391Long64_t AliUEHist::Merge(TCollection* list)
392{
393 // Merge a list of AliUEHist objects with this (needed for
394 // PROOF).
395 // Returns the number of merged objects (including this).
396
397 if (!list)
398 return 0;
399
400 if (list->IsEmpty())
401 return 1;
402
403 TIterator* iter = list->MakeIterator();
404 TObject* obj;
405
406 // collections of objects
ff458f69 407 const UInt_t kMaxLists = fkRegions+2;
a75aacd6 408 TList** lists = new TList*[kMaxLists];
409
ff458f69 410 for (UInt_t i=0; i<kMaxLists; i++)
a75aacd6 411 lists[i] = new TList;
412
413 Int_t count = 0;
414 while ((obj = iter->Next())) {
415
416 AliUEHist* entry = dynamic_cast<AliUEHist*> (obj);
417 if (entry == 0)
418 continue;
419
ff458f69 420 for (UInt_t i=0; i<fkRegions; i++)
a75aacd6 421 if (entry->fTrackHist[i])
422 lists[i]->Add(entry->fTrackHist[i]);
423
424 lists[fkRegions]->Add(entry->fEventHist);
b1831bcb 425 lists[fkRegions+1]->Add(entry->fTrackHistEfficiency);
a75aacd6 426
427 count++;
428 }
ff458f69 429 for (UInt_t i=0; i<fkRegions; i++)
a75aacd6 430 if (fTrackHist[i])
431 fTrackHist[i]->Merge(lists[i]);
432
433 fEventHist->Merge(lists[fkRegions]);
b1831bcb 434 fTrackHistEfficiency->Merge(lists[fkRegions+1]);
a75aacd6 435
ff458f69 436 for (UInt_t i=0; i<kMaxLists; i++)
a75aacd6 437 delete lists[i];
438
439 delete[] lists;
440
441 return count+1;
442}
443
444//____________________________________________________________________
445void AliUEHist::SetBinLimits(AliCFGridSparse* grid)
446{
447 // sets the bin limits in eta and pT defined by fEtaMin/Max, fPtMin/Max
448
449 if (fEtaMax > fEtaMin)
450 grid->SetRangeUser(0, fEtaMin, fEtaMax);
451 if (fPtMax > fPtMin)
452 grid->SetRangeUser(1, fPtMin, fPtMax);
453}
454
455//____________________________________________________________________
456void AliUEHist::ResetBinLimits(AliCFGridSparse* grid)
457{
458 // resets all bin limits
459
460 for (Int_t i=0; i<grid->GetNVar(); i++)
144bd037 461 if (grid->GetGrid()->GetAxis(i)->TestBit(TAxis::kAxisRange))
a75aacd6 462 grid->SetRangeUser(i, 0, -1);
463}
464
144bd037 465//____________________________________________________________________
466void AliUEHist::CountEmptyBins(AliUEHist::CFStep step, Float_t ptLeadMin, Float_t ptLeadMax)
467{
468 // prints the number of empty bins in the track end event histograms in the given step
469
470 Int_t binBegin[4];
471 Int_t binEnd[4];
472
473 for (Int_t i=0; i<4; i++)
474 {
475 binBegin[i] = 1;
476 binEnd[i] = fTrackHist[0]->GetNBins(i);
477 }
478
479 if (fEtaMax > fEtaMin)
480 {
481 binBegin[0] = fTrackHist[0]->GetGrid(step)->GetGrid()->GetAxis(0)->FindBin(fEtaMin);
482 binEnd[0] = fTrackHist[0]->GetGrid(step)->GetGrid()->GetAxis(0)->FindBin(fEtaMax);
483 }
484
485 if (fPtMax > fPtMin)
486 {
487 binBegin[1] = fTrackHist[0]->GetGrid(step)->GetGrid()->GetAxis(1)->FindBin(fPtMin);
488 binEnd[1] = fTrackHist[0]->GetGrid(step)->GetGrid()->GetAxis(1)->FindBin(fPtMax);
489 }
490
491 if (ptLeadMax > ptLeadMin)
492 {
493 binBegin[2] = fTrackHist[0]->GetGrid(step)->GetGrid()->GetAxis(2)->FindBin(ptLeadMin);
494 binEnd[2] = fTrackHist[0]->GetGrid(step)->GetGrid()->GetAxis(2)->FindBin(ptLeadMax);
495 }
496
497 // start from multiplicity 1
498 binBegin[3] = fTrackHist[0]->GetGrid(step)->GetGrid()->GetAxis(3)->FindBin(1);
499
ff458f69 500 for (UInt_t region=0; region<fkRegions; region++)
144bd037 501 {
502 Int_t total = 0;
503 Int_t count = 0;
504 Int_t vars[4];
505
506 for (Int_t i=0; i<4; i++)
507 vars[i] = binBegin[i];
508
509 AliCFGridSparse* grid = fTrackHist[region]->GetGrid(step);
510 while (1)
511 {
512 if (grid->GetElement(vars) == 0)
513 {
514 Printf("Empty bin at eta=%.2f pt=%.2f pt_lead=%.2f mult=%.1f",
515 grid->GetBinCenter(0, vars[0]),
516 grid->GetBinCenter(1, vars[1]),
517 grid->GetBinCenter(2, vars[2]),
518 grid->GetBinCenter(3, vars[3])
519 );
520 count++;
521 }
522
523 vars[3]++;
524 for (Int_t i=3; i>0; i--)
525 {
526 if (vars[i] == binEnd[i]+1)
527 {
528 vars[i] = binBegin[i];
529 vars[i-1]++;
530 }
531 }
532
533 if (vars[0] == binEnd[0]+1)
534 break;
535 total++;
536 }
537
538 Printf("Region %s has %d empty bins (out of %d bins)", GetRegionTitle((Region) region), count, total);
539 }
540}
541
a75aacd6 542//____________________________________________________________________
85bfac17 543TH1* AliUEHist::GetUEHist(AliUEHist::CFStep step, AliUEHist::Region region, Float_t ptLeadMin, Float_t ptLeadMax, Int_t multBinBegin, Int_t multBinEnd, Int_t twoD, Bool_t etaNorm)
a75aacd6 544{
545 // Extracts the UE histogram at the given step and in the given region by projection and dividing tracks by events
546 //
547 // ptLeadMin, ptLeadMax: Only meaningful for vs. delta phi plot (third axis is ptLead)
548 // Histogram has to be deleted by the caller of the function
2a910c25 549 //
550 // twoD: 0: 1D histogram as function of phi
551 // 1: 2D histogram, deltaphi, deltaeta
552 // 10: 1D histogram, within |deltaeta| < 0.8
553 // 11: 1D histogram, within 0.8 < |deltaeta| < 1.6
85bfac17 554 //
555 // etaNorm: if kTRUE (default), the distributions are divided by the area in delta eta
a75aacd6 556
557 // unzoom all axes
558 ResetBinLimits(fTrackHist[region]->GetGrid(step));
559 ResetBinLimits(fEventHist->GetGrid(step));
560
561 SetBinLimits(fTrackHist[region]->GetGrid(step));
85bfac17 562
563 // z vtx
564 if (fZVtxMax > fZVtxMin)
565 {
566 Printf("Using z-vtx range %f --> %f", fZVtxMin, fZVtxMax);
567 fTrackHist[region]->GetGrid(step)->GetGrid()->GetAxis(5)->SetRangeUser(fZVtxMin, fZVtxMax);
568 fEventHist->GetGrid(step)->GetGrid()->GetAxis(2)->SetRangeUser(fZVtxMin, fZVtxMax);
569 }
a75aacd6 570
571 TH1D* tracks = 0;
572
573 if (ptLeadMin < 0)
574 {
575 tracks = fTrackHist[region]->ShowProjection(2, step);
576 tracks->GetYaxis()->SetTitle(fTrackHist[region]->GetTitle());
577 if (fCombineMinMax && region == kMin)
578 {
579 ResetBinLimits(fTrackHist[kMax]->GetGrid(step));
580 SetBinLimits(fTrackHist[kMax]->GetGrid(step));
581
582 TH1D* tracks2 = fTrackHist[kMax]->ShowProjection(2, step);
583 tracks->Add(tracks2);
584
585 ResetBinLimits(fTrackHist[kMax]->GetGrid(step));
586 }
587
588 // normalize to get a density (deta dphi)
589 TAxis* axis = fTrackHist[region]->GetGrid(step)->GetAxis(0);
590 Float_t phiRegion = TMath::TwoPi() / 3;
591 if (!fCombineMinMax && region == kMin)
592 phiRegion /= 2;
85bfac17 593 Float_t normalization = phiRegion;
594 if (etaNorm)
595 normalization *= (axis->GetBinUpEdge(axis->GetLast()) - axis->GetBinLowEdge(axis->GetFirst()));
a75aacd6 596 //Printf("Normalization: %f", normalization);
597 tracks->Scale(1.0 / normalization);
598
599 TH1D* events = fEventHist->ShowProjection(0, step);
600 tracks->Divide(events);
601 }
602 else
603 {
2a910c25 604 if (multBinEnd >= multBinBegin)
ff458f69 605 {
e0331fd9 606 Printf("Using multiplicity range %d --> %d", multBinBegin, multBinEnd);
ff458f69 607 fTrackHist[region]->GetGrid(step)->GetGrid()->GetAxis(3)->SetRange(multBinBegin, multBinEnd);
608 fEventHist->GetGrid(step)->GetGrid()->GetAxis(1)->SetRange(multBinBegin, multBinEnd);
609 }
bf58cbde 610
e741fadd 611 Int_t firstBin = fTrackHist[region]->GetAxis(2, step)->FindBin(ptLeadMin);
612 Int_t lastBin = fTrackHist[region]->GetAxis(2, step)->FindBin(ptLeadMax);
a75aacd6 613
c7245604 614 Printf("Using leading pT range %d --> %d", firstBin, lastBin);
bf58cbde 615
c7245604 616 fTrackHist[region]->GetGrid(step)->GetGrid()->GetAxis(2)->SetRange(firstBin, lastBin);
617
618 if (twoD == 0)
619 tracks = (TH1D*) fTrackHist[region]->GetGrid(step)->Project(4);
620 else
2a910c25 621 tracks = (TH1D*) fTrackHist[region]->GetGrid(step)->Project(4, 0);
622
c7245604 623 Printf("Calculated histogram --> %f tracks", tracks->Integral());
624 fTrackHist[region]->GetGrid(step)->SetRangeUser(2, 0, -1);
625
2a910c25 626 if (twoD == 10 || twoD == 11)
627 {
628 Float_t etaLimit = 0.8;
629 if (twoD == 10)
630 {
631 tracks = (TH1D*) ((TH2*) tracks)->ProjectionX("proj", tracks->GetYaxis()->FindBin(-etaLimit + 0.01), tracks->GetYaxis()->FindBin(etaLimit - 0.01))->Clone();
632
633 // TODO calculate acc with 2 * (deta - 0.5 * deta*deta / 1.6)
634 tracks->Scale(1. / 0.75);
635 }
636 else if (twoD == 11)
637 {
638 TH1D* tracksTmp1 = (TH1D*) ((TH2*) tracks)->ProjectionX("proj1", tracks->GetYaxis()->FindBin(-etaLimit * 2 + 0.01), tracks->GetYaxis()->FindBin(-etaLimit - 0.01))->Clone();
639 TH1D* tracksTmp2 = ((TH2*) tracks)->ProjectionX("proj2", tracks->GetYaxis()->FindBin(etaLimit + 0.01), tracks->GetYaxis()->FindBin(2 * etaLimit - 0.01));
640
641 tracksTmp1->Add(tracksTmp2);
642
643 delete tracks;
644 tracks = tracksTmp1;
645 delete tracksTmp2;
646
647 tracks->Scale(1. / 0.25);
648 }
649 }
650
c7245604 651 // normalize to get a density (deta dphi)
2a910c25 652 // TODO normalization may be off for 2d histogram
c7245604 653 Float_t normalization = fTrackHist[region]->GetGrid(step)->GetAxis(4)->GetBinWidth(1);
85bfac17 654
655 if (etaNorm)
c7245604 656 {
85bfac17 657 TAxis* axis = fTrackHist[region]->GetGrid(step)->GetAxis(0);
658 if (strcmp(axis->GetTitle(), "#eta") == 0)
659 {
660 Printf("Normalizing using eta-axis range");
661 normalization *= axis->GetBinUpEdge(axis->GetLast()) - axis->GetBinLowEdge(axis->GetFirst());
662 }
663 else
664 {
665 Printf("Normalizing assuming accepted range of |eta| < 0.8");
666 normalization *= 0.8 * 2;
667 }
e741fadd 668 }
bf58cbde 669
c7245604 670 //Printf("Normalization: %f", normalization);
671 tracks->Scale(1.0 / normalization);
672
2a910c25 673 // NOTE fEventHist contains the number of events for the underlying event analysis and the number of trigger particles for the azimuthal correlation analysis. In the latter case the naming is therefore somewhat misleading!
c7245604 674 TH1D* events = fEventHist->ShowProjection(0, step);
675 Int_t nEvents = (Int_t) events->Integral(firstBin, lastBin);
676 Printf("Calculated histogram --> %d events", nEvents);
2a910c25 677
678 if (nEvents > 0)
679 tracks->Scale(1.0 / nEvents);
c7245604 680
bf58cbde 681 delete events;
a75aacd6 682 }
683
684 ResetBinLimits(fTrackHist[region]->GetGrid(step));
bf58cbde 685 ResetBinLimits(fEventHist->GetGrid(step));
a75aacd6 686
687 return tracks;
688}
689
c7245604 690//____________________________________________________________________
691TH1* AliUEHist::GetPtHist(CFStep step, Region region, Float_t ptLeadMin, Float_t ptLeadMax, Int_t multBinBegin, Int_t multBinEnd, Float_t phiMin, Float_t phiMax, Float_t etaMin, Float_t etaMax, Bool_t skipPhiNormalization)
692{
693 // returns a histogram projected to pT,assoc with the provided cuts
694
695 // unzoom all axes
696 ResetBinLimits(fTrackHist[region]->GetGrid(step));
697 ResetBinLimits(fEventHist->GetGrid(step));
698
699 TH1D* tracks = 0;
700
701 // the efficiency to have find an event depends on leading pT and this is not corrected for because anyway per bin we calculate tracks over events
702 // therefore the number density must be calculated here per leading pT bin and then summed
703
704 if (multBinEnd > multBinBegin)
705 Printf("Using multiplicity range %d --> %d", multBinBegin, multBinEnd);
706 fTrackHist[region]->GetGrid(step)->GetGrid()->GetAxis(3)->SetRange(multBinBegin, multBinEnd);
707 fEventHist->GetGrid(step)->GetGrid()->GetAxis(1)->SetRange(multBinBegin, multBinEnd);
708
709 fTrackHist[region]->GetGrid(step)->GetGrid()->GetAxis(0)->SetRangeUser(etaMin, etaMax);
710 fTrackHist[region]->GetGrid(step)->GetGrid()->GetAxis(4)->SetRangeUser(phiMin, phiMax);
711
712 // get real phi cuts due to binning
713 Float_t phiMinReal = fTrackHist[region]->GetGrid(step)->GetGrid()->GetAxis(4)->GetBinLowEdge(fTrackHist[region]->GetGrid(step)->GetGrid()->GetAxis(4)->GetFirst());
714 Float_t phiMaxReal = fTrackHist[region]->GetGrid(step)->GetGrid()->GetAxis(4)->GetBinUpEdge(fTrackHist[region]->GetGrid(step)->GetGrid()->GetAxis(4)->GetLast());
715 Printf("phi min = %.2f and max = %.2f requested; due to binning range will be from %.2f to %.2f, i.e. a %.0f%% larger window", phiMin, phiMax, phiMinReal, phiMaxReal, (phiMaxReal - phiMinReal) / (phiMax - phiMin) * 100 - 100);
716
717 Int_t firstBin = fTrackHist[region]->GetAxis(2, step)->FindBin(ptLeadMin);
718 Int_t lastBin = fTrackHist[region]->GetAxis(2, step)->FindBin(ptLeadMax);
719
720 TH1D* events = fEventHist->ShowProjection(0, step);
721
722 for (Int_t bin=firstBin; bin<=lastBin; bin++)
723 {
724 fTrackHist[region]->GetGrid(step)->GetGrid()->GetAxis(2)->SetRange(bin, bin);
725
726 // project to pT,assoc
727 TH1D* tracksTmp = (TH1D*) fTrackHist[region]->GetGrid(step)->Project(1);
728
729 Printf("Calculated histogram in bin %d --> %f tracks", bin, tracksTmp->Integral());
730 fTrackHist[region]->GetGrid(step)->SetRangeUser(2, 0, -1);
731
732 // normalize to get a density (deta dphi)
733 Float_t normalization = 1;
734 TAxis* axis = fTrackHist[region]->GetGrid(step)->GetAxis(0);
735 if (strcmp(axis->GetTitle(), "#eta") == 0)
736 {
737 Printf("Normalizing using eta-axis range");
738 normalization *= axis->GetBinUpEdge(axis->GetLast()) - axis->GetBinLowEdge(axis->GetFirst());
739 }
740 else
741 {
742 Printf("Normalizating assuming accepted range of |eta| < 0.8");
743 normalization *= 0.8 * 2;
744 }
745
746 // dphi
747 if (!skipPhiNormalization)
748 normalization *= phiMaxReal - phiMinReal;
749
750 //Printf("Normalization: %f", normalization);
751 tracksTmp->Scale(1.0 / normalization);
752
753 // and now dpT (bins have different width)
754 for (Int_t i=1; i<=tracksTmp->GetNbinsX(); i++)
755 {
756 tracksTmp->SetBinContent(i, tracksTmp->GetBinContent(i) / tracksTmp->GetXaxis()->GetBinWidth(i));
757 tracksTmp->SetBinError (i, tracksTmp->GetBinError(i) / tracksTmp->GetXaxis()->GetBinWidth(i));
758 }
759
760 Int_t nEvents = (Int_t) events->GetBinContent(bin);
761 if (nEvents > 0)
762 tracksTmp->Scale(1.0 / nEvents);
763 Printf("Calculated histogram in bin %d --> %d events", bin, nEvents);
764
765 if (!tracks)
766 tracks = tracksTmp;
767 else
768 {
769 tracks->Add(tracksTmp);
770 delete tracksTmp;
771 }
772 }
773
774 delete events;
775
776 ResetBinLimits(fTrackHist[region]->GetGrid(step));
777 ResetBinLimits(fEventHist->GetGrid(step));
778
779 return tracks;
780}
781
a75aacd6 782//____________________________________________________________________
783void AliUEHist::CorrectTracks(CFStep step1, CFStep step2, TH1* trackCorrection, Int_t var1, Int_t var2)
784{
785 // corrects from step1 to step2 by multiplying the tracks with trackCorrection
786 // trackCorrection can be a function of eta (var1 == 0), pT (var1 == 1), leading pT (var1 == 2), multiplicity (var1 == 3), delta phi (var1 == 4)
787 // if var2 >= 0 a two dimension correction is assumed in trackCorrection
788 //
789 // if trackCorrection is 0, just copies content from step1 to step2
790
ff458f69 791 for (UInt_t region=0; region<fkRegions; region++)
144bd037 792 CorrectTracks(step1, step2, region, trackCorrection, var1, var2);
793}
794
795//____________________________________________________________________
796void AliUEHist::CorrectTracks(CFStep step1, CFStep step2, Int_t region, TH1* trackCorrection, Int_t var1, Int_t var2)
797{
798 //
799 // see documentation of CorrectTracks above
800 //
801
802 if (!fTrackHist[region])
803 return;
5a53c6f2 804
144bd037 805 THnSparse* grid = fTrackHist[region]->GetGrid(step1)->GetGrid();
806 THnSparse* target = fTrackHist[region]->GetGrid(step2)->GetGrid();
807
808 // clear target histogram
809 target->Reset();
810
811 if (trackCorrection != 0)
a75aacd6 812 {
144bd037 813 if (grid->GetAxis(var1)->GetNbins() != trackCorrection->GetNbinsX())
814 AliFatal(Form("Invalid binning (var1): %d %d", grid->GetAxis(var1)->GetNbins(), trackCorrection->GetNbinsX()));
a75aacd6 815
144bd037 816 if (var2 >= 0 && grid->GetAxis(var2)->GetNbins() != trackCorrection->GetNbinsY())
817 AliFatal(Form("Invalid binning (var2): %d %d", grid->GetAxis(var2)->GetNbins(), trackCorrection->GetNbinsY()));
818 }
819
820 // optimized implementation
821 for (Int_t binIdx = 0; binIdx < grid->GetNbins(); binIdx++)
822 {
823 Int_t bins[5];
824 Double_t value = grid->GetBinContent(binIdx, bins);
825 Double_t error = grid->GetBinError(binIdx);
a75aacd6 826
827 if (trackCorrection != 0)
828 {
144bd037 829 if (var2 < 0)
a75aacd6 830 {
144bd037 831 value *= trackCorrection->GetBinContent(bins[var1]);
832 error *= trackCorrection->GetBinContent(bins[var1]);
833 }
834 else
835 {
836 value *= trackCorrection->GetBinContent(bins[var1], bins[var2]);
837 error *= trackCorrection->GetBinContent(bins[var1], bins[var2]);
a75aacd6 838 }
a75aacd6 839 }
144bd037 840
841 target->SetBinContent(bins, value);
842 target->SetBinError(bins, error);
a75aacd6 843 }
5a53c6f2 844
845 Printf("AliUEHist::CorrectTracks: Corrected from %f to %f entries. Correction histogram: %f entries (integral: %f)", grid->GetEntries(), target->GetEntries(), (trackCorrection) ? trackCorrection->GetEntries() : -1.0, (trackCorrection) ? trackCorrection->Integral() : -1.0);
a75aacd6 846}
847
848//____________________________________________________________________
2a910c25 849void AliUEHist::CorrectEvents(CFStep step1, CFStep step2, TH1* eventCorrection, Int_t var1, Int_t var2)
a75aacd6 850{
851 // corrects from step1 to step2 by multiplying the events with eventCorrection
852 // eventCorrection is as function of leading pT (var == 0) or multiplicity (var == 1)
853 //
854 // if eventCorrection is 0, just copies content from step1 to step2
855
856 AliCFGridSparse* grid = fEventHist->GetGrid(step1);
857 AliCFGridSparse* target = fEventHist->GetGrid(step2);
858
144bd037 859 // clear target histogram
860 target->GetGrid()->Reset();
861
2a910c25 862 if (eventCorrection != 0 && grid->GetNBins(var1) != eventCorrection->GetNbinsX())
863 AliFatal(Form("Invalid binning: %d %d", grid->GetNBins(var1), eventCorrection->GetNbinsX()));
864
865 if (eventCorrection != 0 && var2 != -1 && grid->GetNBins(var2) != eventCorrection->GetNbinsY())
866 AliFatal(Form("Invalid binning: %d %d", grid->GetNBins(var2), eventCorrection->GetNbinsY()));
a75aacd6 867
868 Int_t bins[2];
869 for (Int_t x = 1; x <= grid->GetNBins(0); x++)
870 {
871 bins[0] = x;
872 for (Int_t y = 1; y <= grid->GetNBins(1); y++)
873 {
874 bins[1] = y;
875
876 Double_t value = grid->GetElement(bins);
877 if (value != 0)
878 {
879 Double_t error = grid->GetElementError(bins);
880
881 if (eventCorrection != 0)
882 {
2a910c25 883 if (var2 == -1)
884 {
885 value *= eventCorrection->GetBinContent(bins[var1]);
886 error *= eventCorrection->GetBinContent(bins[var1]);
887 }
888 else
889 {
890 value *= eventCorrection->GetBinContent(bins[var1], bins[var2]);
891 error *= eventCorrection->GetBinContent(bins[var1], bins[var2]);
892 }
a75aacd6 893 }
894
895 target->SetElement(bins, value);
896 target->SetElementError(bins, error);
897 }
898 }
899 }
5a53c6f2 900
901 Printf("AliUEHist::CorrectEvents: Corrected from %f to %f entries. Correction histogram: %f entries (integral: %f)", grid->GetEntries(), target->GetEntries(), (eventCorrection) ? eventCorrection->GetEntries() : -1.0, (eventCorrection) ? eventCorrection->Integral() : -1.0);
a75aacd6 902}
903
904//____________________________________________________________________
905void AliUEHist::Correct(AliUEHist* corrections)
906{
907 // applies the given corrections to extract from the step kCFStepReconstructed all previous steps
908 //
909 // in this object the data is expected in the step kCFStepReconstructed
910
c7245604 911 if (fHistogramType.Length() == 0)
912 {
2a910c25 913 Printf("W-AliUEHist::Correct: fHistogramType not defined. Guessing histogram type...");
914 if (fTrackHist[kToward]->GetNVar() < 5)
915 {
916 if (strcmp(fTrackHist[kToward]->GetTitle(), "d^{2}N_{ch}/d#phid#eta") == 0)
917 fHistogramType = "NumberDensitypT";
918 else if (strcmp(fTrackHist[kToward]->GetTitle(), "d^{2}#Sigma p_{T}/d#phid#eta") == 0)
919 fHistogramType = "SumpT";
920 }
921 else if (fTrackHist[kToward]->GetNVar() == 5)
922 {
923 if (strcmp(fTrackHist[kToward]->GetGrid(0)->GetGrid()->GetAxis(3)->GetTitle(), "multiplicity") == 0)
924 fHistogramType = "NumberDensityPhi";
925 else if (strcmp(fTrackHist[kToward]->GetGrid(0)->GetGrid()->GetAxis(3)->GetTitle(), "centrality") == 0)
926 fHistogramType = "NumberDensityPhiCentrality";
927 }
928
929 if (fHistogramType.Length() == 0)
930 AliFatal("Cannot figure out histogram type. Try setting it manually...");
c7245604 931 }
a75aacd6 932
c7245604 933 Printf("AliUEHist::Correct: Correcting %s...", fHistogramType.Data());
934
2a910c25 935 if (strcmp(fHistogramType, "NumberDensitypT") == 0 || strcmp(fHistogramType, "NumberDensityPhi") == 0 || strcmp(fHistogramType, "SumpT") == 0) // the last is for backward compatibilty
144bd037 936 {
c7245604 937 // ---- track level
938
939 // bias due to migration in leading pT (because the leading particle is not reconstructed, and the subleading is used)
940 // extracted as function of leading pT
941 Bool_t biasFromMC = kFALSE;
ada1a03f 942 const char* projAxis = "z";
943 Int_t secondBin = -1;
944
2a910c25 945 if (strcmp(fHistogramType, "NumberDensityPhi") == 0)
ada1a03f 946 {
947 projAxis = "yz";
948 secondBin = 4;
949 }
950
ff458f69 951 for (UInt_t region = 0; region < fkRegions; region++)
144bd037 952 {
c7245604 953 if (!fTrackHist[region])
954 continue;
955
956 TH1* leadingBiasTracks = 0;
957 if (biasFromMC)
958 {
959 leadingBiasTracks = (TH1*) corrections->GetBias(kCFStepReconstructed, kCFStepTracked, region, projAxis, 0, -1, 1); // from MC
960 Printf("WARNING: Using MC bias correction");
961 }
962 else
963 leadingBiasTracks = (TH1*) GetBias(kCFStepBiasStudy, kCFStepReconstructed, region, projAxis, 0, -1, 1); // from data
964
965 CorrectTracks(kCFStepReconstructed, kCFStepTracked, region, leadingBiasTracks, 2, secondBin);
966 if (region == kMin && fCombineMinMax)
967 {
968 CorrectTracks(kCFStepReconstructed, kCFStepTracked, kMax, leadingBiasTracks, 2, secondBin);
969 delete leadingBiasTracks;
970 break;
971 }
972 delete leadingBiasTracks;
973 }
974
975 TH1* leadingBiasEvents = 0;
976 if (biasFromMC)
977 leadingBiasEvents = (TH1*) corrections->GetBias(kCFStepReconstructed, kCFStepTracked, kToward, projAxis, 0, -1, 2); // from MC
978 else
979 leadingBiasEvents = (TH1*) GetBias(kCFStepBiasStudy, kCFStepReconstructed, kToward, projAxis, 0, -1, 2); // from data
980
981 //new TCanvas; leadingBiasEvents->DrawCopy();
982 CorrectEvents(kCFStepReconstructed, kCFStepTracked, leadingBiasEvents, 0);
983 delete leadingBiasEvents;
984
985 // --- contamination correction ---
986
987 TH2D* contamination = corrections->GetTrackingContamination();
988 if (corrections->fContaminationEnhancement)
989 {
990 Printf("Applying contamination enhancement");
991
992 for (Int_t x=1; x<=contamination->GetNbinsX(); x++)
993 for (Int_t y=1; y<=contamination->GetNbinsX(); y++)
994 contamination->SetBinContent(x, y, contamination->GetBinContent(x, y) * corrections->fContaminationEnhancement->GetBinContent(corrections->fContaminationEnhancement->GetXaxis()->FindBin(contamination->GetYaxis()->GetBinCenter(y))));
995 }
996 CorrectTracks(kCFStepTracked, kCFStepTrackedOnlyPrim, contamination, 0, 1);
997 CorrectEvents(kCFStepTracked, kCFStepTrackedOnlyPrim, 0, 0);
998 delete contamination;
999
1000 // --- efficiency correction ---
1001 // correct single-particle efficiency for associated particles
1002 // in addition correct for efficiency on trigger particles (tracks AND events)
1003
1004 TH1* efficiencyCorrection = corrections->GetTrackingEfficiencyCorrection();
1005 // use kCFStepVertex as a temporary step (will be overwritten later anyway)
1006 CorrectTracks(kCFStepTrackedOnlyPrim, kCFStepVertex, efficiencyCorrection, 0, 1);
1007 delete efficiencyCorrection;
1008
1009 // correct pT,T
1010 efficiencyCorrection = corrections->GetTrackEfficiency(kCFStepTrackedOnlyPrim, kCFStepAnaTopology, 1, -1, 2);
1011 CorrectEvents(kCFStepTrackedOnlyPrim, kCFStepAnaTopology, efficiencyCorrection, 0);
1012 CorrectTracks(kCFStepVertex, kCFStepAnaTopology, efficiencyCorrection, 2);
1013 delete efficiencyCorrection;
1014
1015 // copy
1016 CorrectTracks(kCFStepAnaTopology, kCFStepVertex, 0, -1);
1017 CorrectEvents(kCFStepAnaTopology, kCFStepVertex, 0, 0);
1018
1019 // vertex correction on the level of events as function of multiplicity, weighting tracks and events with the same factor
1020 // practically independent of low pT cut
1021 TH1D* vertexCorrection = (TH1D*) corrections->GetEventEfficiency(kCFStepVertex, kCFStepTriggered, 1);
1022
1023 // convert stage from true multiplicity to observed multiplicity by simple conversion factor
1024 TH1D* vertexCorrectionObs = (TH1D*) vertexCorrection->Clone("vertexCorrection2");
1025 vertexCorrectionObs->Reset();
1026
1027 TF1* func = new TF1("func", "[1]+[0]/(x-[2])");
1028 // some defaults
1029 func->SetParameters(0.1, 1, -0.7);
1030 vertexCorrection->Fit(func, "0I", "", 0, 3);
1031 for (Int_t i=1; i<=vertexCorrectionObs->GetNbinsX(); i++)
1032 {
1033 Float_t xPos = 1.0 / 0.77 * vertexCorrectionObs->GetXaxis()->GetBinCenter(i);
1034 if (xPos < 3)
1035 vertexCorrectionObs->SetBinContent(i, func->Eval(xPos));
1036 else
1037 vertexCorrectionObs->SetBinContent(i, vertexCorrection->Interpolate(xPos));
144bd037 1038 }
a75aacd6 1039
c7245604 1040 #if 0
1041 new TCanvas;
1042 vertexCorrection->DrawCopy();
1043 vertexCorrectionObs->SetLineColor(2);
1044 vertexCorrectionObs->DrawCopy("same");
1045 func->SetRange(0, 4);
1046 func->DrawClone("same");
1047 #endif
144bd037 1048
c7245604 1049 CorrectTracks(kCFStepVertex, kCFStepTriggered, vertexCorrectionObs, 3);
1050 CorrectEvents(kCFStepVertex, kCFStepTriggered, vertexCorrectionObs, 1);
1051 delete vertexCorrectionObs;
1052 delete vertexCorrection;
1053 delete func;
1054
1055 // copy
1056 CorrectTracks(kCFStepTriggered, kCFStepAll, 0, -1);
1057 CorrectEvents(kCFStepTriggered, kCFStepAll, 0, 0);
144bd037 1058 }
c7245604 1059 else if (strcmp(fHistogramType, "NumberDensityPhiCentrality") == 0)
144bd037 1060 {
c7245604 1061 // copy
1062 CorrectTracks(kCFStepReconstructed, kCFStepTracked, 0, -1);
1063 CorrectEvents(kCFStepReconstructed, kCFStepTracked, 0, -1);
1064
2a910c25 1065 // Dont use eta in the following, because it is a Delta-eta axis
1066
c7245604 1067 // contamination correction
1068 // correct single-particle contamination for associated particles
2a910c25 1069
1070 TH1* contamination = corrections->GetTrackingContamination(1);
1071
1072 if (1)
1073 {
1074 Printf("Applying contamination enhancement");
1075
1076 for (Int_t bin = 1; bin <= contamination->GetNbinsX(); bin++)
1077 {
1078 printf("%f", contamination->GetBinContent(bin));
1079 if (contamination->GetBinContent(bin) > 0)
1080 contamination->SetBinContent(bin, 1.0 + 1.1 * (contamination->GetBinContent(bin) - 1.0));
1081 printf(" --> %f\n", contamination->GetBinContent(bin));
1082 }
1083 }
1084
1085 CorrectTracks(kCFStepTracked, kCFStepTrackedOnlyPrim, contamination, 1);
c7245604 1086 delete contamination;
1087
2a910c25 1088 // correct for additional contamination due to trigger particle around phi ~ 0
1089 TH2* correlatedContamination = corrections->GetCorrelatedContamination();
1090 if (1)
1091 {
1092 Printf("Applying contamination enhancement");
1093
1094 for (Int_t bin = 1; bin <= correlatedContamination->GetNbinsX(); bin++)
1095 for (Int_t bin2 = 1; bin2 <= correlatedContamination->GetNbinsY(); bin2++)
1096 {
1097 printf("%f", correlatedContamination->GetBinContent(bin, bin2));
1098 if (correlatedContamination->GetBinContent(bin, bin2) > 0)
1099 correlatedContamination->SetBinContent(bin, bin2, 1.0 + 1.1 * (correlatedContamination->GetBinContent(bin, bin2) - 1.0));
1100 printf(" --> %f\n", correlatedContamination->GetBinContent(bin, bin2));
1101 }
1102 }
1103
1104 //new TCanvas; correlatedContamination->DrawCopy("COLZ");
1105 CorrectCorrelatedContamination(kCFStepTrackedOnlyPrim, 0, correlatedContamination);
1106
1107 delete correlatedContamination;
c7245604 1108
1109 // TODO correct for contamination of trigger particles (for tracks AND events)
1110 CorrectEvents(kCFStepTracked, kCFStepTrackedOnlyPrim, 0, 0);
1111
1112 // --- efficiency correction ---
1113 // correct single-particle efficiency for associated particles
1114 // in addition correct for efficiency on trigger particles (tracks AND events)
1115
2a910c25 1116 // in bins of pT and centrality
1117 TH1* efficiencyCorrection = corrections->GetTrackingEfficiencyCorrectionCentrality();
c7245604 1118 // use kCFStepAnaTopology as a temporary step
2a910c25 1119 CorrectTracks(kCFStepTrackedOnlyPrim, kCFStepAnaTopology, efficiencyCorrection, 1, 3);
c7245604 1120 delete efficiencyCorrection;
1121
2a910c25 1122 // correct pT,T in bins of pT and centrality
1123 efficiencyCorrection = corrections->GetTrackEfficiency(kCFStepTrackedOnlyPrim, kCFStepAnaTopology, 1, 3, 2);
1124 CorrectEvents(kCFStepTrackedOnlyPrim, kCFStepVertex, efficiencyCorrection, 0, 1);
1125 CorrectTracks(kCFStepAnaTopology, kCFStepVertex, efficiencyCorrection, 2, 3);
c7245604 1126 delete efficiencyCorrection;
1127
1128 // no correction for vertex finding efficiency and trigger efficiency needed in PbPb
1129 // copy
1130 CorrectTracks(kCFStepVertex, kCFStepAll, 0, -1);
1131 CorrectEvents(kCFStepVertex, kCFStepAll, 0, -1);
144bd037 1132 }
c7245604 1133 else
1134 AliFatal(Form("Unknown histogram for correction: %s", GetTitle()));
a75aacd6 1135}
1136
1137//____________________________________________________________________
2a910c25 1138TH1* AliUEHist::GetTrackEfficiency(CFStep step1, CFStep step2, Int_t axis1, Int_t axis2, Int_t source, Int_t axis3)
a75aacd6 1139{
1140 // creates a track-level efficiency by dividing step2 by step1
1141 // projected to axis1 and axis2 (optional if >= 0)
b1831bcb 1142 //
c7245604 1143 // source: 0 = fTrackHist; 1 = fTrackHistEfficiency; 2 = fTrackHistEfficiency rebinned for pT,T / pT,lead binning
a75aacd6 1144
1145 // integrate over regions
1146 // cache it for efficiency (usually more than one efficiency is requested)
b1831bcb 1147
1148 AliCFContainer* sourceContainer = 0;
1149
1150 if (source == 0)
a75aacd6 1151 {
b1831bcb 1152 if (!fCache)
1153 {
1154 fCache = (AliCFContainer*) fTrackHist[0]->Clone();
ff458f69 1155 for (UInt_t i = 1; i < fkRegions; i++)
b1831bcb 1156 if (fTrackHist[i])
1157 fCache->Add(fTrackHist[i]);
1158 }
1159 sourceContainer = fCache;
a75aacd6 1160 }
c7245604 1161 else if (source == 1 || source == 2)
b1831bcb 1162 {
1163 sourceContainer = fTrackHistEfficiency;
1164 // step offset because we start with kCFStepAnaTopology
1165 step1 = (CFStep) ((Int_t) step1 - (Int_t) kCFStepAnaTopology);
1166 step2 = (CFStep) ((Int_t) step2 - (Int_t) kCFStepAnaTopology);
1167 }
1168 else
1169 return 0;
1170
2a910c25 1171 // reset all limits and set the right ones except those in axis1, axis2 and axis3
b1831bcb 1172 ResetBinLimits(sourceContainer->GetGrid(step1));
1173 ResetBinLimits(sourceContainer->GetGrid(step2));
2a910c25 1174 if (fEtaMax > fEtaMin && axis1 != 0 && axis2 != 0 && axis3 != 0)
a75aacd6 1175 {
b1831bcb 1176 sourceContainer->GetGrid(step1)->SetRangeUser(0, fEtaMin, fEtaMax);
1177 sourceContainer->GetGrid(step2)->SetRangeUser(0, fEtaMin, fEtaMax);
a75aacd6 1178 }
2a910c25 1179 if (fPtMax > fPtMin && axis1 != 1 && axis2 != 1 && axis3 != 1)
a75aacd6 1180 {
b1831bcb 1181 sourceContainer->GetGrid(step1)->SetRangeUser(1, fPtMin, fPtMax);
1182 sourceContainer->GetGrid(step2)->SetRangeUser(1, fPtMin, fPtMax);
a75aacd6 1183 }
2a910c25 1184 if (fCentralityMax > fCentralityMin && axis1 != 3 && axis2 != 3 && axis3 != 3)
1185 {
1186 sourceContainer->GetGrid(step1)->SetRangeUser(3, fCentralityMin, fCentralityMax);
1187 sourceContainer->GetGrid(step2)->SetRangeUser(3, fCentralityMin, fCentralityMax);
1188 }
a75aacd6 1189
1190 TH1* measured = 0;
1191 TH1* generated = 0;
1192
2a910c25 1193 if (axis3 >= 0)
1194 {
1195 generated = sourceContainer->Project(step1, axis1, axis2, axis3);
1196 measured = sourceContainer->Project(step2, axis1, axis2, axis3);
1197 }
1198 else if (axis2 >= 0)
a75aacd6 1199 {
c7245604 1200 generated = sourceContainer->Project(step1, axis1, axis2);
1201 measured = sourceContainer->Project(step2, axis1, axis2);
a75aacd6 1202 }
1203 else
1204 {
c7245604 1205 generated = sourceContainer->Project(step1, axis1);
1206 measured = sourceContainer->Project(step2, axis1);
a75aacd6 1207 }
1208
2a910c25 1209 // check for bins with less than 50 entries, print warning
1210 Int_t binBegin[3];
1211 Int_t binEnd[3];
144bd037 1212
1213 binBegin[0] = 1;
1214 binBegin[1] = 1;
2a910c25 1215 binBegin[2] = 1;
144bd037 1216
1217 binEnd[0] = generated->GetNbinsX();
1218 binEnd[1] = generated->GetNbinsY();
2a910c25 1219 binEnd[2] = generated->GetNbinsZ();
144bd037 1220
1221 if (fEtaMax > fEtaMin)
1222 {
1223 if (axis1 == 0)
1224 {
1225 binBegin[0] = generated->GetXaxis()->FindBin(fEtaMin);
1226 binEnd[0] = generated->GetXaxis()->FindBin(fEtaMax);
1227 }
1228 if (axis2 == 0)
1229 {
1230 binBegin[1] = generated->GetYaxis()->FindBin(fEtaMin);
1231 binEnd[1] = generated->GetYaxis()->FindBin(fEtaMax);
1232 }
2a910c25 1233 if (axis3 == 0)
1234 {
1235 binBegin[2] = generated->GetZaxis()->FindBin(fEtaMin);
1236 binEnd[2] = generated->GetZaxis()->FindBin(fEtaMax);
1237 }
144bd037 1238 }
1239
1240 if (fPtMax > fPtMin)
1241 {
1242 // TODO this is just checking up to 15 for now
1243 Float_t ptMax = TMath::Min((Float_t) 15., fPtMax);
1244 if (axis1 == 1)
1245 {
1246 binBegin[0] = generated->GetXaxis()->FindBin(fPtMin);
1247 binEnd[0] = generated->GetXaxis()->FindBin(ptMax);
1248 }
1249 if (axis2 == 1)
1250 {
1251 binBegin[1] = generated->GetYaxis()->FindBin(fPtMin);
1252 binEnd[1] = generated->GetYaxis()->FindBin(ptMax);
1253 }
2a910c25 1254 if (axis3 == 1)
1255 {
1256 binBegin[2] = generated->GetZaxis()->FindBin(fPtMin);
1257 binEnd[2] = generated->GetZaxis()->FindBin(ptMax);
1258 }
144bd037 1259 }
1260
1261 Int_t total = 0;
1262 Int_t count = 0;
2a910c25 1263 Int_t vars[3];
144bd037 1264
2a910c25 1265 for (Int_t i=0; i<3; i++)
144bd037 1266 vars[i] = binBegin[i];
1267
1268 const Int_t limit = 50;
1269 while (1)
1270 {
1271 if (generated->GetDimension() == 1 && generated->GetBinContent(vars[0]) < limit)
1272 {
1273 Printf("Empty bin at %s=%.2f (%.2f entries)", generated->GetXaxis()->GetTitle(), generated->GetXaxis()->GetBinCenter(vars[0]), generated->GetBinContent(vars[0]));
1274 count++;
1275 }
1276 else if (generated->GetDimension() == 2 && generated->GetBinContent(vars[0], vars[1]) < limit)
1277 {
1278 Printf("Empty bin at %s=%.2f %s=%.2f (%.2f entries)",
1279 generated->GetXaxis()->GetTitle(), generated->GetXaxis()->GetBinCenter(vars[0]),
1280 generated->GetYaxis()->GetTitle(), generated->GetYaxis()->GetBinCenter(vars[1]),
1281 generated->GetBinContent(vars[0], vars[1]));
1282 count++;
1283 }
2a910c25 1284 else if (generated->GetDimension() == 3 && generated->GetBinContent(vars[0], vars[1], vars[2]) < limit)
1285 {
1286 Printf("Empty bin at %s=%.2f %s=%.2f %s=%.2f (%.2f entries)",
1287 generated->GetXaxis()->GetTitle(), generated->GetXaxis()->GetBinCenter(vars[0]),
1288 generated->GetYaxis()->GetTitle(), generated->GetYaxis()->GetBinCenter(vars[1]),
1289 generated->GetZaxis()->GetTitle(), generated->GetZaxis()->GetBinCenter(vars[2]),
1290 generated->GetBinContent(vars[0], vars[1], vars[2]));
1291 count++;
1292 }
1293
1294 vars[2]++;
1295 if (vars[2] == binEnd[2]+1)
1296 {
1297 vars[2] = binBegin[2];
1298 vars[1]++;
1299 }
144bd037 1300
144bd037 1301 if (vars[1] == binEnd[1]+1)
1302 {
1303 vars[1] = binBegin[1];
1304 vars[0]++;
1305 }
1306
1307 if (vars[0] == binEnd[0]+1)
1308 break;
1309 total++;
1310 }
1311
1312 Printf("Correction has %d empty bins (out of %d bins)", count, total);
1313
c7245604 1314 // rebin if required
1315 if (source == 2)
1316 {
c7245604 1317 TAxis* axis = fEventHist->GetGrid(0)->GetGrid()->GetAxis(0);
1318
1319 if (axis->GetNbins() < measured->GetNbinsX())
1320 {
2a910c25 1321 if (axis2 != -1)
1322 {
1323 // 2d rebin with variable axis does not exist in root
1324
1325 TH1* tmp = measured;
1326 measured = new TH2D(Form("%s_rebinned", tmp->GetName()), tmp->GetTitle(), axis->GetNbins(), axis->GetXbins()->GetArray(), tmp->GetNbinsY(), tmp->GetYaxis()->GetXbins()->GetArray());
1327 for (Int_t x=1; x<=tmp->GetNbinsX(); x++)
1328 for (Int_t y=1; y<=tmp->GetNbinsY(); y++)
1329 {
1330 ((TH2*) measured)->Fill(tmp->GetXaxis()->GetBinCenter(x), tmp->GetYaxis()->GetBinCenter(y), tmp->GetBinContent(x, y));
1331 measured->SetBinError(x, y, 0); // cannot trust bin error, set to 0
1332 }
1333 delete tmp;
1334
1335 tmp = generated;
1336 generated = new TH2D(Form("%s_rebinned", tmp->GetName()), tmp->GetTitle(), axis->GetNbins(), axis->GetXbins()->GetArray(), tmp->GetNbinsY(), tmp->GetYaxis()->GetXbins()->GetArray());
1337 for (Int_t x=1; x<=tmp->GetNbinsX(); x++)
1338 for (Int_t y=1; y<=tmp->GetNbinsY(); y++)
1339 {
1340 ((TH2*) generated)->Fill(tmp->GetXaxis()->GetBinCenter(x), tmp->GetYaxis()->GetBinCenter(y), tmp->GetBinContent(x, y));
1341 generated->SetBinError(x, y, 0); // cannot trust bin error, set to 0
1342 }
1343 delete tmp;
1344 }
1345 else
1346 {
1347 TH1* tmp = measured;
1348 measured = tmp->Rebin(axis->GetNbins(), Form("%s_rebinned", tmp->GetName()), axis->GetXbins()->GetArray());
1349 delete tmp;
1350
1351 tmp = generated;
1352 generated = tmp->Rebin(axis->GetNbins(), Form("%s_rebinned", tmp->GetName()), axis->GetXbins()->GetArray());
1353 delete tmp;
1354 }
c7245604 1355 }
1356 else if (axis->GetNbins() > measured->GetNbinsX())
1357 {
2a910c25 1358 if (axis2 != -1)
1359 AliFatal("Rebinning only works for 1d at present");
1360
c7245604 1361 // this is an unfortunate case where the number of bins has to be increased in principle
1362 // there is a region where the binning is finner in one histogram and a region where it is the other way round
1363 // this cannot be resolved in principle, but as we only calculate the ratio the bin in the second region get the same entries
1364 // only a certain binning is supported here
1365 if (axis->GetNbins() != 100 || measured->GetNbinsX() != 39)
1366 AliFatal(Form("Invalid binning --> %d %d", axis->GetNbins(), measured->GetNbinsX()));
1367
1368 Double_t newBins[] = {0.0, 0.5, 1.0, 1.5, 2.0, 2.5, 3.0, 3.5, 4.0, 4.5, 5.0, 6.0, 7.0, 8.0, 9.0, 10.0, 12.0, 14.0, 16.0, 18.0, 20.0, 25.0, 30.0, 35.0, 40.0, 45.0, 50.0, 100.0};
1369
1370 // reduce binning below 5 GeV/c
1371 TH1* tmp = measured;
1372 measured = tmp->Rebin(27, Form("%s_rebinned", tmp->GetName()), newBins);
1373 delete tmp;
1374
1375 // increase binning above 5 GeV/c
1376 tmp = measured;
1377 measured = new TH1F(Form("%s_rebinned2", tmp->GetName()), tmp->GetTitle(), axis->GetNbins(), axis->GetBinLowEdge(1), axis->GetBinUpEdge(axis->GetNbins()));
1378 for (Int_t bin=1; bin<=measured->GetNbinsX(); bin++)
1379 {
1380 measured->SetBinContent(bin, tmp->GetBinContent(tmp->FindBin(measured->GetBinCenter(bin))));
1381 measured->SetBinError(bin, tmp->GetBinError(tmp->FindBin(measured->GetBinCenter(bin))));
1382 }
1383 delete tmp;
1384
1385 // reduce binning below 5 GeV/c
1386 tmp = generated;
1387 generated = tmp->Rebin(27, Form("%s_rebinned", tmp->GetName()), newBins);
1388 delete tmp;
1389
1390 // increase binning above 5 GeV/c
1391 tmp = generated;
1392 generated = new TH1F(Form("%s_rebinned2", tmp->GetName()), tmp->GetTitle(), axis->GetNbins(), axis->GetBinLowEdge(1), axis->GetBinUpEdge(axis->GetNbins()));
1393 for (Int_t bin=1; bin<=generated->GetNbinsX(); bin++)
1394 {
1395 generated->SetBinContent(bin, tmp->GetBinContent(tmp->FindBin(generated->GetBinCenter(bin))));
1396 generated->SetBinError(bin, tmp->GetBinError(tmp->FindBin(generated->GetBinCenter(bin))));
1397 }
1398 delete tmp;
1399 }
1400 }
1401
144bd037 1402 measured->Divide(measured, generated, 1, 1, "B");
a75aacd6 1403
1404 delete generated;
1405
b1831bcb 1406 ResetBinLimits(sourceContainer->GetGrid(step1));
1407 ResetBinLimits(sourceContainer->GetGrid(step2));
1408
a75aacd6 1409 return measured;
1410}
1411
1412//____________________________________________________________________
1413TH1* AliUEHist::GetEventEfficiency(CFStep step1, CFStep step2, Int_t axis1, Int_t axis2, Float_t ptLeadMin, Float_t ptLeadMax)
1414{
1415 // creates a event-level efficiency by dividing step2 by step1
1416 // projected to axis1 and axis2 (optional if >= 0)
1417
1418 if (ptLeadMax > ptLeadMin)
1419 {
1420 fEventHist->GetGrid(step1)->SetRangeUser(0, ptLeadMin, ptLeadMax);
1421 fEventHist->GetGrid(step2)->SetRangeUser(0, ptLeadMin, ptLeadMax);
1422 }
1423
1424 TH1* measured = 0;
1425 TH1* generated = 0;
1426
144bd037 1427 if (axis2 >= 0)
a75aacd6 1428 {
c7245604 1429 generated = fEventHist->Project(step1, axis1, axis2);
1430 measured = fEventHist->Project(step2, axis1, axis2);
a75aacd6 1431 }
1432 else
1433 {
c7245604 1434 generated = fEventHist->Project(step1, axis1);
1435 measured = fEventHist->Project(step2, axis1);
a75aacd6 1436 }
1437
144bd037 1438 measured->Divide(measured, generated, 1, 1, "B");
a75aacd6 1439
1440 delete generated;
1441
1442 if (ptLeadMax > ptLeadMin)
1443 {
1444 fEventHist->GetGrid(step1)->SetRangeUser(0, 0, -1);
1445 fEventHist->GetGrid(step2)->SetRangeUser(0, 0, -1);
1446 }
1447
1448 return measured;
1449}
1450
1451//____________________________________________________________________
1452void AliUEHist::WeightHistogram(TH3* hist1, TH1* hist2)
1453{
1454 // weights each entry of the 3d histogram hist1 with the 1d histogram hist2
1455 // where the matching is done of the z axis of hist1 with the x axis of hist2
1456
1457 if (hist1->GetNbinsZ() != hist2->GetNbinsX())
1458 AliFatal(Form("Inconsistent binning %d %d", hist1->GetNbinsZ(), hist2->GetNbinsX()));
1459
1460 for (Int_t x=1; x<=hist1->GetNbinsX(); x++)
1461 {
1462 for (Int_t y=1; y<=hist1->GetNbinsY(); y++)
1463 {
1464 for (Int_t z=1; z<=hist1->GetNbinsZ(); z++)
1465 {
1466 if (hist2->GetBinContent(z) > 0)
1467 {
1468 hist1->SetBinContent(x, y, z, hist1->GetBinContent(x, y, z) / hist2->GetBinContent(z));
1469 hist1->SetBinError(x, y, z, hist1->GetBinError(x, y, z) / hist2->GetBinContent(z));
1470 }
1471 else
1472 {
1473 hist1->SetBinContent(x, y, z, 0);
1474 hist1->SetBinError(x, y, z, 0);
1475 }
1476 }
1477 }
1478 }
1479}
1480
1481//____________________________________________________________________
c7245604 1482TH1* AliUEHist::GetBias(CFStep step1, CFStep step2, Int_t region, const char* axis, Float_t leadPtMin, Float_t leadPtMax, Int_t weighting)
a75aacd6 1483{
1484 // extracts the track-level bias (integrating out the multiplicity) between two steps (dividing step2 by step1)
144bd037 1485 // in the given region (sum over all regions is calculated if region == -1)
a75aacd6 1486 // done by weighting the track-level distribution with the number of events as function of leading pT
1487 // and then calculating the ratio between the distributions
1488 // projected to axis which is a TH3::Project3D string, e.g. "x", or "yx"
1489 // no projection is done if axis == 0
c7245604 1490 // weighting: 0 = tracks weighted with events (as discussed above)
1491 // 1 = only track bias is returned
1492 // 2 = only event bias is returned
a75aacd6 1493
144bd037 1494 AliCFContainer* tmp = 0;
1495
1496 if (region == -1)
1497 {
1498 tmp = (AliCFContainer*) fTrackHist[0]->Clone();
ff458f69 1499 for (UInt_t i = 1; i < fkRegions; i++)
144bd037 1500 if (fTrackHist[i])
1501 tmp->Add(fTrackHist[i]);
1502 }
1503 else if (region == kMin && fCombineMinMax)
1504 {
1505 tmp = (AliCFContainer*) fTrackHist[kMin]->Clone();
1506 tmp->Add(fTrackHist[kMax]);
1507 }
1508 else
1509 tmp = fTrackHist[region];
1510
1511 ResetBinLimits(tmp->GetGrid(step1));
1512 ResetBinLimits(fEventHist->GetGrid(step1));
1513 SetBinLimits(tmp->GetGrid(step1));
1514
1515 ResetBinLimits(tmp->GetGrid(step2));
1516 ResetBinLimits(fEventHist->GetGrid(step2));
1517 SetBinLimits(tmp->GetGrid(step2));
a75aacd6 1518
c7245604 1519 TH1D* events1 = (TH1D*)fEventHist->Project(step1, 0);
1520 TH3D* hist1 = (TH3D*)tmp->Project(step1, 0, tmp->GetNVar()-1, 2);
1521 if (weighting == 0)
1522 WeightHistogram(hist1, events1);
a75aacd6 1523
c7245604 1524 TH1D* events2 = (TH1D*)fEventHist->Project(step2, 0);
1525 TH3D* hist2 = (TH3D*)tmp->Project(step2, 0, tmp->GetNVar()-1, 2);
1526 if (weighting == 0)
1527 WeightHistogram(hist2, events2);
a75aacd6 1528
1529 TH1* generated = hist1;
1530 TH1* measured = hist2;
1531
c7245604 1532 if (weighting == 0 || weighting == 1)
a75aacd6 1533 {
c7245604 1534 if (axis)
a75aacd6 1535 {
c7245604 1536 if (leadPtMax > leadPtMin)
1537 {
1538 hist1->GetZaxis()->SetRangeUser(leadPtMin, leadPtMax);
1539 hist2->GetZaxis()->SetRangeUser(leadPtMin, leadPtMax);
1540 }
1541
1542 if (fEtaMax > fEtaMin && !TString(axis).Contains("x"))
1543 {
1544 hist1->GetXaxis()->SetRangeUser(fEtaMin, fEtaMax);
1545 hist2->GetXaxis()->SetRangeUser(fEtaMin, fEtaMax);
1546 }
a75aacd6 1547
c7245604 1548 generated = hist1->Project3D(axis);
1549 measured = hist2->Project3D(axis);
1550
1551 // delete hists here if projection has been done
1552 delete hist1;
1553 delete hist2;
a75aacd6 1554 }
c7245604 1555 delete events1;
1556 delete events2;
1557 }
1558 else if (weighting == 2)
1559 {
a75aacd6 1560 delete hist1;
1561 delete hist2;
c7245604 1562 generated = events1;
1563 measured = events2;
a75aacd6 1564 }
1565
1566 measured->Divide(generated);
1567
a75aacd6 1568 delete generated;
144bd037 1569
1570 ResetBinLimits(tmp->GetGrid(step1));
1571 ResetBinLimits(tmp->GetGrid(step2));
1572
29e8465c 1573 if ((region == -1) || (region == kMin && fCombineMinMax))
144bd037 1574 delete tmp;
a75aacd6 1575
1576 return measured;
1577}
1578
2a910c25 1579//____________________________________________________________________
1580void AliUEHist::CorrectCorrelatedContamination(CFStep step, Int_t region, TH1* trackCorrection)
1581{
1582 // corrects for the given factor in a small delta-eta and delta-phi window as function of pT,A and pT,T
1583
1584 if (!fTrackHist[region])
1585 return;
1586
1587 THnSparse* grid = fTrackHist[region]->GetGrid(step)->GetGrid();
1588
1589 Int_t var1 = 1;
1590 Int_t var2 = 2;
1591
1592 if (grid->GetAxis(var1)->GetNbins() != trackCorrection->GetNbinsX())
1593 AliFatal(Form("Invalid binning (var1): %d %d", grid->GetAxis(var1)->GetNbins(), trackCorrection->GetNbinsX()));
1594
1595 if (grid->GetAxis(var2)->GetNbins() != trackCorrection->GetNbinsY())
1596 AliFatal(Form("Invalid binning (var2): %d %d", grid->GetAxis(var2)->GetNbins(), trackCorrection->GetNbinsY()));
1597
1598 // optimized implementation
1599 for (Int_t binIdx = 0; binIdx < grid->GetNbins(); binIdx++)
1600 {
1601 Int_t bins[5];
1602
1603 Double_t value = grid->GetBinContent(binIdx, bins);
1604 Double_t error = grid->GetBinError(binIdx);
1605
1606 // check eta and phi axes
1607 if (TMath::Abs(grid->GetAxis(0)->GetBinCenter(bins[0])) > 0.1)
1608 continue;
1609 if (TMath::Abs(grid->GetAxis(4)->GetBinCenter(bins[4])) > 0.1)
1610 continue;
1611
1612 value *= trackCorrection->GetBinContent(bins[var1], bins[var2]);
1613 error *= trackCorrection->GetBinContent(bins[var1], bins[var2]);
1614
1615 grid->SetBinContent(bins, value);
1616 grid->SetBinError(bins, error);
1617 }
1618
1619 Printf("AliUEHist::CorrectCorrelatedContamination: Corrected.");
1620}
1621
1622//____________________________________________________________________
1623TH2* AliUEHist::GetCorrelatedContamination()
1624{
1625 // contamination correlated with the trigger particle is evaluated between step kCFStepTracked and kCFStepTrackedOnlyPrim in the region of delta eta and delta phi < 0.1 (smallest bin!)
1626
1627 Int_t step1 = kCFStepTrackedOnlyPrim;
1628 Int_t step2 = kCFStepTracked;
1629
1630 fTrackHist[0]->GetGrid(step1)->SetRangeUser(0, -0.01, 0.01); // delta eta
1631 fTrackHist[0]->GetGrid(step1)->SetRangeUser(4, -0.01, 0.01); // delta phi
1632 TH2* tracksStep1 = (TH2*) fTrackHist[0]->Project(step1, 1, 2);
1633
1634 fTrackHist[0]->GetGrid(step2)->SetRangeUser(0, -0.01, 0.01); // delta eta
1635 fTrackHist[0]->GetGrid(step2)->SetRangeUser(4, -0.01, 0.01); // delta phi
1636 TH2* tracksStep2 = (TH2*) fTrackHist[0]->Project(step2, 1, 2);
1637
1638 tracksStep1->Divide(tracksStep2);
1639
1640 TH1* triggersStep1 = fEventHist->Project(step1, 0);
1641 TH1* triggersStep2 = fEventHist->Project(step2, 0);
1642
1643 TH1* singleParticle = GetTrackingContamination(1);
1644
1645 for (Int_t x=1; x<=tracksStep1->GetNbinsX(); x++)
1646 for (Int_t y=1; y<=tracksStep1->GetNbinsY(); y++)
1647 if (singleParticle->GetBinContent(x) > 0)
1648 tracksStep1->SetBinContent(x, y, tracksStep1->GetBinContent(x, y) / triggersStep1->GetBinContent(y) * triggersStep2->GetBinContent(y) / singleParticle->GetBinContent(x));
1649 else
1650 tracksStep1->SetBinContent(x, y, 0);
1651
1652 delete singleParticle;
1653 delete tracksStep2;
1654 delete triggersStep1;
1655 delete triggersStep2;
1656
1657 return tracksStep1;
1658}
1659
a75aacd6 1660//____________________________________________________________________
1661TH2D* AliUEHist::GetTrackingEfficiency()
1662{
1663 // extracts the tracking efficiency by calculating the efficiency from step kCFStepAnaTopology to kCFStepTrackedOnlyPrim
1664 // integrates over the regions and all other variables than pT and eta to increase the statistics
1665 //
1666 // returned histogram has to be deleted by the user
1667
1668 return dynamic_cast<TH2D*> (GetTrackEfficiency(kCFStepAnaTopology, kCFStepTrackedOnlyPrim, 0, 1));
1669}
1670
2a910c25 1671//____________________________________________________________________
1672TH2D* AliUEHist::GetTrackingEfficiencyCentrality()
1673{
1674 // extracts the tracking efficiency by calculating the efficiency from step kCFStepAnaTopology to kCFStepTrackedOnlyPrim
1675 // integrates over the regions and all other variables than pT, centrality to increase the statistics
1676 //
1677 // returned histogram has to be deleted by the user
1678
1679 return dynamic_cast<TH2D*> (GetTrackEfficiency(kCFStepAnaTopology, kCFStepTrackedOnlyPrim, 1, 3));
1680}
1681
a75aacd6 1682//____________________________________________________________________
1683TH1D* AliUEHist::GetTrackingEfficiency(Int_t axis)
1684{
1685 // extracts the tracking efficiency by calculating the efficiency from step kCFStepAnaTopology to kCFStepTrackedOnlyPrim
1686 // integrates over the regions and all other variables than pT (axis == 0) and eta (axis == 1) to increase the statistics
1687
1688 return dynamic_cast<TH1D*> (GetTrackEfficiency(kCFStepAnaTopology, kCFStepTrackedOnlyPrim, axis));
1689}
1690
1691//____________________________________________________________________
1692TH2D* AliUEHist::GetTrackingCorrection()
1693{
1694 // extracts the tracking correction by calculating the efficiency from step kCFStepAnaTopology to kCFStepTracked
1695 // integrates over the regions and all other variables than pT and eta to increase the statistics
1696 //
1697 // returned histogram has to be deleted by the user
1698
1699 return dynamic_cast<TH2D*> (GetTrackEfficiency(kCFStepTracked, kCFStepAnaTopology, 0, 1));
1700}
1701
1702//____________________________________________________________________
1703TH1D* AliUEHist::GetTrackingCorrection(Int_t axis)
1704{
1705 // extracts the tracking correction by calculating the efficiency from step kCFStepAnaTopology to kCFStepTracked
1706 // integrates over the regions and all other variables than pT (axis == 0) and eta (axis == 1) to increase the statistics
1707
1708 return dynamic_cast<TH1D*> (GetTrackEfficiency(kCFStepTracked, kCFStepAnaTopology, axis));
1709}
1710
144bd037 1711//____________________________________________________________________
1712TH2D* AliUEHist::GetTrackingEfficiencyCorrection()
1713{
1714 // extracts the tracking correction by calculating the efficiency from step kCFStepAnaTopology to kCFStepTracked
1715 // integrates over the regions and all other variables than pT and eta to increase the statistics
1716 //
1717 // returned histogram has to be deleted by the user
1718
1719 return dynamic_cast<TH2D*> (GetTrackEfficiency(kCFStepTrackedOnlyPrim, kCFStepAnaTopology, 0, 1));
1720}
1721
2a910c25 1722//____________________________________________________________________
1723TH2D* AliUEHist::GetTrackingEfficiencyCorrectionCentrality()
1724{
1725 // extracts the tracking correction by calculating the efficiency from step kCFStepAnaTopology to kCFStepTracked
1726 // integrates over the regions and all other variables than pT and centrality to increase the statistics
1727 //
1728 // returned histogram has to be deleted by the user
1729
1730 return dynamic_cast<TH2D*> (GetTrackEfficiency(kCFStepTrackedOnlyPrim, kCFStepAnaTopology, 1, 3));
1731}
1732
144bd037 1733//____________________________________________________________________
1734TH1D* AliUEHist::GetTrackingEfficiencyCorrection(Int_t axis)
1735{
1736 // extracts the tracking correction by calculating the efficiency from step kCFStepAnaTopology to kCFStepTracked
1737 // integrates over the regions and all other variables than pT (axis == 0) and eta (axis == 1) to increase the statistics
1738
1739 return dynamic_cast<TH1D*> (GetTrackEfficiency(kCFStepTrackedOnlyPrim, kCFStepAnaTopology, axis));
1740}
1741
a75aacd6 1742//____________________________________________________________________
1743TH2D* AliUEHist::GetTrackingContamination()
1744{
1745 // extracts the tracking contamination by secondaries by calculating the efficiency from step kCFStepTrackedOnlyPrim to kCFStepTracked
1746 // integrates over the regions and all other variables than pT and eta to increase the statistics
1747 //
1748 // returned histogram has to be deleted by the user
1749
1750 return dynamic_cast<TH2D*> (GetTrackEfficiency(kCFStepTracked, kCFStepTrackedOnlyPrim, 0, 1));
1751}
1752
2a910c25 1753//____________________________________________________________________
1754TH2D* AliUEHist::GetTrackingContaminationCentrality()
1755{
1756 // extracts the tracking contamination by secondaries by calculating the efficiency from step kCFStepTrackedOnlyPrim to kCFStepTracked
1757 // integrates over the regions and all other variables than pT and centrality to increase the statistics
1758 //
1759 // returned histogram has to be deleted by the user
1760
1761 return dynamic_cast<TH2D*> (GetTrackEfficiency(kCFStepTracked, kCFStepTrackedOnlyPrim, 1, 3));
1762}
1763
a75aacd6 1764//____________________________________________________________________
1765TH1D* AliUEHist::GetTrackingContamination(Int_t axis)
1766{
1767 // extracts the tracking contamination by secondaries by calculating the efficiency from step kCFStepTrackedOnlyPrim to kCFStepTracked
1768 // integrates over the regions and all other variables than pT (axis == 0) and eta (axis == 1) to increase the statistics
1769
1770 return dynamic_cast<TH1D*> (GetTrackEfficiency(kCFStepTracked, kCFStepTrackedOnlyPrim, axis));
1771}
1772
1773//____________________________________________________________________
1774const char* AliUEHist::GetRegionTitle(Region region)
1775{
1776 // returns the name of the given region
1777
1778 switch (region)
1779 {
1780 case kToward:
1781 return "Towards";
1782 case kAway:
1783 return "Away";
1784 case kMin:
1785 return (fCombineMinMax) ? "Transverse" : "Min";
1786 case kMax:
1787 return "Max";
1788 }
1789
1790 return 0;
1791}
1792
1793//____________________________________________________________________
1794const char* AliUEHist::GetStepTitle(CFStep step)
1795{
1796 // returns the name of the given step
1797
1798 switch (step)
1799 {
1800 case kCFStepAll:
1801 return "All events";
1802 case kCFStepTriggered:
1803 return "Triggered";
1804 case kCFStepVertex:
1805 return "Primary Vertex";
1806 case kCFStepAnaTopology:
1807 return "Required analysis topology";
1808 case kCFStepTrackedOnlyPrim:
1809 return "Tracked (matched MC, only primaries)";
1810 case kCFStepTracked:
1811 return "Tracked (matched MC, all)";
1812 case kCFStepReconstructed:
1813 return "Reconstructed";
1814 case kCFStepRealLeading:
1815 return "Correct leading particle identified";
1816 case kCFStepBiasStudy:
1817 return "Bias study applying tracking efficiency";
1818 case kCFStepBiasStudy2:
1819 return "Bias study applying tracking efficiency in two steps";
1820 }
1821
1822 return 0;
1823}
b1831bcb 1824
1825//____________________________________________________________________
1826void AliUEHist::CopyReconstructedData(AliUEHist* from)
1827{
1828 // copies those histograms extracted from ESD to this object
1829
1830 // TODO at present only the pointers are copied
1831
1832 for (Int_t region=0; region<4; region++)
1833 {
1834 if (!fTrackHist[region])
1835 continue;
1836
1837 fTrackHist[region]->SetGrid(AliUEHist::kCFStepReconstructed, from->fTrackHist[region]->GetGrid(AliUEHist::kCFStepReconstructed));
df269636 1838 //fTrackHist[region]->SetGrid(AliUEHist::kCFStepTrackedOnlyPrim, from->fTrackHist[region]->GetGrid(AliUEHist::kCFStepTrackedOnlyPrim));
b1831bcb 1839 fTrackHist[region]->SetGrid(AliUEHist::kCFStepBiasStudy, from->fTrackHist[region]->GetGrid(AliUEHist::kCFStepBiasStudy));
1840 }
1841
1842 fEventHist->SetGrid(AliUEHist::kCFStepReconstructed, from->fEventHist->GetGrid(AliUEHist::kCFStepReconstructed));
df269636 1843 //fEventHist->SetGrid(AliUEHist::kCFStepTrackedOnlyPrim, from->fEventHist->GetGrid(AliUEHist::kCFStepTrackedOnlyPrim));
b1831bcb 1844 fEventHist->SetGrid(AliUEHist::kCFStepBiasStudy, from->fEventHist->GetGrid(AliUEHist::kCFStepBiasStudy));
1845}
6f803f6c 1846
1847//____________________________________________________________________
df269636 1848void AliUEHist::ExtendTrackingEfficiency(Bool_t verbose)
6f803f6c 1849{
1850 // fits the tracking efficiency at high pT with a constant and fills all bins with this tracking efficiency
1851
1852 Float_t fitRangeBegin = 5.01;
1853 Float_t fitRangeEnd = 14.99;
1854 Float_t extendRangeBegin = 10.01;
1855
2a910c25 1856 if (fTrackHistEfficiency->GetNVar() == 3)
c7245604 1857 {
2a910c25 1858 TH1* obj = GetTrackingEfficiency(1);
c7245604 1859
2a910c25 1860 if (verbose)
1861 {
1862 new TCanvas;
1863 obj->Draw();
1864 }
1865
1866 obj->Fit("pol0", (verbose) ? "+" : "0+", "SAME", fitRangeBegin, fitRangeEnd);
c7245604 1867
2a910c25 1868 Float_t trackingEff = obj->GetFunction("pol0")->GetParameter(0);
1869
1870 obj = GetTrackingContamination(1);
1871
1872 if (verbose)
1873 {
1874 new TCanvas;
1875 obj->Draw();
1876 }
1877
1878 obj->Fit("pol0", (verbose) ? "+" : "0+", "SAME", fitRangeBegin, fitRangeEnd);
1879
1880 Float_t trackingCont = obj->GetFunction("pol0")->GetParameter(0);
1881
1882 Printf("AliUEHist::ExtendTrackingEfficiency: Fitted efficiency between %f and %f and got %f tracking efficiency and %f tracking contamination correction. Extending from %f onwards (within %f < eta < %f)", fitRangeBegin, fitRangeEnd, trackingEff, trackingCont, extendRangeBegin, fEtaMin, fEtaMax);
1883
1884 // extend for full pT range
1885 for (Int_t x = fTrackHistEfficiency->GetAxis(0, 0)->FindBin(fEtaMin); x <= fTrackHistEfficiency->GetAxis(0, 0)->FindBin(fEtaMax); x++)
1886 for (Int_t y = fTrackHistEfficiency->GetAxis(1, 0)->FindBin(extendRangeBegin); y <= fTrackHistEfficiency->GetNBins(1); y++)
1887 for (Int_t z = 1; z <= fTrackHistEfficiency->GetNBins(2); z++) // particle type axis
1888 {
1889
1890 Int_t bins[3];
1891 bins[0] = x;
1892 bins[1] = y;
1893 bins[2] = z;
1894
1895 fTrackHistEfficiency->GetGrid(0)->SetElement(bins, 100);
1896 fTrackHistEfficiency->GetGrid(1)->SetElement(bins, 100.0 * trackingEff);
1897 fTrackHistEfficiency->GetGrid(2)->SetElement(bins, 100.0 * trackingEff / trackingCont);
1898 }
1899 }
1900 else if (fTrackHistEfficiency->GetNVar() == 4)
1901 {
1902 // fit in centrality intervals of 20% for efficiency, one bin for contamination
1903 Float_t* trackingEff = 0;
1904 Float_t* trackingCont = 0;
1905 Int_t centralityBins = 5;
1906
1907 Printf("AliUEHist::ExtendTrackingEfficiency: Fitting efficiencies between %f and %f. Extending from %f onwards (within %f < eta < %f)", fitRangeBegin, fitRangeEnd, extendRangeBegin, fEtaMin, fEtaMax);
1908
1909 // 0 = eff; 1 = cont
1910 for (Int_t caseNo = 0; caseNo < 2; caseNo++)
1911 {
1912 Float_t* target = 0;
1913 Int_t centralityBinsLocal = centralityBins;
1914
1915 if (caseNo == 0)
6f803f6c 1916 {
2a910c25 1917 trackingEff = new Float_t[centralityBinsLocal];
1918 target = trackingEff;
1919 }
1920 else
1921 {
1922 centralityBinsLocal = 1;
1923 trackingCont = new Float_t[centralityBinsLocal];
1924 target = trackingCont;
6f803f6c 1925 }
2a910c25 1926
1927 for (Int_t i=0; i<centralityBinsLocal; i++)
1928 {
1929 SetCentralityRange(100.0/centralityBinsLocal*i + 0.1, 100.0/centralityBinsLocal*(i+1) - 0.1);
1930 TH1* proj = (caseNo == 0) ? GetTrackingEfficiency(1) : GetTrackingContamination(1);
1931 if (verbose)
1932 {
1933 new TCanvas;
1934 proj->DrawCopy();
1935 }
1936 if ((Int_t) proj->Fit("pol0", (verbose) ? "+" : "Q0+", "SAME", fitRangeBegin, fitRangeEnd) == 0)
1937 target[i] = proj->GetFunction("pol0")->GetParameter(0);
1938 else
1939 target[i] = 0;
1940 Printf("AliUEHist::ExtendTrackingEfficiency: case %d, centrality %d, eff %f", caseNo, i, target[i]);
1941 }
1942 }
1943
1944 // extend for full pT range
1945 for (Int_t x = fTrackHistEfficiency->GetAxis(0, 0)->FindBin(fEtaMin); x <= fTrackHistEfficiency->GetAxis(0, 0)->FindBin(fEtaMax); x++)
1946 for (Int_t y = fTrackHistEfficiency->GetAxis(1, 0)->FindBin(extendRangeBegin); y <= fTrackHistEfficiency->GetNBins(1); y++)
1947 for (Int_t z = 1; z <= fTrackHistEfficiency->GetNBins(2); z++) // particle type axis
1948 {
1949 for (Int_t z2 = 1; z2 <= fTrackHistEfficiency->GetNBins(3); z2++) // centrality axis
1950 {
1951
1952 Int_t bins[4];
1953 bins[0] = x;
1954 bins[1] = y;
1955 bins[2] = z;
1956 bins[3] = z2;
1957
1958 Int_t z2Bin = (Int_t) (fTrackHistEfficiency->GetAxis(3, 0)->GetBinCenter(z2) / (100.0 / centralityBins));
1959 //Printf("%d %d", z2, z2Bin);
1960
1961 fTrackHistEfficiency->GetGrid(0)->SetElement(bins, 100);
1962 fTrackHistEfficiency->GetGrid(1)->SetElement(bins, 100.0 * trackingEff[z2Bin]);
1963 if (trackingCont[0] > 0)
1964 fTrackHistEfficiency->GetGrid(2)->SetElement(bins, 100.0 * trackingEff[z2Bin] / trackingCont[0]);
1965 else
1966 fTrackHistEfficiency->GetGrid(2)->SetElement(bins, 0);
1967 }
1968 }
59064365 1969
1970 delete[] trackingEff;
1971 delete[] trackingCont;
2a910c25 1972 }
1973
1974 SetCentralityRange(0, 0);
6f803f6c 1975}
e741fadd 1976
1977void AliUEHist::AdditionalDPhiCorrection(Int_t step)
1978{
1979 // corrects the dphi distribution with an extra factor close to dphi ~ 0
1980
1981 Printf("WARNING: In AliUEHist::AdditionalDPhiCorrection.");
1982
1983 THnSparse* grid = fTrackHist[0]->GetGrid(step)->GetGrid();
1984
1985 // optimized implementation
1986 for (Int_t binIdx = 0; binIdx < grid->GetNbins(); binIdx++)
1987 {
1988 Int_t bins[5];
1989 Double_t value = grid->GetBinContent(binIdx, bins);
1990 Double_t error = grid->GetBinError(binIdx);
1991
1992 Float_t binCenter = grid->GetAxis(4)->GetBinCenter(bins[4]);
1993 if (TMath::Abs(binCenter) < 0.2)
1994 {
1995 value *= 0.985;
1996 error *= 0.985;
1997 }
1998 else if (TMath::Abs(binCenter) < 0.3)
1999 {
2000 value *= 0.9925;
2001 error *= 0.9925;
2002 }
2003
2004 grid->SetBinContent(bins, value);
2005 grid->SetBinError(bins, error);
2006 }
2007}
c7245604 2008
2009void AliUEHist::Scale(Double_t factor)
2010{
2011 // scales all contained histograms by the given factor
2012
2013 for (Int_t i=0; i<4; i++)
2014 if (fTrackHist[i])
2015 fTrackHist[i]->Scale(factor);
2016
2017 fEventHist->Scale(factor);
2018 fTrackHistEfficiency->Scale(factor);
2019}
2020
2021void AliUEHist::Reset()
2022{
2023 // resets all contained histograms
2024
2025 for (Int_t i=0; i<4; i++)
2026 if (fTrackHist[i])
2027 for (Int_t step=0; step<fTrackHist[i]->GetNStep(); step++)
2028 fTrackHist[i]->GetGrid(step)->GetGrid()->Reset();
2029
2030 for (Int_t step=0; step<fEventHist->GetNStep(); step++)
2031 fEventHist->GetGrid(step)->GetGrid()->Reset();
2032
2033 for (Int_t step=0; step<fTrackHistEfficiency->GetNStep(); step++)
2034 fTrackHistEfficiency->GetGrid(step)->GetGrid()->Reset();
2035}