]>
Commit | Line | Data |
---|---|---|
34d0a9fe | 1 | /******************************************************************************* |
2 | * Copyright(c) 2003, IceCube Experiment at the South Pole. All rights reserved. | |
3 | * | |
4 | * Author: The IceCube RALICE-based Offline 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. | |
12 | * The authors make no claims about the suitability of this software for | |
13 | * any purpose. It is provided "as is" without express or implied warranty. | |
14 | *******************************************************************************/ | |
15 | ||
16 | // $Id$ | |
17 | ||
18 | /////////////////////////////////////////////////////////////////////////// | |
19 | // Class IceCleanHits | |
20 | // TTask derived class to perform hit cleaning. | |
21 | // | |
22 | // The code in this processor is based on the algorithms as developed | |
23 | // by Oladipo Fadiran and George Japaridze (Clark Atlanta University, USA). | |
24 | // | |
25 | // Criteria applied for Amanda modules : | |
26 | // ------------------------------------- | |
27 | // 1) ADC within [min,max] Default : [0.3,999999] PE | |
28 | // 2) TOT within [min,max] Default : electrical [125,2000] optical [20,2000] ns | |
29 | // 3) abs(LE-Ttrig)<=win Default : win=2250 ns (Ttrig represents the trigger time) | |
30 | // 4) At least one other hit within radius R and time difference dt | |
31 | // to remove isolated hits. Defaults : R=70 m dt=500 ns | |
32 | // | |
33 | // The defaults of the various parameters can be changed by the corresponding | |
34 | // Set memberfunctions. | |
35 | // | |
668c6f58 | 36 | // Concerning the trigger time : |
37 | // ----------------------------- | |
38 | // We adopt an overall trigger time setting for each year of data taking. | |
39 | // The mean values obtained from Dipo's uncalibrated LE distributions | |
40 | // are currently used here. | |
41 | // No data were yet available for year<2002, so as default the 2002 | |
42 | // value is used for those early runs. | |
43 | // It seems that in 2005 the trigger time was changed within the year | |
44 | // from 24170 ns to 12138 ns. The latter however shows a 2-bump structure, | |
45 | // which may point at the fact that people have been trying things out | |
46 | // with the DAQ system. | |
47 | // So, currently the 24170 ns will be used for all the 2005 data until | |
48 | // the issue is settled. | |
49 | // | |
34d0a9fe | 50 | // The hits which do not fullfill the criteria are flagged "dead" for the |
51 | // corresponding signal slot. This means they are still present in the | |
52 | // IceEvent structure and are as such still accessible. | |
53 | // It is left to the user to decide (based on the various "dead" flag settings) | |
54 | // whether or not to use these hits in his/her reconstruction or analysis. | |
55 | // | |
56 | // Note : This processor only works properly on Time and ADC calibrated data. | |
57 | // | |
58 | //--- Author: Nick van Eijndhoven 13-oct-2005 Utrecht University | |
59 | //- Modified: NvE $Date$ Utrecht University | |
60 | /////////////////////////////////////////////////////////////////////////// | |
61 | ||
62 | #include "IceCleanHits.h" | |
63 | #include "Riostream.h" | |
64 | ||
65 | ClassImp(IceCleanHits) // Class implementation to enable ROOT I/O | |
66 | ||
67 | IceCleanHits::IceCleanHits(const char* name,const char* title) : TTask(name,title) | |
68 | { | |
69 | // Default constructor. | |
70 | fEvt=0; | |
71 | fAdcminA=0.3; | |
72 | fAdcmaxA=999999; | |
73 | fTotminAE=125; | |
74 | fTotmaxAE=2000; | |
75 | fTotminAO=20; | |
76 | fTotmaxAO=2000; | |
77 | fRmaxA=70; | |
78 | fDtmaxA=500; | |
79 | fTwinA=2250; | |
80 | } | |
81 | /////////////////////////////////////////////////////////////////////////// | |
82 | IceCleanHits::~IceCleanHits() | |
83 | { | |
84 | // Default destructor. | |
85 | } | |
86 | /////////////////////////////////////////////////////////////////////////// | |
87 | void IceCleanHits::SetAdcRangeA(Float_t min,Float_t max) | |
88 | { | |
89 | // Set Amanda ADC range in PE. | |
90 | // The default for the maximum is 999999. | |
91 | fAdcminA=min; | |
92 | fAdcmaxA=max; | |
93 | } | |
94 | /////////////////////////////////////////////////////////////////////////// | |
95 | void IceCleanHits::SetTotRangeAE(Float_t min,Float_t max) | |
96 | { | |
97 | // Set Amanda electrical TOT range in ns. | |
98 | // The default for the maximum is 2000. | |
99 | fTotminAE=min; | |
100 | fTotmaxAE=max; | |
101 | } | |
102 | /////////////////////////////////////////////////////////////////////////// | |
103 | void IceCleanHits::SetTotRangeAO(Float_t min,Float_t max) | |
104 | { | |
105 | // Set Amanda optical TOT range in ns. | |
106 | // The default for the maximum is 2000. | |
107 | fTotminAO=min; | |
108 | fTotmaxAO=max; | |
109 | } | |
110 | /////////////////////////////////////////////////////////////////////////// | |
111 | void IceCleanHits::SetIsolationA(Float_t rmax,Float_t dtmax) | |
112 | { | |
113 | // Set Amanda isolation radius (in m) and time difference (in ns). | |
114 | fRmaxA=rmax; | |
115 | fDtmaxA=dtmax; | |
116 | } | |
117 | /////////////////////////////////////////////////////////////////////////// | |
118 | void IceCleanHits::SetTwindowA(Float_t dtmax) | |
119 | { | |
120 | // Set Amanda maximal trigger window (in ns). | |
121 | // Only hits which occur in [T-dtmax,T+dtmax] will be kept, | |
122 | // where T indicates the trigger time. | |
123 | fTwinA=dtmax; | |
124 | } | |
125 | /////////////////////////////////////////////////////////////////////////// | |
126 | void IceCleanHits::Exec(Option_t* opt) | |
127 | { | |
128 | // Implementation of the hit cleaning procedures. | |
129 | ||
130 | TString name=opt; | |
131 | AliJob* parent=(AliJob*)(gROOT->GetListOfTasks()->FindObject(name.Data())); | |
132 | ||
133 | if (!parent) return; | |
134 | ||
135 | fEvt=(IceEvent*)parent->GetObject("IceEvent"); | |
136 | if (!fEvt) return; | |
137 | ||
138 | Amanda(); | |
139 | InIce(); | |
140 | IceTop(); | |
141 | } | |
142 | /////////////////////////////////////////////////////////////////////////// | |
143 | void IceCleanHits::Amanda() | |
144 | { | |
145 | // Hit cleaning for Amanda modules. | |
146 | ||
668c6f58 | 147 | // Trigger time setting according to year of data taking |
148 | // The mean values obtained from Dipo's uncalibrated LE distributions | |
149 | // are currently used here. | |
150 | // No data were yet available for year<2002, so as default the 2002 | |
151 | // value is used for those early runs. | |
152 | // It seems that in 2005 the trigger time was changed within the year | |
153 | // from 24170 ns to 12138 ns. The latter however shows a 2-bump structure, | |
154 | // so currently the 24170 ns will be used for the 2005 data. | |
e51b7d1a | 155 | Int_t year=(int)fEvt->GetJE(); |
668c6f58 | 156 | Float_t ttrig=23958; |
157 | if (year==2003) ttrig=23994; | |
158 | if (year==2004) ttrig=24059.5; | |
159 | if (year==2005) ttrig=24170; | |
160 | ||
34d0a9fe | 161 | // All Amanda OMs with a signal |
162 | TObjArray* aoms=fEvt->GetDevices("IceAOM"); | |
163 | ||
164 | // Local OM array with bad/dead OMs (as indicated via IceCalibrate) discarded | |
165 | TObjArray oms; | |
166 | IceAOM* omx=0; | |
167 | for (Int_t i=0; i<aoms->GetEntries(); i++) | |
168 | { | |
169 | omx=(IceAOM*)aoms->At(i); | |
170 | if (!omx) continue; | |
171 | if (omx->GetDeadValue("ADC") || omx->GetDeadValue("LE") || omx->GetDeadValue("TOT")) continue; | |
172 | oms.Add(omx); | |
173 | } | |
174 | ||
175 | // Local array with clean hits | |
176 | TObjArray hits; | |
177 | Int_t omid=0; | |
178 | Int_t clean=1; | |
179 | AliSignal* sx=0; | |
180 | Float_t adc,le,tot; | |
34d0a9fe | 181 | for (Int_t iom=0; iom<oms.GetEntries(); iom++) |
182 | { | |
183 | omx=(IceAOM*)oms.At(iom); | |
184 | if (!omx) continue; | |
185 | omid=omx->GetUniqueID(); | |
186 | for (Int_t ih=1; ih<=omx->GetNhits(); ih++) | |
187 | { | |
188 | sx=omx->GetHit(ih); | |
189 | if (!sx) continue; | |
190 | adc=sx->GetSignal("ADC",7); | |
191 | le=sx->GetSignal("LE",7); | |
192 | tot=sx->GetSignal("TOT",7); | |
193 | ||
194 | // Remove hits with an ADC value outside the range | |
195 | if (adc<fAdcminA || adc>fAdcmaxA) | |
196 | { | |
197 | sx->SetDead("ADC"); | |
198 | clean=0; | |
199 | } | |
200 | // Remove hits with a TOT value outside the range | |
201 | // Note : Different ranges for electrical and optical modules | |
202 | if (omid<303) // Electrical OMs | |
203 | { | |
204 | if (tot<fTotminAE || tot>fTotmaxAE) | |
205 | { | |
206 | sx->SetDead("TOT"); | |
207 | clean=0; | |
208 | } | |
209 | } | |
210 | else // Optical OMs | |
211 | { | |
212 | if (tot<fTotminAO || tot>fTotmaxAO) | |
213 | { | |
214 | sx->SetDead("TOT"); | |
215 | clean=0; | |
216 | } | |
217 | } | |
668c6f58 | 218 | // Remove hits that are outside the trigger time window. |
219 | // Since the trigger time was determined from uncalibrated LE's | |
220 | // (to include cable length effects) the uncalibrated LE of each | |
221 | // hit should be used here as well. | |
222 | le=sx->GetSignal("LE",-7); | |
34d0a9fe | 223 | if (fabs(le-ttrig)>fTwinA) |
224 | { | |
225 | sx->SetDead("LE"); | |
226 | clean=0; | |
227 | } | |
34d0a9fe | 228 | // Store only the current clean hits in our local hit array |
229 | // This will save CPU time for the isolation criterion | |
230 | if (clean) hits.Add(sx); | |
231 | } | |
232 | } | |
233 | ||
234 | // Isolation cut | |
235 | // Only retain hits that have at least one other hit within a certain | |
236 | // radius and within a certain time window | |
237 | Int_t nhits=hits.GetEntries(); | |
238 | AliSignal* sx1=0; | |
239 | AliSignal* sx2=0; | |
240 | Float_t t1,t2; | |
241 | IceAOM* omx1=0; | |
242 | IceAOM* omx2=0; | |
243 | AliPosition r1; | |
244 | AliPosition r2; | |
245 | Float_t dt,dr; | |
246 | Int_t iso; | |
247 | for (Int_t jh1=0; jh1<nhits; jh1++) | |
248 | { | |
249 | sx1=(AliSignal*)hits.At(jh1); | |
250 | if (!sx1) continue; | |
251 | iso=1; | |
252 | for (Int_t jh2=0; jh2<nhits; jh2++) | |
253 | { | |
254 | if (jh1==jh2) | |
255 | { | |
256 | iso=0; | |
257 | continue; | |
258 | } | |
259 | sx2=(AliSignal*)hits.At(jh2); | |
260 | if (!sx2) continue; | |
261 | t1=sx1->GetSignal("LE",7); | |
262 | t2=sx2->GetSignal("LE",7); | |
263 | dt=fabs(t2-t1); | |
264 | if (dt>fDtmaxA) continue; | |
265 | omx1=(IceAOM*)sx1->GetDevice(); | |
266 | omx2=(IceAOM*)sx2->GetDevice(); | |
267 | if (omx1 && omx2) | |
268 | { | |
269 | r1=omx1->GetPosition(); | |
270 | r2=omx2->GetPosition(); | |
271 | dr=r1.GetDistance(r2); | |
272 | if (dr>fRmaxA) continue; | |
273 | iso=0; | |
274 | } | |
275 | } | |
276 | if (iso) sx1->SetDead("LE"); | |
277 | } | |
278 | } | |
279 | /////////////////////////////////////////////////////////////////////////// | |
280 | void IceCleanHits::InIce() | |
281 | { | |
282 | // Hit cleaning for IceCube InIce DOMs. | |
283 | } | |
284 | /////////////////////////////////////////////////////////////////////////// | |
285 | void IceCleanHits::IceTop() | |
286 | { | |
287 | // Hit cleaning for IceTop DOMs. | |
288 | } | |
289 | /////////////////////////////////////////////////////////////////////////// |