Line data Source code
1 : /**************************************************************************
2 : * Copyright(c) 1998-2007, 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 :
17 : /// \class AliTPCQAChecker
18 : /// \brief Checks implemented a la AliMUONQAChecker.
19 : ///
20 : /// Checks the quality assurance by realzed checks on histogram content.
21 : ///
22 : /// Based on AliPHOSQAChecker.
23 : /// Checks the quality assurance by comparing with reference data.
24 : ///
25 : /// \author P. Christiansen, Lund
26 : /// \date January 2008 - September 2009.
27 :
28 : // --- ROOT header files ---
29 : #include <TH1.h>
30 :
31 : // --- AliRoot header files ---
32 : #include "AliTPCQAChecker.h"
33 : #include "AliTPCQADataMakerRec.h"
34 :
35 : /// \cond CLASSIMP
36 24 : ClassImp(AliTPCQAChecker)
37 : /// \endcond
38 :
39 :
40 : //__________________________________________________________________
41 : AliTPCQAChecker& AliTPCQAChecker::operator = (const AliTPCQAChecker &checker)
42 : {
43 : /// Equal operator.
44 :
45 0 : this->~AliTPCQAChecker();
46 0 : new(this) AliTPCQAChecker(checker);
47 0 : return *this;
48 0 : }
49 :
50 : //__________________________________________________________________
51 : void
52 : AliTPCQAChecker::Check(Double_t * rv, AliQAv1::ALITASK_t index, TObjArray ** list,
53 : const AliDetectorRecoParam * /*recoParam*/)
54 : {
55 : /// It is important to understand the destinction between indexed tasks (AliQAv1::TASKINDEX_t) which are used in the DataMaker classes and indexed tasks (AliQAv1::ALITASK_t) whihc are used in the checker class.
56 : ///
57 : /// From the AliQAChecker::Run() methods we have:
58 : /// AliQAv1::kRAW
59 : /// - AliQAv1::kRAWS
60 : ///
61 : /// AliQAv1::kSIM
62 : /// - AliQAv1::kHITS
63 : /// - AliQAv1::kSDIGITS
64 : /// - AliQAv1::kDIGITS
65 : ///
66 : /// AliQAv1::kREC
67 : /// - AliQAv1::kDIGITSR
68 : /// - AliQAv1::kRECPOINTS
69 : /// - AliQAv1::kTRACKSEGMENTS
70 : /// - AliQAv1::kRECPARTICLES
71 : ///
72 : /// AliQAv1::kESD ;
73 : /// -AliQAv1::kESDS
74 : ///
75 : /// This means that for each group of tasks the Check will be called
76 : /// one or more times. This also mean that we cannot know what
77 : /// histograms will be or not be there in a single call... And we
78 : /// also do not know the position in the list of the histogram.
79 :
80 : /// Check objects in list
81 18 : if(fDebug>0)
82 0 : AliInfo("In AliTPCQAChecker::Check");
83 :
84 9 : if (index!=AliQAv1::kRAW&&index!=AliQAv1::kSIM&&index!=AliQAv1::kREC&&index!=AliQAv1::kESD) {
85 :
86 0 : AliWarning(Form("Checker for task %d not implement for the moment",index));
87 0 : return;
88 : }
89 :
90 108 : for (Int_t specie = 0 ; specie < AliRecoParam::kNSpecies ; specie++)
91 45 : rv[specie] = 1.0; // All is fine
92 :
93 108 : for (Int_t specie = 0 ; specie < AliRecoParam::kNSpecies ; specie++) {
94 :
95 45 : if ( !AliQAv1::Instance()->IsEventSpecieSet(specie) )
96 : continue ;
97 :
98 0 : if (index == AliQAv1::kRAW)
99 0 : rv[specie] = CheckRAW(specie, list[specie]);
100 0 : if (index == AliQAv1::kSIM)
101 0 : rv[specie] = CheckSIM(specie, list[specie]);
102 0 : if (index == AliQAv1::kREC)
103 0 : rv[specie] = CheckREC(specie, list[specie]);
104 0 : if (index == AliQAv1::kESD)
105 0 : rv[specie] = CheckESD(specie, list[specie]);
106 :
107 0 : if(fDebug>3)
108 0 : AliInfo(Form("Specie: %s. Task: %s. Value: %f",
109 : AliRecoParam::GetEventSpecieName(specie),
110 : AliQAv1::GetAliTaskName(index),
111 : rv[specie]));
112 : }
113 9 : }
114 :
115 : //______________________________________________________________________________
116 : Double_t AliTPCQAChecker::CheckRAW(Int_t specie, TObjArray* list)
117 : {
118 : /// Check ESD
119 :
120 0 : if(fDebug>0)
121 0 : AliInfo("In AliTPCQAChecker::CheckRAW");
122 :
123 0 : if(fDebug>2)
124 0 : list->Print();
125 :
126 0 : TH1* hRawsOccupancyVsSector = static_cast<TH1*>
127 0 : (list->FindObject(Form("%s_hRawsOccupancyVsSector",AliRecoParam::GetEventSpecieName(specie))));
128 0 : TH1* hRawsQmaxVsSector = static_cast<TH1*>
129 0 : (list->FindObject(Form("%s_hRawsQmaxVsSector",AliRecoParam::GetEventSpecieName(specie))));
130 :
131 0 : if (!hRawsOccupancyVsSector || !hRawsQmaxVsSector)
132 0 : return -0.5; // fatal
133 :
134 0 : if(hRawsOccupancyVsSector->GetEntries()==0) {
135 0 : return 0.25; // error - No TPC data!
136 : }
137 :
138 0 : Int_t nBinsX = hRawsOccupancyVsSector->GetNbinsX();
139 0 : for(Int_t i = 1; i <= nBinsX; i++) {
140 :
141 0 : if(hRawsOccupancyVsSector->GetBinContent(i)==0)
142 0 : return 0.75; // warning - no TPC data for at least one sector
143 : }
144 :
145 0 : return 1.0; // ok
146 0 : }
147 :
148 : //______________________________________________________________________________
149 : Double_t AliTPCQAChecker::CheckSIM(Int_t specie, TObjArray* list)
150 : {
151 : /// This method checks the QA histograms associated with simulation
152 : ///
153 : /// For TPC this is:
154 : /// Digits :
155 : /// The digit histogram gives the ADC distribution for all sigbnals
156 : /// above threshold. The check is just that there are digits.
157 : /// Hits : The hit histograms are checked to see that they are not
158 : /// empty. They contain a lot of detailed information on the
159 : /// energyloss model (they were used to debug the AliRoot TPC use of
160 : /// FLUKA).
161 : ///
162 : /// The check methods are simple:
163 : /// We do not know if it is bad that histograms are missing because
164 : /// this will always be the case for summable digits. So this check
165 : /// is not possible here.
166 : /// If digit histogram is empty (set error)
167 : /// If one of the hit histograms are empty (set error)
168 :
169 0 : if(fDebug>0)
170 0 : AliInfo("In AliTPCQAChecker::CheckSIM");
171 :
172 0 : if(fDebug>2)
173 0 : list->Print();
174 :
175 0 : TH1* hDigits = static_cast<TH1*>
176 0 : (list->FindObject(Form("%s_hDigitsADC",AliRecoParam::GetEventSpecieName(specie))));
177 0 : TH1* hHitsNhits = static_cast<TH1*>
178 0 : (list->FindObject(Form("%s_hHitsNhits",AliRecoParam::GetEventSpecieName(specie))));
179 0 : TH1* hHitsElectrons = static_cast<TH1*>
180 0 : (list->FindObject(Form("%s_hHitsElectrons",AliRecoParam::GetEventSpecieName(specie))));
181 0 : TH1* hHitsRadius = static_cast<TH1*>
182 0 : (list->FindObject(Form("%s_hHitsRadius",AliRecoParam::GetEventSpecieName(specie))));
183 0 : TH1* histHitsPrimPerCm = static_cast<TH1*>
184 0 : (list->FindObject(Form("%s_histHitsPrimPerCm",AliRecoParam::GetEventSpecieName(specie))));
185 0 : TH1* histHitsElectronsPerCm = static_cast<TH1*>
186 0 : (list->FindObject(Form("%s_histHitsElectronsPerCm",AliRecoParam::GetEventSpecieName(specie))));
187 :
188 : // if (!(hDigits) || // digit hists
189 : // !(hHitsNhits && hHitsElectrons && hHitsRadius && histHitsPrimPerCm && histHitsElectronsPerCm)) // hit hists
190 : // return -0.5; // fatal
191 :
192 0 : if (hDigits) {
193 0 : if(hDigits->GetEntries()==0)
194 0 : return 0.25; // error
195 : }
196 :
197 0 : if (hHitsNhits && hHitsElectrons && hHitsRadius &&
198 0 : histHitsPrimPerCm && histHitsElectronsPerCm) {
199 0 : if (hHitsNhits->GetEntries()==0 || hHitsElectrons->GetEntries()==0 ||
200 0 : hHitsRadius->GetEntries()==0 || histHitsPrimPerCm->GetEntries()==0 ||
201 0 : histHitsElectronsPerCm->GetEntries()==0)
202 0 : return 0.25; // error
203 : }
204 :
205 0 : return 1; // ok
206 0 : }
207 :
208 : //______________________________________________________________________________
209 : Double_t AliTPCQAChecker::CheckREC(Int_t specie, TObjArray* list)
210 : {
211 : /// This method checks the QA histograms associated with reconstruction
212 : ///
213 : /// For TPC this is:
214 : /// DigitsR :
215 : /// The digit histogram gives the ADC distribution for all sigbnals
216 : /// above threshold. The check is just that there are digits.
217 : /// RecPoints :
218 : /// The cluster histograms are meant to give an idea about the gain
219 : /// from the cluster charge and to indicate iof there are rows with
220 : /// noise clusters, i.e., they are very visual.
221 : ///
222 : /// The check methods are simple:
223 : /// If there are no histogram at all (set fatal)
224 : /// If digit histogram is there, but there are no digits (set error)
225 : /// If cluster histogram is there but there are less than 1000
226 : /// clusters (set warning)
227 : /// If there are more than 1000 clusters but no clusters for either short,
228 : /// medium, or long pads (set error)
229 :
230 0 : if(fDebug>0)
231 0 : AliInfo("In AliTPCQAChecker::CheckREC");
232 :
233 0 : if(fDebug>2)
234 0 : list->Print();
235 :
236 0 : TH1* hDigits = static_cast<TH1*>
237 0 : (list->FindObject(Form("%s_hDigitsADC",AliRecoParam::GetEventSpecieName(specie))));
238 0 : TH1* hNclustersVsRow = static_cast<TH1*>
239 0 : (list->FindObject(Form("%s_hRecPointsRow",AliRecoParam::GetEventSpecieName(specie))));
240 0 : TH1* hQshort = static_cast<TH1*>
241 0 : (list->FindObject(Form("%s_hRecPointsQShort",AliRecoParam::GetEventSpecieName(specie))));
242 0 : TH1* hQmedium = static_cast<TH1*>
243 0 : (list->FindObject(Form("%s_hRecPointsQMedium",AliRecoParam::GetEventSpecieName(specie))));
244 0 : TH1* hQlong = static_cast<TH1*>
245 0 : (list->FindObject(Form("%s_hRecPointsQLong",AliRecoParam::GetEventSpecieName(specie))));
246 : // The Qmax histograms are for now ignored
247 :
248 0 : if (!hDigits && // digits missing
249 0 : (!hNclustersVsRow || !hQshort || !hQmedium || !hQlong)) // 1 recpoint hist missing
250 0 : return -0.5; // fatal
251 :
252 0 : if (hDigits && hDigits->GetEntries()==0)
253 0 : return 0.25; // error
254 :
255 0 : if (hNclustersVsRow && hNclustersVsRow->GetEntries() < 1000) {
256 0 : return 0.75; // warning
257 : } else {
258 0 : if (!hQshort || !hQlong || !hQlong)
259 0 : return -0.5;// fatal - they should be there if the cluster vs row hist is there
260 0 : if (hQshort->GetEntries()==0 || hQmedium->GetEntries()==0 ||
261 0 : hQlong->GetEntries()==0)
262 0 : return 0.25; // error
263 : }
264 0 : return 1; // ok
265 0 : }
266 :
267 : //______________________________________________________________________________
268 : Double_t AliTPCQAChecker::CheckESD(Int_t specie, TObjArray* list)
269 : {
270 : /// This method checks the QA histograms associated with ESDs
271 : /// (Note that there is aslo a globalQA which is running on all
272 : /// the ESD information so for now this is just a few basic
273 : /// histograms)
274 : ///
275 : /// The check methods are simple:
276 : /// If there are no histogram at all (set fatal)
277 :
278 0 : if(fDebug>0)
279 0 : AliInfo("In AliTPCQAChecker::CheckESD");
280 :
281 0 : if(fDebug>2)
282 0 : list->Print();
283 :
284 0 : TH1* hESDclusters = static_cast<TH1*>
285 0 : (list->FindObject(Form("%s_hESDclusters",AliRecoParam::GetEventSpecieName(specie))));
286 0 : TH1* hESDratio = static_cast<TH1*>
287 0 : (list->FindObject(Form("%s_hESDratio",AliRecoParam::GetEventSpecieName(specie))));
288 0 : TH1* hESDpt = static_cast<TH1*>
289 0 : (list->FindObject(Form("%s_hESDpt",AliRecoParam::GetEventSpecieName(specie))));
290 :
291 0 : if (!hESDclusters || !hESDratio || !hESDpt)
292 0 : return -0.5; // fatal
293 :
294 0 : return 1.0; // ok
295 0 : }
296 :
297 : //______________________________________________________________________________
298 : void AliTPCQAChecker::Init(const AliQAv1::DETECTORINDEX_t det)
299 : {
300 : /// intialises QA and QA checker settings
301 :
302 18 : if(fDebug>0)
303 0 : AliInfo("In AliTPCQAChecker::Init");
304 9 : AliQAv1::Instance(det) ;
305 9 : Float_t hiValue[AliQAv1::kNBIT] ;
306 9 : Float_t lowValue[AliQAv1::kNBIT] ;
307 9 : hiValue[AliQAv1::kINFO] = 1.00;
308 9 : lowValue[AliQAv1::kINFO] = 0.99;
309 9 : hiValue[AliQAv1::kWARNING] = 0.99;
310 9 : lowValue[AliQAv1::kWARNING] = 0.50;
311 9 : hiValue[AliQAv1::kERROR] = 0.50;
312 9 : lowValue[AliQAv1::kERROR] = 0.00;
313 9 : hiValue[AliQAv1::kFATAL] = 0.00;
314 9 : lowValue[AliQAv1::kFATAL] =-1.00;
315 : // SetHiLo(&hiValue[0], &lowValue[0]) ;
316 9 : SetHiLo(hiValue, lowValue) ;
317 9 : }
318 :
319 : //______________________________________________________________________________
320 : void
321 : AliTPCQAChecker::SetQA(AliQAv1::ALITASK_t index, Double_t * value) const
322 : {
323 : /// sets the QA according the return value of the Check
324 :
325 18 : if(fDebug>0)
326 0 : AliInfo("In AliTPCQAChecker::SetQA");
327 :
328 9 : AliQAv1 * qa = AliQAv1::Instance(index);
329 :
330 108 : for (Int_t specie = 0 ; specie < AliRecoParam::kNSpecies ; specie++) {
331 :
332 45 : if (value==NULL) { // No checker is implemented, set all QA to Fatal
333 :
334 0 : if(fDebug>1)
335 0 : AliInfo(Form("Fatal QA. Task: %s. Specie: %s",
336 : AliQAv1::GetAliTaskName(index),
337 : AliRecoParam::GetEventSpecieName(specie)));
338 0 : qa->Set(AliQAv1::kFATAL, specie) ;
339 0 : } else {
340 :
341 90 : if ( value[specie] >= fLowTestValue[AliQAv1::kFATAL] &&
342 45 : value[specie] < fUpTestValue[AliQAv1::kFATAL] ) {
343 :
344 0 : if(fDebug>1)
345 0 : AliInfo(Form("QA-Fatal. Task: %s. Specie: %s",
346 : AliQAv1::GetAliTaskName(index),
347 : AliRecoParam::GetEventSpecieName(specie)));
348 0 : qa->Set(AliQAv1::kFATAL, specie) ;
349 90 : } else if ( value[specie] > fLowTestValue[AliQAv1::kERROR] &&
350 45 : value[specie] <= fUpTestValue[AliQAv1::kERROR] ) {
351 :
352 0 : if(fDebug>1)
353 0 : AliInfo(Form("QA-Error. Task: %s. Specie: %s",
354 : AliQAv1::GetAliTaskName(index),
355 : AliRecoParam::GetEventSpecieName(specie)));
356 0 : qa->Set(AliQAv1::kERROR, specie) ;
357 90 : } else if (value[specie] > fLowTestValue[AliQAv1::kWARNING] &&
358 45 : value[specie] <= fUpTestValue[AliQAv1::kWARNING]) {
359 :
360 0 : if(fDebug>1)
361 0 : AliInfo(Form("QA-Warning. Task: %s. Specie: %s",
362 : AliQAv1::GetAliTaskName(index),
363 : AliRecoParam::GetEventSpecieName(specie)));
364 0 : qa->Set(AliQAv1::kWARNING, specie) ;
365 90 : } else if (value[specie] > fLowTestValue[AliQAv1::kINFO] &&
366 45 : value[specie] <= fUpTestValue[AliQAv1::kINFO] ) {
367 :
368 45 : if(fDebug>1)
369 0 : AliInfo(Form("QA-Info. Task: %s. Specie: %s",
370 : AliQAv1::GetAliTaskName(index),
371 : AliRecoParam::GetEventSpecieName(specie)));
372 45 : qa->Set(AliQAv1::kINFO, specie) ;
373 45 : }
374 : }
375 : }
376 9 : }
|