]> git.uio.no Git - u/mrichter/AliRoot.git/blame - PWGLF/FORWARD/analysis2/AliFMDESDFixer.cxx
Merge branch 'feature-movesplit'
[u/mrichter/AliRoot.git] / PWGLF / FORWARD / analysis2 / AliFMDESDFixer.cxx
CommitLineData
0ccdab7b 1#include "AliFMDESDFixer.h"
2#include "AliESDFMD.h"
3#include "AliFMDStripIndex.h"
4#include "AliForwardUtil.h"
5#include "AliForwardCorrectionManager.h"
6#include "AliFMDCorrNoiseGain.h"
7#include <TH1.h>
8#include <TList.h>
9#include <TObjArray.h>
10#include <TROOT.h>
11#include <TMath.h>
12#include <iostream>
13#include <iomanip>
14
15
16//____________________________________________________________________
17AliFMDESDFixer::AliFMDESDFixer()
18 : TObject(),
19 fRecoFactor(1),
20 fMaxNoiseCorr(0.05),
21 fRecalculateEta(true),
22 fXtraDead(0),
23 fHasXtraDead(false),
24 fInvalidIsEmpty(false),
25 fNoiseChange(0),
26 fEtaChange(0),
27 fDeadChange(0)
28{}
29
30//____________________________________________________________________
31AliFMDESDFixer::AliFMDESDFixer(const char*)
32 : TObject(),
33 fRecoFactor(1),
34 fMaxNoiseCorr(0.05),
35 fRecalculateEta(false),
36 fXtraDead(AliFMDStripIndex::Pack(3,'O',19,511)+1),
37 fHasXtraDead(false),
38 fInvalidIsEmpty(false),
39 fNoiseChange(0),
40 fEtaChange(0),
41 fDeadChange(0)
42{}
43
44
45//____________________________________________________________________
46AliFMDESDFixer::AliFMDESDFixer(const AliFMDESDFixer& o)
47 : TObject(),
48 fRecoFactor(o.fRecoFactor),
49 fMaxNoiseCorr(o.fMaxNoiseCorr),
50 fRecalculateEta(o.fRecalculateEta),
51 fXtraDead(o.fXtraDead),
52 fHasXtraDead(o.fHasXtraDead),
53 fInvalidIsEmpty(o.fInvalidIsEmpty),
54 fNoiseChange(0),
55 fEtaChange(0),
56 fDeadChange(0)
57{}
58
59//____________________________________________________________________
60AliFMDESDFixer&
61AliFMDESDFixer::operator=(const AliFMDESDFixer& o)
62{
63 if (&o == this) return *this;
64
65 fRecoFactor = o.fRecoFactor;
66 fMaxNoiseCorr = o.fMaxNoiseCorr;
67 fRecalculateEta = o.fRecalculateEta;
68 fXtraDead = o.fXtraDead;
69 fHasXtraDead = o.fHasXtraDead;
70 fInvalidIsEmpty = o.fInvalidIsEmpty;
71 fNoiseChange = 0;
72 fEtaChange = 0;
73 fDeadChange = 0;
74
75 return *this;
76};
77
78//____________________________________________________________________
79void
80AliFMDESDFixer::CreateOutputObjects(TList* l)
81{
82 TList* d = new TList;
83 d->SetName(GetName());
84 l->Add(d);
85
86 d->Add(AliForwardUtil::MakeParameter("recoFactor", fRecoFactor));
87 d->Add(AliForwardUtil::MakeParameter("recalcEta", fRecalculateEta));
88 d->Add(AliForwardUtil::MakeParameter("invalidIsEmpty", fInvalidIsEmpty));
89
90 fNoiseChange = new TH1D("noiseChange", "#delta#Delta due to noise",30,0,.3);
91 fNoiseChange->SetDirectory(0);
92 fNoiseChange->SetFillColor(kYellow+1);
93 fNoiseChange->SetFillStyle(3001);
94 d->Add(fNoiseChange);
95
96 fEtaChange = new TH1D("etaChange", "#delta#eta",40,-1,1);
97 fEtaChange->SetDirectory(0);
98 fEtaChange->SetFillColor(kCyan+1);
99 fEtaChange->SetFillStyle(3001);
100 d->Add(fEtaChange);
101
102 fDeadChange = new TH1D("deadChange", "#deltaN_{dead}",100,0,51200);
103 fDeadChange->SetDirectory(0);
104 fDeadChange->SetFillColor(kMagenta+1);
105 fDeadChange->SetFillStyle(3001);
106 d->Add(fDeadChange);
107
108 TObjArray* extraDead = new TObjArray;
109 extraDead->SetOwner();
110 extraDead->SetName("extraDead");
111 fXtraDead.Compact();
112 UInt_t firstBit = fXtraDead.FirstSetBit();
113 UInt_t nBits = fXtraDead.GetNbits();
114 for (UInt_t i = firstBit; i < nBits; i++) {
115 if (!fXtraDead.TestBitNumber(i)) continue;
116 UShort_t dd, s, t;
117 Char_t r;
118 AliFMDStripIndex::Unpack(i, dd, r, s, t);
119 extraDead->Add(AliForwardUtil::MakeParameter(Form("FMD%d%c[%02d,%03d]",
120 dd, r, s, t),
121 UShort_t(i)));
122 }
123 d->Add(extraDead);
124 fHasXtraDead = nBits > 0;
125
126}
127
128//____________________________________________________________________
129void
130AliFMDESDFixer::AddDead(UShort_t d, Char_t r, UShort_t s, UShort_t t)
131{
132 if (d < 1 || d > 3) {
133 Warning("AddDead", "Invalid detector FMD%d", d);
134 return;
135 }
136 Bool_t inner = (r == 'I' || r == 'i');
137 if (d == 1 && !inner) {
138 Warning("AddDead", "Invalid ring FMD%d%c", d, r);
139 return;
140 }
141 if ((inner && s >= 20) || (!inner && s >= 40)) {
142 Warning("AddDead", "Invalid sector FMD%d%c[%02d]", d, r, s);
143 return;
144 }
145 if ((inner && t >= 512) || (!inner && t >= 256)) {
146 Warning("AddDead", "Invalid strip FMD%d%c[%02d,%03d]", d, r, s, t);
147 return;
148 }
149
150 Int_t id = AliFMDStripIndex::Pack(d, r, s, t);
151 // Int_t i = 0;
152 fXtraDead.SetBitNumber(id, true);
153}
154//____________________________________________________________________
155void
156AliFMDESDFixer::AddDeadRegion(UShort_t d, Char_t r,
157 UShort_t s1, UShort_t s2,
158 UShort_t t1, UShort_t t2)
159{
160 // Add a dead region spanning from FMD<d><r>[<s1>,<t1>] to
161 // FMD<d><r>[<s2>,<t2>] (both inclusive)
162 for (Int_t s = s1; s <= s2; s++)
163 for (Int_t t = t1; t <= t2; t++)
164 AddDead(d, r, s, t);
165}
166//____________________________________________________________________
167void
168AliFMDESDFixer::AddDead(const Char_t* script)
169{
170 if (!script || script[0] == '\0') return;
171
172 gROOT->Macro(Form("%s((AliFMDESDFixer*)%p);", script, this));
173}
174
175//____________________________________________________________________
176Bool_t
177AliFMDESDFixer::IsDead(UShort_t d, Char_t r, UShort_t s, UShort_t t) const
178{
179 Int_t id = AliFMDStripIndex::Pack(d, r, s, t);
180 return fXtraDead.TestBitNumber(id);
181}
182
183//____________________________________________________________________
184Int_t
185AliFMDESDFixer::FindTargetNoiseFactor(const AliESDFMD& esd, Bool_t check) const
186{
187 if (!IsUseNoiseCorrection())
188 // If the reconstruction factor was high (4 or more), do nothing
189 return 0;
06714d86 190
191 Int_t target = 0;
192 if (AliESDFMD::Class_Version() < 4) {
193 // IF we running with older STEER - we fix it here
194 target = 4;
195 } else {
0da75ff8 196#if 1
06714d86 197 if (!esd.TestBit(1 << 14)) {
198 // If the bit isn't set, do nothing
199 return 0;
200 }
0da75ff8 201#else
06714d86 202 // Uncommented until Peter commits patch to STEER/ESD
203 if (!esd.NeedNoiseFix()) {
204 // If the bit isn't set, do nothing
205 return 0;
206 }
0da75ff8 207#endif
5108032e 208 target = Int_t(esd.GetNoiseFactor());
06714d86 209 }
0ccdab7b 210 // Get the target factor - even thought the method below returns a
211 // floating point value, we know that the noise factor is always
212 // integer, so we coerce it to be the same here.
06714d86 213 target -= fRecoFactor;
0ccdab7b 214
215 // If the target factor is the same or smaller than the assumed
216 // factor, we have nothing to do here, and we return immediately
217 if (target <= 0) return 0;
218
219 // Get the scaled noise from the correction mananger
220 if (check && !AliForwardCorrectionManager::Instance().GetNoiseGain())
221 return 0;
222
223 return target;
224}
225
226//____________________________________________________________________
227#define ETA2COS(ETA) \
228 TMath::Cos(2*TMath::ATan(TMath::Exp(-TMath::Abs(ETA))))
229
230//____________________________________________________________________
231void
232AliFMDESDFixer::Fix(AliESDFMD& esd, Double_t zvtx)
233{
234
235 const AliFMDCorrNoiseGain* ng = 0;
236 Int_t tgtFactor = FindTargetNoiseFactor(esd, false);
237 if (tgtFactor > 0)
238 ng = AliForwardCorrectionManager::Instance().GetNoiseGain();
239
240 if (!ng && !fHasXtraDead && !fRecalculateEta && !fInvalidIsEmpty)
241 // We have nothing to do!
242 return;
243
244 UShort_t nDead = 0;
245 for (UShort_t d = 1; d <= 3; d++) {
246 UShort_t nQ = d == 1 ? 1 : 2;
247
248 for (UShort_t q = 0; q < nQ; q++) {
249 Char_t r = (q == 0 ? 'I' : 'O');
250 UShort_t nS = (q == 0 ? 20 : 40);
251 UShort_t nT = (q == 0 ? 512 : 256);
252
253 for (UShort_t s = 0; s < nS; s++) {
254 for (UShort_t t = 0; t < nT; t++) {
255 Double_t mult = esd.Multiplicity(d,r,s,t);
256 Double_t eta = esd.Eta(d,r,s,t);
257 Double_t cosTheta = 0;
258
259 if (CheckDead(d,r,s,t,mult)) nDead++;
260
261 // Possibly re-calculate eta
262 if (fRecalculateEta) RecalculateEta(d,r,s,t,zvtx,eta,mult,cosTheta);
263
264 // Possibly correct for poor treatment of ZS in reconstruction.
265 if (ng && mult != AliESDFMD::kInvalidMult) {
266 if (cosTheta <= 0) cosTheta = ETA2COS(eta);
267 if (!NoiseCorrect(tgtFactor,ng->Get(d,r,s,t), cosTheta, mult))
268 nDead++;
269 }
270
271 // Write out final values to object
272 if (mult >= AliESDFMD::kInvalidMult) mult = AliESDFMD::kInvalidMult;
273 esd.SetMultiplicity(d,r,s,t,mult);
274 esd.SetEta(d,r,s,t,eta);
275 } // for t
276 } // for s
277 } // for q
278 } // for d
279 fDeadChange->Fill(nDead);
280}
281
282//____________________________________________________________________
283Bool_t
284AliFMDESDFixer::CheckDead(UShort_t d, Char_t r, UShort_t s, UShort_t t,
285 Double_t& mult)
286{
287 // Correct for zero's being flagged as invalid
288 if (mult == AliESDFMD::kInvalidMult && fInvalidIsEmpty) mult = 0;
289
290 // Take into account what we're defined as dead
291 if (IsDead(d,r,s,t)) {
292 mult = AliESDFMD::kInvalidMult;
293 return true;
294 }
295 return false;
296}
297
298//____________________________________________________________________
299void
300AliFMDESDFixer::RecalculateEta(UShort_t d, Char_t r, UShort_t s, UShort_t t,
301 Double_t zvtx, Double_t& eta, Double_t& mult,
302 Double_t& cosTheta)
303{
304 Double_t oldEta = eta;
305 Double_t newEta = AliForwardUtil::GetEtaFromStrip(d,r,s,t, zvtx);
306 eta = newEta;
307
308 fEtaChange->Fill(newEta-oldEta);
309
310 if (mult == AliESDFMD::kInvalidMult) return;
311
312 Double_t newCos = ETA2COS(newEta);
313 Double_t oldCos = ETA2COS(oldEta);
314 Double_t corr = newCos / oldCos;
315 cosTheta = newCos;
316 mult *= corr;
317}
318//____________________________________________________________________
319Bool_t
320AliFMDESDFixer::NoiseCorrect(Int_t target, Double_t corr, Double_t cosTheta,
321 Double_t& mult)
322{
323 if (corr > fMaxNoiseCorr || corr <= 0) {
324 mult = AliESDFMD::kInvalidMult;
325 return false;
326 }
327 Double_t add = corr * target * cosTheta;
328 fNoiseChange->Fill(add);
329
330 mult += add;
331 return true;
332}
333
334#define PF(N,V,...) \
335 AliForwardUtil::PrintField(N,V, ## __VA_ARGS__)
336#define PFB(N,FLAG) \
337 do { \
338 AliForwardUtil::PrintName(N); \
339 std::cout << std::boolalpha << (FLAG) << std::noboolalpha << std::endl; \
340 } while(false)
341#define PFV(N,VALUE) \
342 do { \
343 AliForwardUtil::PrintName(N); \
344 std::cout << (VALUE) << std::endl; } while(false)
345
346//____________________________________________________________________
347void
348AliFMDESDFixer::Print(Option_t*) const
349{
350 AliForwardUtil::PrintTask(*this);
351 gROOT->IncreaseDirLevel();
352 PFB("Consider invalid null", fInvalidIsEmpty);
c1351982 353 PFB("Has extra dead", fHasXtraDead || fXtraDead.GetNbits() > 0);
0ccdab7b 354 PFV("Reco noise factor", fRecoFactor);
355 PFV("Max noise corr", fMaxNoiseCorr);
356 PFB("Recalc. eta", fRecalculateEta);
357 gROOT->DecreaseDirLevel();
358}
359
360//____________________________________________________________________
361//
362// EOF
363//