]> git.uio.no Git - u/mrichter/AliRoot.git/blame - TRD/AliTRDtrapAlu.cxx
Using const char * instead of char *
[u/mrichter/AliRoot.git] / TRD / AliTRDtrapAlu.cxx
CommitLineData
1d93b218 1#include "AliTRDtrapAlu.h"\r
2\r
3ClassImp(AliTRDtrapAlu)\r
4\r
5//usage of the class: \r
6//declaration of class instances: AliTRDtrapAlu a,b,c;\r
7//initialization: a.Init(2,11); b.Init(4,4); c.Init(5,4);\r
8//assigning values: a.AssignDouble(5.7); b.AssignInt(3);(you can also do b.AssignDouble(3) with same effect);\r
9//calculation: c = a*b; \r
10//test if c has right value: c.WriteWord();\r
11//don't declare pointers; operators not overridden for pointer types; you have to dereference yourself;\r
12//use operators +,-,*,/ only with instances of the class; don't do things like c=a*2 but rather b.AssignInt(2); c=a*b;\r
13\r
14\r
15\r
16 \r
17AliTRDtrapAlu::AliTRDtrapAlu():TObject()\r
18\r
19 ,fValue(0)\r
20 ,fPreCom(0)\r
21 ,fPostCom(0)\r
22 ,fuRestriction(0)\r
23 ,flRestriction(0)\r
24 ,fSigned(kFALSE)\r
25\r
26{\r
27 \r
28 // default constructor\r
29 \r
30 \r
31}\r
32\r
33\r
34AliTRDtrapAlu::~AliTRDtrapAlu(){\r
35 //destructor\r
36}\r
37\r
38\r
39\r
40void AliTRDtrapAlu::Init(const Int_t& precom, const Int_t& postcom, const Int_t& lRestriction, const Int_t& uRestriction){\r
41 // initialization: characterizes the bit-word (nr of pre- and post-comma bits, boundaries)\r
42 fPostCom = postcom;\r
43 fPreCom = precom;\r
44 fValue = 0; //currently, re-initialization kills the value\r
45 fSigned = kFALSE;\r
46\r
47 if (fPreCom + fPostCom > 32 || fPreCom > 31) {fPreCom = 1; fPostCom = 0;return;} // prevent pre-comma part exceeding 31 spaces\r
48 if (fPreCom <= 0) {fPreCom = 1;}\r
49 if (fPostCom < 0) {fPostCom = 0;}\r
50 \r
51 Int_t lut = LUT(fPreCom + fPostCom)-1;\r
52 if (uRestriction <= -1 || uRestriction > lut) {fuRestriction = lut;}\r
53 else {fuRestriction = uRestriction;}\r
54 if (lRestriction <= -1 || lRestriction > fuRestriction) {flRestriction = -lut;}\r
55 else {flRestriction = lRestriction;}\r
56 // up to now you can only choose a non-negative lower restriction (e.g. if you want your values to be >=0) ; can't deal with asymmetric borders; have to be implemented if needed\r
57}\r
58\r
59\r
60Double_t AliTRDtrapAlu::GetValueWhole() const { \r
61 // get the actual value (respecting pre- and post-comma parts) in integer-description\r
62 Double_t valPre = (Double_t)(fValue>>fPostCom);\r
63 Double_t valPost = 0.0;\r
64 for(Int_t i = 0; i<=fPostCom-1; i++){\r
65 Double_t num = (fValue>>i)&1;\r
66 Double_t denom = LUT(fPostCom-i);\r
67 valPost = valPost + num/denom;\r
68 }\r
69 Double_t val = valPre + valPost;\r
70 return val;\r
71 }\r
72\r
73\r
74void AliTRDtrapAlu::WriteWord(){\r
75 // for debugging purposes\r
76 printf("bit-word: ");\r
77 if (fSigned == true) printf("-");\r
78 for(Int_t i = fPostCom + fPreCom - 1; i >= fPostCom; i--){ //read from behind in order to write the word from left to right\r
79 printf("%d",(fValue>>i) & 1);\r
80 }\r
81 printf(".");\r
82 for (Int_t j = fPostCom - 1; j >= 0; j--){\r
83 printf("%d",(fValue>>j) & 1);\r
84 }\r
85 printf("\n");\r
86 \r
87}\r
88\r
89\r
90\r
91\r
92\r
93AliTRDtrapAlu& AliTRDtrapAlu::AssignInt(const Int_t& first){ \r
94 // assign an integer\r
95\r
96 // parameter "first" is an integer for the pre-comma part (not UInt in order to match the error case first<0)\r
97 fSigned = kFALSE;\r
98 Int_t exponent = fPreCom + fPostCom;\r
99\r
100 \r
101 if (first<0) {\r
102 fValue = 0; //setting fValue to 0; first should not be negative\r
103 fValue = fValue & 0;\r
104 return *this;\r
105 }\r
106\r
107 if (CheckUSize(first<<fPostCom) == kFALSE){\r
108 \r
109 //setting fValue to maximum; first was to big\r
110 fValue = fuRestriction;\r
111 fValue = fValue & LUT(exponent)-1;\r
112 return *this;\r
113 }\r
114\r
115 if (CheckLSize(first<<fPostCom) == kFALSE){\r
116 \r
117 //setting fValue to minimum; first was to small\r
118 fValue = flRestriction;\r
119 fValue = fValue & LUT(exponent)-1;\r
120 return *this;\r
121 }\r
122\r
123 \r
124 fValue = first;\r
125 fValue = fValue<<fPostCom; \r
126 fValue = fValue & LUT(exponent)-1;\r
127 \r
128 return *this;\r
129 \r
130}\r
131\r
132AliTRDtrapAlu& AliTRDtrapAlu::AssignDouble(const Double_t& first){\r
133 // assign a double\r
134 \r
135 fSigned = kFALSE;\r
136 Int_t exponent = fPreCom + fPostCom;\r
137 Int_t firstPre = 0; //integer part of first\r
138 Int_t firstPost = 0; //comma part of first (cut off with enough accuracy\r
139 Int_t c = 0;\r
140 Double_t firstPreFloat = 0;\r
141 \r
142 \r
143 Int_t power1 = LUT(exponent);\r
144 \r
145 firstPre = (Int_t)first;\r
146 firstPreFloat = firstPre;\r
147 \r
148 if(firstPre < 0){\r
149 fValue = 0;\r
150 fValue = fValue & 0;\r
151 return *this;\r
152 }\r
153 \r
154 if(CheckUSize((Int_t)(first*LUT(fPostCom))) == kFALSE){\r
155 \r
156 //fValue = MakePower(2,fPreCom) - 1;\r
157 fValue = fuRestriction;\r
158 fValue = fValue & (power1 - 1);\r
159 return *this;\r
160 }\r
161 \r
162 if(CheckLSize((Int_t)(first*LUT(fPostCom))) == kFALSE){\r
163 \r
164 //fValue = MakePower(2,fPreCom) - 1;\r
165 fValue = flRestriction;\r
166 fValue = fValue & (power1 - 1);\r
167 return *this;\r
168 }\r
169 \r
170\r
171 fValue = firstPre;\r
172 \r
173 //get post comma part with adequate accuracy\r
174 firstPost = (Int_t)((first - firstPreFloat)*LUT(fPostCom));\r
175 for(Int_t i = 1; i <= fPostCom; i++) {\r
176 c = (firstPost>>(fPostCom - i)) & 1;\r
177 fValue = fValue<<1;\r
178 fValue = fValue | c;\r
179 }\r
180\r
181 fValue = fValue & (power1 - 1);\r
182 return *this;\r
183}\r
184\r
185\r
186AliTRDtrapAlu& AliTRDtrapAlu::operator=(const AliTRDtrapAlu& binary){\r
187 // assign an object of type AliTRDtrapAlu\r
188\r
189 Int_t c = 0;\r
190 //Int_t exponent = fPreCom + fPostCom;\r
191 \r
192 \r
193 Int_t power1 = LUT(fPreCom + fPostCom);\r
194\r
195 fValue = binary.GetValue(); // in case this==&binary : binary's values are overwritten\r
196 Int_t diffPost = binary.GetPost()-fPostCom;\r
197 Int_t check = 0;\r
198 if(diffPost<0) check = fValue<<(-diffPost);\r
199 else check = fValue>>(diffPost);\r
200 if (CheckUSize(check)==kFALSE){ //checking size of pre-comma part\r
201 \r
202 //setting fValue to maximum\r
203 \r
204 \r
205 fValue = fuRestriction; // fuRestriction >= 0 \r
206 fValue = fValue & (power1 - 1);\r
207 fSigned = kFALSE;\r
208 return *this;\r
209 }\r
210\r
211 Int_t val = (binary.GetSign()==kFALSE) ? check : -check; \r
212 if (CheckLSize(val)==kFALSE){ //checking size of pre-comma part\r
213 \r
214 //setting fValue to minimum\r
215 \r
216 \r
217 if (flRestriction < 0) {\r
218 fValue = -flRestriction;\r
219 fSigned = kTRUE;\r
220 }\r
221 else {\r
222 fValue = flRestriction;\r
223 fSigned = kFALSE;\r
224 }\r
225 fValue = fValue & (power1 - 1);\r
226 return *this;\r
227 }\r
228 \r
229 if (this == & binary) return *this;\r
230 \r
231 fSigned = kFALSE;\r
232 Int_t iValue = fValue;\r
233 fValue = fValue>>(binary.GetPost()); //only keep the valid pre-comma bits\r
234 \r
235 //append existing post-comma bits to fValue; cut off or add 0 if post-comma numbers don`t match\r
236 for(Int_t i = 1; i <= fPostCom; i++){\r
237 if(i <= (binary.GetPost())){\r
238 c = ((iValue)>>(binary.GetPost()-i)) & 1;\r
239 }\r
240 else{\r
241 c = 0;\r
242 }\r
243 fValue = fValue<<1;\r
244 fValue = fValue | c;\r
245 }\r
246 \r
247 fValue = fValue & (power1 - 1);\r
248 fSigned = binary.GetSign();\r
249 return *this;\r
250}\r
251\r
252\r
253\r
254AliTRDtrapAlu& AliTRDtrapAlu::operator+(AliTRDtrapAlu& binary){ \r
255 // + operator\r
256\r
257 //no const parameter because referenced object will be changed\r
258 \r
259 \r
260 Int_t binPre = binary.GetPre();\r
261 Int_t binPost = binary.GetPost();\r
262 Int_t binVal = binary.GetValue();\r
263 \r
264 Int_t min = Min(binPost,fPostCom);\r
265 Int_t max = Max(binPre,fPreCom);\r
266 \r
267 Int_t shift = binPost - min;\r
268 Int_t add1 = (binVal)>>(shift); //for addition: cut off at minimum accuracy\r
269 shift = fPostCom - min;\r
270 Int_t add2 = fValue>>(shift);\r
271 if(binary.GetSign() == kTRUE) add1 = -add1;\r
272 if(fSigned == kTRUE) add2 = -add2;\r
273 Int_t add = add1 + add2;\r
274 \r
275 \r
276 //because the parameter "binary" could be a reference to the object to which Mem() is a reference, do not change Mem() until you have extracted all information from "binary"; otherwise you change the information you would like to read\r
277 Mem().Init(max + 1,min); //buffer: enough space for pre-comma,post-comma according to accuracy\r
278 Mem().AssignFormatted(Max(add,-add));\r
279 Mem().SetSign(add);\r
280 \r
281\r
282 //Mem().FastInit(max+1,min,add);\r
283 return Mem();\r
284}\r
285\r
286\r
287AliTRDtrapAlu& AliTRDtrapAlu::operator-(AliTRDtrapAlu& binary){\r
288 // - operator \r
289\r
290 Int_t binPre = binary.GetPre();\r
291 Int_t binPost = binary.GetPost();\r
292 Int_t binVal = binary.GetValue();\r
293\r
294\r
295 Int_t min = Min(binPost,fPostCom);\r
296 Int_t max = Max(binPre,fPreCom);\r
297\r
298 Int_t shift = binPost - min;\r
299 Int_t sub1 = (binVal)>>(shift); //for addition: cut off at minimum accuracy\r
300 shift = fPostCom - min;\r
301 Int_t sub2 = fValue>>(shift);\r
302 if(binary.GetSign() == kTRUE) sub1 = -sub1;\r
303 if(fSigned == kTRUE) sub2 = -sub2;\r
304 Int_t sub = sub2 - sub1; // order of subtraction is important\r
305 \r
306\r
307 Mem().Init(max + 1,min); //buffer: enough space for pre-comma, post-comma according to accuracy\r
308 Mem().AssignFormatted(Max(sub,-sub)); \r
309 Mem().SetSign(sub);\r
310 //Mem().FastInit(max+1,min,sub);\r
311 return Mem();\r
312} \r
313\r
314\r
315AliTRDtrapAlu& AliTRDtrapAlu::operator*(AliTRDtrapAlu& binary){\r
316 // * operator\r
317 \r
318\r
319 Int_t binPre = binary.GetPre();\r
320 Int_t binPost = binary.GetPost();\r
321\r
322\r
323 Int_t min = Min(binPost,fPostCom);\r
324 Int_t max = Max(binPre,fPreCom);\r
325\r
326 \r
327 Int_t mult1 = binary.GetValue();\r
328 Int_t mult2 = fValue;\r
329 Int_t shift = (Int_t)(fPostCom + binPost - min);\r
330 Double_t fmult1 = (Double_t)mult1;\r
331 Double_t fmult2 = (Double_t)mult2;\r
332 (fmult1 > fmult2) ? fmult1 = fmult1/LUT(shift) : fmult2 = fmult2/LUT(shift);\r
333 \r
334 \r
335 if (binary.GetSign() == kTRUE) fmult1 = -fmult1;\r
336 if (fSigned == kTRUE) fmult2 = -fmult2;\r
337 Double_t fmult = fmult1*fmult2;\r
338 Int_t mult = (Int_t)fmult;\r
339 Int_t sign = 1;\r
340 if(mult<0) sign = -1;\r
341 mult = Max(mult,-mult);\r
342 //Int_t shift = fPostCom + binPost - min;\r
343 //mult = mult>>(shift);\r
344 Mem().Init(2 * max + 1, min); // +1 to consider the borrow from the past-comma part; accuracy of past-comma part is determined by the minimum; therefore, for the result not more accuracy is guaranteed\r
345 // be aware that this only works if 2*max+1+min <= 32!! adjusting the pre-comma place to the value would consume too much time\r
346\r
347 Mem().AssignFormatted(mult);\r
348 Mem().SetSign(sign);\r
349 //mult = sign*mult;\r
350 //Mem().FastInit(2*max+1,min,mult);\r
351 return Mem();\r
352}\r
353 \r
354\r
355\r
356AliTRDtrapAlu& AliTRDtrapAlu::operator/(AliTRDtrapAlu& binary){\r
357 // / operator\r
358 \r
359\r
360 Int_t binPre = binary.GetPre();\r
361 Int_t binPost = binary.GetPost();\r
362 Int_t min = Min(binPost,fPostCom);\r
363 Int_t max = Max(binPre,fPreCom);\r
364 \r
365 Int_t div1 = binary.GetValue(); //value in integer format\r
366 Int_t div2 = fValue;\r
367 \r
368 // this approach does not always work because it can exceed the range of integers\r
369 //Int_t numerator = div2 * LUT(min);\r
370 Int_t numerator = div2;\r
371 if (fSigned == kTRUE) numerator = numerator*(-1);\r
372 Int_t denominator = div1;\r
373 if (binary.GetSign() == kTRUE) denominator = denominator*(-1);\r
374 Double_t fdiv = 0.0;\r
375 Double_t fLUT = 0.0;\r
376 Int_t div = 0;\r
377 \r
378\r
379 if (div1 == 0){\r
380 Mem().Init(max + 1,min);\r
381 Mem().AssignFormatted(LUT(max+min+1)-1); // division by 0: set to max value\r
382 //Mem().FastInit(max+1,min,div1);\r
383 return Mem();\r
384 }\r
385 \r
386 fdiv = (Double_t)numerator/denominator;\r
387 \r
388 Int_t shift = fPostCom - binPost;\r
389 \r
390 if(shift>0){\r
391 //denominator = denominator * LUT(shift);\r
392 fLUT = (Double_t)LUT(min)/LUT(shift);\r
393 }\r
394 else {\r
395 if(shift<0) {\r
396 shift = -shift;\r
397 //numerator = numerator * LUT(shift);\r
398 fLUT = (Double_t)LUT(min)*LUT(shift);\r
399 }\r
400 else {\r
401 fLUT = (Double_t)LUT(min);\r
402 }\r
403 }\r
404\r
405 fdiv = fdiv*fLUT;\r
406 div = (Int_t)fdiv;\r
407 \r
408 Int_t sign = (div>=0) ? 1 : -1;\r
409 div = Max(div,-div);\r
410 \r
411 // chose min as past-comma part because from a division of integers you can't get only an integer\r
412 Mem().Init(max + 1,min); // max+1+min must <= 32!!\r
413 Mem().SetSign(sign);\r
414 Mem().AssignFormatted(div);\r
415 \r
416 return Mem();\r
417 \r
418}\r
419\r
420\r
421\r
422Int_t AliTRDtrapAlu::MakePower(const Int_t& base,const Int_t& exponent)const{\r
423// calculate "base" to the power of "exponent"\r
424 Int_t result = 1;\r
425 \r
426 for(Int_t i = 1; i <= exponent; i++){\r
427 result = result * base;\r
428 }\r
429 return result;\r
430}\r
431\r
432\r
433\r
434\r
435Int_t AliTRDtrapAlu::LUT(const Int_t& index){ \r
436 // simple look-up table for base=2\r
437 \r
438 static Bool_t fLUT = kFALSE;\r
439 static Int_t gLUT[30];\r
440 if (fLUT == kFALSE) {\r
441 gLUT[0] = 1;\r
442 for(Int_t i = 1; i<30; i++) {\r
443 gLUT[i] = gLUT[i-1] * 2;\r
444 }\r
445 fLUT = kTRUE;\r
446 } \r
447 if (index >=0 && index < 30){\r
448 return gLUT[index];\r
449 }\r
450 else {\r
451 \r
452 return Mem().MakePower(2,index);\r
453 }\r
454}\r