Line data Source code
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$ */
17 :
18 : //____________________________________________________________________
19 : //
20 : // Base class for caches of per-strip information.
21 : // This is used to index a strip.
22 : // Data stored depends on derived class.
23 : // This class provides some common infra-structure.
24 : // Derived classes sould define Reset, and operator().
25 : //
26 : #include "AliFMDMap.h" // ALIFMDMAP_H
27 : #include "AliLog.h"
28 : //#include <TClass.h>
29 : //#include <TBuffer.h>
30 : #include <TFile.h>
31 : #include <TList.h>
32 : #include <TStreamerInfo.h>
33 :
34 : //____________________________________________________________________
35 172 : ClassImp(AliFMDMap)
36 : #if 0
37 : ; // This is here to keep Emacs for indenting the next line
38 : #endif
39 :
40 : //____________________________________________________________________
41 81 : AliFMDMap::AliFMDMap(UShort_t maxDet,
42 : UShort_t maxRing,
43 : UShort_t maxSec,
44 : UShort_t maxStr)
45 81 : : fMaxDetectors(maxDet),
46 81 : fMaxRings(maxRing),
47 81 : fMaxSectors(maxSec),
48 81 : fMaxStrips(maxStr)
49 243 : {
50 : // Construct a map
51 : //
52 : // Parameters:
53 : // maxDet Maximum # of detectors
54 : // maxRinf Maximum # of rings
55 : // maxSec Maximum # of sectors
56 : // maxStr Maximum # of strips
57 81 : SetBit(kNeedUShort, kFALSE);
58 81 : }
59 :
60 : //____________________________________________________________________
61 : AliFMDMap::AliFMDMap(const AliFMDMap& other)
62 0 : : TObject(other),
63 0 : fMaxDetectors(other.fMaxDetectors),
64 0 : fMaxRings(other.fMaxRings),
65 0 : fMaxSectors(other.fMaxSectors),
66 0 : fMaxStrips(other.fMaxStrips)
67 0 : {
68 0 : SetBit(kNeedUShort, other.TestBit(kNeedUShort));
69 0 : }
70 :
71 : //____________________________________________________________________
72 : void
73 : AliFMDMap::CheckNeedUShort(TFile* file)
74 : {
75 0 : if (!file) return;
76 0 : TObject* o = file->GetStreamerInfoList()->FindObject("AliFMDMap");
77 0 : if (!o) return;
78 0 : TStreamerInfo* info = static_cast<TStreamerInfo*>(o);
79 0 : if (info->GetClassVersion() == 2) SetBit(kNeedUShort);
80 0 : }
81 : //____________________________________________________________________
82 : void
83 : AliFMDMap::Index2CoordsOld(Int_t idx,
84 : UShort_t& det,
85 : Char_t& ring,
86 : UShort_t& sec,
87 : UShort_t& str) const
88 : {
89 : UShort_t rng;
90 0 : str = idx % fMaxStrips;
91 0 : sec = (idx / fMaxStrips) % fMaxSectors;
92 0 : rng = (idx / fMaxStrips / fMaxSectors) % fMaxRings;
93 0 : det = (idx / fMaxStrips / fMaxSectors / fMaxRings) % fMaxDetectors + 1;
94 0 : ring = (rng == 0 ? 'I' : 'O');
95 0 : }
96 :
97 : //____________________________________________________________________
98 : void
99 : AliFMDMap::Index2Coords(Int_t idx,
100 : UShort_t& det,
101 : Char_t& ring,
102 : UShort_t& sec,
103 : UShort_t& str) const
104 : {
105 : UShort_t nStr;
106 : Int_t i = idx;
107 0 : if (i >= kFMD3Base) { det = 3; i -= kFMD3Base; }
108 0 : else if (i >= kFMD2Base) { det = 2; i -= kFMD2Base; }
109 0 : else { det = 1; i -= kFMD1Base; }
110 0 : if (i >= kBaseOuter) { ring = 'O';i -= kBaseOuter; nStr = kNStripOuter; }
111 0 : else { ring = 'I'; nStr = kNStripInner; }
112 0 : sec = i / nStr;
113 0 : str = i % nStr;
114 0 : }
115 :
116 : //____________________________________________________________________
117 : void
118 : AliFMDMap::CalcCoords(Int_t idx,
119 : UShort_t& det,
120 : Char_t& ring,
121 : UShort_t& sec,
122 : UShort_t& str) const
123 : {
124 0 : if (fMaxDetectors == 0) {
125 0 : Index2Coords(idx, det, ring, sec, str);
126 0 : }
127 : else {
128 0 : Index2CoordsOld(idx, det, ring, sec, str);
129 : }
130 0 : }
131 :
132 : //____________________________________________________________________
133 : Int_t
134 : AliFMDMap::Coords2IndexOld(UShort_t det, Char_t ring, UShort_t sec,
135 : UShort_t str) const
136 : {
137 : // Check that the index supplied is OK. Returns true index, or -1
138 : // on error.
139 5429504 : if (det < 1) return -1;
140 6508032 : UShort_t ringi = (ring == 'I' || ring == 'i' ? 0 : 1);
141 : Int_t idx =
142 2714752 : (str + fMaxStrips * (sec + fMaxSectors * (ringi + fMaxRings * (det-1))));
143 2714752 : if (TestBit(kNeedUShort)) idx = UShort_t(idx);
144 5429504 : if (idx < 0 || idx >= fMaxDetectors * fMaxRings * fMaxSectors * fMaxStrips)
145 0 : return -1;
146 2714752 : return idx;
147 2714752 : }
148 :
149 : //____________________________________________________________________
150 : Int_t
151 : AliFMDMap::Coords2Index(UShort_t det, Char_t ring, UShort_t sec,
152 : UShort_t str) const
153 : {
154 : // Check that the index supplied is OK. Returns true index, or -1
155 : // on error.
156 29886033 : UShort_t irg = (ring == 'I' || ring == 'i' ? kInner :
157 6295938 : (ring == 'O' || ring == 'o' ? kOuter : kOuter+1));
158 7863365 : if (irg > kOuter) return -1;
159 :
160 : Int_t idx = 0;
161 7863365 : switch (det) {
162 1571796 : case 1: idx = kFMD1Base; if (irg > 0) return -1; break;
163 3145703 : case 2: idx = kFMD2Base + irg * kBaseOuter; break;
164 3145866 : case 3: idx = kFMD3Base + irg * kBaseOuter; break;
165 0 : default: return -1;
166 : }
167 7863365 : UShort_t nSec = (irg == 0 ? kNSectorInner : kNSectorOuter);
168 7863365 : if (sec >= nSec) return -1;
169 7863365 : UShort_t nStr = (irg == 0 ? kNStripInner : kNStripOuter);
170 7863365 : if (str >= nStr) return -1;
171 7863365 : idx += nStr * sec + str;
172 :
173 7863365 : return idx;
174 7863365 : }
175 :
176 : //____________________________________________________________________
177 : Int_t
178 : AliFMDMap::CheckIndex(UShort_t det, Char_t ring, UShort_t sec,
179 : UShort_t str) const
180 : {
181 : // Check that the index supplied is OK. Returns true index, or -1
182 : // on error.
183 21156234 : if (fMaxDetectors == 0)
184 7863365 : return Coords2Index(det, ring, sec, str);
185 2714752 : return Coords2IndexOld(det, ring, sec, str);
186 10578117 : }
187 :
188 :
189 :
190 : //____________________________________________________________________
191 : Int_t
192 : AliFMDMap::CalcIndex(UShort_t det, Char_t ring, UShort_t sec, UShort_t str) const
193 : {
194 : // Calculate index into storage from arguments.
195 : //
196 : // Parameters:
197 : // det Detector #
198 : // ring Ring ID
199 : // sec Sector #
200 : // str Strip #
201 : //
202 : // Returns appropriate index into storage
203 : //
204 21156234 : Int_t idx = CheckIndex(det, ring, sec, str);
205 10578117 : if (idx < 0) {
206 0 : UShort_t ringi = (ring == 'I' || ring == 'i' ? 0 :
207 0 : (ring == 'O' || ring == 'o' ? 1 : 2));
208 0 : AliFatal(Form("Index FMD%d%c[%2d,%3d] out of bounds, "
209 : "in particular the %s index ",
210 : det, ring, sec, str,
211 : (det > fMaxDetectors ? "Detector" :
212 : (ringi >= fMaxRings ? "Ring" :
213 : (sec >= fMaxSectors ? "Sector" : "Strip")))));
214 : return 0;
215 : }
216 10578117 : return idx;
217 10578117 : }
218 :
219 : #define INCOMP_OP(self, other, OP) do { \
220 : AliWarning("Incompatible sized AliFMDMap"); \
221 : UShort_t maxDet = TMath::Min(self->MaxDetectors(), other.MaxDetectors()); \
222 : UShort_t maxRng = TMath::Min(self->MaxRings(), other.MaxRings()); \
223 : UShort_t maxSec = TMath::Min(self->MaxSectors(), other.MaxSectors()); \
224 : UShort_t maxStr = TMath::Min(self->MaxStrips(), other.MaxStrips()); \
225 : for (UShort_t d = 1; d <= maxDet; d++) { \
226 : UShort_t nRng = TMath::Min(UShort_t(d == 1 ? 1 : 2), maxRng); \
227 : for (UShort_t q = 0; q < nRng; q++) { \
228 : Char_t r = (q == 0 ? 'I' : 'O'); \
229 : UShort_t nSec = TMath::Min(UShort_t(q == 0 ? 20 : 40), maxSec); \
230 : UShort_t nStr = TMath::Min(UShort_t(q == 0 ? 512 : 256), maxStr); \
231 : for (UShort_t s = 0; s < nSec; s++) { \
232 : for (UShort_t t = 0; t < nStr; t++) { \
233 : Int_t idx1 = self->CalcIndex(d, r, s, t); \
234 : Int_t idx2 = other.CalcIndex(d, r, s, t); \
235 : if (idx1 < 0 || idx2 < 0) { \
236 : AliWarning("Index out of bounds"); \
237 : continue; \
238 : } \
239 : if (self->IsFloat()) \
240 : self->AtAsFloat(idx1) OP other.AtAsFloat(idx2); \
241 : else if (self->IsInt()) \
242 : self->AtAsInt(idx1) OP other.AtAsInt(idx2); \
243 : else if (self->IsUShort()) \
244 : self->AtAsUShort(idx1) OP other.AtAsUShort(idx2); \
245 : else if (self->IsBool()) \
246 : self->AtAsBool(idx1) OP other.AtAsBool(idx2); \
247 : } \
248 : } \
249 : } \
250 : } \
251 : } while (false)
252 :
253 : #define COMP_OP(self,other,OP) do { \
254 : for (Int_t i = 0; i < self->MaxIndex(); i++) { \
255 : if (self->IsFloat()) \
256 : self->AtAsFloat(i) OP other.AtAsFloat(i); \
257 : else if (self->IsInt()) \
258 : self->AtAsInt(i) OP other.AtAsInt(i); \
259 : else if (self->IsUShort()) \
260 : self->AtAsUShort(i) OP other.AtAsUShort(i); \
261 : else if (self->IsBool()) \
262 : self->AtAsBool(i) OP other.AtAsBool(i); \
263 : } } while (false)
264 :
265 : //__________________________________________________________
266 : AliFMDMap&
267 : AliFMDMap::operator*=(const AliFMDMap& other)
268 : {
269 : // Right multiplication assignment operator
270 0 : if(fMaxDetectors!= other.fMaxDetectors||
271 0 : fMaxRings != other.fMaxRings ||
272 0 : fMaxSectors != other.fMaxSectors ||
273 0 : fMaxStrips != other.fMaxStrips ||
274 0 : MaxIndex() != other.MaxIndex()) {
275 0 : INCOMP_OP(this, other, *=);
276 0 : return *this;
277 : }
278 0 : COMP_OP(this, other, *=);
279 0 : return *this;
280 0 : }
281 :
282 : //__________________________________________________________
283 : AliFMDMap&
284 : AliFMDMap::operator/=(const AliFMDMap& other)
285 : {
286 : // Right division assignment operator
287 0 : if(fMaxDetectors!= other.fMaxDetectors||
288 0 : fMaxRings != other.fMaxRings ||
289 0 : fMaxSectors != other.fMaxSectors ||
290 0 : fMaxStrips != other.fMaxStrips ||
291 0 : MaxIndex() != other.MaxIndex()) {
292 0 : INCOMP_OP(this, other, /=);
293 0 : return *this;
294 : }
295 0 : COMP_OP(this, other, /=);
296 0 : return *this;
297 0 : }
298 :
299 : //__________________________________________________________
300 : AliFMDMap&
301 : AliFMDMap::operator+=(const AliFMDMap& other)
302 : {
303 : // Right addition assignment operator
304 0 : if(fMaxDetectors!= other.fMaxDetectors||
305 0 : fMaxRings != other.fMaxRings ||
306 0 : fMaxSectors != other.fMaxSectors ||
307 0 : fMaxStrips != other.fMaxStrips ||
308 0 : MaxIndex() != other.MaxIndex()) {
309 0 : INCOMP_OP(this, other, +=);
310 0 : return *this;
311 : }
312 0 : COMP_OP(this, other, +=);
313 0 : return *this;
314 0 : }
315 :
316 : //__________________________________________________________
317 : AliFMDMap&
318 : AliFMDMap::operator-=(const AliFMDMap& other)
319 : {
320 : // Right subtraction assignment operator
321 0 : if(fMaxDetectors!= other.fMaxDetectors||
322 0 : fMaxRings != other.fMaxRings ||
323 0 : fMaxSectors != other.fMaxSectors ||
324 0 : fMaxStrips != other.fMaxStrips ||
325 0 : MaxIndex() != other.MaxIndex()) {
326 0 : INCOMP_OP(this, other, +=);
327 0 : return *this;
328 : }
329 0 : COMP_OP(this, other, +=);
330 0 : return *this;
331 0 : }
332 :
333 : //__________________________________________________________
334 : Bool_t
335 : AliFMDMap::ForEach(ForOne& algo) const
336 : {
337 : // Assignment operator
338 : Bool_t ret = kTRUE;
339 0 : for (Int_t i = 0; i < this->MaxIndex(); i++) {
340 0 : UShort_t d, s, t;
341 0 : Char_t r;
342 0 : CalcCoords(i, d, r, s, t);
343 : Bool_t rr = kTRUE;
344 0 : if (IsFloat())
345 0 : rr = algo.operator()(d, r, s, t, this->AtAsFloat(i));
346 0 : else if (IsInt())
347 0 : rr = algo.operator()(d, r, s, t, this->AtAsInt(i));
348 0 : else if (IsUShort())
349 0 : rr = algo.operator()(d, r, s, t, this->AtAsUShort(i));
350 0 : else if (IsBool())
351 0 : rr = algo.operator()(d, r, s, t, this->AtAsBool(i));
352 0 : if (!rr) {
353 : ret = kFALSE;
354 0 : break;
355 : }
356 0 : }
357 0 : return ret;
358 : }
359 :
360 : //__________________________________________________________
361 : void
362 : AliFMDMap::Print(Option_t* option) const
363 : {
364 : // Print contents of map
365 0 : if (!option || option[0] == '\0') TObject::Print();
366 0 : Printer p(option);
367 0 : ForEach(p);
368 0 : printf("\n");
369 0 : }
370 :
371 : //===================================================================
372 0 : AliFMDMap::Printer::Printer(const char* format)
373 0 : : fFormat(format), fOldD(0), fOldR('-'), fOldS(1024)
374 0 : {}
375 :
376 : //___________________________________________________________________
377 : AliFMDMap::Printer::Printer(const Printer& p)
378 0 : : AliFMDMap::ForOne(p),
379 0 : fFormat(p.fFormat),
380 0 : fOldD(p.fOldD),
381 0 : fOldR(p.fOldR),
382 0 : fOldS(p.fOldS)
383 0 : {}
384 : //___________________________________________________________________
385 : void
386 : AliFMDMap::Printer::PrintHeadings(UShort_t d, Char_t r, UShort_t s, UShort_t t)
387 : {
388 0 : if (d != fOldD) {
389 0 : fOldD = d;
390 0 : fOldR = '-';
391 0 : if (d != 0) printf("\n");
392 0 : printf("FMD%d", fOldD);
393 0 : }
394 0 : if (r != fOldR) {
395 0 : fOldR = r;
396 0 : fOldS = 1024;
397 0 : printf("\n %s ring", (r == 'I' ? "Inner" : "Outer"));
398 0 : }
399 0 : if (s != fOldS) {
400 0 : fOldS = s;
401 0 : printf("\n Sector %2d", fOldS);
402 0 : }
403 0 : if (t % 4 == 0) printf("\n %3d-%3d ", t, t+3);
404 0 : }
405 : //___________________________________________________________________
406 : Bool_t
407 : AliFMDMap::Printer::operator()(UShort_t d, Char_t r, UShort_t s, UShort_t t,
408 : Float_t m)
409 : {
410 0 : PrintHeadings(d, r, s, t);
411 0 : printf(fFormat, m);
412 0 : return kTRUE;
413 : }
414 : //___________________________________________________________________
415 : Bool_t
416 : AliFMDMap::Printer::operator()(UShort_t d, Char_t r, UShort_t s, UShort_t t,
417 : Int_t m)
418 : {
419 0 : PrintHeadings(d, r, s, t);
420 0 : printf(fFormat, m);
421 0 : return kTRUE;
422 : }
423 : //___________________________________________________________________
424 : Bool_t
425 : AliFMDMap::Printer::operator()(UShort_t d, Char_t r, UShort_t s, UShort_t t,
426 : UShort_t m)
427 : {
428 0 : PrintHeadings(d, r, s, t);
429 0 : printf(fFormat, m);
430 0 : return kTRUE;
431 : }
432 : //___________________________________________________________________
433 : Bool_t
434 : AliFMDMap::Printer::operator()(UShort_t d, Char_t r, UShort_t s, UShort_t t,
435 : Bool_t m)
436 : {
437 0 : PrintHeadings(d, r, s, t);
438 0 : printf(fFormat, int(m));
439 0 : return kTRUE;
440 : }
441 :
442 : #if 0
443 : //___________________________________________________________________
444 : void AliFMDMap::Streamer(TBuffer &R__b)
445 : {
446 : // Stream an object of class AliFMDMap.
447 : // This is overridden so that we can know the version of the object
448 : // that we are reading in. In this way, we can fix problems that
449 : // might occur in the class.
450 : if (R__b.IsReading()) {
451 : // read the class version from the buffer
452 : UInt_t R__s, R__c;
453 : Version_t version = R__b.ReadVersion(&R__s, &R__c, this->Class());
454 : TFile *file = (TFile*)R__b.GetParent();
455 : if (file && file->GetVersion() < 30000) version = -1;
456 : AliFMDMap::Class()->ReadBuffer(R__b, this, version, R__s, R__c);
457 : if (version == 2) SetBit(kNeedUShort);
458 : } else {
459 : AliFMDMap::Class()->WriteBuffer(R__b, this);
460 : }
461 : }
462 : #endif
463 :
464 : //___________________________________________________________________
465 : //
466 : // EOF
467 : //
|