]> git.uio.no Git - u/mrichter/AliRoot.git/blame - PWGLF/FORWARD/analysis2/AliAODForwardMult.h
Updates
[u/mrichter/AliRoot.git] / PWGLF / FORWARD / analysis2 / AliAODForwardMult.h
CommitLineData
f49fc45d 1//
2// See implementation or Doxygen comments for more information
3//
4#ifndef ALIAODFORWARDMULT_H
5#define ALIAODFORWARDMULT_H
ffca499d 6/**
7 * @file AliAODForwardMult.h
8 * @author Christian Holm Christensen <cholm@dalsgaard.hehi.nbi.dk>
9 * @date Wed Mar 23 13:58:00 2011
10 *
77f97e3f 11 * @brief Per-event @f$ N_{ch}@f$ per @f$(\eta,\varphi)@f$ bin
ffca499d 12 *
bd6f5206 13 * @ingroup pwglf_forward_aod
ffca499d 14 *
15 */
7e4038b5 16#include <TObject.h>
17#include <TH2D.h>
18class TBrowser;
e938e22b 19class TH1I;
7e4038b5 20/**
21 * Class that contains the forward multiplicity data per event
22 *
23 * This class contains a histogram of
24 * @f[
25 * \frac{d^2N_{ch}}{d\eta d\phi}\quad,
26 * @f]
27 * as well as a trigger mask for each analysed event.
28 *
29 * The eta acceptance of the event is stored in the underflow bins of
30 * the histogram. So to build the final histogram, one needs to
31 * correct for this acceptance (properly weighted by the events), and
32 * the vertex efficiency. This simply boils down to defining a 2D
33 * histogram and summing the event histograms in that histogram. One
34 * should of course also do proper book-keeping of the accepted event.
35 *
36 * @code
fa4236ed 37 * TTree* GetAODTree()
38 * {
39 * TFile* file = TFile::Open("AliAODs.root","READ");
40 * TTree* tree = static_cast<TTree*>(file->Get("aodTree"));
41 * return tree;
42 * }
43 *
44 * void Analyse()
45 * {
46 * TH2D* sum = 0; // Summed hist
47 * TTree* tree = GetAODTree(); // AOD tree
48 * AliAODForwardMult* mult = 0; // AOD object
49 * Int_t nTriggered = 0; // # of triggered ev.
50 * Int_t nWithVertex= 0; // # of ev. w/vertex
51 * Int_t nAccepted = 0; // # of ev. used
52 * Int_t nAvailable = tree->GetEntries(); // How many entries
53 * Float_t vzLow = -10; // Lower ip cut
54 * Float_t vzHigh = 10; // Upper ip cut
55 * Int_t mask = AliAODForwardMult::kInel;// Trigger mask
56 * tree->SetBranchAddress("forward", &forward); // Set the address
7e4038b5 57 *
58 * for (int i = 0; i < nAvailable; i++) {
59 * // Create sum histogram on first event - to match binning to input
60 * if (!sum) sum = static_cast<TH2D*>(mult->Clone("d2ndetadphi"));
61 *
62 * tree->GetEntry(i);
63 *
64 * // Other trigger/event requirements could be defined
65 * if (!mult->IsTriggerBits(mask)) continue;
66 * nTriggered++;
fa4236ed 67 *
68 * // Check if we have vertex
69 * if (!mult->HasIpZ()) continue;
70 * nWithVertex++;
7e4038b5 71 *
72 * // Select vertex range (in centimeters)
73 * if (!mult->InRange(vzLow, vzHigh) continue;
74 * nAccepted++;
75 *
76 * // Add contribution from this event
77 * sum->Add(&(mult->GetHistogram()));
78 * }
79 *
80 * // Get acceptance normalisation from underflow bins
cd548b09 81 * TH1D* norm = sum->ProjectionX("norm", 0, 1, "");
7e4038b5 82 * // Project onto eta axis - _ignoring_underflow_bins_!
83 * TH1D* dndeta = sum->Projection("dndeta", 1, -1, "e");
84 * // Normalize to the acceptance
85 * dndeta->Divide(norm);
86 * // Scale by the vertex efficiency
fa4236ed 87 * dndeta->Scale(Double_t(nWithVertex)/nTriggered, "width");
7e4038b5 88 * // And draw the result
89 * dndeta->Draw();
fa4236ed 90 * }
7e4038b5 91 * @endcode
92 *
93 * The above code will draw the final @f$ dN_{ch}/d\eta@f$ for the
94 * selected event class and vertex range
95 *
96 * The histogram can be used as input for other kinds of analysis too,
97 * like flow, event-plane, centrality, and so on.
98 *
bd6f5206 99 * @ingroup pwglf_forward
100 * @ingroup pwglf_forward_aod
7e4038b5 101 */
102class AliAODForwardMult : public TObject
103{
104public:
105 /**
106 * Bits of the trigger pattern
107 */
108 enum {
eb7691d5 109 /** In-elastic collision - really MBOR*/
8449e3e0 110 kInel = 0x0001,
7e4038b5 111 /** In-elastic collision with at least one SPD tracklet */
8449e3e0 112 kInelGt0 = 0x0002,
eb7691d5 113 /** Non-single diffractive collision - (V0AND||FASTOR>5) */
8449e3e0 114 kNSD = 0x0004,
7e4038b5 115 /** Empty bunch crossing */
8449e3e0 116 kEmpty = 0x0008,
7e4038b5 117 /** A-side trigger */
8449e3e0 118 kA = 0x0010,
7e4038b5 119 /** B(arrel) trigger */
8449e3e0 120 kB = 0x0020,
7e4038b5 121 /** C-side trigger */
8449e3e0 122 kC = 0x0080,
7e4038b5 123 /** Empty trigger */
8449e3e0 124 kE = 0x0100,
e58000b7 125 /** pileup from SPD */
8449e3e0 126 kPileUp = 0x0200,
e58000b7 127 /** true NSD from MC */
8449e3e0 128 kMCNSD = 0x0400,
0be6c8cd 129 /** Offline MB triggered */
8449e3e0 130 kOffline = 0x0800,
5bb5d1f6 131 /** At least one SPD cluster */
e6463868 132 kNClusterGt0 = 0x1000,
133 /** V0-AND trigger */
8449e3e0 134 kV0AND = 0x2000,
135 /** Satellite event */
5f2f85f0 136 kSatellite = 0x4000,
137 /** SPD outlier event */
138 kSPDOutlier = 0x8000,
139 /** SPD pile-up */
140 kPileupSPD = 0x10000,
141 /** Track pile-up */
142 kPileupTrack = 0x20000,
143 /** Out of bunch pileup */
144 kPileupBC = 0x40000
145
7e4038b5 146 };
e938e22b 147 /**
148 * Bin numbers in trigger histograms
149 */
150 enum {
151 kBinAll=1,
152 kBinInel,
153 kBinInelGt0,
154 kBinNSD,
e6463868 155 kBinV0AND,
e938e22b 156 kBinA,
157 kBinB,
158 kBinC,
159 kBinE,
8449e3e0 160 kBinSatellite,
e938e22b 161 kBinPileUp,
162 kBinMCNSD,
0be6c8cd 163 kBinOffline,
5bb5d1f6 164 kBinNClusterGt0,
e938e22b 165 kWithTrigger,
166 kWithVertex,
167 kAccepted
168 };
bfab35d9 169 /**
170 * User bits of these objects (bits 14-23 can be used)
171 */
172 enum {
173 /** Secondary correction maps where applied */
174 kSecondary = (1 << 14),
175 /** Vertex bias correction was applied */
176 kVertexBias = (1 << 15),
177 /** Acceptance correction was applied */
178 kAcceptance = (1 << 16),
179 /** Merging efficiency correction was applied */
180 kMergingEfficiency = (1 << 17),
181 /** Signal in overlaps is the sum */
182 kSum = (1 << 18),
183 /** Used eta dependent empirical correction - to be implemented */
184 kEmpirical = (1 << 19)
185 };
186 /**
187 * Return codes of CheckEvent
188 */
189 enum ECheckStatus {
190 /** Event accepted by cuts */
191 kGoodEvent = 0,
192 /** Event centrality not in range */
193 kWrongCentrality,
194 /** Event trigger isn't in the supplied mask */
195 kWrongTrigger,
196 /** Event is a pile-up event */
197 kIsPileup,
198 /** Event has no interaction point information */
199 kNoVertex,
200 /** Event interaction point is out of range */
201 kWrongVertex
202 };
203
7e4038b5 204 /**
205 * Default constructor
206 *
207 * Used by ROOT I/O sub-system - do not use
208 */
209 AliAODForwardMult();
210 /**
211 * Constructor
212 *
f49fc45d 213 * @param isMC Whether this was from MC or not
7e4038b5 214 */
f49fc45d 215 AliAODForwardMult(Bool_t isMC);
7e4038b5 216 /**
217 * Destructor
218 */
f49fc45d 219 virtual ~AliAODForwardMult() {} // Destructor
7e4038b5 220 /**
221 * Initialize
222 *
223 * @param etaAxis Pseudo-rapidity axis
224 */
225 void Init(const TAxis& etaAxis);
226 /**
227 * Get the @f$ d^2N_{ch}/d\eta d\phi@f$ histogram,
228 *
229 * @return @f$ d^2N_{ch}/d\eta d\phi@f$ histogram,
230 */
f49fc45d 231 const TH2D& GetHistogram() const { return fHist; } // Get histogram
7e4038b5 232 /**
233 * Get the @f$ d^2N_{ch}/d\eta d\phi@f$ histogram,
234 *
235 * @return @f$ d^2N_{ch}/d\eta d\phi@f$ histogram,
236 */
f49fc45d 237 TH2D& GetHistogram() { return fHist; } // Get histogram
7e4038b5 238 /**
9453b19e 239 * Get the trigger bits
7e4038b5 240 *
9453b19e 241 * @return Trigger bits
7e4038b5 242 */
9453b19e 243 UInt_t GetTriggerBits() const { return fTriggers; } // Get triggers
7e4038b5 244 /**
245 * Set the trigger mask
246 *
247 * @param trg Trigger mask
248 */
f49fc45d 249 void SetTriggerMask(UInt_t trg) { fTriggers = trg; } // Set triggers
7e4038b5 250 /**
251 * Set bit(s) in trigger mask
252 *
253 * @param bits bit(s) to set
254 */
f49fc45d 255 void SetTriggerBits(UInt_t bits) { fTriggers |= bits; } // Set trigger bits
7e4038b5 256 /**
5bb5d1f6 257 * Check if all bit(s) are set in the trigger mask. Note, this is
258 * an @e and between the bits. If you need an @e or you should use
259 * the member function IsTriggerOrBits
7e4038b5 260 *
261 * @param bits Bits to test for
262 *
5bb5d1f6 263 * @return true if all enabled bits in the argument is also set in
264 * the trigger word
7e4038b5 265 */
266 Bool_t IsTriggerBits(UInt_t bits) const;
5bb5d1f6 267 /**
268 * Check if any of bit(s) are enabled in the trigger word. This is
269 * an @e or between the selected bits. If you need and @a and you
270 * should use the member function IsTriggerBits;
271 *
272 * @param bits Bits to check for
273 *
274 * @return true if any of the enabled bits in the arguments are also
275 * enabled in the trigger mask
276 */
277 Bool_t IsTriggerOrBits(UInt_t bits) const;
7e4038b5 278 /**
279 * Whether we have any trigger bits
290052e7 280 *
281 * @return true if we have some trigger
7e4038b5 282 */
f49fc45d 283 Bool_t HasTrigger() const { return fTriggers != 0; } // Check for triggers
7e4038b5 284 /**
285 * Clear all data
286 *
287 * @param option Passed on to TH2::Reset verbatim
288 */
289 void Clear(Option_t* option="");
290 /**
291 * browse this object
292 *
293 * @param b Browser
294 */
295 void Browse(TBrowser* b);
296 /**
297 * This is a folder
298 *
299 * @return Always true
300 */
f49fc45d 301 Bool_t IsFolder() const { return kTRUE; } // Always true
eb7691d5 302 /**
303 * Check if the data has been secondary corrected by MC maps
304 *
305 * @return true if secondary corrected via MC maps
306 */
bfab35d9 307 Bool_t IsSecondaryCorrected() const { return TestBit(kSecondary); }
eb7691d5 308 /**
309 * Check if vertex bias correction was applied
310 *
311 * @return true if MC based vertex bias was applied
312 */
bfab35d9 313 Bool_t IsVertexBiasCorrected() const { return TestBit(kVertexBias); }
eb7691d5 314 /**
315 * Check if acceptance correction (from dead strips) was applied
316 *
317 * @return true if acceptance correction was applied
318 */
bfab35d9 319 Bool_t IsAcceptanceCorrected() const { return TestBit(kAcceptance); }
eb7691d5 320 /**
321 * Check if merging efficiency (from MC) was applied
322 *
323 * @return true if merging efficiency was applied
324 */
bfab35d9 325 Bool_t IsMergingEfficiencyCorrected() const {
326 return TestBit(kMergingEfficiency); }
eb7691d5 327 /**
328 * Check if an empirical correction was applied in the event level.
329 *
330 * @return True if the empirical correction was applied per event.
331 */
bfab35d9 332 Bool_t IsEmpiricalCorrected() const { return TestBit(kEmpirical); }
eb7691d5 333 /**
334 * Check if the output is the sum (not average) in regions of
335 * overlap between detectors.
336 *
337 *
338 * @return true if the sum (not average) is stored in overlap
339 * regions.
340 */
bfab35d9 341 Bool_t IsSumSignal() const { return TestBit(kSum); }
7e4038b5 342 /**
343 * Print content
344 *
345 * @param option Passed verbatim to TH2::Print
346 */
347 void Print(Option_t* option="") const;
348 /**
349 * Set the z coordinate of the interaction point
350 *
351 * @param ipZ Interaction point z coordinate
352 */
f49fc45d 353 void SetIpZ(Float_t ipZ) { fIpZ = ipZ; } // Set Ip's Z coordinate
b2e7f2d6 354 /**
355 * Set the center of mass energy per nucleon-pair. This is stored
356 * in the (0,0) of the histogram
357 *
358 * @param sNN Center of mass energy per nucleon pair (GeV)
359 */
360 void SetSNN(UShort_t sNN);
361 /**
362 * Get the collision system number
363 * - 0: Unknown
364 * - 1: pp
365 * - 2: PbPb
366 *
367 * @param sys Collision system number
368 */
369 void SetSystem(UShort_t sys);
e58000b7 370 /**
371 * Set the event centrality
372 *
373 * @param c Centrality
374 */
375 void SetCentrality(Float_t c) { fCentrality = c; }
7e4038b5 376 /**
377 * Set the z coordinate of the interaction point
378 *
379 * @return Interaction point z coordinate
380 */
f49fc45d 381 Float_t GetIpZ() const { return fIpZ; } // Get Ip's Z coordinate
7e4038b5 382 /**
383 * Check if we have a valid z coordinate of the interaction point
384 *
385 * @return True if we have a valid interaction point z coordinate
386 */
387 Bool_t HasIpZ() const;
b2e7f2d6 388 /**
389 * Get the center of mass energy per nucleon pair (GeV)
390 *
391 * @return Center of mass energy per nucleon pair (GeV)
392 */
393 UShort_t GetSNN() const;
394 /**
395 * Get the collision system number
396 * - 0: Unknown
397 * - 1: pp
398 * - 2: PbPb
399 *
400 * @return Collision system number
401 */
402 UShort_t GetSystem() const;
7e4038b5 403 /**
404 * Check if the z coordinate of the interaction point is within the
405 * given limits. Note that the convention used corresponds to the
406 * convention used in ROOTs TAxis.
407 *
408 * @param low Lower cut (inclusive)
409 * @param high Upper cut (exclusive)
410 *
411 * @return true if @f$ low \ge ipz < high@f$
412 */
413 Bool_t InRange(Float_t low, Float_t high) const;
e58000b7 414 /**
415 * Get the event centrality
416 *
eb7691d5 417 * @return Centrality
e58000b7 418 */
419 Float_t GetCentrality() const { return fCentrality; }
420 /**
421 * Check if we have a valid centrality
422 *
eb7691d5 423 * @return true if the centrality information is valid
e58000b7 424 */
425 Bool_t HasCentrality() const { return !(fCentrality < 0); }
5bb5d1f6 426 /**
427 * Get the number of SPD clusters seen in @f$ |\eta|<1@f$
428 *
429 * @return Number of SPD clusters seen
430 */
431 UShort_t GetNClusters() const { return fNClusters; }
432 /**
433 * Set the number of SPD clusters seen in @f$ |\eta|<1@f$
434 *
435 * @param n Number of SPD clusters
436 */
437 void SetNClusters(UShort_t n) { fNClusters = n; }
7e4038b5 438 /**
439 * Get the name of the object
440 *
441 * @return Name of object
442 */
f49fc45d 443 const Char_t* GetName() const { return (fIsMC ? "ForwardMC" : "Forward"); }
e938e22b 444 /**
ffca499d 445 * Check if event meets the passses requirements.
446 *
447 * It returns true if @e all of the following is true
448 *
449 * - The trigger is within the bit mask passed.
450 * - The vertex is within the specified limits.
451 * - The centrality is within the specified limits, or if lower
452 * limit is equal to or larger than the upper limit.
453 *
950ab33b 454 * Note, for data with out a centrality estimate (e.g., pp), one
455 * must pass equal centrality cuts, or no data will be accepted. In
456 * other words, for pp data, always pass cMin=0, cMax=0
457 *
ffca499d 458 * If a histogram is passed in the last parameter, then that
459 * histogram is filled with the trigger bits.
e938e22b 460 *
461 * @param triggerMask Trigger mask
462 * @param vzMin Minimum @f$ v_z@f$ (in centimeters)
463 * @param vzMax Maximum @f$ v_z@f$ (in centimeters)
464 * @param cMin Minimum centrality (in percent)
465 * @param cMax Maximum centrality (in percent)
466 * @param hist Histogram to fill
c8b1a7db 467 * @param status Histogram to fill
5f2f85f0 468 * @param removePileup If true, do not accept pile-up events (default)
e938e22b 469 *
470 * @return @c true if the event meets the requirements
471 */
472 Bool_t CheckEvent(Int_t triggerMask=kInel,
473 Double_t vzMin=-10, Double_t vzMax=10,
474 UShort_t cMin=0, UShort_t cMax=100,
bfab35d9 475 TH1* hist=0,
5f2f85f0 476 TH1* status=0,
477 Bool_t removePileup=true) const;
7e4038b5 478 /**
479 * Get a string correspondig to the trigger mask
480 *
481 * @param mask Trigger mask
482 *
483 * @return Static string (copy before use)
484 */
485 static const Char_t* GetTriggerString(UInt_t mask);
e938e22b 486 /**
ffca499d 487 * Make a histogram to record triggers in.
488 *
489 * The bins defined by the trigger enumeration in this class. One
490 * can use this enumeration to retrieve the number of triggers for
491 * each class.
e938e22b 492 *
493 * @param name Name of the histogram
33438b4c 494 * @param mask Trigger mask
e938e22b 495 *
496 * @return Newly allocated histogram
497 */
321cf27d 498 static TH1I* MakeTriggerHistogram(const char* name="triggers",
499 Int_t mask=0);
bfab35d9 500 /**
501 * Make a histogram to record status in.
502 *
503 * The bins defined by the status enumeration in this class.
504 *
505 * @param name Name of the histogram
506 *
507 * @return Newly allocated histogram
508 */
509 static TH1I* MakeStatusHistogram(const char* name="status");
9453b19e 510 /**
511 * Utility function to make a trigger mask from the passed string.
512 *
513 * The string is a comma or space seperated list of case-insensitive
514 * strings
515 *
516 * - INEL
517 * - INEL>0
518 * - NSD
519 *
520 * @param what Which triggers to put in the mask.
521 *
522 * @return The generated trigger mask.
523 */
524 static UInt_t MakeTriggerMask(const char* what);
7e4038b5 525protected:
290052e7 526 /** From MC or not */
5bb5d1f6 527 Bool_t fIsMC; // Whether this is from MC
290052e7 528 /** Histogram of @f$d^2N_{ch}/(d\eta d\phi)@f$ for this event */
5bb5d1f6 529 TH2D fHist; // Histogram of d^2N_{ch}/(deta dphi) for this event
290052e7 530 /** Trigger bits */
5bb5d1f6 531 UInt_t fTriggers; // Trigger bit mask
290052e7 532 /** Interaction point @f$z@f$ coordinate */
5bb5d1f6 533 Float_t fIpZ; // Z coordinate of the interaction point
290052e7 534 /** Centrality */
5bb5d1f6 535 Float_t fCentrality; // Event centrality
290052e7 536 /** Number of clusters in @f$|\eta|<1@f$ */
5bb5d1f6 537 UShort_t fNClusters; // Number of SPD clusters in |eta|<1
290052e7 538 /** Invalid value for interaction point @f$z@f$ coordiante */
7e4038b5 539 static const Float_t fgkInvalidIpZ; // Invalid IpZ value
bfab35d9 540 ClassDef(AliAODForwardMult,5); // AOD forward multiplicity
7e4038b5 541};
542
543//____________________________________________________________________
544inline Bool_t
545AliAODForwardMult::InRange(Float_t low, Float_t high) const
546{
547 return HasIpZ() && fIpZ >= low && fIpZ < high;
548}
549
550//____________________________________________________________________
551inline Bool_t
552AliAODForwardMult::IsTriggerBits(UInt_t bits) const
553{
0be6c8cd 554 return HasTrigger() && ((fTriggers & bits) == bits);
7e4038b5 555}
5bb5d1f6 556//____________________________________________________________________
557inline Bool_t
558AliAODForwardMult::IsTriggerOrBits(UInt_t bits) const
559{
560 return HasTrigger() && ((fTriggers & bits) != 0);
561}
7e4038b5 562
563#endif
564// Local Variables:
565// mode: C++
566// End:
567