Geometry and hit structure update
[u/mrichter/AliRoot.git] / TRD / AliTRDdataArrayF.cxx
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 /*
17 $Log$
18 Revision 1.9  2001/05/07 08:08:05  cblume
19 Update of TRD code
20
21 Revision 1.8  2000/11/23 14:34:08  cblume
22 Fixed bug in expansion routine of arrays (initialize buffers properly)
23
24 Revision 1.7  2000/11/20 08:56:07  cblume
25 Cleanup of data arrays
26
27 Revision 1.6  2000/11/01 14:53:20  cblume
28 Merge with TRD-develop
29
30 Revision 1.1.2.3  2000/10/06 16:49:46  cblume
31 Made Getters const
32
33 Revision 1.1.2.2  2000/10/04 16:34:58  cblume
34 Replace include files by forward declarations
35
36 Revision 1.5  2000/06/27 13:08:50  cblume
37 Changed to Copy(TObject &A) to appease the HP-compiler
38
39 Revision 1.4  2000/06/09 11:10:07  cblume
40 Compiler warnings and coding conventions, next round
41
42 Revision 1.3  2000/06/08 18:32:58  cblume
43 Make code compliant to coding conventions
44
45 Revision 1.2  2000/05/08 16:17:27  cblume
46 Merge TRD-develop
47
48 Revision 1.1.2.1  2000/05/08 15:14:34  cblume
49 Add new data array classes
50
51 */
52
53 ///////////////////////////////////////////////////////////////////////////////
54 //                                                                           //
55 //  General container for integer data of a TRD detector segment.            //
56 //  Adapted from AliDigits (origin: M.Ivanov).                               //
57 //                                                                           //
58 ///////////////////////////////////////////////////////////////////////////////
59
60 #include "AliTRDdataArrayF.h"
61 #include "AliTRDarrayI.h"
62 #include "AliTRDarrayF.h"
63
64 ClassImp(AliTRDdataArrayF)
65
66 //_____________________________________________________________________________
67 AliTRDdataArrayF::AliTRDdataArrayF():AliTRDdataArray()
68 {
69   //
70   // Default constructor
71   //
72
73   fElements = 0;
74
75 }
76
77 //_____________________________________________________________________________
78 AliTRDdataArrayF::AliTRDdataArrayF(Int_t nrow, Int_t ncol, Int_t ntime)
79                  :AliTRDdataArray(nrow,ncol,ntime)
80 {
81   //
82   // Creates a AliTRDdataArrayF with the dimensions <nrow>, <ncol>, and <ntime>.
83   // The row- and column dimensions are compressible.
84   //
85
86   fElements = 0;
87
88   Allocate(nrow,ncol,ntime);
89   
90 }
91
92 //_____________________________________________________________________________
93 AliTRDdataArrayF::AliTRDdataArrayF(const AliTRDdataArrayF &a)
94 {
95   //
96   // AliTRDdataArrayF copy constructor
97   //
98
99   ((AliTRDdataArrayF &) a).Copy(*this);
100
101 }
102
103 //_____________________________________________________________________________
104 AliTRDdataArrayF::~AliTRDdataArrayF()
105 {
106   //
107   // Destructor
108   //
109
110   if (fElements) delete fElements;
111   
112 }
113
114 //_____________________________________________________________________________
115 void AliTRDdataArrayF::Allocate(Int_t nrow, Int_t ncol, Int_t ntime)
116 {
117   //
118   // Allocates memory for a AliTRDdataArrayF with the dimensions 
119   // <nrow>, <ncol>, and <ntime>.
120   // The row- and column dimensions are compressible.
121   //
122
123   if (fNelems < 0) AliTRDdataArray::Allocate(nrow,ncol,ntime);
124
125   if (fElements) delete fElements;
126   fElements = new AliTRDarrayF();
127   fElements->Set(fNelems);
128
129 }
130
131 //_____________________________________________________________________________
132 void AliTRDdataArrayF::Copy(TObject &a)
133 {
134   //
135   // Copy function
136   //
137
138   fElements->Copy(*((AliTRDdataArrayF &) a).fElements);
139
140   ((AliTRDdataArrayF &) a).fThreshold = fThreshold;
141
142   AliTRDdataArray::Copy(a);
143
144 }
145
146 //_____________________________________________________________________________
147 void AliTRDdataArrayF::Reset() 
148
149   //
150   // Reset the array (old content gets deleted)
151   //
152   
153   if (fElements) delete fElements;
154   fElements = new AliTRDarrayF();
155   fElements->Set(0); 
156
157   AliTRDdataArray::Reset();
158
159 }
160
161 //_____________________________________________________________________________
162 Int_t AliTRDdataArrayF::GetSize()
163 {
164   //
165   // Returns the size of the complete object
166   //
167
168   Int_t size = sizeof(this);
169
170   if (fIndex)    size += sizeof(fIndex)    
171                          + fIndex->GetSize()    * sizeof(Int_t);
172   if (fElements) size += sizeof(fElements) 
173                          + fElements->GetSize() * sizeof(Float_t);
174
175   return size;
176
177 }
178
179 //_____________________________________________________________________________
180 Int_t AliTRDdataArrayF::GetDataSize() 
181 {
182   //
183   // Returns the size of only the data part
184   //
185
186   if (fElements == 0) 
187     return 0;
188   else 
189     return sizeof(fElements) + fElements->GetSize() * sizeof(Float_t);
190
191 }
192
193 //_____________________________________________________________________________
194 Int_t AliTRDdataArrayF::GetOverThreshold(Float_t threshold) 
195 {
196   //
197   // Returns the number of entries over threshold
198   //
199  
200   if ((fElements == 0) || (fElements->GetSize() <= 0))
201     return 0;
202  
203   Int_t over = 0;
204
205   for (Bool_t cont = First(); cont == kTRUE; cont = Next()) {
206     if ((fCurrentIdx1 < 0) || (fCurrentIdx1 >= fNdim1)) continue;
207     if ((fCurrentIdx2 < 0) || (fCurrentIdx2 >= fNdim2)) continue;
208     if (fElements->At(fCurrentIndex) > threshold) over++;
209   }
210
211   return over;
212
213 }
214
215 //_____________________________________________________________________________
216 Float_t AliTRDdataArrayF::GetData(Int_t row, Int_t col, Int_t time) const
217 {
218   //
219   // Returns the data value at a given position of the array
220   // Includes boundary checking
221   //
222
223   if ((row >= 0) && (col >= 0) && (time >= 0)) {
224     Int_t idx1 = GetIdx1(row,col);
225     if ((idx1 >= 0) && (time < fNdim2)) {
226       if (fBufType == 0) return GetDataFast(idx1,time);
227       if (fBufType == 1) return GetData1(idx1,time);
228     }
229     else {
230       if (idx1 >= 0) {
231         TObject::Error("GetData"
232                       ,"time %d out of bounds (size: %d, this: 0x%08x)"
233                       ,time,fNdim2,this);
234       }
235     }
236   }
237
238   return -1;
239
240 }
241
242 //_____________________________________________________________________________
243 Float_t AliTRDdataArrayF::GetDataFast(Int_t idx1, Int_t idx2) const
244 {
245   //
246   // Returns the data value at a given position of the array
247   // No boundary checking
248   //
249
250   return fElements->At(fIndex->At(idx2)+idx1);
251
252 }
253
254 //_____________________________________________________________________________
255 void AliTRDdataArrayF::Compress(Int_t bufferType, Float_t threshold)
256 {
257   //
258   // Compresses the buffer
259   //
260
261   fThreshold = threshold;
262   Compress(bufferType);
263
264 }
265
266 //_____________________________________________________________________________
267 void AliTRDdataArrayF::Compress(Int_t bufferType)
268 {
269   //
270   // Compresses the buffer
271   //
272
273   if (fBufType  < 0) {
274     Error("AliTRDdataArrayF::Compress","Buffer does not exist");
275     return;
276   }
277   if (fBufType == bufferType) {
278     return;
279   }  
280   if (fBufType > 0) {
281     Expand();
282   }
283   if (fBufType !=0)  {
284     Error("AliTRDdataArrayF::Compress","Buffer does not exist");
285     return;
286   }
287
288   // Compress a buffer of type 1
289   if (bufferType == 1) {
290     Compress1();
291   }
292
293 }
294
295 //_____________________________________________________________________________
296 void AliTRDdataArrayF::Expand()
297 {  
298   //
299   // Expands the compressed buffer
300   //
301
302   if (fBufType  < 0) {
303     Error("AliTRDdataArrayF::Expand","Buffer does not exist");
304     return;
305   }
306   if (fBufType == 0) {  
307     return;
308   } 
309  
310   // Expand a buffer of type 1
311   if (fBufType == 1) Expand1();
312   
313   fBufType = 0;
314
315 }
316
317 //_____________________________________________________________________________
318 Bool_t AliTRDdataArrayF::First() 
319 {
320   //
321   // Returns the position of the first valid data value
322   //
323
324   if (fBufType == 0) return First0();
325   if (fBufType == 1) return First1();
326   return kFALSE;
327
328 }
329
330 //_____________________________________________________________________________
331 Bool_t  AliTRDdataArrayF::Next()
332 {
333   //
334   // Returns the position of the next valid data value
335   //
336
337   if (fBufType == 0) return Next0();
338   if (fBufType == 1) return Next1();
339   return kFALSE;
340
341 }
342
343 //_____________________________________________________________________________
344 void AliTRDdataArrayF::Expand1()
345 {
346   //
347   // Expands a buffer of type 1
348   //
349
350   Int_t i, k;
351
352   fNelems = fNdim1 * fNdim2;
353
354   Float_t *buf = new Float_t[fNelems];
355   memset(buf,0,fNelems*sizeof(Float_t)); 
356
357   fIndex->Set(fNdim2);
358
359   for (i = 0, k = 0; i < fNdim2; i++, k += fNdim1) (*fIndex)[i] = k;
360
361   Int_t idx1 = 0;
362   Int_t idx2 = 0;
363   Int_t n    = fElements->fN;
364
365   for (i = 0; i < n; i++){
366
367     // Negative sign counts the unwritten values (under threshold)
368     if ((*fElements)[i] < 0) {
369       idx1 -= TMath::Nint(fElements->At(i));
370     } 
371     else {
372       buf[(*fIndex)[idx2] + idx1] = (*fElements)[i];
373       idx1++;
374     }
375     if (idx1 == fNdim1) {
376       idx1 = 0;
377       idx2++;
378     }
379     else { 
380       if (idx1 > fNdim1){
381         Reset();
382         return;
383       }      
384     }
385   }
386
387   fElements->Adopt(fNelems,buf); 
388    
389 }
390
391 //_____________________________________________________________________________
392 void AliTRDdataArrayF::Compress1()
393 {
394   //
395   // Compress a buffer of type 1
396   //
397
398   AliTRDarrayF *buf   = new AliTRDarrayF();  
399   buf->Set(fNelems);
400   AliTRDarrayI *index = new AliTRDarrayI();
401   index->Set(fNdim2);
402
403   Int_t icurrent = -1;
404   Int_t izero;
405   for (Int_t idx2 = 0; idx2 < fNdim2; idx2++){      
406
407     // Set the idx2 pointer
408     (*index)[idx2] = icurrent + 1;
409
410     // Reset the zero counter 
411     izero = 0;  
412
413     for (Int_t idx1 = 0; idx1 < fNdim1; idx1++){
414       // If below threshold
415       if (GetDataFast(idx1,idx2) <= fThreshold) {
416         izero++;
417       }
418       else {
419         if (izero > 0) {
420           // If we have currently izero counts under threshold
421           icurrent++;     
422           if (icurrent >= buf->fN) buf->Expand(icurrent*2);
423           // Store the number of entries below zero
424           (*buf)[icurrent] = -izero;  
425           izero = 0;
426         } 
427         icurrent++;
428         if (icurrent >= buf->fN) buf->Expand(icurrent*2);
429         (*buf)[icurrent] = GetDataFast(idx1,idx2);          
430       } // If signal larger than threshold              
431     } // End of loop over idx1
432
433     if (izero > 0) {
434       icurrent++;         
435       if (icurrent >= buf->fN) buf->Expand(icurrent*2);
436       // Store the number of entries below zero
437       (*buf)[icurrent] = -izero;  
438     }
439
440   }
441
442   buf->Expand(icurrent+1);
443   if (fElements) delete fElements;
444   fElements = buf;
445   fNelems   = fElements->fN;
446   fBufType  = 1;
447   if (fIndex) delete fIndex;
448   fIndex    = index;
449
450 }
451
452 //_____________________________________________________________________________
453 void AliTRDdataArrayF::Expand2()
454 {
455   //
456   // Expands a buffer of type 2 
457   //
458
459   Int_t i, k;
460
461   Float_t *buf = new Float_t[fNelems];
462   memset(buf,0,fNelems*sizeof(Float_t)); 
463
464   fNelems = fNdim1 * fNdim2;
465   fIndex->Set(fNdim2);
466
467   for (i = 0, k = 0; i < fNdim2; i++, k += fNdim1) (*fIndex)[i] = k;
468
469   Int_t idx1 = 0;
470   Int_t idx2 = 0;
471   Int_t n    = fElements->fN;
472   for (i = 0; i < n; i++){
473     // Negative sign counts the unwritten values (under threshold)
474     if ((*fElements)[i] < 0) {
475       //idx1 -= (Int_t) fElements->At(i); 
476       idx1 -= TMath::Nint(fElements->At(i)); 
477     }
478     else {
479       buf[(*fIndex)[idx2]+idx1] = fElements->At(i);
480       idx1++;
481     }
482     if (idx1 == fNdim1) {
483       idx1 = 0;
484       idx2++;
485     }
486     else { 
487       if (idx1 > fNdim1){
488         Reset();
489         return;
490       }      
491     }
492   }
493
494   fElements->Adopt(fNelems,buf);    
495
496 }
497
498 //_____________________________________________________________________________
499 void AliTRDdataArrayF::Compress2()
500 {
501   //
502   // Compress a buffer of type 2 - not implemented!
503   //
504
505 }
506
507 //_____________________________________________________________________________
508 Bool_t AliTRDdataArrayF::First0() 
509 {
510   //
511   // Returns the first entry for a buffer of type 0
512   //
513
514   fCurrentIdx1  = -1;
515   fCurrentIdx2  = -1;
516   fCurrentIndex = -1;
517
518   Int_t i;
519   for (i = 0; ((i < fNelems) && (fElements->At(i) <= fThreshold)); i++)
520   if (i == fNelems) return kFALSE;
521
522   fCurrentIdx1  = i % fNdim1;
523   fCurrentIdx2  = i / fNdim1;
524   fCurrentIndex = i;
525   return kTRUE; 
526
527 }
528
529 //_____________________________________________________________________________
530 Bool_t AliTRDdataArrayF::Next0()
531 {
532   //
533   // Returns the next entry for a buffer of type 0
534   //
535
536   if (fCurrentIndex < 0) return kFALSE; 
537
538   Int_t i;
539   for (i = fCurrentIndex + 1; 
540        ((i < fNelems) && (fElements->At(i) <= fThreshold)); 
541        i++);
542   if (i >= fNelems)  {
543     fCurrentIndex = -1;
544     return kFALSE;
545   }
546
547   fCurrentIdx1  = i % fNdim1;
548   fCurrentIdx2  = i / fNdim1;
549   fCurrentIndex = i;
550   return kTRUE; 
551
552 }
553
554 //_____________________________________________________________________________
555 Bool_t AliTRDdataArrayF::First1() 
556 {
557   //
558   // Returns the first entry for a buffer of type 1
559   //
560
561   fCurrentIdx1  = -1;
562   fCurrentIdx2  =  0;
563   fCurrentIndex = -1;
564
565   Int_t i;
566   for (i = 0; i < fNelems; i++){
567     if (fElements->At(i) < 0) {
568       //fCurrentIdx1 -= (Int_t) fElements->At(i);
569       fCurrentIdx1 -= TMath::Nint(fElements->At(i));
570     }
571     else {     
572       fCurrentIdx1++;
573     }
574     if (fCurrentIdx1 >= fNdim1) {
575       fCurrentIdx2++;
576       fCurrentIdx1 -= fNdim1;
577     }
578     if (fElements->At(i) > fThreshold) break;
579   }
580
581   fCurrentIndex = i;
582   if (fCurrentIndex >= 0) return kTRUE;
583   fCurrentIdx1  = -1;
584   fCurrentIdx2  = -1;
585   return kFALSE;        
586
587 }
588
589 //_____________________________________________________________________________
590 Bool_t AliTRDdataArrayF::Next1() 
591 {
592   //
593   // Returns the next entry for a buffer of type 1
594   //
595
596   if (fCurrentIndex < 0) return kFALSE;
597
598   Int_t i;
599   for (i = fCurrentIndex + 1; i < fNelems; i++){
600     if (fElements->At(i) < 0) {
601       //fCurrentIdx1 -= (Int_t) fElements->At(i);
602       fCurrentIdx1 -= TMath::Nint(fElements->At(i));
603     }
604     else {      
605       fCurrentIdx1++;
606     }
607     if (fCurrentIdx1 >= fNdim1) {
608       fCurrentIdx2++;
609       fCurrentIdx1 -= fNdim1;
610     }
611     if (fElements->At(i) > fThreshold) break;
612   }
613
614   fCurrentIndex =  i;
615   if ((i >= 0) && (i < fNelems)) return kTRUE;
616   fCurrentIdx1  = -1;
617   fCurrentIdx2  = -1;
618   return kFALSE;
619
620 }
621
622 //_____________________________________________________________________________
623 Float_t AliTRDdataArrayF::GetData1(Int_t idx1, Int_t idx2) const
624 {
625   //
626   // Returns the value at a given position of the array
627   //
628   
629   Int_t i, n2;
630
631   if ((idx2 + 1) >= fNdim2) {
632     n2 = fNelems;
633   }
634   else {
635     n2 = fIndex->At(idx2 + 1);
636   }
637
638   // Current idx1    
639   Int_t curidx1 = 0; 
640  
641   for (i = fIndex->At(idx2); ((i < n2) && (curidx1 < idx1)); i++){
642     if (fElements->At(i) < 0) {
643       //curidx1 -= (Int_t) fElements->At(i);
644       curidx1 -= TMath::Nint(fElements->At(i));
645     }
646     else {      
647       curidx1++;
648     }
649   }
650
651   if ((curidx1 == idx1) && (fElements->At(i) > 0)) {
652     return fElements->At(i);
653   }
654   else {
655     return 0;
656   }
657
658 }
659
660 //_____________________________________________________________________________
661 void AliTRDdataArrayF::SetData(Int_t row, Int_t col, Int_t time, Float_t value)
662 {
663   //
664   // Sets the data value at a given position of the array
665   // Includes boundary checking
666   //
667
668   if ((row >= 0) && (col >= 0) && (time >= 0)) {
669     Int_t idx1 = GetIdx1(row,col);
670     if ((idx1 >= 0) && (time < fNdim2)) {
671       SetDataFast(idx1,time,value);
672     }
673     else {
674       if (idx1 >= 0) {
675         TObject::Error("SetData"
676                       ,"time %d out of bounds (size: %d, this: 0x%08x)"
677                       ,time,fNdim2,this);
678       }
679     }
680   }
681
682 }
683
684 //_____________________________________________________________________________
685 void AliTRDdataArrayF::SetDataFast(Int_t idx1, Int_t idx2, Float_t value)
686 {
687   //
688   // Sets the data value at a given position of the array
689   // No boundary checking
690   //
691
692   (*fElements)[fIndex->fArray[idx2]+idx1] = value;
693
694 }
695
696 //_____________________________________________________________________________
697 AliTRDdataArrayF &AliTRDdataArrayF::operator=(const AliTRDdataArrayF &a)
698 {
699   //
700   // Assignment operator
701   //
702
703   if (this != &a) ((AliTRDdataArrayF &) a).Copy(*this);
704   return *this;
705
706 }
707