Copy of event header for delta-AOD on demand.
[u/mrichter/AliRoot.git] / MUON / AliMUONTrackerData.cxx
CommitLineData
0145e89a 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#include "AliMUONTrackerData.h"
19
8741815f 20#include "AliCodeTimer.h"
21#include "AliLog.h"
22#include "AliMUON1DArray.h"
23#include "AliMUON1DMap.h"
24#include "AliMUON2DMap.h"
0145e89a 25#include "AliMUONCalibParamND.h"
8741815f 26#include "AliMUONSparseHisto.h"
0145e89a 27#include "AliMUONVStore.h"
28#include "AliMpBusPatch.h"
8741815f 29#include "AliMpConstants.h"
0145e89a 30#include "AliMpDDLStore.h"
0145e89a 31#include "AliMpDEIterator.h"
8741815f 32#include "AliMpDEManager.h"
0145e89a 33#include "AliMpDetElement.h"
34#include "AliMpHVNamer.h"
8741815f 35#include "AliMpManuIterator.h"
0145e89a 36#include <Riostream.h>
37#include <TMath.h>
38#include <TObjArray.h>
39#include <TObjString.h>
40#include <TString.h>
41#include <TVector2.h>
42#include <float.h>
43
44/// \class AliMUONTrackerData
45///
46/// Implementation of AliMUONVTrackerData class
47///
48/// \author Laurent Aphecetche, Subatech
49
50///\cond CLASSIMP
51ClassImp(AliMUONTrackerData)
52///\endcond
53
54const Int_t AliMUONTrackerData::fgkExtraDimension = 2;
55const Int_t AliMUONTrackerData::fgkVirtualExtraDimension = 1;
56
57//_____________________________________________________________________________
58AliMUONTrackerData::AliMUONTrackerData(const char* name, const char* title,
59 Int_t dimension,
49419555 60 Bool_t issingleevent)
0145e89a 61: AliMUONVTrackerData(name,title),
49419555 62fIsSingleEvent(issingleevent),
0145e89a 63fChannelValues(0x0),
64fManuValues(0x0),
65fBusPatchValues(0x0),
66fDEValues(0x0),
67fChamberValues(0x0),
68fPCBValues(0x0),
49419555 69fDimension(External2Internal(dimension)+fgkExtraDimension),
0145e89a 70fNevents(0x0),
71fDimensionNames(new TObjArray(fDimension+fgkVirtualExtraDimension)),
8741815f 72fExternalDimensionNames(new TObjArray(dimension)),
0145e89a 73fExternalDimension(dimension),
8741815f 74fHistogramming(new Int_t[fExternalDimension]),
10eb3d17 75fChannelHistos(0x0),
76fXmin(0.0),
77fXmax(0.0)
0145e89a 78{
79 /// ctor
10eb3d17 80 memset(fHistogramming,0,sizeof(Int_t)); // histogramming is off by default. Use MakeHistogramForDimension to turn it on.
8741815f 81 fExternalDimensionNames->SetOwner(kTRUE);
0145e89a 82 fDimensionNames->SetOwner(kTRUE);
83 fDimensionNames->AddAt(new TObjString("occ"),IndexOfOccupancyDimension());
84 fDimensionNames->AddAt(new TObjString("N"),IndexOfNumberDimension());
85 fDimensionNames->AddAt(new TObjString("n"),NumberOfDimensions()-fgkVirtualExtraDimension);
86 Clear();
87}
88
89//_____________________________________________________________________________
90AliMUONTrackerData::~AliMUONTrackerData()
91{
92 /// dtor
93 delete fChannelValues;
94 delete fManuValues;
95 delete fBusPatchValues;
96 delete fDEValues;
97 delete fChamberValues;
98 delete fPCBValues;
99 delete fDimensionNames;
8741815f 100 delete fExternalDimensionNames;
101 delete[] fHistogramming;
102 delete fChannelHistos;
0145e89a 103}
104
105//_____________________________________________________________________________
106Bool_t
49419555 107AliMUONTrackerData::Add(const AliMUONVStore& store)
0145e89a 108{
8741815f 109 /// Add the given external store to our internal store
0145e89a 110
8741815f 111 AliCodeTimerAuto(GetName());
112
49419555 113 if ( IsSingleEvent() && fNevents == 1 )
114 {
115 AliError(Form("%s is supposed to be single event only",GetName()));
116 return kFALSE;
117 }
118
119 ++fNevents;
120
8741815f 121 NumberOfEventsChanged();
0145e89a 122
8741815f 123 if (!fChannelValues)
124 {
49419555 125 Int_t numberOfBusPatches(0);
126 Int_t numberOfDEs(0);
127
128 // get number of bus patches and number of detection element
129 // to initialize fBusPatchValues and fDEValues below
130
131 TExMapIter it(AliMpDDLStore::Instance()->GetBusPatchesIterator());
132 Long_t key,value;
133 while ( it.Next(key,value) ) ++numberOfBusPatches;
134 AliMpDEIterator deIt;
135 deIt.First();
136 while (!deIt.IsDone())
137 {
138 ++numberOfDEs;
139 deIt.Next();
140 }
141
7b6684fe 142 fChannelValues = new AliMUON2DMap(kTRUE);
143 fManuValues = new AliMUON2DMap(kTRUE);
144 fPCBValues = new AliMUON2DMap(kFALSE);
49419555 145 fBusPatchValues = new AliMUON1DMap(numberOfBusPatches);
146 fDEValues = new AliMUON1DMap(numberOfDEs);
8741815f 147 fChamberValues = new AliMUON1DArray;
148 }
0145e89a 149
150 TIter next(store.CreateIterator());
151 AliMUONVCalibParam* external;
152
49419555 153 Int_t nk(2);
154
155 if ( IsSingleEvent() ) nk = 1;
156
0145e89a 157 while ( ( external = static_cast<AliMUONVCalibParam*>(next()) ) )
158 {
8741815f 159 if ( external->Dimension() != ExternalDimension() )
160 {
161 AliError(Form("Incompatible dimensions %d vs %d",
162 external->Dimension(),ExternalDimension()));
163 return kFALSE;
164 }
0145e89a 165
8741815f 166
167 AliMUONVCalibParam* chamber, *de, *busPatch, *pcb, *manu, *channel;
168 AliMpDetElement* mpde;
0145e89a 169
8741815f 170 Int_t manuId = GetParts(external,chamber,de,busPatch,pcb,manu,channel,mpde);
0145e89a 171
7b6684fe 172 if ( manuId < 0 ) continue;
173
8741815f 174 Int_t detElemId = mpde->GetId();
175
176 Double_t value[] = { 0.0, 0.0 };
177
178 Int_t nch = mpde->NofChannelsInManu(manuId);
0145e89a 179
180 for ( Int_t i = 0; i < external->Size(); ++i )
181 {
8741815f 182 Bool_t existingChannel = ( nch == AliMpConstants::ManuNofChannels() ? kTRUE
183 : mpde->IsConnectedChannel(manuId,i));
184 // note we only use IsConnectedChannel method when really needed, as
185 // it costs (some) CPU time...
0145e89a 186
8741815f 187 if ( existingChannel )
0145e89a 188 {
8741815f 189 Bool_t validChannel(kFALSE);
0145e89a 190
8741815f 191 for ( Int_t j = 0; j < external->Dimension(); ++j )
192 {
193 Double_t vext = external->IsDoublePrecision() ?
194 external->ValueAsDoubleFast(i,j) :
195 external->ValueAsFloatFast(i,j);
196
197 if ( vext >= AliMUONVCalibParam::InvalidFloatValue() ) continue;
198
199 validChannel = kTRUE;
200
201 Int_t ix = External2Internal(j);
202
203 value[0] = vext;
204 value[1] = vext*vext;
205
206 if ( IsHistogrammed(j) )
207 {
208 FillChannel(detElemId,manuId,i,j,vext);
209 }
210
49419555 211 for ( Int_t k = 0; k < nk; ++k )
8741815f 212 {
213 channel->SetValueAsDoubleFast(i,ix+k,channel->ValueAsDoubleFast(i,ix+k)+value[k]);
214
215 manu->SetValueAsDoubleFast(0,ix+k,manu->ValueAsDoubleFast(0,ix+k)+value[k]);
216
217 busPatch->SetValueAsDoubleFast(0,ix+k,busPatch->ValueAsDoubleFast(0,ix+k)+value[k]);
218
219 de->SetValueAsDoubleFast(0,ix+k,de->ValueAsDoubleFast(0,ix+k)+value[k]);
220
221 chamber->SetValueAsDoubleFast(0,ix+k,chamber->ValueAsDoubleFast(0,ix+k)+value[k]);
222
223 if ( pcb )
224 {
225 pcb->SetValueAsDoubleFast(0,ix+k,pcb->ValueAsDoubleFast(0,ix+k)+value[k]);
226 }
227 }
228 }
0145e89a 229
8741815f 230 if ( validChannel )
231 {
232 channel->SetValueAsDoubleFast(i,IndexOfOccupancyDimension(),
233 channel->ValueAsDoubleFast(i,IndexOfOccupancyDimension())+1.0);
234 manu->SetValueAsDoubleFast(0,IndexOfOccupancyDimension(),
235 manu->ValueAsDoubleFast(0,IndexOfOccupancyDimension())+1.0);
236 busPatch->SetValueAsDoubleFast(0,IndexOfOccupancyDimension(),
237 busPatch->ValueAsDoubleFast(0,IndexOfOccupancyDimension())+1.0);
238 de->SetValueAsDoubleFast(0,IndexOfOccupancyDimension(),
239 de->ValueAsDoubleFast(0,IndexOfOccupancyDimension())+1.0);
240 chamber->SetValueAsDoubleFast(0,IndexOfOccupancyDimension(),
241 chamber->ValueAsDoubleFast(0,IndexOfOccupancyDimension())+1.0);
242 if ( pcb )
243 {
244 pcb->SetValueAsDoubleFast(0,IndexOfOccupancyDimension(),
245 pcb->ValueAsDoubleFast(0,IndexOfOccupancyDimension())+1.0);
246 }
247 }
0145e89a 248 }
249 }
250 }
251
0145e89a 252 return kTRUE;
253}
254
255//_____________________________________________________________________________
256Double_t
257AliMUONTrackerData::BusPatch(Int_t busPatchId, Int_t dim) const
258{
259 /// Return the value of a given buspatch for a given dimension
260 /// or 0 if not existing
261 AliMUONVCalibParam* param = BusPatchParam(busPatchId);
262 return param ? Value(*param,0,dim) : 0.0;
263}
264
265//_____________________________________________________________________________
266AliMUONVCalibParam*
8741815f 267AliMUONTrackerData::BusPatchParam(Int_t busPatchId, Bool_t create) const
0145e89a 268{
269 /// Return (if it exist), the VCalibParam for a given busPatch
8741815f 270
271 AliMUONVCalibParam* busPatch = fBusPatchValues ? static_cast<AliMUONVCalibParam*>
272 (fBusPatchValues->FindObject(busPatchId)) : 0x0;
273
274 if (!busPatch && create && fBusPatchValues)
275 {
276 busPatch = CreateBusPatchParam(busPatchId);
277 fBusPatchValues->Add(busPatch);
278 }
279
280 return busPatch;
281}
282
283//_____________________________________________________________________________
284AliMUONVCalibParam*
285AliMUONTrackerData::CreateBusPatchParam(Int_t busPatchId) const
286{
287 /// Create storage for one bus patch
288
289 AliCodeTimerAuto("");
290
291 AliMpBusPatch* bp = AliMpDDLStore::Instance()->GetBusPatch(busPatchId);
292
293 if (!bp)
294 {
295 AliError(Form("Got an invalid buspatchId = %d",busPatchId));
296 return 0x0;
297 }
298
299 AliMUONVCalibParam* busPatch = new AliMUONCalibParamND(Dimension(),1,busPatchId,0,0.0);
300
301 // set the number of channels in that buspatch
302
303 Int_t nchannels(0);
304
305 Int_t detElemId = AliMpDDLStore::Instance()->GetDEfromBus(busPatchId);
306
307 AliMpDetElement* de = AliMpDDLStore::Instance()->GetDetElement(detElemId);
308
309 for ( Int_t i = 0; i < bp->GetNofManus(); ++i )
310 {
311 Int_t manuId = bp->GetManuId(i);
312 nchannels += de->NofChannelsInManu(manuId);
313 }
314
315 busPatch->SetValueAsDouble(0,IndexOfNumberDimension(),nchannels);
316
317 return busPatch;
0145e89a 318}
319
320//_____________________________________________________________________________
321Double_t
322AliMUONTrackerData::Chamber(Int_t chamberId, Int_t dim) const
323{
324 /// Return the value fo a given chamber for a given dimension,
325 /// or zero if not existing
326 AliMUONVCalibParam* param = ChamberParam(chamberId);
327 return param ? Value(*param,0,dim) : 0.0;
328}
329
330//_____________________________________________________________________________
331AliMUONVCalibParam*
8741815f 332AliMUONTrackerData::ChamberParam(Int_t chamberId, Bool_t create) const
0145e89a 333{
334 /// Return (if it exist) the VCalibParam for a given chamber
8741815f 335
336 AliMUONVCalibParam* chamber = fChamberValues ? static_cast<AliMUONVCalibParam*>
0145e89a 337 (fChamberValues->FindObject(chamberId)) : 0x0;
8741815f 338
339 if (!chamber && create && fChamberValues)
340 {
341 chamber = CreateChamberParam(chamberId);
342 fChamberValues->Add(chamber);
343 }
344
345 return chamber;
346}
347
348//_____________________________________________________________________________
349AliMUONVCalibParam*
350AliMUONTrackerData::CreateChamberParam(Int_t chamberId) const
351{
352 /// Create storage for one chamber
353
354 AliCodeTimerAuto("");
355
356 AliMUONVCalibParam* chamber = new AliMUONCalibParamND(Dimension(),1,chamberId,0,0.0);
357
358 // set the number of channels in that chamber
359
360 Int_t nchannels(0);
361
362 AliMpDEIterator it;
363
364 it.First(chamberId);
365
366 while ( !it.IsDone() )
367 {
368 AliMpDetElement* det = it.CurrentDE();
369
370 for ( Int_t i = 0; i < det->GetNofBusPatches(); ++i )
371 {
372 Int_t busPatchId = det->GetBusPatchId(i);
373 AliMpBusPatch* bp = AliMpDDLStore::Instance()->GetBusPatch(busPatchId);
374 for ( Int_t j = 0; j < bp->GetNofManus(); ++j )
375 {
376 Int_t manuId = bp->GetManuId(j);
377 nchannels += det->NofChannelsInManu(manuId);
378 }
379 }
380
381 it.Next();
382 }
383
384 chamber->SetValueAsDouble(0,IndexOfNumberDimension(),nchannels);
385
386 return chamber;
0145e89a 387}
388
389//_____________________________________________________________________________
390Double_t
391AliMUONTrackerData::Channel(Int_t detElemId, Int_t manuId,
392 Int_t manuChannel, Int_t dim) const
393{
394 /// Return the value for a given channel for a given dimension
395
396 AliMUONVCalibParam* param = ChannelParam(detElemId,manuId);
397
398 return param ? Value(*param,manuChannel,dim) : 0.0;
399}
400
401//_____________________________________________________________________________
402AliMUONVCalibParam*
8741815f 403AliMUONTrackerData::ChannelParam(Int_t detElemId, Int_t manuId,
404 AliMUONVCalibParam* external) const
0145e89a 405{
406 /// Return (if it exist) the VCalibParam for a given manu
8741815f 407
408 AliMUONVCalibParam* param = fChannelValues ? static_cast<AliMUONVCalibParam*>
409 (fChannelValues->FindObject(detElemId,manuId)) : 0x0 ;
410
411 if (!param && external && fChannelValues)
412 {
7b6684fe 413 param = CreateDouble(*external,detElemId,manuId);
8741815f 414 fChannelValues->Add(param);
415 }
416
417 return param;
0145e89a 418}
419
0145e89a 420//_____________________________________________________________________________
421void
422AliMUONTrackerData::Clear(Option_t*)
423{
424 /// Clear all the values
425 if ( fChannelValues ) fChannelValues->Clear();
426 if ( fManuValues ) fManuValues->Clear();
427 if ( fBusPatchValues) fBusPatchValues->Clear();
428 if ( fPCBValues ) fPCBValues->Clear();
429 if ( fDEValues) fDEValues->Clear();
8741815f 430 if ( fChamberValues ) fChamberValues->Clear();
431 if ( fChannelHistos ) fChannelHistos->Clear();
0145e89a 432 fNevents = 0;
433 NumberOfEventsChanged();
434}
435
436//_____________________________________________________________________________
437Double_t
438AliMUONTrackerData::Count(Int_t detElemId, Int_t manuId,
439 Int_t manuChannel) const
440{
441 /// Return the number of times a given channel had data
0145e89a 442
8741815f 443 return Channel(detElemId,manuId,manuChannel,IndexOfNumberDimension());
0145e89a 444}
445
446//_____________________________________________________________________________
447AliMUONVCalibParam*
7b6684fe 448AliMUONTrackerData::CreateDouble(const AliMUONVCalibParam& param,
449 Int_t detElemId, Int_t manuId) const
0145e89a 450{
451 /// Create a double version of VCalibParam, for internal use
8741815f 452
453 AliCodeTimerAuto("");
454
455 AliMUONVCalibParam* c = new AliMUONCalibParamND(Dimension(),
456 param.Size(),
7b6684fe 457 detElemId,
458 manuId,
8741815f 459 0.0);
0145e89a 460
7b6684fe 461 AliMpDetElement* de = AliMpDDLStore::Instance()->GetDetElement(detElemId,manuId);
462
0145e89a 463 for ( Int_t i = 0; i < c->Size(); ++i )
464 {
7b6684fe 465 Double_t value(0.0);
466
467 if ( de->IsConnectedChannel(manuId,i) ) value = 1.0;
468
469 c->SetValueAsDouble(i,IndexOfNumberDimension(),value);
0145e89a 470 }
471
472 return c;
473}
474
475//_____________________________________________________________________________
476Double_t
477AliMUONTrackerData::DetectionElement(Int_t detElemId, Int_t dim) const
478{
479 /// Return the value for a given detection element for a given dimension
480 AliMUONVCalibParam* param = DetectionElementParam(detElemId);
481 return param ? Value(*param,0,dim) : 0.0;
482
483}
484
485//_____________________________________________________________________________
486AliMUONVCalibParam*
8741815f 487AliMUONTrackerData::DetectionElementParam(Int_t detElemId, Bool_t create) const
0145e89a 488{
489 /// Return (if it exist) the VCalibParam for a given detection element
8741815f 490
491 AliMUONVCalibParam* de = fDEValues ? static_cast<AliMUONVCalibParam*>
492 (fDEValues->FindObject(detElemId)) : 0x0 ;
493
494 if (!de && create && fDEValues)
495 {
496 de = CreateDetectionElementParam(detElemId);
497 fDEValues->Add(de);
498 }
499
500 return de;
501
502}
503
504//_____________________________________________________________________________
505AliMUONVCalibParam*
506AliMUONTrackerData::CreateDetectionElementParam(Int_t detElemId) const
507{
508 /// Create storage for one detection element
509
510 AliCodeTimerAuto("");
511
512 AliMUONVCalibParam* de = new AliMUONCalibParamND(Dimension(),1,detElemId,0,0.0);
513
514 AliMpDetElement* det = AliMpDDLStore::Instance()->GetDetElement(detElemId);
515 Int_t nchannels(0);
516
517 for ( Int_t i = 0; i < det->GetNofBusPatches(); ++i )
518 {
519 Int_t busPatchId = det->GetBusPatchId(i);
520 AliMpBusPatch* bp = AliMpDDLStore::Instance()->GetBusPatch(busPatchId);
521 for ( Int_t j = 0; j < bp->GetNofManus(); ++j )
522 {
523 Int_t manuId = bp->GetManuId(j);
524 nchannels += det->NofChannelsInManu(manuId);
525 }
526 }
527
528 de->SetValueAsDouble(0,IndexOfNumberDimension(),nchannels);
529
530 return de;
0145e89a 531}
532
533//_____________________________________________________________________________
534TString
535AliMUONTrackerData::DimensionName(Int_t dim) const
536{
537 /// Get the name of a given dimension
538 TObjString* value = static_cast<TObjString*>(fDimensionNames->At(dim));
539 if ( value )
540 {
541 return value->String();
542 }
543 else
544 {
545 return TString("Invalid");
546 }
547}
548
549//_____________________________________________________________________________
49419555 550Int_t
551AliMUONTrackerData::External2Internal(Int_t index) const
552{
553 /// From external to internal dimension
554 return IsSingleEvent() ? index : index*2;
555}
556
557//_____________________________________________________________________________
8741815f 558TString
559AliMUONTrackerData::ExternalDimensionName(Int_t dim) const
0145e89a 560{
8741815f 561 /// Get the name of a given external dimension
562
563 TObjString* value = static_cast<TObjString*>(fExternalDimensionNames->At(dim));
564 if ( value )
565 {
566 return value->String();
567 }
568 else
569 {
570 return TString("Invalid");
571 }
0145e89a 572}
573
574//_____________________________________________________________________________
8741815f 575void
576AliMUONTrackerData::FillChannel(Int_t detElemId, Int_t manuId, Int_t manuChannel,
577 Int_t dim, Double_t value)
0145e89a 578{
8741815f 579 /// Fill histogram of a given channel
580
10eb3d17 581 AliMUONSparseHisto* h = GetChannelSparseHisto(detElemId, manuId, manuChannel,dim);
8741815f 582
583 h->Fill(static_cast<Int_t>(TMath::Nint(value)));
0145e89a 584}
585
586//_____________________________________________________________________________
10eb3d17 587AliMUONSparseHisto*
588AliMUONTrackerData::GetChannelSparseHisto(Int_t detElemId, Int_t manuId,
589 Int_t manuChannel, Int_t dim) const
8741815f 590{
10eb3d17 591 /// Get histogram of a given channel
8741815f 592
10eb3d17 593 if (!fChannelHistos) return 0x0;
8741815f 594
10eb3d17 595 AliMUON1DMap* m = static_cast<AliMUON1DMap*>(fChannelHistos->FindObject(detElemId,manuId));
596 if (!m) return 0x0;
8741815f 597
10eb3d17 598 UInt_t uid = ( manuChannel << 16 ) | dim;
8741815f 599
10eb3d17 600 AliMUONSparseHisto* h = static_cast<AliMUONSparseHisto*>(m->FindObject(uid));
8741815f 601
602 return h;
603}
0145e89a 604
8741815f 605//_____________________________________________________________________________
606AliMUONSparseHisto*
10eb3d17 607AliMUONTrackerData::GetChannelSparseHisto(Int_t detElemId, Int_t manuId,
608 Int_t manuChannel, Int_t dim)
8741815f 609{
10eb3d17 610 /// Get histogram of a given channel. Create it if necessary
8741815f 611
612 if (!fChannelHistos) fChannelHistos = new AliMUON2DMap(kTRUE);
613
10eb3d17 614 AliMUON1DMap* m = static_cast<AliMUON1DMap*>(fChannelHistos->FindObject(detElemId,manuId));
615 if (!m)
8741815f 616 {
10eb3d17 617 m = new AliMUON1DMap(AliMpConstants::ManuNofChannels()); // start with only 1 dim
618 m->SetUniqueID( ( manuId << 16 ) | detElemId );
619 fChannelHistos->Add(m);
8741815f 620 }
621
10eb3d17 622 UInt_t uid = ( manuChannel << 16 ) | dim;
8741815f 623
10eb3d17 624 AliMUONSparseHisto* h = static_cast<AliMUONSparseHisto*>(m->FindObject(uid));
8741815f 625 if (!h)
626 {
10eb3d17 627 h = new AliMUONSparseHisto(fXmin,fXmax);
628
629 h->SetUniqueID(uid);
630
631 m->Add(h);
8741815f 632 }
0145e89a 633
8741815f 634 return h;
635}
0145e89a 636
8741815f 637//_____________________________________________________________________________
638Int_t
639AliMUONTrackerData::GetParts(AliMUONVCalibParam* external,
640 AliMUONVCalibParam*& chamber,
641 AliMUONVCalibParam*& de,
642 AliMUONVCalibParam*& busPatch,
643 AliMUONVCalibParam*& pcb,
644 AliMUONVCalibParam*& manu,
645 AliMUONVCalibParam*& channel,
646 AliMpDetElement*& mpde)
647{
648 /// Get containers at all levels
649
650 AliMpDDLStore* ddlStore = AliMpDDLStore::Instance();
651
7b6684fe 652 Int_t detElemId;
653 Int_t manuId;
8741815f 654
7b6684fe 655 if ( external->ID1() <= 0 )
656 {
657 // we get a manu serial number
658 Int_t serial = external->ID0();
659 AliMpIntPair pair = ddlStore->GetDetElemIdManu(serial);
660 detElemId = pair.GetFirst();
661 manuId = pair.GetSecond();
662 if ( !detElemId )
663 {
664 AliError(Form("DE %d manuId %d from serial %d is not correct !",
665 detElemId,manuId,serial));
666 return -1;
667 }
668 }
669 else
670 {
671 // we get a (de,manu) pair
672 detElemId = external->ID0();
673 manuId = external->ID1();
674 }
675
8741815f 676 mpde = ddlStore->GetDetElement(detElemId);
7b6684fe 677
678 Int_t chamberId = AliMpDEManager::GetChamberId(detElemId);
679
8741815f 680 Int_t busPatchId = ddlStore->GetBusPatchId(detElemId,manuId);
681
682 Int_t pcbIndex = -1;
683
684 AliMp::StationType stationType = mpde->GetStationType();
685
686 if ( stationType == AliMp::kStation345 )
687 {
688 AliMpHVNamer namer;
689 pcbIndex = namer.ManuId2PCBIndex(detElemId,manuId);
690 }
691
692 channel = ChannelParam(detElemId,manuId,external);
693
694 manu = ManuParam(detElemId,manuId,kTRUE);
695
696 busPatch = BusPatchParam(busPatchId,kTRUE);
697
698 de = DetectionElementParam(detElemId,kTRUE);
699
700 chamber = ChamberParam(chamberId,kTRUE);
701
702 pcb = 0x0;
703
704 if ( pcbIndex >= 0 )
705 {
706 pcb = PCBParam(detElemId,pcbIndex,kTRUE);
0145e89a 707 }
8741815f 708
709 return manuId;
710}
0145e89a 711
8741815f 712//_____________________________________________________________________________
713Bool_t
714AliMUONTrackerData::HasBusPatch(Int_t busPatchId) const
715{
716 /// Whether we have data for a given buspatch
717 return ( BusPatchParam(busPatchId) != 0 );
718}
719
720//_____________________________________________________________________________
721Bool_t
722AliMUONTrackerData::HasChamber(Int_t chamberId) const
723{
724 /// Whether we have data for a given chamber
725 return ( ChamberParam(chamberId) != 0 );
726}
727
728//_____________________________________________________________________________
729Bool_t
730AliMUONTrackerData::HasDetectionElement(Int_t detElemId) const
731{
732 /// Whether we have data for a given detection element
733 return ( DetectionElementParam(detElemId) != 0 );
734}
735
736//_____________________________________________________________________________
737Bool_t
738AliMUONTrackerData::HasManu(Int_t detElemId, Int_t manuId) const
739{
740 /// Whether we have data for a given manu
741 return ( ManuParam(detElemId,manuId) != 0 );
742}
743
744//_____________________________________________________________________________
745Bool_t
746AliMUONTrackerData::HasPCB(Int_t detElemId, Int_t pcbIndex) const
747{
748 /// Whether we have data for a given pcb
749 return ( PCBParam(detElemId,pcbIndex) != 0 );
0145e89a 750}
751
752//_____________________________________________________________________________
753Double_t
754AliMUONTrackerData::Manu(Int_t detElemId, Int_t manuId, Int_t dim) const
755{
9016a84e 756 /// Return the value for a given manu and a given dimension
757
0145e89a 758 AliMUONVCalibParam* param = ManuParam(detElemId,manuId);
759 return param ? Value(*param,0,dim) : 0.0;
760}
761
762//_____________________________________________________________________________
763AliMUONVCalibParam*
8741815f 764AliMUONTrackerData::ManuParam(Int_t detElemId, Int_t manuId, Bool_t create) const
0145e89a 765{
9016a84e 766 /// Get the VCalibParam for a given manu
8741815f 767
768 AliMUONVCalibParam* manu = fManuValues ? static_cast<AliMUONVCalibParam*>
769 (fManuValues->FindObject(detElemId,manuId)) : 0x0 ;
770
771 if (!manu && create && fManuValues)
772 {
773 manu = CreateManuParam(detElemId,manuId);
774 fManuValues->Add(manu);
775 }
776
777 return manu;
778}
779
780//_____________________________________________________________________________
781AliMUONVCalibParam*
782AliMUONTrackerData::CreateManuParam(Int_t detElemId, Int_t manuId) const
783{
784 /// Create storage for one manu
785
786 AliCodeTimerAuto("");
787
788 AliMUONVCalibParam* manu = new AliMUONCalibParamND(Dimension(),1,detElemId,manuId,0.0);
789
790 // set the number of channels in that manu
791
792 AliMpDetElement* de = AliMpDDLStore::Instance()->GetDetElement(detElemId);
793
794 manu->SetValueAsDouble(0,IndexOfNumberDimension(),de->NofChannelsInManu(manuId));
795
796 return manu;
0145e89a 797}
798
799//_____________________________________________________________________________
7b6684fe 800Long64_t
4a3224ff 801AliMUONTrackerData::Merge(TCollection*)
7b6684fe 802{
803 /// Merge all tracker data objects from li into a single one.
804
805 AliError("Not implemented yet");
806
807 return 0;
808}
809
810//_____________________________________________________________________________
0145e89a 811Int_t
812AliMUONTrackerData::NumberOfDimensions() const
813{
814 /// Number of dimensions we're dealing with
815
816 return fDimension + fgkVirtualExtraDimension;
817}
818
819//_____________________________________________________________________________
820Double_t
821AliMUONTrackerData::PCB(Int_t detElemId, Int_t pcbIndex, Int_t dim) const
822{
823 /// Return the value of a given pcb for a given dimension
824
825 AliMUONVCalibParam* param = PCBParam(detElemId,pcbIndex);
826
827 return param ? Value(*param,pcbIndex,dim) : 0.0;
828}
829
830//_____________________________________________________________________________
831AliMUONVCalibParam*
8741815f 832AliMUONTrackerData::PCBParam(Int_t detElemId, Int_t pcbIndex, Bool_t create) const
0145e89a 833{
834 /// Return (if it exist) the VCalibParam for a given pcb
8741815f 835
836 AliMUONVCalibParam* pcb = fPCBValues ? static_cast<AliMUONVCalibParam*>
837 (fPCBValues->FindObject(detElemId,pcbIndex)) : 0x0 ;
838
839 if (create && fPCBValues && !pcb)
840 {
841 pcb = CreatePCBParam(detElemId,pcbIndex);
842 fPCBValues->Add(pcb);
843 }
844
845 return pcb;
846}
847
848//_____________________________________________________________________________
849AliMUONVCalibParam*
850AliMUONTrackerData::CreatePCBParam(Int_t detElemId, Int_t pcbIndex) const
851{
852 /// Create storage for one PCB (station345 only)
853
854 AliCodeTimerAuto("");
855
856 AliMpHVNamer namer;
857
858 AliMUONVCalibParam* pcb = new AliMUONCalibParamND(Dimension(),
859 namer.NumberOfPCBs(detElemId),
860 detElemId,
861 pcbIndex,
862 0.0);
863 return pcb;
0145e89a 864}
865
866//_____________________________________________________________________________
867void
868AliMUONTrackerData::Print(Option_t* wildcard, Option_t* opt) const
869{
870 /// Printout
871
872 TNamed::Print(opt);
873
49419555 874 if ( !fIsSingleEvent )
0145e89a 875 {
876 cout << " Nevents=" << fNevents << endl;
877 }
8741815f 878
879 for ( Int_t i = 0; i <= fExternalDimensionNames->GetLast(); ++i )
880 {
881 TObjString* name = static_cast<TObjString*>(fExternalDimensionNames->At(i));
882 cout << Form("External Dimension %2d Name %s %s",i,
883 ( name ? name->String().Data() : "null"),
884 ( IsHistogrammed(i) ? "(histogrammed)" : "")) << endl;
885 }
0145e89a 886
887 for ( Int_t i = 0; i <= fDimensionNames->GetLast(); ++i )
888 {
889 TObjString* name = static_cast<TObjString*>(fDimensionNames->At(i));
8741815f 890 cout << Form("Internal Dimension %2d Name %s",i,
0145e89a 891 ( name ? name->String().Data() : "null")) << endl;
892 }
8741815f 893
0145e89a 894 TString sopt(opt);
895 sopt.ToUpper();
896
897 if ( sopt.Contains("CHANNEL") && fChannelValues )
898 {
899 fChannelValues->Print(wildcard,opt);
900 }
901
902 if ( sopt.Contains("MANU") && fManuValues )
903 {
904 fManuValues->Print(wildcard,opt);
905 }
906
907 if ( sopt.Contains("BUSPATCH") && fBusPatchValues )
908 {
909 fBusPatchValues->Print(wildcard,opt);
910 }
911
912 if ( sopt.Contains("DE") && fDEValues )
913 {
914 fDEValues->Print(wildcard,opt);
915 }
916
917 if ( sopt.Contains("CHAMBER") && fChamberValues )
918 {
919 fChamberValues->Print(wildcard,opt);
920 }
921
922}
923
924//_____________________________________________________________________________
925void
926AliMUONTrackerData::SetDimensionName(Int_t index, const char* name)
927{
928 /// Set the name of a given dimension
929
930 if ( index >= fExternalDimension )
931 {
932 AliError(Form("Index out of bounds : %d / %d",index,fExternalDimension));
933 return;
934 }
935
936 Int_t ix = External2Internal(index);
937
49419555 938 if ( !IsSingleEvent() )
0145e89a 939 {
49419555 940 const char* prefix[] = { "mean", "sigma" };
941
942 for ( Int_t i = 0; i < 2; ++i )
943 {
944 Int_t j = ix+i;
0145e89a 945
49419555 946 SetInternalDimensionName(j,Form("%s of %s",prefix[i],name));
947 }
948 }
949 else
950 {
951 SetInternalDimensionName(index,name);
0145e89a 952 }
8741815f 953
954 SetExternalDimensionName(index,name);
955}
956
957//_____________________________________________________________________________
958void
10eb3d17 959AliMUONTrackerData::MakeHistogramForDimension(Int_t index, Bool_t value, Double_t xmin, Double_t xmax)
8741815f 960{
961 /// decide to make histos for a given dimension
962 if ( index >= ExternalDimension() )
963 {
964 AliError(Form("Index out of bounds : %d / %d",index,ExternalDimension()));
965 return;
966 }
967
968 fHistogramming[index] = value;
10eb3d17 969 fXmin = xmin;
970 fXmax = xmax;
0145e89a 971}
972
973//_____________________________________________________________________________
974void
975AliMUONTrackerData::SetInternalDimensionName(Int_t index, const char* value)
976{
977 /// Set the name of a given internal dimension
978 if ( index >= fDimension )
979 {
980 AliError(Form("Index out of bounds : %d / %d",index,fDimension));
981 return;
982 }
983
984 TObjString* ovalue = static_cast<TObjString*>(fDimensionNames->At(index));
985
986 if ( ovalue )
987 {
988 fDimensionNames->Remove(ovalue);
989 delete ovalue;
990 }
991 fDimensionNames->AddAt(new TObjString(value),index);
992}
993
994//_____________________________________________________________________________
8741815f 995void
996AliMUONTrackerData::SetExternalDimensionName(Int_t index, const char* value)
997{
998 /// Set the name of a given external dimension
999 if ( index >= fExternalDimension )
1000 {
1001 AliError(Form("Index out of bounds : %d / %d",index,fExternalDimension));
1002 return;
1003 }
1004
1005 TObjString* ovalue = static_cast<TObjString*>(fExternalDimensionNames->At(index));
1006
1007 if ( ovalue )
1008 {
1009 fExternalDimensionNames->Remove(ovalue);
1010 delete ovalue;
1011 }
1012 fExternalDimensionNames->AddAt(new TObjString(value),index);
1013}
1014
1015//_____________________________________________________________________________
0145e89a 1016Double_t
1017AliMUONTrackerData::Value(const AliMUONVCalibParam& param, Int_t i, Int_t dim) const
1018{
1019 /// Compute the value for a given dim, using the internal information we have
1020 /// Basically we're converting sum of weights and sum of squares of weights
1021 /// into means and sigmas, and number of events into occupancy number.
1022
1023 Double_t n = param.ValueAsDouble(i,IndexOfNumberDimension());
1024
1025 if ( dim == IndexOfNumberDimension() ) return n; // the number of channels in any given element does not depend on the number of events
1026
1027 Double_t occ = param.ValueAsDouble(i,IndexOfOccupancyDimension());
1028
1029 if ( dim >= fDimension )
1030 {
1031 return occ;
1032 }
1033
1034 if ( dim == IndexOfOccupancyDimension() ) return occ/n/NumberOfEvents();
1035
1036 Double_t value = param.ValueAsDouble(i,dim);
1037
1038 if ( value >= AliMUONVCalibParam::InvalidFloatValue() ) return AliMUONVCalibParam::InvalidFloatValue();
1039
49419555 1040 if ( TMath::Even(dim) || IsSingleEvent() )
0145e89a 1041 {
1042 return value/occ;
1043 }
1044 else
1045 {
bf0d3528 1046 Double_t nn = occ;
0145e89a 1047
bf0d3528 1048 if ( nn > 1.0 )
49419555 1049 {
bf0d3528 1050 Double_t mean = param.ValueAsDouble(i,dim-1)/nn;
b0565451 1051
bf0d3528 1052 return TMath::Sqrt(TMath::Abs((value-nn*mean*mean)/(nn-1.0)));
49419555 1053 }
1054 else
1055 {
1056 return 0.0;
1057 }
0145e89a 1058 }
1059
1060 AliError("Why am I here ?");
1061 return 0.0;
1062}
1063