3 /**************************************************************************
4 * This file is property of and copyright by the ALICE HLT Project *
5 * ALICE Experiment at CERN, All rights reserved. *
7 * Primary Authors: Matthias Richter <Matthias.Richter@ift.uib.no> *
8 * Kenneth Aamodt <Kenneth.aamodt@ift.uib.no> *
9 * for The ALICE HLT Project. *
11 * Permission to use, copy, modify and distribute this software and its *
12 * documentation strictly for non-commercial purposes is hereby granted *
13 * without fee, provided that the above copyright notice appears in all *
14 * copies and that both the copyright notice and this permission notice *
15 * appear in the supporting documentation. The authors make no claims *
16 * about the suitability of this software for any purpose. It is *
17 * provided "as is" without express or implied warranty. *
18 **************************************************************************/
20 /** @file AliHLTTPCPad.cxx
21 @author Matthias Richter, Kenneth Aamodt
23 @brief Container Class for TPC Pads.
31 #include "AliHLTTPCPad.h"
32 #include "AliHLTStdIncludes.h"
36 #include "AliHLTTPCTransform.h"
37 #include "AliHLTTPCClusters.h"
39 //------------------------------
41 /** margin for the base line be re-avaluated */
42 #define ALIHLTPAD_BASELINE_MARGIN (2*fAverage)
44 /** ROOT macro for the implementation of ROOT specific class methods */
45 ClassImp(AliHLTTPCPad)
47 AliHLTTPCPad::AliHLTTPCPad()
66 fUsedClusterCandidates(0),
68 fSignalPositionArray(NULL),
69 fSizeOfSignalPositionArray(0)
71 // see header file for class documentation
73 // refer to README to build package
75 // visit http://web.ift.uib.no/~kjeks/doc/alice-hlt
76 // HLTInfo("Entering default constructor");
77 fDataSignals= new AliHLTTPCSignal_t[AliHLTTPCTransform::GetNTimeBins()];
78 memset( fDataSignals, 0xFF, sizeof(Int_t)*(AliHLTTPCTransform::GetNTimeBins()));
80 fSignalPositionArray= new AliHLTTPCSignal_t[AliHLTTPCTransform::GetNTimeBins()];
81 memset( fSignalPositionArray, 0xFF, sizeof(Int_t)*(AliHLTTPCTransform::GetNTimeBins()));
82 fSizeOfSignalPositionArray=0;
85 AliHLTTPCPad::AliHLTTPCPad(Int_t offset, Int_t nofBins)
103 fClusterCandidates(),
104 fUsedClusterCandidates(0),
106 fSignalPositionArray(NULL),
107 fSizeOfSignalPositionArray(0)
109 // see header file for class documentation
112 AliHLTTPCPad::AliHLTTPCPad(const AliHLTTPCPad& srcPad)
114 fRowNo(srcPad.fRowNo),
115 fPadNo(srcPad.fPadNo),
130 fClusterCandidates(),
131 fUsedClusterCandidates(0),
133 fSignalPositionArray(NULL),
134 fSizeOfSignalPositionArray(0)
136 // see header file for class documentation
137 HLTFatal("copy constructor not implemented");
140 AliHLTTPCPad& AliHLTTPCPad::operator=(const AliHLTTPCPad&)
142 // see header file for class documentation
143 HLTFatal("assignment operator not implemented");
147 AliHLTTPCPad::~AliHLTTPCPad()
149 // see header file for class documentation
151 HLTWarning("event data acquisition not stopped");
155 AliHLTTPCSignal_t* pData=fDataSignals;
159 if (fSignalPositionArray) {
160 AliHLTTPCSignal_t* pData=fSignalPositionArray;
161 fSignalPositionArray=NULL;
167 Int_t AliHLTTPCPad::SetID(Int_t rowno, Int_t padno)
169 // see header file for class documentation
175 Int_t AliHLTTPCPad::StartEvent()
177 // see header file for class documentation
179 if (fpRawData==NULL) {
188 fpRawData=new AliHLTTPCSignal_t[fNofBins];
190 for (int i=0; i<fNofBins; i++) fpRawData[i]=-1;
192 HLTError("memory allocation failed");
197 HLTWarning("event data acquisition already started");
203 Int_t AliHLTTPCPad::CalculateBaseLine(Int_t reqMinCount)
205 // see header file for class documentation
207 AliHLTTPCSignal_t avBackup=fAverage;
208 //HLTDebug("reqMinCount=%d fCount=%d fTotal=%d fSum=%d fBLMax=%d fBLMin=%d", reqMinCount, fCount, fTotal, fSum, fBLMax, fBLMin);
209 if (fCount>=reqMinCount && fCount>=fTotal/2) {
210 fAverage=fCount>0?fSum/fCount:0;
212 //HLTDebug("average for current event %d (%d - %d)", fAverage, fBLMax, fBLMin);
214 if (fBLMax>ALIHLTPAD_BASELINE_MARGIN) {
216 //HLTDebug("maximum value %d exceeds margin for base line (%d) "
217 // "-> re-evaluate base line", fBLMax, ALIHLTPAD_BASELINE_MARGIN);
219 for (Int_t i=fFirstBLBin; i<fNofBins; i++)
220 if (fpRawData[i]>=0) AddBaseLineValue(i, fpRawData[i]);
221 if (fCount>0 && fCount>=reqMinCount && fCount>=fTotal/2) {
222 fAverage=fSum/fCount;
223 //HLTDebug("new average %d", fAverage);
225 // HLTDebug("baseline re-eveluation skipped because of to few "
226 // "contributing bins: total=%d, contributing=%d, req=%d"
227 // "\ndata might be already zero suppressed"
228 // , fTotal, fCount, reqMinCount);
233 HLTError("missing raw data for base line calculation");
238 // calculate average for all events
239 fAverage=((avBackup*fNofEvents)+fAverage)/(fNofEvents+1);
240 //HLTDebug("base line average for %d event(s): %d", fNofEvents+1, fAverage);
248 // HLTDebug("baseline calculation skipped because of to few contributing "
249 // "bins: total=%d, contributing=%d, required=%d \ndata might be "
250 // "already zero suppressed", fTotal, fCount, reqMinCount);
256 Int_t AliHLTTPCPad::StopEvent()
258 // see header file for class documentation
261 AliHLTTPCSignal_t* pData=fpRawData;
267 } else if (fNofBins>0) {
268 HLTError("event data acquisition not started");
274 Int_t AliHLTTPCPad::ResetHistory()
276 // see header file for class documentation
283 Int_t AliHLTTPCPad::SetThreshold(AliHLTTPCSignal_t thresh)
285 // see header file for class documentation
291 Int_t AliHLTTPCPad::AddBaseLineValue(Int_t bin, AliHLTTPCSignal_t value)
293 // see header file for class documentation
295 if (bin>=fFirstBLBin) {
296 if (fAverage<0 || value<ALIHLTPAD_BASELINE_MARGIN) {
297 // add to the current sum and count
301 // keep the maximum value for later quality control of the base
306 if (fBLMin<0 || fBLMin>value) {
307 // keep the minimum value for later quality control of the base
313 // HLTDebug("ignoring value %d (bin %d) for base line calculation "
314 // "(current average is %d)",
315 // value, bin, fAverage);
321 Int_t AliHLTTPCPad::SetRawData(Int_t bin, AliHLTTPCSignal_t value)
323 // see header file for class documentation
328 if (fpRawData[bin]<0) {
329 AddBaseLineValue(bin, value);
332 // ignore value for average calculation
333 HLTWarning("overriding content of bin %d (%d)", bin, fpRawData[bin]);
335 fpRawData[bin]=value;
337 HLTWarning("ignoring neg. raw data");
340 HLTWarning("bin %d out of range (%d)", bin, fNofBins);
343 } else if (fNofBins>0) {
344 HLTError("event cycle not started");
350 Int_t AliHLTTPCPad::Next(Int_t bZeroSuppression)
352 // see header file for class documentation
353 if (fpRawData==NULL) return 0;
354 Int_t iResult=fReadPos<fNofBins;
355 if (iResult>0 && (iResult=(++fReadPos<fNofBins))>0) {
356 if (bZeroSuppression) {
357 while ((iResult=(fReadPos<fNofBins))>0 &&
358 GetCorrectedData(fReadPos)<=0)
365 Int_t AliHLTTPCPad::Rewind(Int_t bZeroSuppression)
367 // see header file for class documentation
368 fReadPos=(bZeroSuppression>0?0:fFirstBLBin)-1;
369 return Next(bZeroSuppression);
372 AliHLTTPCSignal_t AliHLTTPCPad::GetRawData(Int_t bin) const
374 // see header file for class documentation
375 AliHLTTPCSignal_t data=0;
380 HLTWarning("requested bin %d out of range (%d)", bin, fNofBins);
382 } else if (fNofBins>0) {
383 HLTWarning("data only available within event cycle");
388 AliHLTTPCSignal_t AliHLTTPCPad::GetCorrectedData(Int_t bin) const
390 // see header file for class documentation
391 AliHLTTPCSignal_t data=GetRawData(bin)-GetBaseLine(bin);
392 AliHLTTPCSignal_t prev=0;
393 if (bin>1) prev=GetRawData(bin-1)-GetBaseLine(bin-1);
394 AliHLTTPCSignal_t succ=0;
395 if (bin+1<GetSize()) succ=GetRawData(bin+1)-GetBaseLine(bin+1);
403 // the signal is below the base-line and threshold
407 // the neighboring bins are both below base-line/threshold
408 // a real signal is always more than one bin wide because of the shaper
409 if (prev<=0 && succ<=0) data=0;
412 // the bin is inside the range of ignored bins
413 if (bin<fFirstBLBin) data=0;
414 //HLTDebug("fReadPos=%d data=%d threshold=%d raw data=%d base line=%d", fReadPos, data, fThreshold, GetRawData(bin), GetBaseLine(bin));
418 AliHLTTPCSignal_t AliHLTTPCPad::GetBaseLine(Int_t bin) const
420 // see header file for class documentation
421 AliHLTTPCSignal_t val=0;
423 // we take the minumum value as the base line if it doesn't differ from
424 // the average to much
427 const AliHLTTPCSignal_t kMaxDifference=15;
428 if ((fAverage-fBLMin)<=kMaxDifference) val=fBLMin;
429 else val>kMaxDifference?val-=kMaxDifference:0;
433 // here we should never get
435 HLTFatal("wrong base line value");
440 AliHLTTPCSignal_t AliHLTTPCPad::GetAverage() const
442 // see header file for class documentation
443 return fAverage>0?fAverage:0;
446 Float_t AliHLTTPCPad::GetOccupancy() const
448 // see header file for class documentation
450 if (fpRawData && fNofBins>0) {
451 for (Int_t i=fFirstBLBin; i<fNofBins; i++) {
452 if (GetCorrectedData(i)>0) occupancy+=1;
454 if (fNofBins-fFirstBLBin>0)
455 occupancy/=fNofBins-fFirstBLBin;
460 Float_t AliHLTTPCPad::GetAveragedOccupancy() const
462 // see header file for class documentation
464 // history is not yet implemented
465 return GetOccupancy();
467 void AliHLTTPCPad::PrintRawData(){
468 for(Int_t bin=0;bin<AliHLTTPCTransform::GetNTimeBins();bin++){
469 if(GetDataSignal(bin)>0)
470 cout<<fRowNo<<"\t"<<fPadNo<<"\t"<<bin<<"\t"<<GetDataSignal(bin)<<endl;;
472 cout<<"bins: "<<AliHLTTPCTransform::GetNTimeBins()<<endl;
475 void AliHLTTPCPad::SetDataToDefault(){
477 memset( fDataSignals, 0xFF, sizeof(Int_t)*(AliHLTTPCTransform::GetNTimeBins()));
478 memset( fSignalPositionArray, 0xFF, sizeof(Int_t)*(AliHLTTPCTransform::GetNTimeBins()));
479 fSizeOfSignalPositionArray=0;
482 void AliHLTTPCPad::SetDataSignal(Int_t bin,Int_t signal){
483 fDataSignals[bin]=signal;
484 fSignalPositionArray[fSizeOfSignalPositionArray]=bin;
485 fSizeOfSignalPositionArray++;
487 Int_t AliHLTTPCPad::GetDataSignal(Int_t bin){
488 return fDataSignals[bin];
490 void AliHLTTPCPad::FindClusterCandidates(){
494 vector<Int_t> tmpPos;
495 vector<Int_t> tmpSig;
498 for(Int_t pos=fSizeOfSignalPositionArray-2;pos>=0;pos--){
500 if(fSignalPositionArray[pos]==fSignalPositionArray[pos+1]+1){
501 seqcharge+=fDataSignals[fSignalPositionArray[pos+1]];
502 seqaverage += fSignalPositionArray[pos+1]*fDataSignals[fSignalPositionArray[pos+1]];
503 seqerror += fSignalPositionArray[pos+1]*fSignalPositionArray[pos+1]*fDataSignals[fSignalPositionArray[pos+1]];
505 tmpPos.push_back(fSignalPositionArray[pos+1]);
506 tmpSig.push_back(fDataSignals[fSignalPositionArray[pos+1]]);
508 if(fDataSignals[fSignalPositionArray[pos+1]]>fDataSignals[fSignalPositionArray[pos]]){
511 if(fDataSignals[fSignalPositionArray[pos+1]]<fDataSignals[fSignalPositionArray[pos]]&&isFalling){
513 seqmean = seqaverage/seqcharge;
515 //Calculate mean in pad direction:
516 Int_t padmean = seqcharge*fPadNo;
517 Int_t paderror = fPadNo*padmean;
518 AliHLTTPCClusters candidate;
519 candidate.fTotalCharge = seqcharge;
520 candidate.fPad = padmean;
521 candidate.fPad2 = paderror;
522 candidate.fTime = seqaverage;
523 candidate.fTime2 = seqerror;
524 candidate.fMean = seqmean;
525 candidate.fLastMergedPad = fPadNo;
526 fClusterCandidates.push_back(candidate);
527 fUsedClusterCandidates.push_back(0);
540 seqcharge+=fDataSignals[fSignalPositionArray[0]];
541 seqaverage += fSignalPositionArray[0]*fDataSignals[fSignalPositionArray[0]];
542 seqerror += fSignalPositionArray[0]*fSignalPositionArray[0]*fDataSignals[fSignalPositionArray[0]];
543 tmpPos.push_back(fSignalPositionArray[0]);
544 tmpSig.push_back(fDataSignals[fSignalPositionArray[0]]);
546 //Calculate mean of sequence:
548 seqmean = seqaverage/seqcharge;
550 //Calculate mean in pad direction:
551 Int_t padmean = seqcharge*fPadNo;
552 Int_t paderror = fPadNo*padmean;
553 AliHLTTPCClusters candidate;
554 candidate.fTotalCharge = seqcharge;
555 candidate.fPad = padmean;
556 candidate.fPad2 = paderror;
557 candidate.fTime = seqaverage;
558 candidate.fTime2 = seqerror;
559 candidate.fMean = seqmean;
560 candidate.fLastMergedPad = fPadNo;
561 fClusterCandidates.push_back(candidate);
562 fUsedClusterCandidates.push_back(0);
572 else if(seqcharge>0){
573 seqcharge+=fDataSignals[fSignalPositionArray[pos+1]];
574 seqaverage += fSignalPositionArray[pos+1]*fDataSignals[fSignalPositionArray[pos+1]];
575 seqerror += fSignalPositionArray[pos+1]*fSignalPositionArray[pos+1]*fDataSignals[fSignalPositionArray[pos+1]];
576 tmpPos.push_back(fSignalPositionArray[pos+1]);
577 tmpSig.push_back(fDataSignals[fSignalPositionArray[pos+1]]);
579 //Calculate mean of sequence:
581 seqmean = seqaverage/seqcharge;
583 //Calculate mean in pad direction:
584 Int_t padmean = seqcharge*fPadNo;
585 Int_t paderror = fPadNo*padmean;
586 AliHLTTPCClusters candidate;
587 candidate.fTotalCharge = seqcharge;
588 candidate.fPad = padmean;
589 candidate.fPad2 = paderror;
590 candidate.fTime = seqaverage;
591 candidate.fTime2 = seqerror;
592 candidate.fMean = seqmean;
593 candidate.fLastMergedPad = fPadNo;
594 fClusterCandidates.push_back(candidate);
595 fUsedClusterCandidates.push_back(0);