--- /dev/null
+/**************************************************************************
+ * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
+ * *
+ * Author: The ALICE Off-line Project. *
+ * Contributors are mentioned in the code where appropriate. *
+ * *
+ * Permission to use, copy, modify and distribute this software and its *
+ * documentation strictly for non-commercial purposes is hereby granted *
+ * without fee, provided that the above copyright notice appears in all *
+ * copies and that both the copyright notice and this permission notice *
+ * appear in the supporting documentation. The authors make no claims *
+ * about the suitability of this software for any purpose. It is *
+ * provided "as is" without express or implied warranty. *
+ **************************************************************************/
+
+/*
+$Log$
+Revision 1.1.4.2 2000/04/10 11:32:37 kowal2
+
+"ROOT"-based class with some extra functionality
+
+*/
+
+///////////////////////////////////////////////////////////////////////
+// Added additional functionality to original TArrayI //
+// multiple inheritance from TObject to be possible use automatic //
+// branch mechanism for tree
+// function Expand to be possible expand array without deleting //
+// array contents //
+// //
+// Origin: Marian Ivanov, Uni. of Bratislava, ivanov@fmph.uniba.sk //
+// //
+///////////////////////////////////////////////////////////////////////
+#include "AliArrayI.h"
+ClassImp(AliArrayI)
+void AliArrayI::Expand(Int_t n)
+{
+ //
+ // Set array size of TArrayI object to n integers and copy old array
+ // If n<0 leave array unchanged.
+ // user are responsible for appopiate size of array
+ //
+ if (n < 0) return;
+ fArray = (Int_t*) TStorage::ReAlloc(fArray, n * sizeof(Int_t),fN * sizeof(Int_t));
+ if (fArray!=0) fN= n;
+}
+
+void AliArrayI::Streamer(TBuffer &R__b)
+{
+ // Stream an object of class AliTPC.
+
+ if (R__b.IsReading()) {
+ Version_t R__v = R__b.ReadVersion(); if (R__v) { }
+ TObject::Streamer(R__b);
+ //read pad parameters
+ R__b >> fN;
+ if (fArray!=0) {
+ delete [] fArray;
+ fArray = 0;
+ }
+ if (fN>0){
+ fArray = new Int_t[fN];
+ R__b.ReadFastArray(fArray,fN);
+ }
+ } else {
+ R__b.WriteVersion(AliArrayI::IsA());
+ TObject::Streamer(R__b);
+ R__b << fN;
+ if (fN>0) R__b.WriteFastArray(fArray,fN);
+ }
+}
--- /dev/null
+#ifndef AliArrayI_H
+#define AliArrayI_H
+/* Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
+ * See cxx source for full Copyright notice */
+
+/* $Id$ */
+
+////////////////////////////////////////////////
+// Manager class generaol Alice segment
+// segment is for example one pad row in TPC //
+////////////////////////////////////////////////
+
+#include "TObject.h"
+#include "TArrayI.h"
+
+class AliArrayI: public TObject ,public TArrayI {
+public:
+ void Expand(Int_t n);
+ ClassDef(AliArrayI,1)
+};
+
+#endif //ALIARRAY_I
+
--- /dev/null
+/**************************************************************************
+ * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
+ * *
+ * Author: The ALICE Off-line Project. *
+ * Contributors are mentioned in the code where appropriate. *
+ * *
+ * Permission to use, copy, modify and distribute this software and its *
+ * documentation strictly for non-commercial purposes is hereby granted *
+ * without fee, provided that the above copyright notice appears in all *
+ * copies and that both the copyright notice and this permission notice *
+ * appear in the supporting documentation. The authors make no claims *
+ * about the suitability of this software for any purpose. It is *
+ * provided "as is" without express or implied warranty. *
+ **************************************************************************/
+
+/*
+$Log$
+Revision 1.1.4.2 2000/04/10 11:32:37 kowal2
+
+"ROOT"-based class with some extra functionality
+
+*/
+
+///////////////////////////////////////////////////////////////////////
+// Added additional functionality to original TArrayS //
+// multiple inheritance from TObject to be possible use automatic //
+// branch mechanism for tree
+// function Expand to be possible expand array without deleting //
+// array contents // //
+// //
+// Origin: Marian Ivanov, Uni. of Bratislava, ivanov@fmph.uniba.sk //
+// //
+///////////////////////////////////////////////////////////////////////
+#include "AliArrayS.h"
+ClassImp(AliArrayS)
+void AliArrayS::Expand(Int_t n)
+{
+ //
+ // Set array size of TArrayS object to n integers and copy old array
+ // If n<0 leave array unchanged.
+ // user are responsible for apropriate size of array
+ //
+ if (n < 0) return;
+ fArray = (Short_t*) TStorage::ReAlloc(fArray, n * sizeof(UShort_t),fN * sizeof(UShort_t));
+ if (fArray!=0) fN= n;
+ else fN =0;
+}
+
+
+
+void AliArrayS::Streamer(TBuffer &R__b)
+{
+ // Stream an object of class AliTPC.
+
+ if (R__b.IsReading()) {
+ Version_t R__v = R__b.ReadVersion(); if (R__v) { }
+ TObject::Streamer(R__b);
+ //read pad parameters
+ R__b >> fN;
+ if (fArray!=0){
+ delete [] fArray;
+ fArray =0;
+ }
+ if (fN>0){
+ fArray = new Short_t[fN];
+ R__b.ReadFastArray(fArray,fN);
+ }
+ } else {
+ R__b.WriteVersion(AliArrayS::IsA());
+ TObject::Streamer(R__b);
+ R__b << fN;
+ if (fN>0) R__b.WriteFastArray(fArray,fN);
+ }
+}
+
--- /dev/null
+#ifndef ALIARRAYS_H
+#define ALIARRAYS_H
+/* Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
+ * See cxx source for full Copyright notice */
+
+/* $Id$ */
+
+////////////////////////////////////////////////
+// Manager class generaol Alice segment digits
+// segment is for example one pad row in TPC //
+////////////////////////////////////////////////
+
+#include "TObject.h"
+#include "TArrayS.h"
+
+
+class AliArrayS: public TObject,public TArrayS {
+public:
+ void Expand(Int_t n);
+ ClassDef(AliArrayS,1)
+};
+#endif //ALIARRAYS_H
--- /dev/null
+/**************************************************************************
+ * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
+ * *
+ * Author: The ALICE Off-line Project. *
+ * Contributors are mentioned in the code where appropriate. *
+ * *
+ * Permission to use, copy, modify and distribute this software and its *
+ * documentation strictly for non-commercial purposes is hereby granted *
+ * without fee, provided that the above copyright notice appears in all *
+ * copies and that both the copyright notice and this permission notice *
+ * appear in the supporting documentation. The authors make no claims *
+ * about the suitability of this software for any purpose. It is *
+ * provided "as is" without express or implied warranty. *
+ **************************************************************************/
+
+/*
+$Log$
+Revision 1.1.4.2 2000/04/10 11:34:02 kowal2
+
+Clusters handling in a new data structure
+
+*/
+
+///////////////////////////////////////////////////////////////////////////////
+// //
+// Time Projection Chamber clusters objects //
+//
+// Origin: Marian Ivanov , GSI Darmstadt
+// //
+//Begin_Html
+/*
+<img src="gif/AliTPCCluster.gif">
+*/
+//End_Html
+// //
+// //
+///////////////////////////////////////////////////////////////////////////////
+
+#include "AliCluster.h"
+
+ClassImp(AliCluster)
+//_____________________________________________________________________________
+Int_t AliCluster::Compare(TObject * o)
+{
+ //
+ // compare two clusters according y coordinata
+ AliCluster *cl= (AliCluster *)o;
+ if (fY<cl->fY) return -1;
+ if (fY==cl->fY) return 0;
+ return 1;
+}
+
+Bool_t AliCluster::IsSortable() const
+{
+ //
+ //make AliCluster sortabale
+ return kTRUE;
+}
+
+ClassImp(AliDigitCluster)
+ClassImp(AliDifCluster)
--- /dev/null
+#ifndef ALICLUSTER_H
+#define ALICLUSTER_H
+/* Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
+ * See cxx source for full Copyright notice */
+
+/* $Id$ */
+
+#include "TObject.h"
+
+class AliCluster : public TObject {
+public:
+ Int_t fTracks[3];//labels of overlapped tracks
+ Float_t fX ; //Y of cluster
+ Float_t fY ; //Z of cluster
+ Float_t fQ ; //Q of cluster (in ADC counts)
+ Float_t fSigmaX2; //Sigma Y square of cluster
+ Float_t fSigmaY2; //Sigma Z square of cluster
+ Float_t fSigmaXY; // XY moment
+ Float_t fArea; //area of cluster
+ Float_t fMax; //amplitude at maximum
+public:
+ AliCluster() {
+ fTracks[0]=fTracks[1]=fTracks[2]=0;
+ fX=fY=fQ=fSigmaX2=fSigmaY2=0.;
+ }
+ virtual ~AliCluster() {;}
+ Bool_t IsSortable() const;
+ Int_t Compare(TObject *o) ;
+ ClassDef(AliCluster,1) // Tclusters
+};
+
+class AliDigitCluster : public AliCluster {
+public:
+ Int_t fNx; //number of accepted x bins
+ Int_t fNy; //number of accepted y bins
+ Float_t fMaxX; //maximum x bin
+ Float_t fMaxY; //maximum y bin
+public:
+ ClassDef(AliDigitCluster,1) // Tclusters
+};
+
+class AliDifCluster : public AliDigitCluster {
+public:
+ Float_t fDx; //delta x
+ Float_t fDy; //delta y
+ Float_t fAngleX;//x angle
+ Float_t fAngleY;//y angle
+ Float_t fOrigQ; //original charge
+ Int_t fGenerTrack; //track number of nearest track
+ ClassDef(AliDifCluster,1) // Tclusters
+};
+
+#endif //ALICLUSTER_H
--- /dev/null
+/**************************************************************************
+ * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
+ * *
+ * Author: The ALICE Off-line Project. *
+ * Contributors are mentioned in the code where appropriate. *
+ * *
+ * Permission to use, copy, modify and distribute this software and its *
+ * documentation strictly for non-commercial purposes is hereby granted *
+ * without fee, provided that the above copyright notice appears in all *
+ * copies and that both the copyright notice and this permission notice *
+ * appear in the supporting documentation. The authors make no claims *
+ * about the suitability of this software for any purpose. It is *
+ * provided "as is" without express or implied warranty. *
+ **************************************************************************/
+
+/*
+$Log$
+Revision 1.1.4.2 2000/04/10 11:34:56 kowal2
+
+Experimental cluster finder
+
+*/
+
+//-----------------------------------------------------------------------------
+//
+// Implementation of class ALICLUSTERFINDER
+//
+//Class for cluster finding in two dimension.
+//In the present there are implemented two algorithm
+//primitive recursion algorithm. (FindPeaks)
+//Algorithm is not working in case of overlaping clusters
+//Maximum - minimum in direction algoritm (Find clusters)
+//In this algoritm we suppose that each cluster has local
+//maximum. From this local maximum I mus see each point
+//of cluster.
+//From maximum i can accept every point in radial
+//direction which is before border in direction
+//Border in direction occur if we have next in
+//direction nder threshold or response begin
+//to increase in given radial direction
+//-----------------------------------------------------------------------------
+#include "TMinuit.h"
+#include "AliArrayI.h"
+#include "TClonesArray.h"
+#include "AliTPC.h"
+#include "TRandom.h"
+#include "AliH2F.h"
+#include "TMarker.h"
+#include "AliCluster.h"
+#include "AliClusterFinder.h"
+
+#include "iostream.h" //I.Belikov
+
+//direction constants possible direction in 8 different sectors
+//
+
+
+const Int_t kClStackSize =1000;
+
+
+
+
+static AliClusterFinder * gClusterFinder; //for fitting routine
+
+void gauss(Int_t &npar, Double_t *gin, Double_t &f, Double_t *par, Int_t iflag)
+{
+ AliArrayI * points = gClusterFinder->GetStack();
+ const Int_t nbins = gClusterFinder->GetStackIndex();
+ Int_t i;
+ //calculate chisquare
+ Double_t chisq = 0;
+ Double_t delta;
+ for (i=0;i<nbins; i++) {
+ Float_t x = points->At(i*3);
+ Float_t y = points->At(i*3+1);
+ Float_t z = points->At(i*3+2);
+ Float_t deltax2 = (x-par[1]);
+ deltax2*=deltax2;
+ deltax2*=par[3];
+ Float_t deltay2 = (y-par[2]);
+ deltay2*=deltay2;
+ deltay2*=par[4];
+
+ delta = z-par[0]*TMath::Exp(-deltax2-deltay2);
+ chisq += delta*delta;
+ }
+ f = chisq;
+}
+
+
+ClassImp(AliClusterFinder)
+
+AliClusterFinder::AliClusterFinder()
+{
+ fDigits =0;
+ fDimX = 0;
+ fDimY = 0;
+ fOver = 0;
+ fNoiseTh = 3;
+ fMulSigma2 = 16; //4 sigma
+ fDirSigmaFac = 1.4;
+ fDirAmpFac =1.3;
+ fNType=8;
+ fThreshold = 2;
+ fStack = new AliArrayI;
+ fStack->Set(kClStackSize);
+ fClustersArray =0;
+
+ fDetectorParam = 0;
+ ResetStatus();
+ fBFit = kFALSE;
+ fMinuit= new TMinuit(5);
+ fMinuit->SetFCN(gauss);
+ gClusterFinder = this;
+
+}
+
+
+AliClusterFinder::~AliClusterFinder()
+{
+ if (fDigits != 0) delete fDigits;
+}
+
+void AliClusterFinder::GetHisto(TH2F * his2)
+{
+
+ Int_t idim =his2->GetNbinsX();
+ Int_t jdim =his2->GetNbinsY();
+ fX1 = his2->GetXaxis()->GetXmin();
+ fX2 = his2->GetXaxis()->GetXmax();
+ fY1 = his2->GetYaxis()->GetXmin();
+ fY2 = his2->GetYaxis()->GetXmax();
+
+ if ( (idim>0) && (jdim>0))
+ {
+ rOK = kTRUE;
+ fDimX = idim;
+ fDimY = jdim;
+ //Int_t size =idim*jdim;
+ if (fDigits !=0) delete fDigits;
+ fDigits = (AliCell*) new AliCell[idim*jdim];
+ } else
+ rOK=kFALSE;
+ for (Int_t i = 0; i<idim;i++)
+ for (Int_t j = 0; j<jdim;j++)
+ {
+ Int_t index = his2->GetBin(i+1,j+1);
+ AliCell * cell = GetCell(i,j);
+ if (cell!=0) cell->SetSignal(his2->GetBinContent(index));
+ }
+
+}
+
+
+
+
+void AliClusterFinder::FindMaxima()
+{
+ for (Int_t i=0; i<fDimX; i++)
+ for (Int_t j=0;j<fDimY; j++)
+ if (IsMaximum(i,j)) cout<<i<<" "<<j<<"\n";
+}
+
+
+void AliClusterFinder::Transform(AliDigitCluster * c)
+{
+ //transform coordinata from bin coordinata to "normal coordinata"
+ //for example if we initialize finder with histogram
+ //it transform values from bin coordinata to the histogram coordinata
+ c->fX=ItoX(c->fX);
+ c->fY=JtoY(c->fY);
+ c->fMaxX=ItoX(c->fMaxX);
+ c->fMaxY=JtoY(c->fMaxY);
+
+ c->fSigmaX2=c->fSigmaX2*(fX2-fX1)*(fX2-fX1)/(fDimX*fDimX);
+ c->fSigmaY2=c->fSigmaY2*(fY2-fY1)*(fY2-fY1)/(fDimY*fDimY);
+ c->fArea =c->fArea*(fX2-fX1)*(fY2-fY1)/(fDimX*fDimY);
+}
+void AliClusterFinder::AddToStack(Int_t i, Int_t j, Int_t signal)
+{
+ //
+ //add digit to stack
+ //
+ if ( ((fStackIndex+2)>=kClStackSize) || (fStackIndex<0) ) return;
+ fStack->AddAt(i,fStackIndex);
+ fStack->AddAt(j,fStackIndex+1);
+ fStack->AddAt(signal,fStackIndex+2);
+ fStackIndex+=3;
+}
+
+void AliClusterFinder::GetClusterStatistic(AliDigitCluster & cluster)
+{
+ //
+ //calculate statistic of cluster
+ //
+ Double_t sumxw,sumyw,sumx2w,sumy2w,sumxyw,sumw;
+ Int_t minx,maxx,miny,maxy,maxQ;
+ sumxw=sumyw=sumx2w=sumy2w=sumxyw=sumw=0;
+ minx=fDimX;
+ maxx=-fDimX;
+ miny=fDimY;
+ maxy=-fDimY;
+ Int_t x0=fStack->At(0);
+ Int_t y0=fStack->At(1);
+ maxQ=fStack->At(2);
+ for (Int_t i = 0; i<fStackIndex;i+=3){
+ Int_t x = fStack->At(i);
+ Int_t y = fStack->At(i+1);
+ Int_t dx=x-x0;
+ Int_t dy=y-y0;
+ Int_t w = fStack->At(i+2);
+ if (x<minx) minx=x;
+ if (y<miny) miny=y;
+ if (x>maxx) maxx=x;
+ if (y>maxy) maxy=y;
+ sumxw+=dx*w;
+ sumyw+=dy*w;
+ sumx2w+=dx*dx*w;
+ sumy2w+=dy*dy*w;
+ sumxyw+=dx*dy*w;
+ sumw+=w;
+ }
+ cluster.fQ = sumw;
+ if (sumw>0){
+ cluster.fX = sumxw/sumw;
+ cluster.fY = sumyw/sumw;
+ cluster.fQ = sumw;
+ cluster.fSigmaX2 = sumx2w/sumw-cluster.fX*cluster.fX;
+ cluster.fSigmaY2 = sumy2w/sumw-cluster.fY*cluster.fY;
+ cluster.fSigmaXY = sumxyw/sumw-cluster.fX*cluster.fY;
+ cluster.fMaxX = x0;
+ cluster.fMaxY = y0;
+ cluster.fMax = maxQ;
+ cluster.fArea = fStackIndex/3;
+ cluster.fNx = maxx-minx+1;
+ cluster.fNy = maxy-miny+1;
+ cluster.fX +=x0;
+ cluster.fY +=y0;
+ }
+}
+void AliClusterFinder::GetClusterFit(AliDigitCluster & cluster)
+{
+ //
+ //calculate statistic of cluster
+ //
+ Double_t arglist[10];
+ Int_t ierflg = 0;
+
+ arglist[0] = 1;
+ fMinuit->mnexcm("SET ERR", arglist ,1,ierflg);
+
+ //fistly find starting parameters
+ Int_t minx,maxx,miny,maxy,maxQ,maxQx,maxQy;
+ Int_t over =0;
+ Float_t sumxw,sumyw,sumw;
+ sumxw=sumyw=sumw=0;
+ minx=fDimX;
+ maxx=-fDimX;
+ miny=fDimY;
+ maxy=-fDimY;
+ maxQx=fStack->At(0);
+ maxQy=fStack->At(1);
+ maxQ=fStack->At(2);
+
+ for (Int_t i = 0; i<fStackIndex;i+=3){
+ Int_t x = fStack->At(i);
+ Int_t y = fStack->At(i+1);
+ Int_t w = fStack->At(i+2);
+ if (w>fThreshold) {
+ over++;
+ sumw+=w;
+ sumxw+=x*w;
+ sumyw+=y*w;
+ if (x<minx) minx=x;
+ if (y<miny) miny=y;
+ if (x>maxx) maxx=x;
+ if (y>maxy) maxy=y;
+ if (w>maxQ) {
+ maxQ=w;
+ maxQx=x;
+ maxQy=y;
+ }
+ }
+ }
+ Int_t nx = maxx-minx+1;
+ Int_t ny = maxy-miny+1;
+
+ SetSigma2(maxQx,maxQy,fCurrentSigmaX2,fCurrentSigmaY2);
+ Double_t vstart[5]={maxQ,sumxw/sumw,sumyw/sumw,1/(2*fCurrentSigmaX2),1/(2*fCurrentSigmaY2)};
+ Double_t step[5]={1.,0.01,0.01,0.01,0.01};
+ fMinuit->mnparm(0, "amp", vstart[0], step[0], 0,0,ierflg);
+ fMinuit->mnparm(1, "x0", vstart[1], step[1], 0,0,ierflg);
+ fMinuit->mnparm(2, "y0", vstart[2], step[2], 0,0,ierflg);
+ fMinuit->mnparm(3, "sx2", vstart[3], step[3], 0,0,ierflg);
+ fMinuit->mnparm(4, "sy2", vstart[4], step[4], 0,0,ierflg);
+ arglist[0] = 500;
+ arglist[1] = 1.;
+
+ fMinuit->mnfree(0); //set unfixed all parameters
+ //if we have area less then
+ if (over<=21) { //if we dont't have more then 7 points
+ fMinuit->FixParameter(3);
+ fMinuit->FixParameter(4);
+ }
+ else {
+ if (nx<3) fMinuit->FixParameter(3); //fix sigma x if no data in x direction
+ if (ny<3) fMinuit->FixParameter(4); //fix sigma y if no data in y direction
+ }
+ fMinuit->mnexcm("MIGRAD", arglist ,2,ierflg);
+
+ if (sumw>0){
+ Double_t x[5];
+ Double_t error[5];
+ fMinuit->GetParameter(0,x[0],error[0]);
+ fMinuit->GetParameter(1,x[1],error[1]);
+ fMinuit->GetParameter(2,x[2],error[2]);
+ fMinuit->GetParameter(3,x[3],error[3]);
+ fMinuit->GetParameter(4,x[4],error[4]);
+
+ cluster.fX = x[1];
+ cluster.fY = x[2];
+ cluster.fMaxX = maxQx;
+ cluster.fMaxY = maxQy;
+
+ cluster.fQ = sumw;
+ cluster.fSigmaX2 = 1/TMath::Sqrt(2*x[3]);
+ cluster.fSigmaY2 = 1/TMath::Sqrt(2*x[4]);
+ cluster.fSigmaXY = 0;
+ cluster.fMax = x[0];
+ cluster.fArea = over;
+ cluster.fNx = nx;
+ cluster.fNy = ny;
+ }
+}
+
+Bool_t AliClusterFinder::CheckIfDirBorder(Float_t x, Float_t y,
+ Int_t i,Int_t j)
+{
+ //
+ //function which control if given cell with index i, j is the
+ //minimum in direction
+ // x and y are estimate of local maximum
+ //direction is given by the
+ Float_t virtualcell;
+ AliCell * cellor= GetCell(i,j);
+
+ //control derivation in direction
+ //if function grows up in direction then there is border
+ Float_t dx = i-x;
+ Float_t dy = j-y;
+ Float_t dd = TMath::Sqrt(dx*dx+dy*dy);
+ Float_t ddx = TMath::Abs(dx);
+ ddx = (ddx>0.5) ? ddx-0.5: 0;
+ ddx*=ddx;
+ Float_t ddy = TMath::Abs(dy);
+ ddy = (ddy>0.5) ? ddy-0.5: 0;
+ ddy*=ddy;
+ Float_t d2 = ddx/(2*fDirSigmaFac*fCurrentSigmaX2)+ddy/(2*fDirSigmaFac*fCurrentSigmaY2); //safety factor
+ //I accept sigmax and sigma y bigge by factor sqrt(fDirsigmaFac)
+ Float_t amp = TMath::Exp(-d2)*fCurrentMaxAmp*fDirAmpFac; //safety factor fDirFac>1
+
+ if (cellor->GetSignal()>amp) return kTRUE;
+ if (dd==0) return kFALSE;
+
+ dx/=dd;
+ dy/=dd;
+ virtualcell = GetVirtualSignal(i+dx,j+dy);
+ if (virtualcell <=fThreshold) return kFALSE;
+ if (virtualcell>cellor->GetSignal())
+ if (virtualcell>(cellor->GetSignal()+fNoiseTh))
+ {cellor->SetDirBorder(fIndex+1); return kTRUE;}
+ else
+ {
+ virtualcell = GetVirtualSignal(i+2*dx,j+2*dy);
+ if (virtualcell>cellor->GetSignal())
+ { cellor->SetDirBorder(fIndex+1); return kTRUE;}
+ };
+ return kFALSE;
+}
+
+
+
+Bool_t AliClusterFinder::IsMaximum(Int_t i, Int_t j)
+{
+ //there is maximum if given digits is 1 sigma over all adjacent
+ //in 8 neighborow
+ //or ther exist virual maximum
+ //is maximum on 24 points neighboring
+ // Bool_t res = kFALSE;
+ Int_t over =0;
+ Int_t overth=0;
+ Int_t oversigma =0;
+ AliCell * cell = GetCell(i,j);
+ if (cell == 0) return kFALSE;
+ for ( Int_t di=-1;di<=1;di++)
+ for ( Int_t dj=-1;dj<=1;dj++){
+ if ( (di!=0) || (dj!=0))
+ {
+ AliCell * cell2=GetCell(i+di,j+dj);
+ if (cell2 == 0) {
+ over+=1;
+ oversigma+=1;
+ }
+ else
+ {
+ if (cell2->GetSignal()>cell->GetSignal()) return kFALSE;
+ if (cell2->GetSignal()>fThreshold) overth++;
+ if (cell2->GetSignal()==cell->GetSignal()) {
+ if (di<0) return kFALSE;
+ if ( (di+dj)<0) return kFALSE;
+ }
+ // if (cell->GetSignal()>=cell2->GetSignal()){
+ over+=1;
+ if (cell->GetSignal()>fNoiseTh+cell2->GetSignal())
+ oversigma+=1;
+ //}
+ }
+ }
+ }
+ //if I have only one neighborough over threshold
+ if (overth<2) return kFALSE;
+ if (over<8) return kFALSE;
+ if (oversigma==8) {
+ fCurrentMaxX = i;
+ fCurrentMaxY = j;
+ fCurrentMaxAmp =cell->GetSignal();
+ SetMaximum(fIndex+1,i,j);
+ return kTRUE;
+ }
+ //check if there exist virtual maximum
+ for (Float_t dii=0;(dii<1);dii+=0.5)
+ for (Float_t dj=0;(dj<1);dj+=0.5)
+ if (IsVirtualMaximum(Float_t(i)+dii,Float_t(j)+dj)){
+ fCurrentMaxX = i+dii;
+ fCurrentMaxY = j+dj;
+ fCurrentMaxAmp =cell->GetSignal();
+ SetMaximum(fIndex+1,i,j);
+ return kTRUE;
+ }
+ return kFALSE;
+}
+
+Bool_t AliClusterFinder::IsVirtualMaximum(Float_t x, Float_t y)
+{
+ //there is maximum if given digits is 1 sigma over all adjacent
+ //in 8 neighborow or
+ //is maximum on 24 points neighboring
+ Bool_t res = kFALSE;
+ Int_t over =0;
+ Int_t overth=0;
+ Int_t oversigma =0;
+ Float_t virtualcell = GetVirtualSignal(x,y);
+ if (virtualcell < 0) return kFALSE;
+ for ( Int_t di=-1;di<=1;di++)
+ for ( Int_t dj=-1;dj<=1;dj++)
+ if ( (di!=0) || (dj!=0))
+ {
+ Float_t virtualcell2=GetVirtualSignal(x+di,y+dj);
+ if (virtualcell2 < 0) {
+ over+=1;
+ oversigma+=1;
+ }
+ else
+ {
+ if (virtualcell2>fThreshold) overth++;
+ if (virtualcell>=virtualcell2){
+ over+=1;
+ if (virtualcell>fNoiseTh+virtualcell2)
+ oversigma+=1;
+ }
+ }
+ }
+ if (overth<2) return kFALSE;
+ //if there exist only one or less neighboring above threshold
+ if (oversigma==8) res = kTRUE;
+ else if ((over==8)&&(GetNType()==8)) res=kTRUE;
+ else if (over ==8 )
+ for ( Int_t dia=-2;dia<=2;dia++)
+ for ( Int_t dj=-2;dj<=2;dj++)
+ if ( (dia==2)||(dia==-2) || (dj==2)|| (dj==-2) )
+ {
+ Float_t virtualcell2=GetVirtualSignal(x+dia,y+dj);
+ if (virtualcell2 < 0) {
+ over+=1;
+ oversigma+=1;
+ }
+ else
+ {
+ if (virtualcell>=virtualcell2) over+=1;
+ }
+ }
+ if (over == 24) res=kTRUE;
+ return res;
+
+}
+
+
+void AliClusterFinder::ResetSignal()
+{
+ //reset dignals to 0
+ Int_t size = fDimX*fDimY;
+ AliCell *dig=fDigits;
+ if (rOK==kTRUE) for (Int_t i=0 ; i<size;i++) dig[i] = 0;
+}
+
+
+
+void AliClusterFinder::ResetStatus()
+{
+ //reset status of signals to not used
+ Int_t size = fDimX*fDimY;
+ AliCell *dig=fDigits;
+ if (rOK==kTRUE) for (Int_t i=0 ; i<size;i++)
+ dig[i].SetStatus(0);
+}
+
+
+AliCell * AliClusterFinder::GetCell(Int_t i, Int_t j)
+{
+ //return reference to the cell with index i,j
+ if (rOK == kTRUE)
+ if ( (i>=0) && (i<fDimX) && (j>=0) && (j<fDimY) )
+ return &fDigits[i+j*fDimX];
+ return 0;
+}
+
+Float_t AliClusterFinder::GetVirtualSignal(Float_t ri, Float_t rj)
+{
+ //it generate virtual cell as mean value from different cels
+ //after using it must be destructed !!!
+ Int_t i=(Int_t)ri;
+ Int_t j=(Int_t)rj;
+ Int_t ddi = (ri>i)? 1:0;
+ Int_t ddj = (rj>j)? 1:0;
+ Float_t sum = 0;
+ Float_t sumw= 0;
+ for (Int_t di=0;di<=ddi;di++)
+ for (Int_t dj=0;dj<=ddj;dj++)
+ {
+ Float_t w = (ri-i-di)*(ri-i-di)+(rj-j-dj)*(rj-j-dj);
+ if (w>0) w=1/TMath::Sqrt(w);
+ else w=9999999;
+ AliCell * cel2 =GetCell(i+di,j+dj);
+ if (cel2!=0) {
+ sumw+=w;
+ sum+= cel2->GetSignal()*w;
+ }
+ }
+ if (sumw>0) return (sum/sumw);
+ else
+ return -1;
+}
+
+
+
+void AliClusterFinder::Streamer(TBuffer & R__b)
+{
+ if (R__b.IsReading()) {
+ // Version_t R__v = R__b.ReadVersion();
+ } else {
+ R__b.WriteVersion(AliClusterFinder::IsA());
+ }
+}
+
+
+Bool_t AliClusterFinder::SetSigma2(Int_t i, Int_t j, Float_t & sigmax2, Float_t &sigmay2)
+{
+ //
+ //set sigmax2 and sigma y2 accordig i and j position of cell
+ //
+ if (fDetectorParam==0) {
+ sigmax2=1;
+ sigmay2=1;
+ return kFALSE;
+ }
+ Float_t x[3] = {ItoX(i),JtoY(j),0};
+ Float_t sigma[2];
+ fDetectorParam->GetClusterSize(x,fDetectorIndex,0,0,sigma);
+ sigmax2=sigma[0]*(fX2-fX1)*(fX2-fX1)/(fDimX*fDimX);
+ sigmay2=sigma[1]*(fY2-fY1)*(fY2-fY1)/(fDimY*fDimY);
+ return kTRUE;
+}
+
+void AliClusterFinder::SetBlockIndex(Int_t * index)
+{
+ //
+ //calculate which indexes we must check for border
+ //
+ if (TMath::Abs(index[0])<2) index[2] = 0;
+ else {
+ index[2] = TMath::Abs(index[0])-1;
+ if (index[0]<0) index[2]*=-1; //first x block
+ }
+ if (TMath::Abs(index[1])<2) index[3] = 0;
+ else {
+ index[3] = TMath::Abs(index[1])-1;
+ if (index[1]<0) index[3]*=-1; //first y block
+ }
+ if (TMath::Abs(index[0])<TMath::Abs(index[1])){
+ index[4]=index[0];
+ index[5]=index[3];
+ }
+ else
+ if (index[0]==index[1]) {
+ index[4]=0;
+ index[5]=0;
+ }
+ else{
+ index[4]=index[2];
+ index[5]=index[1];
+ }
+ return;
+}
+
+//***********************************************************************
+//***********************************************************************
+
+TClonesArray * AliClusterFinder::FindPeaks1(TClonesArray *arr)
+{
+ //find peaks and write it in form of AliTPCcluster to array
+ TClonesArray * clusters;
+ if (arr==0) clusters=new TClonesArray("AliDigitCluster",300);
+ else clusters = arr;
+ fClustersArray = clusters;
+ AliDigitCluster c;
+ Int_t index = clusters->GetEntriesFast();
+ ResetStatus();
+
+ for (Int_t i=0; i<fDimX; i++)
+ for (Int_t j=0;j<fDimY; j++)
+ {
+ fStackIndex=0;
+ fBDistType = kFALSE;
+ AliCell * cell = GetCell(i,j);
+ if (!(cell->IsChecked())) Adjacent(i,j);
+ //if there exists more then 2 digits cluster
+ if (fStackIndex >2 ){
+ if (fBFit==kFALSE) GetClusterStatistic(c);
+ else GetClusterFit(c);
+ //write some important chracteristic area of cluster
+ //
+ Transform(&c);
+ //write cluster information to array
+ TClonesArray &lclusters = *clusters;
+ new(lclusters[index++]) AliDigitCluster(c);
+ // cout<<"fx="<<c.fX<<" fy"<<c.fY<<"\n";
+ }
+ }
+ return clusters;
+}
+
+
+TClonesArray * AliClusterFinder::FindPeaks2(TClonesArray *arr)
+{
+ //find peaks and write it in form of AliTPCcluster to array
+ TClonesArray * clusters;
+ if (arr==0) clusters=new TClonesArray("AliDigitCluster",300);
+ else clusters = arr;
+ fClustersArray = clusters;
+ AliDigitCluster c;
+ fIndex = clusters->GetEntriesFast();
+
+ ResetStatus();
+
+ for (Int_t i=0; i<fDimX; i++)
+ for (Int_t j=0;j<fDimY; j++)
+ {
+ fStackIndex=0;
+ if (IsMaximum(i,j) == kTRUE){
+ SetSigma2(i,j,fCurrentSigmaX2,fCurrentSigmaY2);
+ fBDistType = kTRUE;
+ Adjacent(i,j);
+ //if there exists more then 2 digits cluster
+ if (fStackIndex >2 ){
+ if (fBFit==kFALSE) GetClusterStatistic(c);
+ else GetClusterFit(c);
+ //write some important chracteristic area of cluster
+ //
+ Transform(&c);
+ //write cluster information to array
+ TClonesArray &lclusters = *clusters;
+ new(lclusters[fIndex++]) AliDigitCluster(c);
+ // cout<<"fx="<<c.fX<<" fy"<<c.fY<<"\n";
+ }
+ }
+ }
+ return clusters;
+}
+
+
+TClonesArray * AliClusterFinder::FindPeaks3(TClonesArray *arr)
+{
+ //find peaks and write it in form of AliTPCcluster to array
+ TClonesArray * clusters;
+ if (arr==0) clusters=new TClonesArray("AliDigitCluster",300);
+ else clusters = arr;
+ fClustersArray = clusters;
+ AliDigitCluster c;
+ fIndex = clusters->GetEntriesFast();
+
+ ResetStatus();
+
+ Int_t dmax=5;
+ Int_t naccepted =1;
+ for (Int_t i=0; i<fDimX; i++)
+ for (Int_t j=0;j<fDimY; j++)
+ {
+ fStackIndex=0;
+ if (IsMaximum(i,j) == kTRUE){
+ SetSigma2(i,j,fCurrentSigmaX2,fCurrentSigmaY2);
+ AddToStack(i,j,GetCell(i,j)->GetSignal());
+
+ //loop over different distance
+ naccepted =1;
+ for ( Int_t dd =1;((dd<=dmax) && (naccepted>0));dd++){
+ naccepted=0;
+ for (Int_t di = -dd;di<=dd;di++){
+ Int_t ddj = dd-TMath::Abs(di);
+ Int_t sigstart = (ddj>0) ? -1 : 0;
+ for (Int_t sig = sigstart;sig<=1;sig+=2){
+ Int_t dj= sig*ddj;
+ AliCell *cell= GetCell(i+di,j+dj);
+ if (cell==0) continue;
+ Int_t index[6];
+ index[0]=di;
+ index[1]=dj;
+ if (dd>2) {
+ SetBlockIndex(index); //adjust index to control
+ if ( IsBorder(fIndex+1,i+index[2],j+index[3]) ||
+ IsBorder(fIndex+1,i+index[4],j+index[5])) {
+ cell->SetBorder(fIndex+1);
+ continue;
+ }
+ }
+ if ( cell->GetSignal()<=fThreshold ){
+ //if under threshold
+ cell->SetThBorder(fIndex+1);
+ if (fBFit==kTRUE) AddToStack(i+di,j+dj,cell->GetSignal());
+ continue;
+ }
+ naccepted++;
+ if (CheckIfDirBorder(fCurrentMaxX,fCurrentMaxY,i+di,j+dj) == kTRUE) {
+ if (fBFit==kFALSE) AddToStack(i+di,j+dj,cell->GetSignal()/2);
+ continue;
+ }
+ AddToStack(i+di,j+dj,cell->GetSignal());
+
+ } //loop over sig dj
+ } //loop over di
+
+ }//loop over dd
+ } //if there is maximum
+ //if there exists more then 2 digits cluster
+ if (fStackIndex >2 ){
+ if (fBFit==kFALSE) GetClusterStatistic(c);
+ else GetClusterFit(c);
+ //write some important chracteristic area of cluster
+ //
+ Transform(&c);
+ //write cluster information to array
+ TClonesArray &lclusters = *clusters;
+ new(lclusters[fIndex++]) AliDigitCluster(c);
+ // cout<<"fx="<<c.fX<<" fy"<<c.fY<<"\n";
+ }
+ } //lopp over all digits
+
+ return clusters;
+}
+
+
+
+
+
+
+void AliClusterFinder::Adjacent(Int_t i,Int_t j)
+{
+ //
+ //recursive agorithm program
+ //
+ if (fBDistType==kTRUE) {
+ Float_t delta = (i-fCurrentMaxX)*(i-fCurrentMaxX)/fCurrentSigmaX2;
+ delta+=(j-fCurrentMaxY)*(j-fCurrentMaxY)/fCurrentSigmaY2;
+ if (delta > fMulSigma2) {
+ SetDirBorder(fIndex+1,i,j);
+ return;
+ }
+ }
+ AliCell *cell = GetCell(i,j);
+ Int_t q=cell->GetSignal();
+ cell->SetChecked(fIndex+1);
+ if ( (q>fThreshold) || (fBFit==kTRUE)) AddToStack(i,j,q);
+ if ( q >fThreshold )
+ {
+
+ AliCell * newcel;
+ newcel = GetCell(i-1,j);
+ if (newcel !=0) if (!newcel->IsChecked(fIndex+1) ) Adjacent(i-1,j);
+ newcel = GetCell(i,j-1);
+ if (newcel !=0) if (!newcel->IsChecked(fIndex+1) ) Adjacent(i,j-1);
+ newcel = GetCell(i+1,j);
+ if (newcel !=0) if (!newcel->IsChecked(fIndex+1) ) Adjacent(i+1,j);
+ newcel = GetCell(i,j+1);
+ if (newcel !=0) if (!newcel->IsChecked(fIndex+1) ) Adjacent(i,j+1);
+ }
+ else cell->SetThBorder(fIndex+1);
+}
+
+
+
+AliH2F * AliClusterFinder::Draw( const char *option,
+ Float_t x1, Float_t x2, Float_t y1, Float_t y2)
+{
+ //
+ //draw digits in given array
+ //
+ //make digits histo
+ char ch[30];
+ sprintf(ch,"Cluster finder digits ");
+ if ( (fDimX<1)|| (fDimY<1)) {
+ return 0;
+ }
+ AliH2F * his = new AliH2F(ch,ch,fDimX,fX1,fX2,fDimY,fY1,fY2);
+ //set histogram values
+ for (Int_t i = 0; i<fDimX;i++)
+ for (Int_t j = 0; j<fDimY;j++){
+ Float_t x = ItoX(i);
+ Float_t y= JtoY(j);
+ his->Fill(x,y,GetSignal(i,j));
+ }
+ if (x1>=0) {
+ AliH2F *h2fsub = his->GetSubrange2d(x1,x2,y1,y2);
+ delete his;
+ his=h2fsub;
+ }
+ if (his==0) return 0;
+ if (option!=0) his->Draw(option);
+ else his->Draw();
+ return his;
+}
+
+
+void AliClusterFinder::DrawCluster(
+ Int_t color, Int_t size, Int_t style)
+{
+
+ if (fClustersArray==0) return;
+ //draw marker for each of cluster
+ Int_t ncl=fClustersArray->GetEntriesFast();
+ for (Int_t i=0;i<ncl;i++){
+ AliCluster *cl = (AliCluster*)fClustersArray->UncheckedAt(i);
+ TMarker * marker = new TMarker;
+ marker->SetX(cl->fX);
+ marker->SetY(cl->fY);
+ marker->SetMarkerSize(size);
+ marker->SetMarkerStyle(style);
+ marker->SetMarkerColor(color);
+ marker->Draw();
+ }
+}
+
+
+
+AliH2F * AliClusterFinder::DrawBorders( const char *option, AliH2F *h, Int_t type ,
+ Float_t x1, Float_t x2, Float_t y1, Float_t y2)
+{
+ //
+ //draw digits in given array
+ //
+ //make digits histo
+ char ch[30];
+ sprintf(ch,"Cluster finder digits borders");
+ if ( (fDimX<1)|| (fDimY<1)) {
+ return 0;
+ }
+ AliH2F * his;
+ if (h!=0) his =h;
+ else his = new AliH2F(ch,ch,fDimX,fX1,fX2,fDimY,fY1,fY2);
+ //set histogram values
+ for (Int_t i = 0; i<fDimX;i++)
+ for (Int_t j = 0; j<fDimY;j++){
+ Float_t x = ItoX(i);
+ Float_t y= JtoY(j);
+ if (((type==1)||(type==0))&&IsMaximum(0,i,j)) his->Fill(x,y,16);
+ if (((type==3)||(type==0))&&(IsDirBorder(0,i,j))) his->Fill(x,y,8);
+ if (((type==4)||(type==0))&&(IsThBorder(0,i,j))) his->Fill(x,y,4);
+ if (((type==2)||(type==0))&&IsBorder(0,i,j)) his->Fill(x,y,1);
+
+ }
+
+ if (x1>=0) {
+ AliH2F *h2fsub = his->GetSubrange2d(x1,x2,y1,y2);
+ delete his;
+ his=h2fsub;
+ }
+ if (his==0) return 0;
+ if (option!=0) his->Draw(option);
+ else his->Draw();
+ return his;
+}
--- /dev/null
+#ifndef TCLUSTERFINDER_H
+#define TCLUSTERFINDER_H
+/* Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
+ * See cxx source for full Copyright notice */
+
+/* $Id$ */
+
+// include files and class forward declarations
+#include "TObject.h"
+#include "TH2.h"
+class TClonesArray;
+class AliCluster;
+class AliCell;
+class AliArrayI;
+class AliDetectorParam;
+class TMinuit;
+class AliH2F;
+class AliClusterFinder : public TObject {
+
+public:
+ AliClusterFinder();
+ // constructor which create cluster finder object
+ ~AliClusterFinder();
+ void GetHisto(TH2F * his2);
+ //reset object to include histograms values
+ TClonesArray * FindPeaks1( TClonesArray *arr=0);
+ TClonesArray * FindPeaks2( TClonesArray *arr=0);
+ TClonesArray * FindPeaks3( TClonesArray *arr=0);
+
+ void FindMaxima();
+ // if at point is local maximum return cell with maximum information (for testing only
+ Int_t & GetNType(){return fNType;} //return type of neighborow for max determinatio
+ void SetThreshold(Float_t threshold) { fThreshold = threshold;}
+ void SetNoise(Float_t noise) {fNoiseTh =noise;}
+ void SetDirSigmaFac(Float_t fac) {fDirSigmaFac = fac;}
+ void SetDirAmpFac(Float_t fac) {fDirAmpFac = fac;}
+
+ void SetDetectorParam(AliDetectorParam*param) {fDetectorParam = param;}
+ //set Detector parameters -necesssary to estimate cluster size
+ void SetDetectorIndex(Int_t *index) {fDetectorIndex = index;}
+ //set index of described detector
+ Bool_t SetSigma2(Int_t i, Int_t j, Float_t & sigmax2, Float_t & sigmay2);
+ //set sigmax and sigma y accordig i and j position of cell
+ void SetMulSigma(Float_t sigma) {fMulSigma2= sigma*sigma;}
+ AliArrayI * GetStack(){return fStack;}
+ Int_t GetStackIndex(){return fStackIndex;}
+ void SetBFit(Bool_t fit) {fBFit = fit;}
+ TMinuit * GetMinuit() {return fMinuit;}
+ AliH2F * Draw( const char *option=0,Float_t x1=-1, Float_t x2=-1, Float_t y1=-1, Float_t y2=-1);
+ //draw digits
+ void DrawCluster(Int_t color=5, Int_t size=5, Int_t style=4);
+ AliH2F * DrawBorders( const char *option=0, AliH2F *his=0, Int_t type =0, Float_t x1=-1, Float_t x2=-1, Float_t y1=-1, Float_t y2=-1);
+ //draw digits
+public:
+ Bool_t IsMaximum(Int_t i, Int_t j);
+ Bool_t IsVirtualMaximum(Float_t x, Float_t y);
+
+ void ResetSignal(); //reset signals to 0
+ void ResetStatus(); //reset status of signals to not used
+
+ AliCell * GetCell(Int_t i, Int_t j);
+ //return reference to the cell with index i,j
+ void SetBlockIndex(Int_t *index); //calculate which indexes we must check for border
+public:
+ void AddToStack(Int_t i, Int_t j, Int_t signal);
+ //add given cell to the stack of particles
+ void GetClusterStatistic(AliDigitCluster & cluster);
+ //go through the cluster and calculate statistic
+ void GetClusterFit(AliDigitCluster & cluster);
+ Bool_t CheckIfDirBorder(Float_t x, Float_t y, Int_t i,Int_t j);
+ //check if given cell is border
+ void Adjacent(Int_t i, Int_t j);
+ //recursion procedure
+ Float_t ItoX(Float_t i) {return (fX1)+(i+0.5)*(fX2-fX1)/fDimX;}
+ Float_t JtoY(Float_t j) {return (fY1)+(j+0.5)*(fY2-fY1)/fDimY;}
+
+ inline Bool_t IsChecked(Int_t index, Int_t i, Int_t j);
+ inline Bool_t IsBorder(Int_t index, Int_t i, Int_t j);
+ inline Bool_t IsThBorder(Int_t index, Int_t i, Int_t j);
+ inline Bool_t IsDirBorder(Int_t index, Int_t i, Int_t j);
+ inline Bool_t IsMaximum(Int_t index, Int_t i, Int_t j);
+ inline void SetChecked(Int_t index, Int_t i, Int_t j);
+ inline void SetBorder(Int_t index, Int_t i, Int_t j);
+ inline void SetThBorder(Int_t index, Int_t i, Int_t j);
+ inline void SetDirBorder(Int_t index, Int_t i, Int_t j);
+ inline void SetMaximum(Int_t index, Int_t i, Int_t j);
+
+
+
+ inline Int_t GetSignal(Int_t i, Int_t j);
+ Float_t GetVirtualSignal(Float_t ri, Float_t rj);
+ //create new virtual cell and interpolate signal at position ri,rj
+
+ void Transform(AliDigitCluster *c);
+private:
+ Int_t fNType; //type of neighborow for maximum determination
+ Float_t fCurrentMaxX; //!current cluster maximum X index
+ Float_t fCurrentMaxY; //!current cluster maximum X index
+ Float_t fCurrentSigmaX2; //!current sigmax2 according detector (updated by function ...)
+ Float_t fCurrentSigmaY2;//!
+ Float_t fCurrentMaxAmp;//!current cluster maximum amplitude
+ Bool_t fBDistType; //
+ Bool_t fBFit; //
+ Float_t fMulSigma2; //
+ Float_t fDirSigmaFac; //!for direction border calculation
+ Float_t fDirAmpFac; //!for direction border calculation
+
+ Float_t fThreshold; //treshold;
+ Float_t fNoiseTh; //noise threshoshol to accept maximum
+ AliCell * fDigits; //field with all cell digits
+
+
+ Int_t fIndex; //!index of current cluster
+ AliArrayI * fStack; //!stack with digits index
+ Int_t fStackIndex; //!stack index
+ TMinuit *fMinuit; //!minuit object
+ AliDetectorParam * fDetectorParam; //pointer to detector param - finder is not owner
+ Int_t * fDetectorIndex; // detector index -
+ //original frame
+ Float_t fX1;
+ Float_t fY1;
+ Float_t fX2;
+ Float_t fY2;
+ Int_t fDimX;
+ Int_t fDimY;
+ Int_t fOver;
+
+ //
+ TClonesArray * fClustersArray; //array with current clusters
+ Bool_t rOK;
+ //signalize that all fields were initialised
+ ClassDef(AliClusterFinder,2)
+};
+
+
+
+////////////////////////////////////////////////////////////////////////////
+////////////////////////////////////////////////////////////////////////////
+//objec AliCell
+
+const Int_t krCheck = 1;
+const Int_t krBorder = 2;
+const Int_t krThBorder = 4;
+const Int_t krDirBorder = 8;
+const Int_t krMaximum = 16;
+const Int_t krIndexNull =0x1F;
+
+class AliCell{
+public :
+ AliCell(Int_t signal =0, Int_t status = 0){fSignal =signal;fStatus = status;}
+ //at the begining set
+ void SetSignal(Int_t signal){fSignal = signal;}
+ void SetStatus(Int_t status){fStatus = status;}
+ void SetChecked(Int_t index) {fStatus &=krIndexNull; fStatus+=(index<<5); fStatus|=krCheck;}
+ void SetChecked() {fStatus|=krCheck;}
+ void SetBorder(Int_t index) {fStatus &=krIndexNull; fStatus |= krBorder;fStatus+=(index<<5);}
+ void SetThBorder(Int_t index) {fStatus &=krIndexNull;fStatus|=krBorder|krThBorder;fStatus+=(index<<5);}
+ void SetDirBorder(Int_t index) {fStatus &=krIndexNull;fStatus|=krBorder|krDirBorder;fStatus+=(index<<5);}
+ void SetMaximum(Int_t index) {fStatus &=krIndexNull;fStatus|=krMaximum;fStatus+=(index<<5);}
+
+
+ void SetUnChecked(){if (fStatus&krCheck) fStatus-=krCheck;}
+ void SetUnBorder(){if (fStatus&krBorder) fStatus-=krBorder;}
+ void SetThUnBorder(){SetUnBorder();if (fStatus&krBorder) fStatus-=krThBorder+krBorder;}
+ void SetDirUnBorder(){SetUnBorder();if (fStatus&krBorder) fStatus-=krDirBorder+krBorder;}
+
+ Bool_t IsChecked() {return fStatus&&krBorder;}
+ Bool_t IsChecked(Int_t index) {return ((fStatus>>5)==index);}
+
+ Bool_t IsBorder() {return ((fStatus&krBorder)!=0);}
+ Bool_t IsBorder(Int_t index) {return ( ((fStatus&krBorder)!=0) && ((fStatus>>5)==index));}
+ Bool_t IsDirBorder() {return ((fStatus&krDirBorder)!=0);}
+ Bool_t IsDirBorder(Int_t index) {return ( ((fStatus&krDirBorder)!=0) && ((fStatus>>5)==index));}
+ Bool_t IsThBorder() {return ((fStatus&krThBorder)!=0);}
+ Bool_t IsThBorder(Int_t index) {return ( ((fStatus&krThBorder)!=0) && ((fStatus>>5)==index));}
+
+ Bool_t IsMaximum() {return ((fStatus&krMaximum)!=0);}
+ Bool_t IsMaximum(Int_t index) {return ( ((fStatus&krMaximum)!=0) && ((fStatus>>5)==index));}
+
+ void Reset() { fStatus = 0; fSignal =0;}
+ Int_t GetSignal() {return fSignal;}
+ Int_t GetStatus() {return fStatus;}
+
+
+private:
+ Int_t fSignal;
+ Int_t fStatus;
+};
+
+
+
+Int_t AliClusterFinder::GetSignal(Int_t i, Int_t j)
+{
+ AliCell *c = GetCell(i,j);
+ Int_t res;
+ if (c==0) res = -1;
+ else res = c->GetSignal();
+ return res;
+}
+
+
+
+Bool_t AliClusterFinder::IsBorder(Int_t index, Int_t i, Int_t j)
+{
+ AliCell *c = GetCell(i,j);
+ Bool_t res;
+ if (c==0) res = kFALSE;
+ else {
+ if (index == 0) res = c->IsBorder();
+ else res = c->IsBorder(index);
+ }
+ return res;
+}
+
+
+
+Bool_t AliClusterFinder::IsThBorder(Int_t index, Int_t i, Int_t j)
+{
+ AliCell *c = GetCell(i,j);
+ Bool_t res;
+ if (c==0) res = kFALSE;
+ else {
+ if (index == 0) res = c->IsThBorder();
+ else res = c->IsThBorder(index);
+ }
+ return res;
+}
+
+Bool_t AliClusterFinder::IsDirBorder(Int_t index, Int_t i, Int_t j)
+{
+ AliCell *c = GetCell(i,j);
+ Bool_t res;
+ if (c==0) res = kFALSE;
+ else {
+ if (index == 0) res = c->IsDirBorder();
+ else res = c->IsDirBorder(index);
+ }
+ return res;
+}
+
+Bool_t AliClusterFinder::IsChecked(Int_t index, Int_t i, Int_t j)
+{
+ AliCell *c = GetCell(i,j);
+ Bool_t res;
+ if (c==0) res = kTRUE;
+ else {
+ if (index == 0) res = c->IsChecked();
+ else res = c->IsChecked(index);
+ }
+ return res;
+}
+
+Bool_t AliClusterFinder::IsMaximum(Int_t index, Int_t i, Int_t j)
+{
+ AliCell *c = GetCell(i,j);
+ Bool_t res;
+ if (c==0) res = kTRUE;
+ else {
+ if (index == 0) res = c->IsMaximum();
+ else res = c->IsMaximum(index);
+ }
+ return res;
+}
+
+
+void AliClusterFinder::SetChecked(Int_t index, Int_t i, Int_t j)
+{
+ AliCell *c = GetCell(i,j);
+ if (c!=0) {
+ if (index>0) c->SetChecked(index);
+ else c->SetChecked();
+ }
+}
+
+void AliClusterFinder::SetBorder(Int_t index, Int_t i, Int_t j)
+{
+ AliCell *c = GetCell(i,j);
+ if (c!=0) {
+ if (index>0) c->SetBorder(index);
+ // else c->SetBorder();
+ }
+}
+
+
+void AliClusterFinder::SetThBorder(Int_t index, Int_t i, Int_t j)
+{
+ AliCell *c = GetCell(i,j);
+ if (c!=0) {
+ if (index>0) c->SetThBorder(index);
+ else c->SetThBorder(0);
+ }
+}
+
+
+void AliClusterFinder::SetDirBorder(Int_t index, Int_t i, Int_t j)
+{
+ AliCell *c = GetCell(i,j);
+ if (c!=0) {
+ if (index>0) c->SetDirBorder(index);
+ else c->SetDirBorder(0);
+ }
+}
+
+
+void AliClusterFinder::SetMaximum(Int_t index, Int_t i, Int_t j)
+{
+ AliCell *c = GetCell(i,j);
+ if (c!=0) {
+ if (index>0) c->SetMaximum(index);
+ else c->SetMaximum(0);
+ }
+}
+
+#endif /* TCLUSTERFINDER_H */
--- /dev/null
+/**************************************************************************
+ * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
+ * *
+ * Author: The ALICE Off-line Project. *
+ * Contributors are mentioned in the code where appropriate. *
+ * *
+ * Permission to use, copy, modify and distribute this software and its *
+ * documentation strictly for non-commercial purposes is hereby granted *
+ * without fee, provided that the above copyright notice appears in all *
+ * copies and that both the copyright notice and this permission notice *
+ * appear in the supporting documentation. The authors make no claims *
+ * about the suitability of this software for any purpose. It is *
+ * provided "as is" without express or implied warranty. *
+ **************************************************************************/
+
+/*
+$Log$
+Revision 1.1.4.2 2000/04/10 11:34:02 kowal2
+
+Clusters handling in a new data structure
+
+*/
+
+///////////////////////////////////////////////////////////////////////////////
+// //
+// Time Projection Chamber clusters objects //
+//
+// Origin: Marian Ivanov , GSI Darmstadt
+// //
+// //
+// //
+///////////////////////////////////////////////////////////////////////////////
+#include "TError.h"
+#include "TClass.h"
+#include <TROOT.h>
+#include "AliCluster.h"
+#include "AliClusters.h"
+#include "TClonesArray.h"
+#include "TMarker.h"
+
+
+const Int_t kDefSize = 1; //defalut size
+
+
+ClassImp(AliClusters)
+
+//*****************************************************************************
+//
+//_____________________________________________________________________________
+AliClusters::AliClusters()
+{
+ //
+ //default constructor
+ fNclusters=0;
+ fClusters =0;
+ fClass =0;
+}
+
+Bool_t AliClusters::SetClass(const Text_t *classname)
+{
+ //
+ //set class of stored object
+ if ( fClass !=0 ) {
+ delete fClass;
+ fClass = 0;
+ }
+
+ if (!gROOT)
+ ::Fatal("AliClusters::SetClass", "ROOT system not initialized");
+
+ fClass = gROOT->GetClass(classname);
+ if (!fClass) {
+ Error("AliClusters", "%s is not a valid class name", classname);
+ return kFALSE;
+ }
+ if (!fClass->InheritsFrom(AliCluster::Class())) {
+ Error("AliClusters", "%s does not inherit from AliCluster", classname);
+ return kFALSE;
+ }
+ return kTRUE;
+}
+
+//_____________________________________________________________________________
+void AliClusters::SetArray(Int_t length)
+{
+ //
+ // construct Clones array of object
+ //
+ if (fClusters!=0) delete fClusters;
+ if (fClass==0){
+ Error("AliClusters", "cluster type not initialised \n SetClass before!");
+ return;
+ }
+ fClusters = new TClonesArray(fClass->GetName(),length);
+}
+
+
+
+//_____________________________________________________________________________
+const AliCluster* AliClusters::operator[](Int_t i)
+{
+ //
+ // return cluster at internal position i
+ //
+ if (fClusters==0) return 0;
+ void * cl = fClusters->UncheckedAt(i);
+ if (cl==0) return 0;
+ return (AliCluster*)cl;
+}
+//_____________________________________________________________________________
+void AliClusters::Sort()
+{
+ // sort cluster
+ if (fClusters!=0) fClusters->Sort();
+}
+
+//_____________________________________________________________________________
+AliCluster * AliClusters::InsertCluster( const AliCluster * c)
+{
+ //
+ // Add a simulated cluster copy to the list
+ //
+ if (fClass==0) {
+ Error("AliClusters", "class type not specified");
+ return 0;
+ }
+ if(!fClusters) fClusters=new TClonesArray(fClass->GetName(),1000);
+ TClonesArray &lclusters = *fClusters;
+ return new(lclusters[fNclusters++]) AliCluster(*c);
+}
+
+//_____________________________________________________________________________
+Int_t AliClusters::Find(Double_t y) const
+{
+ //
+ // return index of cluster nearest to given y position
+ //
+ AliCluster* cl;
+ cl=(AliCluster*)fClusters->UncheckedAt(0);
+ if (y <= cl->fY) return 0;
+ cl=(AliCluster*)fClusters->UncheckedAt(fNclusters-1);
+ if (y > cl->fY) return fNclusters;
+ Int_t b=0, e=fNclusters-1, m=(b+e)/2;
+ for (; b<e; m=(b+e)/2) {
+ cl = (AliCluster*)fClusters->UncheckedAt(m);
+ if (y > cl->fY) b=m+1;
+ else e=m;
+ }
+ return m;
+}
+
+
+//_____________________________________________________________________________
+
+void AliClusters::Draw(Float_t shiftx, Float_t shifty,
+ Int_t color, Int_t size, Int_t style)
+{
+
+ if (fClusters==0) return;
+ //draw marker for each of cluster
+ Int_t ncl=fClusters->GetEntriesFast();
+ for (Int_t i=0;i<ncl;i++){
+ AliCluster *cl = (AliCluster*)fClusters->UncheckedAt(i);
+ TMarker * marker = new TMarker;
+ marker->SetX(cl->fX+shiftx);
+ marker->SetY(cl->fY+shifty);
+ marker->SetMarkerSize(size);
+ marker->SetMarkerStyle(style);
+ marker->SetMarkerColor(color);
+ marker->Draw();
+ }
+}
+
--- /dev/null
+#ifndef ALICLUSTERS_H
+#define ALICLUSTERS_H
+/* Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
+ * See cxx source for full Copyright notice */
+
+/* $Id$ */
+
+////////////////////////////////////////////////
+// Manager class for TPC clusters //
+////////////////////////////////////////////////
+
+
+#include "AliSegmentID.h"
+class TClonesArray;
+class TObjArray;
+
+
+class AliClusters : public AliSegmentID{
+public:
+ AliClusters();
+ virtual AliCluster* InsertCluster(const AliCluster* c ); //insert copy of cluster
+ const AliCluster* operator[](Int_t i);
+ virtual Int_t Find(Double_t y) const; //find nearest cluster in y direction
+ void Sort();
+ TClonesArray * GetArray(){return fClusters;}
+ void SetArray(Int_t length); //construct clonnes array of objects of type fClass
+ void Draw(Float_t shiftx, Float_t shifty, Int_t color, Int_t size, Int_t style);
+ Bool_t SetClass(const Text_t *classname);
+protected:
+ TClonesArray * fClusters;
+ Int_t fNclusters;
+ TClass * fClass; //!type of cluster class
+ ClassDef(AliClusters,1)
+};
+
+
+#endif //ALICLUSTERS_H
--- /dev/null
+/**************************************************************************
+ * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
+ * *
+ * Author: The ALICE Off-line Project. *
+ * Contributors are mentioned in the code where appropriate. *
+ * *
+ * Permission to use, copy, modify and distribute this software and its *
+ * documentation strictly for non-commercial purposes is hereby granted *
+ * without fee, provided that the above copyright notice appears in all *
+ * copies and that both the copyright notice and this permission notice *
+ * appear in the supporting documentation. The authors make no claims *
+ * about the suitability of this software for any purpose. It is *
+ * provided "as is" without express or implied warranty. *
+ **************************************************************************/
+
+/*
+$Log$
+Revision 1.1.4.2 2000/04/10 11:34:02 kowal2
+
+Clusters handling in a new data structure
+
+*/
+
+///////////////////////////////////////////////////////////////////////////////
+// //
+// AliClustersArray object //
+//
+// Origin: Marian Ivanov , GSI Darmstadt
+// //
+// //
+///////////////////////////////////////////////////////////////////////////////
+
+#include "TObject.h"
+#include "TClass.h"
+#include <TROOT.h>
+#include "AliSegmentID.h"
+#include "TObjArray.h"
+#include "AliSegmentArray.h"
+
+#include "AliCluster.h"
+#include "AliClusters.h"
+#include "AliClusterFinder.h"
+#include "AliDetectorParam.h"
+#include "AliClustersArray.h"
+
+
+
+ClassImp(AliClustersArray)
+//
+
+AliClustersArray::AliClustersArray()
+{
+ //
+ //Default constructor
+ //
+ fParam = 0;
+ fClusterType = 0;
+}
+
+Bool_t AliClustersArray::SetClusterType(Text_t * classname)
+{
+ //
+ //set type of Clusters
+ //
+ if ( fClusterType !=0 ) {
+ delete fClusterType;
+ fClusterType = 0;
+ }
+
+ if (!gROOT)
+ ::Fatal("AliTPCClustersArray", "ROOT system not initialized");
+
+ fClusterType = gROOT->GetClass(classname);
+ if (!fClusterType) {
+ Error("AliTPCClustersArray", "%s is not a valid class name", classname);
+ return kFALSE;
+ }
+ if (!fClusterType->InheritsFrom(AliCluster::Class())) {
+ Error("AliTPCClustersArray", "%s does not inherit from AliCluster", classname);
+ return kFALSE;
+ }
+ return kTRUE;
+}
+
+Bool_t AliClustersArray::Setup(AliDetectorParam *param)
+{
+ //
+ //make copy of param object
+
+ return kTRUE;
+}
+
+Bool_t AliClustersArray::SetParam(AliDetectorParam * param)
+{
+ return kTRUE;
+}
+
+Bool_t AliClustersArray::SetFinder(AliClustersFinder * finder)
+{
+ return kTRUE;
+}
--- /dev/null
+#ifndef ALICLUSTERSARRAY_H
+#define ALICLUSTERSARRAY_H
+/* Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
+ * See cxx source for full Copyright notice */
+
+/* $Id$ */
+
+////////////////////////////////////////////////
+// Manager class for AliClustersArray //
+////////////////////////////////////////////////
+class AliDetectorParam;
+class AliClustersFinder;
+
+class AliClustersArray : public AliSegmentArray {
+public:
+ AliClustersArray();
+ virtual Bool_t Setup(AliDetectorParam *param);
+ const AliDetectorParam * GetParam() {return fParam;}
+ AliClustersFinder * GetFinder() {return fClFinder;}
+ virtual Bool_t SetParam(AliDetectorParam * param);
+ virtual Bool_t SetFinder(AliClustersFinder * finder);
+ Bool_t SetClusterType(Text_t *classname );
+ TClass * GetClusterType() {return fClusterType;}
+protected:
+ AliDetectorParam * fParam; //pointer to detector parameters
+ AliClustersFinder * fClFinder; //!pointer to cluster finder object
+ TClass *fClusterType; //!
+ ClassDef(AliClustersArray,1)
+};
+
+#endif
--- /dev/null
+/**************************************************************************
+ * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
+ * *
+ * Author: The ALICE Off-line Project. *
+ * Contributors are mentioned in the code where appropriate. *
+ * *
+ * Permission to use, copy, modify and distribute this software and its *
+ * documentation strictly for non-commercial purposes is hereby granted *
+ * without fee, provided that the above copyright notice appears in all *
+ * copies and that both the copyright notice and this permission notice *
+ * appear in the supporting documentation. The authors make no claims *
+ * about the suitability of this software for any purpose. It is *
+ * provided "as is" without express or implied warranty. *
+ **************************************************************************/
+
+/*
+$Log$
+Revision 1.1.4.2 2000/04/10 11:36:13 kowal2
+
+New Detector parameters handling class
+
+*/
+
+///////////////////////////////////////////////////////////////////////
+// Paramter class for AliDetector //
+// //
+// Origin: Marian Ivanov, Uni. of Bratislava, ivanov@fmph.uniba.sk //
+// //
+///////////////////////////////////////////////////////////////////////
+
+#include "TObject.h"
+#include "AliDetectorParam.h"
+
+
+
+
+Float_t * AliDetectorParam::GetAnglesAccMomentum(Float_t *x, Int_t * index, Float_t *momentum, Float_t *angle)
+{
+ //
+ //calculates deflection angle of particle with longitudinal
+ //longitudinal momentum[0] and transversal momentum momentum[1]
+ //at position (x,y,z) = (x[0],x[1],x[2])
+ //angle[0] - deep angle
+ //angle[1] - magnetic deflection angle
+ if (momentum==0) {
+ Float_t rtotal =TMath::Sqrt(x[0]*x[0]+x[1]*x[1]);
+ if (rtotal==0) angle[0]=0;
+ else
+ angle[0] = TMath::ATan(x[2]/rtotal);
+ angle[1]=0;
+ return angle;
+ }
+ Float_t mtotal =TMath::Sqrt(momentum[0]*momentum[0]+momentum[1]*momentum[1]);
+ if (mtotal==0) {
+ angle[0]= 0;
+ angle[1]=0;
+ return angle;
+ }
+ angle[0]= TMath::ATan(momentum[2]/mtotal);
+ Float_t radius1 = TMath::Sqrt(x[0]*x[0]+x[1]*x[1]); //axial symetry in z
+ Float_t radius2 = 1000*mtotal/(3*fBField);
+ if (radius1<radius2)
+ angle[1]= TMath::ASin(radius1/radius2);
+ else
+ angle[1]=0;
+ return angle;
+}
+
+
+
+
+
+ClassImp(AliDetectorParam)
--- /dev/null
+#ifndef ALIDPARAM_H
+#define ALIDPARAM_H
+/* Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
+ * See cxx source for full Copyright notice */
+
+/* $Id$ */
+
+////////////////////////////////////////////////
+// Manager class for detector parameters //
+////////////////////////////////////////////////
+
+
+
+// rootcint problems befor including AliDetectorParam.h you must include TObject.h
+
+#include <TNamed.h>
+class AliDetectorParam : public TNamed {
+public:
+ AliDetectorParam(){;}
+ virtual Int_t GetNSegmentsTotal(){return 0;} //get total nuber of segments
+ virtual Bool_t Get1DIndex(Int_t *index, const Int_t * arrindex) {return kFALSE;}
+ //transform multidimensional index to one dimesional
+ virtual Bool_t GetNDIndex(const Int_t * index1, Int_t * arrIndex) {return kFALSE;}
+ //trasnform one dimesional index to multidimesional
+ virtual Float_t GetPrimaryLoss(Float_t *x, Int_t *index, Float_t *angle){return 0;}
+ virtual Float_t GetTotalLoss(Float_t *x, Int_t *index, Float_t *angle){return 0;}
+ virtual void GetClusterSize(Float_t *x, Int_t *index, Float_t *angle, Int_t mode, Float_t *sigma){;}
+ virtual void GetSpaceResolution(Float_t *x, Int_t *index, Float_t *angle, Float_t amplitude, Int_t mode,
+ Float_t *sigma){;}
+ virtual Float_t * GetAnglesAccMomentum(Float_t *x, Int_t * index, Float_t* momentum, Float_t *angle);
+
+ void SetBField(Float_t b){fBField=b;} //set magnetic field intensity
+ void SetNPrimLoss(Float_t loss) {fNPrimLoss = loss;}
+ void SetNTotalLoss(Float_t loss) {fNTotalLoss = loss;}
+ Float_t GetBFiled() {return fBField;}
+ Float_t GetNPrimLoss() {return fNPrimLoss;}
+ Float_t GetNTotalLoss() {return fNTotalLoss;}
+protected:
+ Float_t fBField; //intensity of magnetic field
+ Float_t fNPrimLoss; //number of produced primary electrons per cm
+ Float_t fNTotalLoss; //total number of produced electrons per cm
+
+ ClassDef(AliDetectorParam,1) //parameter object for set:TPC
+};
+
+
+
+
+#endif //ALIDPARAM_H
--- /dev/null
+/**************************************************************************
+ * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
+ * *
+ * Author: The ALICE Off-line Project. *
+ * Contributors are mentioned in the code where appropriate. *
+ * *
+ * Permission to use, copy, modify and distribute this software and its *
+ * documentation strictly for non-commercial purposes is hereby granted *
+ * without fee, provided that the above copyright notice appears in all *
+ * copies and that both the copyright notice and this permission notice *
+ * appear in the supporting documentation. The authors make no claims *
+ * about the suitability of this software for any purpose. It is *
+ * provided "as is" without express or implied warranty. *
+ **************************************************************************/
+
+/*
+$Log$
+Revision 1.1.4.2 2000/04/10 11:37:42 kowal2
+
+Digits handling in a new data structure
+
+*/
+
+///////////////////////////////////////////////////////////////////////////////
+// //
+// Alice digits array object AliDigits //
+// //
+// //
+// //
+///////////////////////////////////////////////////////////////////////////////
+
+
+#include "TClass.h"
+#include <iostream.h>
+#include "TError.h"
+#include "AliSegmentID.h"
+#include "AliH2F.h"
+#include "AliArrayI.h"
+#include "AliArrayS.h"
+#include "AliDigits.h"
+
+
+
+//_____________________________________________________________________________
+//_____________________________________________________________________________
+//_____________________________________________________________________________
+ClassImp(AliDigits)
+
+
+AliDigits::AliDigits()
+{
+ fIndex = 0;
+ fElements = 0;
+ fThreshold =0;
+ Invalidate();
+}
+
+AliDigits::~AliDigits()
+{
+ //
+ //defaulta destructor
+ if (fIndex !=0 ) fIndex->Delete();;
+ if (fElements != 0) fElements->Delete();
+
+}
+
+
+Bool_t AliDigits::OutOfBoundsError(const char *where, Int_t row, Int_t column)
+{
+ // Generate an out-of-bounds error. Always returns false.
+ ::Error(where, "row %d col %d out of bounds (size: %d x %d, this: 0x%08x)",
+ row, column, fNrows, fNcols, this);
+ return kFALSE;
+}
+
+
+void AliDigits::Invalidate()
+{
+ //
+ //set default (invalid parameters)
+ if (fIndex != 0) delete fIndex;
+ fIndex = new AliArrayI;
+
+ if (fElements!= 0) delete fElements;
+
+ fElements = new AliArrayS;
+
+ fNrows = fNcols =fNelems= -1;
+ fElements->Set(0);
+ fIndex->Set(0);
+ fBufType = -1;
+}
+
+void AliDigits::Allocate(Int_t rows, Int_t columns)
+{
+ //
+ //construct empty buffer fDigits with size rows x columns
+ Invalidate();
+ if (rows <= 0) {
+ Error("Allocate", "no of rows has to be positive");
+ return;
+ }
+ if (columns <= 0) {
+ Error("Allocate", "no of columns has to be positive");
+ return;
+ }
+ fNrows = rows;
+ fNcols=columns;
+ fNelems = fNrows * fNcols;
+ fElements->Set(fNelems);
+ fIndex->Set(fNcols);
+ for (Int_t i =0,k=0; i<fNcols;i++,k+=fNrows)
+ (*fIndex)[i]=k;
+ fBufType =0;
+}
+
+
+Short_t AliDigits::GetDigit(Int_t row, Int_t column)
+{
+ if (fBufType ==0) return GetDigitFast(row,column);
+ if (fBufType ==1) return GetDigit1(row,column);
+
+ return 0;
+}
+
+
+void AliDigits::ExpandBuffer()
+{
+ //
+ //expand buffer to two dimensional array
+ if (fBufType<0) {
+ Error("ExpandBuffer", "buffer doesn't exist");
+ return;
+ }
+ if (fBufType==0) return;
+
+ //expanding of buffer type 1
+ if (fBufType==1) ExpandBuffer1();
+
+ fBufType = 0;
+}
+
+void AliDigits::CompresBuffer(Int_t bufferType,Int_t threshold)
+{
+ //
+ //compres buffer according buffertype algorithm
+ if (fBufType<0) {
+ Error("CompressBuffer", "buffer doesn't exist");
+ return;
+ }
+ if (fBufType == bufferType) return;
+ //
+ if (fBufType>0) ExpandBuffer();
+ if (fBufType !=0) {
+ Error("CompressBuffer", "buffer doesn't exist");
+ return;
+ }
+ fThreshold = threshold;
+ //compress buffer of type 1
+ if ( bufferType == 1) CompresBuffer1();//end of compresing bufer of type 1
+}
+
+Bool_t AliDigits::First()
+{
+ //adjust first valid current digit
+ if (fBufType ==0) return First0();
+ if (fBufType ==1) return First1();
+ return kFALSE;
+}
+
+Bool_t AliDigits::Next()
+{
+ //addjust next valid current digit
+ if (fBufType ==0) return Next0();
+ if (fBufType ==1) return Next1();
+ return kFALSE;
+}
+
+void AliDigits::AcceptHisto(AliH2F * his)
+{
+ //
+ //make digits buffer with value according histograms values
+ //for testing purpose
+ Int_t idim =his->GetNbinsX();
+ Int_t jdim =his->GetNbinsY();
+ if ( (idim<1)|| (jdim<1)) {
+ return;
+ }
+ //allocate proper buffer size
+ Allocate(idim,jdim);
+ //set digits values
+ for (Int_t i = 0; i<idim;i++)
+ for (Int_t j = 0; j<jdim;j++)
+ {
+ Int_t index = his->GetBin(i+1,j+1);
+ SetDigitFast((Short_t)his->GetBinContent(index),i,j);
+ }
+}
+
+AliH2F * AliDigits::GenerHisto()
+{
+ //
+ //make digits histo
+ char ch[30];
+ sprintf(ch,"Segment_%d ",GetID());
+ if ( (fNrows<1)|| (fNcols<1)) {
+ return 0;
+ }
+ AliH2F * his = new AliH2F("Digit histo",ch,fNrows,0,fNrows,fNcols,0,fNcols);
+ ExpandBuffer();
+ //set histogram values
+ for (Int_t i = 0; i<fNrows;i++)
+ for (Int_t j = 0; j<fNcols;j++)
+ his->Fill(i,j,GetDigitFast(i,j));
+ return his;
+}
+
+AliH2F * AliDigits::Draw(const char *option,Float_t x1, Float_t x2, Float_t y1, Float_t y2)
+{
+ //
+ //draw digits in given array
+ //
+ AliH2F *h2f = GenerHisto();
+ if (x1>=0) {
+ AliH2F *h2fsub = h2f->GetSubrange2d(x1,x2,y1,y2);
+ delete h2f;
+ h2f=h2fsub;
+ }
+ if (h2f==0) return 0;
+ if (option!=0) h2f->Draw(option);
+ else h2f->Draw();
+ return h2f;
+}
+
+void AliDigits::ExpandBuffer1()
+{
+ //
+ //expand buffer of type to twodimensional array
+ Int_t i,k;
+ fNelems = fNrows*fNcols;
+ Short_t * buf = new Short_t[fNelems];
+ fIndex->Set(fNcols);
+ for (i =0,k=0 ;i<fNcols;i++,k+=fNrows) (*fIndex)[i]=k;
+ Int_t col=0;
+ Int_t row = 0;
+ Int_t N=fElements->fN;
+ for (i=0;i<N;i++){
+ //oposite signa means how many unwrited (under threshold) values
+ if ((*fElements)[i]<0) row-=fElements->At(i);
+ else {
+ buf[(*fIndex)[col]+row]=fElements->At(i);
+ row++;
+ }
+ if (row==fNrows) {
+ row=0;
+ col++;
+ }else
+ if (row>fNrows){
+ Invalidate();
+ return;
+ }
+ }
+ fElements->Adopt(fNelems,buf);
+}
+void AliDigits::CompresBuffer1()
+{
+ //
+ //compres buffer according algorithm 1
+ //
+ AliArrayS buf; //lets have the nearly the "worst case"
+ buf.Set(fNelems);
+ AliArrayI index;
+ index.Set(fNcols);
+ Int_t icurrent=-1;
+ Int_t izero;
+ for (Int_t col = 0; col<fNcols; col++){
+ index[col]=icurrent+1;//set collumn pointer
+ izero = 0; //reset zer counter at the begining of the column
+ for (Int_t row = 0; row< fNrows;row++){
+ //if under threshold
+ if (GetDigitFast(row,col)<=fThreshold) izero++;
+ else{
+ if (izero>0) {
+ //if we have currently izero count under threshold
+ icurrent++;
+ if (icurrent>=buf.fN) buf.Expand(icurrent*2);
+ buf[icurrent]= -izero; //write how many under zero
+ izero = 0;
+ } //end of reseting izero
+ icurrent++;
+ if (icurrent>=buf.fN) buf.Expand(icurrent*2);
+ buf[icurrent] = GetDigitFast(row,col);
+ }//if signal bigger then threshold
+ } //end of loop over rows
+ if (izero>0) {
+ icurrent++;
+ if (icurrent>=buf.fN) buf.Expand(icurrent*2);
+ buf[icurrent]= -izero; //write how many under zero
+ }
+ }//end of lopping over digits
+ buf.Expand(icurrent+1);
+ (*fElements)=buf;
+ fNelems = fElements->fN;
+ fBufType = 1;
+ (*fIndex) =index;
+ //end of compresing bufer of type 1
+}
+
+
+
+Bool_t AliDigits::First0()
+{
+ //
+ //first for the buffer type 0
+ fCurrentRow = -1;
+ fCurrentCol = -1;
+ fCurrentIndex = -1;
+ Int_t i;
+ for (i=0; (( i<fNelems) && (fElements->At(i)<=fThreshold));i++)
+ if (i == fNelems) return kFALSE;
+ fCurrentCol =i/fNrows;
+ fCurrentRow =i%fNrows;
+ fCurrentIndex = i;
+ return kTRUE;
+}
+
+Bool_t AliDigits::Next0()
+{
+ //
+ //next for the buffer type 0
+ //
+ if (fCurrentIndex<0) return kFALSE; // if we didn't adjust first
+ Int_t i;
+ for (i=fCurrentIndex+1; ( (i<fNelems) && (fElements->At(i)<=fThreshold) ) ;i++);
+ if (i >= fNelems) {
+ fCurrentIndex = -1;
+ return kFALSE;
+ }
+ fCurrentCol =i/fNrows;
+ fCurrentRow =i%fNrows;
+ fCurrentIndex = i;
+ return kTRUE;
+}
+
+Bool_t AliDigits::First1()
+{
+ //
+ //first for the buffer type 1
+ fCurrentRow = -1;
+ fCurrentCol = 0;
+ fCurrentIndex = -1;
+ Int_t i;
+ for (i=0; i<fNelems; i++){
+ if (fElements->At(i) < 0) fCurrentRow-=fElements->At(i);
+ else
+ fCurrentRow++;
+ if (fCurrentRow>=fNrows) {
+ fCurrentCol++;
+ fCurrentRow-=fNrows;
+ }
+ if (fElements->At(i)>fThreshold) break;
+ }
+ fCurrentIndex = i;
+ if (fCurrentIndex>=0) return kTRUE;
+ fCurrentRow =-1;
+ fCurrentCol =-1;
+ return kFALSE;
+}
+
+Bool_t AliDigits::Next1()
+{
+ //
+ //next for the buffer type 1
+ if (fCurrentIndex<0) return kFALSE; // if we didn't adjust first
+ Int_t i;
+ for (i=fCurrentIndex+1; i<fNelems;i++){
+ if (fElements->At(i) < 0) fCurrentRow-=fElements->At(i);
+ else
+ fCurrentRow++;
+ if (fCurrentRow>=fNrows) {
+ fCurrentCol++;
+ fCurrentRow-=fNrows;
+ }
+ if (fElements->At(i)>fThreshold) break;
+ }
+ fCurrentIndex = i;
+ if ( (i>=0) && (i<fNelems) ) return kTRUE;
+ fCurrentRow =-1;
+ fCurrentCol =-1;
+ return kFALSE;
+}
+
+Short_t AliDigits::GetDigit1(Int_t row, Int_t column)
+{
+ //
+ //return digit for given row and column the buffer type 1
+ //no control performed
+
+ Int_t i,n2;
+ if ( (column+1)>=fNcols) n2 = fNelems;
+ else
+ n2 = fIndex->At(column+1);
+ Int_t irow = 0; //current row
+
+ for (i=fIndex->At(column); ( (i<n2) && (irow<row) );i++){
+ if (fElements->At(i) < 0) irow-=fElements->At(i);
+ else
+ irow++;
+ }
+ if ( irow == row ) return fElements->At(i);
+ return -1;
+}
+
--- /dev/null
+#ifndef ALIDIGITS_H
+#define ALIDIGITS_H
+/* Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
+ * See cxx source for full Copyright notice */
+
+/* $Id$ */
+
+////////////////////////////////////////////////
+// Manager class generaol Alice segment digits
+// segment is for example one pad row in TPC //
+////////////////////////////////////////////////
+
+#include "AliArrayI.h"
+#include "AliArrayS.h"
+#include "AliSegmentID.h"
+class AliH2F;
+
+class AliDigits: public AliSegmentID{
+public:
+ AliDigits();
+ ~AliDigits();
+ inline Short_t GetDigitFast(Int_t row, Int_t column); //return value at given row and collumn
+ inline void SetDigitFast(Short_t value,Int_t row, Int_t column); //set value at given row and collumn
+ inline Bool_t BoundsOK(const char *where, Int_t row, Int_t col) ; //Check If Bound Ok
+ Bool_t OutOfBoundsError(const char *where, Int_t row, Int_t column);
+ virtual void Allocate(Int_t rows, Int_t columns); //construct empty buffer fDigits with size rows x columns
+ virtual Short_t GetDigit(Int_t row, Int_t column);
+ virtual void ExpandBuffer(); //expand buffer to twodimensional array
+ virtual void CompresBuffer(Int_t bufferType,Int_t threshold); //compres buffer according buffertype algorithm
+ virtual Bool_t First(); //adjust first valid current digit
+ virtual Bool_t Next(); //addjust next valid current digit
+ void SetThreshold(Int_t th) {fThreshold = th;}
+ Int_t GetThreshold() {return fThreshold;}
+ Int_t CurrentRow(){ return fCurrentRow;} //return current row
+ Int_t CurrentColumn(){ return fCurrentCol;} //return current column
+ Int_t CurrentDigit() {return fElements->At(fCurrentIndex);} //return degit for current row and column
+ void AcceptHisto(AliH2F * his); //update buffer for - it will content histogram values
+ AliH2F * GenerHisto(); //generate 2 dimensional histogram with digits
+ AliH2F * Draw( const char *option=0,Float_t x1=-1, Float_t x2=-1, Float_t y1=-1, Float_t y2=-1); //draw digits
+ Int_t GetSize() {return fNelems;} //return main buffer size
+protected:
+ virtual void Invalidate();
+ void ExpandBuffer1(); //expand buffer of type to twodimensional array
+ void CompresBuffer1(); //compres buffer according algorithm 1
+ Bool_t First0(); //first for the buffer type 0
+ Bool_t Next0(); //next for the buffer type 0
+ Bool_t First1(); //first for the buffer type 1
+ Bool_t Next1();//next for the buffer type 1
+ Short_t GetDigit1(Int_t row, Int_t column); //return digit for given row and column
+
+ Int_t fNrows; //number of rows in Segment
+ Int_t fNcols; //number of collumns in Segment
+private:
+ AliArrayS *fElements; //buffer of 2 bytes integers for digits
+ AliArrayI *fIndex; //index position of column
+ Int_t fBufType; //type of the buffer - define compression algorithm
+ Int_t fThreshold; //treshold for zero suppresion
+ Int_t fNelems; //total number of elements
+ Int_t fCurrentRow; //!current row iteration
+ Int_t fCurrentCol; //!current column iteration
+ Int_t fCurrentIndex; //!current index in field
+
+ ClassDef(AliDigits,1)
+};
+
+
+
+inline Bool_t AliDigits::BoundsOK(const char *where, Int_t row, Int_t col)
+{
+ //Check If Bound Ok
+ if ( (col>=fNcols) || (col<0) ) return OutOfBoundsError(where,row,col);
+ Int_t index =(*fIndex).At(col)+row;
+ if ( (index<0) || (index>fNelems)) return OutOfBoundsError(where,row,col);
+ return kTRUE;
+}
+
+Short_t AliDigits::GetDigitFast(Int_t row, Int_t column)
+{
+ //
+ //return digit from fDigits array
+ //if out of range return dummy value ( value at row = 0, collumn = 0)
+ //
+ return fElements->At(fIndex->At(column)+row);
+}
+
+void AliDigits::SetDigitFast(Short_t value, Int_t row, Int_t column)
+{
+ //
+ //set digit
+ //
+ if ( (row<0) || (row>=fNrows) || (column<0) || (column>=fNrows) )
+ ::Error("AliDigits::SetDigitFast", "row %d col %d out of bounds (size: %d x %d, this: 0x%08x)",
+ row, column, fNrows, fNcols, this);
+ (*fElements)[fIndex->At(column)+row]=value;
+}
+
+#endif
+
--- /dev/null
+/**************************************************************************
+ * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
+ * *
+ * Author: The ALICE Off-line Project. *
+ * Contributors are mentioned in the code where appropriate. *
+ * *
+ * Permission to use, copy, modify and distribute this software and its *
+ * documentation strictly for non-commercial purposes is hereby granted *
+ * without fee, provided that the above copyright notice appears in all *
+ * copies and that both the copyright notice and this permission notice *
+ * appear in the supporting documentation. The authors make no claims *
+ * about the suitability of this software for any purpose. It is *
+ * provided "as is" without express or implied warranty. *
+ **************************************************************************/
+
+/*
+$Log$
+Revision 1.1.4.2 2000/04/10 11:37:42 kowal2
+
+Digits handling in a new data structure
+
+*/
+
+///////////////////////////////////////////////////////////////////////////////
+// //
+// AliDigitsArray object //
+//
+// Origin: Marian Ivanov , GSI Darmstadt
+// //
+// //
+///////////////////////////////////////////////////////////////////////////////
+
+#include "TObject.h"
+#include "AliSegmentID.h"
+#include "TObjArray.h"
+#include "AliSegmentArray.h"
+
+#include "TError.h"
+#include "AliDigits.h"
+#include "AliDetectorParam.h"
+#include "AliDigitsArray.h"
+
+
+
+ClassImp(AliDigitsArray)
+//
+
+AliDigitsArray::AliDigitsArray()
+{
+ fParam = 0;
+}
+
+AliDigitsArray::~AliDigitsArray()
+{
+ if (fParam != 0) delete fParam;
+}
+
+Bool_t AliDigitsArray::Setup(AliDetectorParam *param)
+{
+ //
+ //setup array according parameters
+ SetParam(param);
+ return kTRUE;
+}
+
+
+Bool_t AliDigitsArray::SetParam(AliDetectorParam * param)
+{
+ fParam = param;
+ return kTRUE;
+}
--- /dev/null
+#ifndef ALIDIGITSARRAY_H
+#define ALIDIGITSARRAY_H
+/* Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
+ * See cxx source for full Copyright notice */
+
+/* $Id$ */
+
+////////////////////////////////////////////////
+// Manager class for AliDigitsArray //
+////////////////////////////////////////////////
+class AliDetectorParam;
+
+class AliDigitsArray : public AliSegmentArray {
+public:
+ AliDigitsArray();
+ ~AliDigitsArray();
+ virtual Bool_t Setup(AliDetectorParam *param); //setup array according parameters
+ const AliDetectorParam * GetParam() {return fParam;}
+ virtual Bool_t SetParam(AliDetectorParam * param);
+protected:
+ AliDetectorParam * fParam; //pointer to detector parameters
+ ClassDef(AliDigitsArray,1)
+};
+
+#endif //ALIDIGITSARRAY_H
--- /dev/null
+/**************************************************************************
+ * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
+ * *
+ * Author: The ALICE Off-line Project. *
+ * Contributors are mentioned in the code where appropriate. *
+ * *
+ * Permission to use, copy, modify and distribute this software and its *
+ * documentation strictly for non-commercial purposes is hereby granted *
+ * without fee, provided that the above copyright notice appears in all *
+ * copies and that both the copyright notice and this permission notice *
+ * appear in the supporting documentation. The authors make no claims *
+ * about the suitability of this software for any purpose. It is *
+ * provided "as is" without express or implied warranty. *
+ **************************************************************************/
+
+/*
+$Log$
+Revision 1.1.4.2 2000/04/10 11:32:37 kowal2
+
+"ROOT"-based class with some extra functionality
+
+*/
+
+//----------------------------------------------------------------------------
+// Author: Marian Ivanov
+//
+// Implementation of class AliH2F
+//
+//-----------------------------------------------------------------------------
+
+#include "AliH2F.h"
+#include "TClonesArray.h"
+#include "AliTPC.h"
+#include "TRandom.h"
+#include "AliCluster.h"
+#include "AliClusterFinder.h"
+//*KEEP,TMath.
+
+// other include files follow here
+
+
+ClassImp(AliH2F)
+//***********************************************************************
+//***********************************************************************
+//***********************************************************************
+//***********************************************************************
+AliH2F::AliH2F():TH2F()
+{
+ fSigmaX2 = 1.;
+ fSigmaY2 = 1.;
+ fdx = 1;
+ fdy=1;
+ fFitMatrix.ResizeTo(5,1);
+}
+AliH2F::AliH2F(const Text_t *name,const Text_t *title,
+ Int_t nbinsx,Axis_t xlow,Axis_t xup
+ ,Int_t nbinsy,Axis_t ylow,Axis_t yup):
+ TH2F(name,title,nbinsx,xlow,xup
+ ,nbinsy,ylow,yup)
+{
+ fSigmaX2 = 1.;
+ fSigmaY2 = 1.;
+ fdx = 1;
+ fdy=1;
+ fFitMatrix.ResizeTo(5,1);
+}
+
+AliH2F::~AliH2F()
+{
+}
+
+AliH2F::AliH2F(const AliH2F &)
+{
+}
+
+AliH2F & AliH2F::operator = (const AliH2F &)
+{
+ return *this;
+}
+
+TClonesArray * AliH2F::FindPeaks(Float_t threshold, Float_t noise)
+{
+ //find peaks and write it in form of AliTPCcluster to array
+
+ //firstly we need to create object for cluster finding
+ //and fill it with contents of histogram
+ AliClusterFinder cfinder;
+ cfinder.SetThreshold(threshold);
+ cfinder.SetNoise(noise);
+ cfinder.GetHisto(this);
+ return cfinder.FindPeaks3();
+}
+
+void AliH2F::ClearSpectrum()
+{
+ Int_t dimx = fXaxis.GetNbins();
+ Int_t dimy = fYaxis.GetNbins();
+ for (Int_t i = 0 ;i<dimx;i++)
+ for (Int_t j = 0 ;j<dimy;j++)
+ {
+ SetCellContent(i,j,0);
+ SetCellError(i,j,0);
+ }
+}
+
+
+void AliH2F::AddNoise(Float_t sn)
+{
+ Int_t dimx = fXaxis.GetNbins();
+ Int_t dimy = fYaxis.GetNbins();
+ for (Int_t i = 0 ;i<dimx;i++)
+ for (Int_t j = 0 ;j<dimy;j++)
+ {
+ Float_t noise = gRandom->Gaus(0,sn);
+ Float_t oldv =GetCellContent(i,j);
+ Float_t olds =GetCellError(i,j);
+ if (noise >0)
+ {
+ SetCellContent(i,j,noise+oldv);
+ SetCellError(i,j,TMath::Sqrt((noise*noise+olds*olds)));
+ }
+ }
+}
+void AliH2F::AddGauss(Float_t x, Float_t y,
+ Float_t sx, Float_t sy, Float_t max)
+{
+ //transform to histogram coordinata
+ Int_t dimx = fXaxis.GetNbins();
+ Int_t dimy = fYaxis.GetNbins();
+ Float_t dx =(GetXaxis()->GetXmax()-GetXaxis()->GetXmin())/Float_t(dimx);
+ Float_t dy =(GetYaxis()->GetXmax()-GetYaxis()->GetXmin())/Float_t(dimy);
+ // x=(x-GetXaxis()->GetXmin())/dx;
+ //y=(y-GetYaxis()->GetXmin())/dy;
+ sx/=dx;
+ sy/=dy;
+
+
+ for (Int_t i = 0 ;i<dimx;i++)
+ for (Int_t j = 0 ;j<dimy;j++)
+ {
+ Float_t x2 =GetXaxis()->GetBinCenter(i+1);
+ Float_t y2 =GetYaxis()->GetBinCenter(j+1);
+ Float_t dx2 = (x2-x)*(x2-x);
+ Float_t dy2 = (y2-y)*(y2-y);
+ Float_t amp =max*exp(-(dx2/(2*sx*sx)+dy2/(2*sy*sy)));
+ //Float_t oldv =GetCellContent(i+1,j+1);
+ // SetCellContent(i+1,j+1,amp+oldv);
+ Fill(x2,y2,amp);
+ }
+}
+
+void AliH2F::ClearUnderTh(Int_t threshold)
+{
+ Int_t dimx = fXaxis.GetNbins();
+ Int_t dimy = fYaxis.GetNbins();
+ for (Int_t i = 0 ;i<=dimx;i++)
+ for (Int_t j = 0 ;j<=dimy;j++)
+ {
+ Float_t oldv =GetCellContent(i,j);
+ if (oldv <threshold)
+ SetCellContent(i,j,0);
+ }
+}
+
+void AliH2F::Round()
+{
+ Int_t dimx = fXaxis.GetNbins();
+ Int_t dimy = fYaxis.GetNbins();
+ for (Int_t i = 0 ;i<=dimx;i++)
+ for (Int_t j = 0 ;j<=dimy;j++)
+ {
+ Float_t oldv =GetCellContent(i,j);
+ oldv=(Int_t)oldv;
+ SetCellContent(i,j,oldv);
+ }
+}
+
+
+
+AliH2F *AliH2F::GetSubrange2d(Float_t xmin, Float_t xmax,
+ Float_t ymin, Float_t ymax)
+{
+ //this function return pointer to the new created
+ //histogram which is subhistogram of the
+ //calculate number
+ //subhistogram range must be inside histogram
+
+ if (xmax<=xmin) {
+ xmin=fXaxis.GetXmin();
+ xmax=fXaxis.GetXmax();
+ }
+ if (ymax<=ymin) {
+ ymin=fYaxis.GetXmin();
+ ymax=fYaxis.GetXmax();
+ }
+
+ Int_t nx = Int_t((xmax-xmin)/(fXaxis.GetXmax()-fXaxis.GetXmin()) *
+ Float_t(fXaxis.GetNbins()));
+ Int_t ny = Int_t((ymax-ymin)/(fYaxis.GetXmax()-fYaxis.GetXmin()) *
+ Float_t(fYaxis.GetNbins()));
+ TString t1 = fName ;
+ TString t2 = fTitle ;
+ t1+="_subrange";
+ t2+="_subrange";
+ const Text_t * tt1 = t1;
+ const Text_t * tt2 = t2;
+
+ AliH2F * sub = new AliH2F(tt1,tt2,nx,xmin,xmax,ny,ymin,ymax);
+
+ Int_t i1 = Int_t( Float_t(fXaxis.GetNbins())*(xmin-fXaxis.GetXmin())/
+ (fXaxis.GetXmax()-fXaxis.GetXmin()) ) ;
+ Int_t i2 = Int_t( Float_t(fYaxis.GetNbins())*(ymin-fYaxis.GetXmin())/
+ (fYaxis.GetXmax()-fYaxis.GetXmin()) ) ;
+ for (Int_t i=0;i<nx;i++)
+ for (Int_t j=0;j<ny;j++)
+ {
+ Int_t index1 = GetBin(i1+i,i2+j);
+ // Int_t index2 = sub->GetBin(i,j);
+ Float_t val = GetBinContent(index1);
+ // sub->SetBinContent(index2,val);
+ // Float_t err = GetBinError(index1);
+ //sub->SetBinError(index2,GetBinError(index1));
+ sub->SetCellContent(i,j,val);
+ }
+ return sub;
+}
+
+TH1F *AliH2F::GetAmplitudes(Float_t zmin, Float_t zmax, Float_t th, Float_t xmin, Float_t xmax,
+ Float_t ymin, Float_t ymax)
+{
+ //this function return pointer to the new created
+ //histogram which is subhistogram of the
+ //calculate number
+ //subhistogram range must be inside histogram
+
+ if (xmax<=xmin) {
+ xmin=fXaxis.GetXmin();
+ xmax=fXaxis.GetXmax();
+ }
+ if (ymax<=ymin) {
+ ymin=fYaxis.GetXmin();
+ ymax=fYaxis.GetXmax();
+ }
+ Int_t nx = Int_t((xmax-xmin)/(fXaxis.GetXmax()-fXaxis.GetXmin()) *
+ Float_t(fXaxis.GetNbins()));
+ Int_t ny = Int_t((ymax-ymin)/(fYaxis.GetXmax()-fYaxis.GetXmin()) *
+ Float_t(fYaxis.GetNbins()));
+ TString t1 = fName ;
+ TString t2 = fTitle ;
+ t1+="_amplitudes";
+ t2+="_amplitudes";
+ const Text_t * tt1 = t1;
+ const Text_t * tt2 = t2;
+
+ TH1F * h = new TH1F(tt1,tt2,100,zmin,zmax);
+
+ Int_t i1 = Int_t( Float_t(fXaxis.GetNbins())*(xmin-fXaxis.GetXmin())/
+ (fXaxis.GetXmax()-fXaxis.GetXmin()) ) ;
+ Int_t i2 = Int_t( Float_t(fYaxis.GetNbins())*(ymin-fYaxis.GetXmin())/
+ (fYaxis.GetXmax()-fYaxis.GetXmin()) ) ;
+ for (Int_t i=0;i<nx;i++)
+ for (Int_t j=0;j<ny;j++)
+ {
+ Int_t index1 = GetBin(i1+i,i2+j);
+ Float_t val = GetBinContent(index1);
+ if (val>th) h->Fill(val);
+ }
+ return h;
+}
+
+Float_t AliH2F::GetOccupancy(Float_t th , Float_t xmin, Float_t xmax,
+ Float_t ymin, Float_t ymax)
+{
+ //this function return pointer to the new created
+ //histogram which is subhistogram of the
+ //calculate number
+ //subhistogram range must be inside histogram
+
+ if (xmax<=xmin) {
+ xmin=fXaxis.GetXmin();
+ xmax=fXaxis.GetXmax();
+ }
+ if (ymax<=ymin) {
+ ymin=fYaxis.GetXmin();
+ ymax=fYaxis.GetXmax();
+ }
+ Int_t nx = Int_t((xmax-xmin)/(fXaxis.GetXmax()-fXaxis.GetXmin()) *
+ Float_t(fXaxis.GetNbins()));
+ Int_t ny = Int_t((ymax-ymin)/(fYaxis.GetXmax()-fYaxis.GetXmin()) *
+ Float_t(fYaxis.GetNbins()));
+
+ Int_t over =0;
+ Int_t i1 = Int_t( Float_t(fXaxis.GetNbins())*(xmin-fXaxis.GetXmin())/
+ (fXaxis.GetXmax()-fXaxis.GetXmin()) ) ;
+ Int_t i2 = Int_t( Float_t(fYaxis.GetNbins())*(ymin-fYaxis.GetXmin())/
+ (fYaxis.GetXmax()-fYaxis.GetXmin()) ) ;
+ for (Int_t i=0;i<nx;i++)
+ for (Int_t j=0;j<ny;j++)
+ {
+ Int_t index1 = GetBin(i1+i,i2+j);
+ Float_t val = GetBinContent(index1);
+ if (val>th) over++;
+ }
+ Int_t all = nx*ny;
+ if (all>0) return Float_t(over)/Float_t(all);
+ else
+ return 0;
+}
+
+//TH1F * AliH2F::GetSubrange1dx(Float_t xmin, Float_t xmax, Float_t y)
+//{
+//
+//}
+//TH1F * AliH2F::GetSubrange1dy(Float_t x, Float_t ymin, Float_t ymax)
+//{
+//
+//}
+
+void AliH2F::SetSmoothSigma(Float_t sigmaX, Float_t sigmaY)
+{
+ Float_t wx = (fXaxis.GetXmax()-fXaxis.GetXmin()) / Float_t(fXaxis.GetNbins());
+ Float_t wx2 = wx*wx;
+ Float_t wy = (fYaxis.GetXmax()-fYaxis.GetXmin()) / Float_t(fYaxis.GetNbins()) ;
+ Float_t wy2 =wy*wy;
+ fSigmaX2 = sigmaX*sigmaX/wx2;
+ fSigmaY2 = sigmaY*sigmaX/wy2;
+}
+
+void AliH2F::SetSmoothRange(Float_t dx,Float_t dy)
+{
+ Float_t wx = (fXaxis.GetXmax()-fXaxis.GetXmin()) / Float_t(fXaxis.GetNbins());
+ Float_t wy = (fYaxis.GetXmax()-fYaxis.GetXmin()) / Float_t(fYaxis.GetNbins());
+ fdx = Int_t(dx/wx);
+ fdy = Int_t(dy/wy);
+}
+
+TMatrix * AliH2F::GetFitMatrix(Int_t irow, Int_t icolumn)
+{
+ SmoothCell(irow,icolumn);
+ return &fFitMatrix;
+}
+
+void AliH2F::SmoothCell(Int_t irow, Int_t icolumn)
+{
+ //calculate interpolation around point irow icollumn
+ //fitting by surface of second oreder
+ Int_t index;
+ Float_t x,y,z,x2,x3,x4,y2,y3,y4;
+ Float_t sz = 0.0,szx = 0.0 ,szy = 0.0 ,szx2 = 0.0,szy2 = 0.0;
+ Float_t sx = 0.,sx2 = 0.,sx3 = 0.,sx4 = 0.;
+ Float_t sy = 0.,sy2 = 0. ,sy3 = 0. ,sy4 = 0.;
+ Float_t sxy = 0.,sxy2 = 0. ,sx2y =0.0 ,sx2y2 =0.0;
+ Float_t w;
+ Float_t sumweight = 0;
+ for (Int_t i = -fdx; i <=fdx; i++)
+ for (Int_t j = -fdy; j <=fdy; j++)
+ {
+ index = GetBin(irow+i,icolumn+j);
+ w = 1/(Float_t(i*i)+fSigmaX2)*1/(Float_t(j*j)+fSigmaY2);
+ z = GetBinContent(index);
+ x = irow+i;
+ x2 = x*x; x3 = x2*x; x4 = x2*x2;
+ y = icolumn+j;
+ y2 = y*y; y3 = y2*y; y4 = y2*y2;
+ sz += z*w; sx += x*w; sy += y*w;
+ szx += z*x*w; szy += z*y*w; szx2+= z*x2*w; szy2 += z*y3*w;
+ sx2 += x2*w; sx3 += x3*w; sx4 += x4*w;
+ sy2 += y2*w; sy3 += y3*w; sy4 += y4*w;
+ sxy += x*y*w; sxy2+= x*y2*w; sx2y+=x2*y*w; sx2y2+= x2*y2*w;
+ sumweight +=w;
+ }
+ TMatrix mat(5,5);
+ if (!fFitMatrix.IsValid()) fFitMatrix.ResizeTo(5,1);
+
+ fFitMatrix(0,0) = sz;
+ fFitMatrix(1,0) = szx;
+ fFitMatrix(2,0) = szy;
+ fFitMatrix(3,0) = szx2;
+ fFitMatrix(4,0) = szy2;
+
+ mat(0,0) = sumweight;
+ mat(0,1) = sx; mat(0,2) = sy; mat(0,3) = sx2; mat(0,4) =sy2;
+ mat(1,0) = sx; mat(1,1) = sx2; mat(1,2) = sxy; mat(1,3) = sx3; mat(1,4) =sxy2;
+ mat(2,0) = sy; mat(2,1) = sxy; mat(2,2) = sy2; mat(2,3) = sx2y; mat(2,4) =sy3 ;
+ mat(3,0) = sx2; mat(3,1) = sx3; mat(3,2) = sx2y;mat(3,3) = sx4 ; mat(3,4) =sx2y2;
+ mat(4,0) = sy2; mat(4,1) = sxy2; mat(4,2) = sy3; mat(4,3) = sx2y2;mat(4,4) =sy4;
+}
--- /dev/null
+#ifndef TH2FSMOOTH_H
+#define TH2FSMOOTH_H
+/* Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
+ * See cxx source for full Copyright notice */
+
+/* $Id$ */
+
+// include files and class forward declarations
+
+#include "TH2.h"
+#include "TMatrix.h"
+
+class TMatrix;
+class TH1F;
+class TClonesArray;
+
+class AliH2F : public TH2F {
+public:
+ AliH2F();
+ AliH2F(const Text_t *name,const Text_t *title,Int_t nbinsx,
+ Axis_t xlow,Axis_t xup,Int_t nbinsy,Axis_t ylow,Axis_t yup);
+ ~AliH2F();
+
+public:
+ AliH2F(const AliH2F &);
+ AliH2F & operator = (const AliH2F &);
+ TClonesArray * FindPeaks(Float_t threshold, Float_t noise);
+ //find peaks and write it in form of AliTPCcluster to array
+ void ClearSpectrum();
+ void AddGauss(Float_t x,Float_t y,Float_t sx, Float_t sy, Float_t max);
+ void AddNoise(Float_t sn);
+ void ClearUnderTh(Int_t threshold);
+ void Round();
+ //round float values to integer values
+ // void Smooth();
+ AliH2F * GetSubrange2d(Float_t xmin, Float_t xmax,
+ Float_t ymin, Float_t ymax);
+ //create new 2D histogram
+ Float_t GetOccupancy(Float_t th=1. , Float_t xmin=0, Float_t xmax=0,
+ Float_t ymin=0, Float_t ymax=0);
+ //calculate ration of channel over threshold to all channels
+ TH1F * GetAmplitudes(Float_t zmin, Float_t zmax, Float_t th=1. , Float_t xmin=0, Float_t xmax=0,
+ Float_t ymin=0, Float_t ymax=0);
+ //generate one dim histogram of amplitudes
+ void SetSmoothSigma(Float_t sigmaX, Float_t sigmaY);
+ void SetSmoothRange(Float_t dx,Float_t dy);
+ TMatrix * GetFitMatrix(Int_t irow, Int_t icolumn);
+
+public:
+
+protected:
+
+private:
+ void SmoothCell(Int_t irow, Int_t icolumn) ;
+ Float_t fSigmaX2; //sigma x used for weight calculation in smooth proces
+ Float_t fSigmaY2; //sigma x used for weight calculation in smooth proces
+ Int_t fdx; //dx range on which we are smoothing around 1 point
+ Int_t fdy; //dy range on which we are smoothing around 1 point
+ TMatrix fFitMatrix; //matrix with fitted parameters
+ ClassDef(AliH2F,1)
+};
+
+#endif /*TH2FSMOOTH_H */
--- /dev/null
+/**************************************************************************
+ * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
+ * *
+ * Author: The ALICE Off-line Project. *
+ * Contributors are mentioned in the code where appropriate. *
+ * *
+ * Permission to use, copy, modify and distribute this software and its *
+ * documentation strictly for non-commercial purposes is hereby granted *
+ * without fee, provided that the above copyright notice appears in all *
+ * copies and that both the copyright notice and this permission notice *
+ * appear in the supporting documentation. The authors make no claims *
+ * about the suitability of this software for any purpose. It is *
+ * provided "as is" without express or implied warranty. *
+ **************************************************************************/
+
+/*
+$Log$
+Revision 1.1.4.2 2000/04/10 11:39:36 kowal2
+
+New data structure handling
+
+*/
+
+///////////////////////////////////////////////////////////////////////////////
+// //
+// Alice segment manager object //
+//
+// AliSegmentIDArray object is array of pointers to object derived from
+// AliSegmentID object //
+// AliSegmentID - object in comparison with TObject enhalt
+// additional information fSegmentID
+//
+// //
+// //
+///////////////////////////////////////////////////////////////////////////////
+
+#include <TROOT.h>
+#include <TTree.h>
+#include "TClonesArray.h"
+#include "TDirectory.h"
+#include "AliArrayI.h"
+#include "TError.h"
+#include "TClass.h"
+
+#include "AliSegmentID.h"
+#include "AliSegmentArray.h"
+#include "TObjString.h"
+
+
+//_____________________________________________________________________________
+ClassImp(AliSegmentArray)
+
+AliSegmentArray::AliSegmentArray()
+{
+ //
+ //
+ //
+ fNSegment=0;
+ fSegment =0;
+ fTreeIndex = 0;
+ fTree = 0;
+ fClass = 0;
+}
+
+AliSegmentArray::AliSegmentArray(Text_t *classname, Int_t n)
+{
+ //
+ //constructor which
+ //
+ // Create an array of objects of classname. The class must inherit from
+ // AliSegmentID . The second argument adjust number of entries in
+ // the array.
+ fNSegment=0;
+ fSegment =0;
+ fTreeIndex = 0;
+ fTree = 0;
+ fClass = 0;
+ SetName("SegmentArray");
+ SetTitle("SegmentArray");
+
+ SetClass(classname);
+ if (MakeArray(n)==kFALSE){
+ Error("AliSegmentArray", "can't allocate %d segments in memory",n);
+ return;
+ }
+}
+
+Bool_t AliSegmentArray::SetClass(Text_t *classname)
+{
+ //
+ //set class of stored object
+ if ( fClass !=0 ) {
+ delete fClass;
+ fClass = 0;
+ }
+ if (fTree !=0) {
+ delete fTree;
+ fTree = 0;
+ fBranch = 0;
+ delete fTreeIndex;
+ fTreeIndex = 0;
+ }
+ if (fSegment != 0) {
+ fSegment->Delete();
+ delete fSegment;
+ fSegment = 0;
+ }
+ if (!gROOT)
+ ::Fatal("AliSegmentArray::AliSegmentArray", "ROOT system not initialized");
+
+ fClass = gROOT->GetClass(classname);
+ if (!fClass) {
+ Error("AliSegmentArray", "%s is not a valid class name", classname);
+ return kFALSE;
+ }
+ if (!fClass->InheritsFrom(AliSegmentID::Class())) {
+ Error("AliSegmentArray", "%s does not inherit from AliSegmentID", classname);
+ return kFALSE;
+ }
+ return kTRUE;
+}
+
+AliSegmentArray::~AliSegmentArray()
+{
+ if (fNSegment>0){
+ fSegment->Delete();
+ delete fSegment;
+ }
+ if (fTree) delete fTree;
+ if (fTreeIndex) delete fTreeIndex;
+ if (fClass!=0) delete fClass;
+}
+
+AliSegmentID * AliSegmentArray::NewSegment()
+{
+ //
+ //create object according class information
+ if (fClass==0) return 0;
+ AliSegmentID * segment = (AliSegmentID * )fClass->New();
+ if (segment == 0) return 0;
+ return segment;
+}
+
+
+Bool_t AliSegmentArray::AddSegment(AliSegmentID *segment)
+{
+ //
+ // add segment to array
+ //
+ if (segment==0) return kFALSE;
+ if (fSegment==0) return kFALSE;
+ if (fClass==0) return kFALSE;
+ if (!(segment->IsA()->InheritsFrom(fClass))){
+ Error("AliSegmentArray", "added class %s is not of proper type ",
+ segment->IsA()->GetName());
+ return kFALSE;
+ }
+ fSegment->AddAt(segment,segment->GetID());
+ fNSegment = fSegment->GetLast()+1;
+ return kTRUE;
+}
+
+AliSegmentID * AliSegmentArray::AddSegment(Int_t index)
+{
+ //
+ // add segment to array
+ //
+ if (fSegment==0) return 0;
+ if (fClass==0) return 0;
+ AliSegmentID * segment = NewSegment();
+ if (segment == 0) return 0;
+ fSegment->AddAt(segment,index);
+ segment->SetID(index);
+ fNSegment = fSegment->GetLast()+1;
+ return segment;
+}
+
+
+void AliSegmentArray::ClearSegment(Int_t index)
+{
+ //
+ //remove segment from active memory
+ //
+ if ((*fSegment)[index]){
+ // (*fSegment)[index]->Delete(); //not working for TClonesArray
+ delete (*fSegment)[index]; //because problem with deleting TClonesArray
+ fSegment->RemoveAt(index);
+ }
+}
+
+
+Bool_t AliSegmentArray::MakeArray(Int_t n)
+{
+ //
+ //make array of pointers to Segments
+ //
+ if (fSegment) {
+ fSegment->Delete();
+ delete fSegment;
+ }
+ fSegment = new TObjArray(n);
+ fNSegment=n;
+ if (fSegment) return kTRUE;
+ else return kFALSE;
+}
+
+
+void AliSegmentArray::MakeTree()
+{
+ // AliSegmentID segment;
+ AliSegmentID * psegment = NewSegment();
+ if (fTree) delete fTree;
+ fTree = new TTree("Segment Tree","Tree with segments");
+ fBranch = fTree->Branch("Segment",psegment->IsA()->GetName(),&psegment,64000,1);
+ delete psegment;
+}
+
+Bool_t AliSegmentArray::MakeDictionary(Int_t size)
+{
+ //
+ //create index table for tree
+ //
+ if (size<1) return kFALSE;
+ if (fTreeIndex) delete fTreeIndex;
+ fTreeIndex = new AliArrayI();
+ fTreeIndex->Set(size);
+
+ AliSegmentID segment;
+ AliSegmentID * psegment = &segment;
+ fBranch->SetAddress(&psegment);
+ TBranch * brindix = fTree->GetBranch("fSegmentID");
+ Int_t nevent = (Int_t)fTree->GetEntries();
+ for (Int_t i = 0; i<nevent; i++){
+ brindix->GetEvent(i);
+ Int_t treeIndex=segment.GetID();
+ if (fTreeIndex->fN<treeIndex) fTreeIndex->Expand(Int_t(Float_t(treeIndex)*1.5)+1);
+ // Int_t index = segment.GetID();
+ (*fTreeIndex)[treeIndex]=i+1; //
+ }
+ return kTRUE;
+}
+
+Bool_t AliSegmentArray::ConnectTree(const char * treeName)
+{
+ //connect tree from current directory
+ if (fTree){
+ delete fTree;
+ fTree = 0;
+ fBranch = 0;
+ }
+ fTree =(TTree*)gDirectory->Get(treeName);
+ if (fTree == 0) return kFALSE;
+ fBranch = fTree->GetBranch("Segment");
+ if (fBranch==0) return kFALSE;
+ MakeDictionary(TMath::Max(fNSegment,Int_t(fTree->GetEntries())));
+ MakeArray(fTreeIndex->fN);
+ return kTRUE;
+}
+
+AliSegmentID *AliSegmentArray::LoadSegment(Int_t index)
+{
+ //
+ //load segment with index to the memory
+ //
+ //
+ if (fTreeIndex ==0 ) MakeDictionary(3000);
+ //firstly try to load dictionary
+ if (fTreeIndex ==0 ) return 0;
+ if (fBranch==0) return 0;
+ if (index>fTreeIndex->fN) return 0;
+ AliSegmentID *s = (AliSegmentID*)(*fSegment)[index];
+ if (s==0) s= NewSegment();
+ s->SetID(index);
+ // new AliSegmentID(index);
+
+ if (s!=0) {
+ Int_t treeIndex =(*fTreeIndex)[index];
+ if (treeIndex<1) return 0;
+ else treeIndex--; //I don't like it Int table I have index shifted by 1
+ fBranch->SetAddress(&s);
+ fTree->GetEvent(treeIndex);
+ (*fSegment)[index] = (TObject*) s;
+ }
+ else
+ return 0;
+ return s;
+
+}
+AliSegmentID *AliSegmentArray::LoadEntry(Int_t index)
+{
+ //
+ //load segment at position inex in tree to the memory
+ //
+ //
+ if (fBranch==0) return 0;
+ if (index>fTree->GetEntries()) return 0;
+ AliSegmentID * s = NewSegment();
+
+ if (s) {
+ fBranch->SetAddress(&s);
+ fTree->GetEvent(index);
+ }
+ else
+ return 0;
+ Int_t nindex = s->GetID();
+ ClearSegment(nindex);
+ (*fSegment)[nindex] = (TObject*) s;
+ return s;
+}
+
+void AliSegmentArray::StoreSegment(Int_t index)
+{
+ //
+ //make segment persistent
+ //
+ const AliSegmentID * segment = (*this)[index];
+ if (segment == 0 ) return;
+ if (fTree==0) MakeTree();
+ fBranch->SetAddress(&segment);
+ fTree->Fill();
+}
+
+
+void AliSegmentArray::Streamer(TBuffer &R__b)
+{
+ TObjString treeName, * ptreeName=&treeName;
+ if (R__b.IsReading()) {
+ Version_t R__v = R__b.ReadVersion(); if (R__v) { }
+ TNamed::Streamer(R__b);
+ R__b>>ptreeName;
+ if (fTree) delete fTree;
+ ConnectTree(ptreeName->String());
+ } else {
+ R__b.WriteVersion(AliSegmentArray::IsA());
+ TNamed::Streamer(R__b);
+ // char ch[200];
+ // sprintf(ch,"%s",fTrre->GetTitle());
+ treeName.String() = fTree->GetTitle();
+ R__b<<ptreeName;
+ fTree->Write();
+ }
+}
--- /dev/null
+#ifndef ALISEGARRAY_H
+#define ALISEGARRAY_H
+/* Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
+ * See cxx source for full Copyright notice */
+
+/* $Id$ */
+
+////////////////////////////////////////////////
+// Manager class general Alice segment
+// segment is for example one pad row in TPC //
+////////////////////////////////////////////////
+
+#include "TNamed.h"
+#include "TError.h"
+//#include "AliSegmentID.h"
+
+class TTree;
+class TBranch;
+class AliArrayI;
+class AliSegmentID;
+class TObjArray;
+
+class AliSegmentArray: public TNamed{
+public:
+ AliSegmentArray();
+ AliSegmentArray(Text_t *classname, Int_t n); //
+ Bool_t SetClass(Text_t *classname); //set class of stored object
+ ~AliSegmentArray();
+ inline const AliSegmentID * At(Int_t i); //return pointer to segment with index i
+ inline const AliSegmentID * operator[](Int_t i); //return pointer to segment with index i
+
+ Bool_t AddSegment(AliSegmentID *segment); // add segment to array
+ AliSegmentID * AddSegment(Int_t index); //create objet and set index
+ Bool_t MakeArray(Int_t n); //make array of pointers to Segments
+ void ClearSegment(Int_t index); //remove segment from active
+ virtual AliSegmentID * NewSegment(); //dynamicaly create new segment
+ //input output functions
+ TTree * GetTree(){return fTree;} //return pointer to connected tree
+
+ virtual void MakeTree(); //Make tree with the name
+ virtual Bool_t ConnectTree(const char * treeName); //connect tree from current directory
+ virtual AliSegmentID * LoadSegment(Int_t index);//load segment with index to the memory
+ virtual AliSegmentID * LoadEntry(Int_t index); //load segment entry from position index in tree
+ virtual void StoreSegment(Int_t index);//write segmen persistent
+ Bool_t MakeDictionary(Int_t size);//create index table for tree
+ TClass * GetClass() {return fClass;}
+
+public:
+ TObjArray * fSegment; //!pointer to array of pointers to segment
+ AliArrayI * fTreeIndex; //!pointers(index) table in tree
+ Int_t fNSegment;
+ TTree * fTree; //!tree with segment objects
+ TBranch * fBranch; //!total branch
+private:
+ TClass * fClass; //!class type of included objects
+ ClassDef(AliSegmentArray,1)
+};
+
+
+
+const AliSegmentID* AliSegmentArray::operator[](Int_t i)
+{
+ //
+ //return segment with given index
+ //
+ if ( (i<0) || (i>=fNSegment)) return 0;
+ return (AliSegmentID *)((*fSegment)[i]);
+}
+const AliSegmentID* AliSegmentArray::At(Int_t i)
+{
+ //
+ //return segment with given index
+ //
+ if ( (i<0) || (i>=fNSegment)) return 0;
+ return (AliSegmentID *)((*fSegment)[i]);
+}
+
+#endif //ALISEGARRAY_H
--- /dev/null
+/**************************************************************************
+ * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
+ * *
+ * Author: The ALICE Off-line Project. *
+ * Contributors are mentioned in the code where appropriate. *
+ * *
+ * Permission to use, copy, modify and distribute this software and its *
+ * documentation strictly for non-commercial purposes is hereby granted *
+ * without fee, provided that the above copyright notice appears in all *
+ * copies and that both the copyright notice and this permission notice *
+ * appear in the supporting documentation. The authors make no claims *
+ * about the suitability of this software for any purpose. It is *
+ * provided "as is" without express or implied warranty. *
+ **************************************************************************/
+
+/*
+$Log$
+Revision 1.1.4.2 2000/04/10 11:39:36 kowal2
+
+New data structure handling
+
+*/
+
+///////////////////////////////////////////////////////////////////////////////
+// //
+// Alice AliSementID object //
+//
+// //
+// //
+///////////////////////////////////////////////////////////////////////////////
+
+
+#include "AliSegmentID.h"
+AliSegmentID::AliSegmentID()
+{
+}
+
+ClassImp(AliSegmentID)
--- /dev/null
+#ifndef ALISEGMENTID_H
+#define ALISEGMENTID_H
+/* Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
+ * See cxx source for full Copyright notice */
+
+/* $Id$ */
+
+////////////////////////////////////////////////
+// Manager class generaol Alice segment
+// segment is for example one pad row in TPC //
+////////////////////////////////////////////////
+
+#include "TObject.h"
+
+class AliSegmentID: public TObject{
+public:
+ AliSegmentID();
+ AliSegmentID(Int_t index){fSegmentID = index;}
+ Int_t GetID() {return fSegmentID;}
+ void SetID(Int_t index){fSegmentID = index;}
+protected:
+ Int_t fSegmentID; //identification number of Segment
+ ClassDef(AliSegmentID,1)
+};
+
+#endif //ALISEGMENTID_H
+
--- /dev/null
+/**************************************************************************
+ * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
+ * *
+ * Author: The ALICE Off-line Project. *
+ * Contributors are mentioned in the code where appropriate. *
+ * *
+ * Permission to use, copy, modify and distribute this software and its *
+ * documentation strictly for non-commercial purposes is hereby granted *
+ * without fee, provided that the above copyright notice appears in all *
+ * copies and that both the copyright notice and this permission notice *
+ * appear in the supporting documentation. The authors make no claims *
+ * about the suitability of this software for any purpose. It is *
+ * provided "as is" without express or implied warranty. *
+ **************************************************************************/
+
+/*
+$Log$
+Revision 1.1.4.2 2000/04/10 11:37:42 kowal2
+
+Digits handling in a new data structure
+
+*/
+
+
+///////////////////////////////////////////////////////////////////////////////
+// //
+// Alice segment manager object //
+//
+// AliSimDigits object (derived from AliDigits) //
+// provide additional track information to digit //
+//
+// Origin: Marian Ivanov GSI Darmstadt //
+//
+// //
+// //
+///////////////////////////////////////////////////////////////////////////////
+
+#include "TClass.h"
+#include <iostream.h>
+#include "TError.h"
+#include "AliSegmentID.h"
+#include "AliH2F.h"
+#include "AliArrayI.h"
+#include "AliArrayS.h"
+#include "AliDigits.h"
+#include "AliSimDigits.h"
+#include "AliTPC.h"
+
+
+
+//_____________________________________________________________________________
+//_____________________________________________________________________________
+//_____________________________________________________________________________
+ClassImp(AliSimDigits)
+
+AliSimDigits::AliSimDigits()
+{
+ // AliDigits::Invalite();
+ fTracks = 0;
+ fTrIndex = 0;
+ InvalidateTrack();
+}
+AliSimDigits::~AliSimDigits()
+{
+ // AliDigits::Invalidate();
+ if (fTracks != 0) fTracks->Delete();
+ if (fTrIndex != 0) fTrIndex->Delete();
+
+}
+
+void AliSimDigits::InvalidateTrack()
+{
+ //
+ //set default (invalid parameters)
+ if ( fTracks != 0) delete fTracks;
+ fTracks = new AliArrayI;
+ if ( fTrIndex != 0) delete fTrIndex;
+ fTrIndex = new AliArrayI;
+
+ for (Int_t i = 0; i<3; i++){
+ fTracks->Set(0);
+ fTrIndex->Set(0);
+ }
+}
+
+void AliSimDigits::AllocateTrack(Int_t length)
+{
+ //
+ //construct empty buffer fElements and fTracks with size fNrows x fNcols x
+ //length
+ InvalidateTrack();
+ fNlevel = length;
+ fTracks->Set(fNcols*fNrows*fNlevel);
+ fTrIndex->Set(0);
+ fTrBufType =0;
+}
+
+Int_t AliSimDigits::GetTrackID(Int_t row, Int_t column, Int_t level)
+{
+ //
+ //Get track ID
+ if (fTrBufType == 0) return GetTrackIDFast(row, column,level);
+ if (fTrBufType == 1) return GetTrackID1(row, column,level);
+ if (fTrBufType == 2) return GetTrackID2(row, column,level);
+ return 0;
+}
+
+void AliSimDigits::ExpandTrackBuffer()
+{
+ //
+ //expand buffer to two dimensional array
+ if (fTrBufType<0) {
+ Error("ExpandBuffer", "buffer doesn't exist");
+ return;
+ }
+ if (fTrBufType==0) return; //buffer expanded
+ if (fTrBufType==1) {ExpandTrackBuffer1(); return;}
+ if (fTrBufType==2) ExpandTrackBuffer2();
+
+}
+
+void AliSimDigits::CompresTrackBuffer(Int_t bufType)
+{
+ //
+ //compres buffer according buffertype algorithm
+ //
+ if (fTrBufType<0) {
+ Error("CompressBuffer", "buffer doesn't exist");
+ return;
+ }
+ if (fTrBufType == bufType) return;
+ //
+ if (fTrBufType>0) ExpandTrackBuffer();
+ if (fTrBufType !=0) {
+ Error("CompressBuffer", "buffer doesn't exist");
+ return;
+ }
+ //compress buffer of type 1
+
+ if (bufType==1) {CompresTrackBuffer1();return;}
+ if (bufType==2) CompresTrackBuffer2();
+
+}
+
+Int_t AliSimDigits::GetTrackID1(Int_t row, Int_t column, Int_t level)
+{
+ //return track ID of digits - for buffer compresion 2
+ Int_t i,n1,n2;
+ i = level*fNcols+column;
+ if ( (i+1)>=fTrIndex->fN) n2 = fTracks->fN;
+ else
+ n2 = fTrIndex->At(i+1);
+ n1 = fTrIndex->At(i);
+ Int_t rownew = 0;
+ Int_t rowold=0;
+ Int_t ID;
+ for (i = n1;(i<n2);i++){
+ ID = 0;
+ Int_t num = fTracks->At(i);
+ if (num<0) {
+ rownew-=num;
+ rowold = rownew;
+ i++;
+ if (i<n2){
+ num = fTracks->At(i);
+ rownew+=num;
+ i++;
+ ID = fTracks->At(i);
+ }
+ }
+ else {
+ rowold = rownew;
+ rownew+=num;
+ i++;
+ ID = fTracks->At(i);
+ }
+ID-=2;
+ if ( (row>=rowold) && (row<=rownew) ) return ID;
+ if (row < rownew ) return -2; //empty track
+ }
+ return -2;
+}
+
+void AliSimDigits::ExpandTrackBuffer1()
+{
+ //
+ //expand track compressed according algorithm 1 (track ID comression independent to the digit compression)
+ // !!in expanded tracks we don't use fTrIndex array
+ //
+ fTrBufType = 0;
+ Int_t i,j;
+ Int_t all = fNrows*fNcols; //total number of digits
+ Int_t elems = all*fNlevel; //length of the buffer
+
+ AliArrayI * buf = new AliArrayI;
+ buf->Set(elems);
+ fTrIndex->Set(0);
+ //
+ Int_t level = 0;
+ Int_t col=0;
+ Int_t row = 0;
+ Int_t N=fTracks->fN;
+ //
+ for (i=0;i<N;i++){
+ //oposite signa means how many unwrited (under threshold) values
+ Int_t num = fTracks->At(i);
+ if (num<0) row-=num; //negative number mean number of zeroes (no tracks of gibven level no need to write to array)
+ else {
+ i++;
+ Int_t ID = fTracks->At(i);
+ for (j = 0; j<num; j++,row++) (*buf)[level*all+col*fNrows+row]=ID;
+ }
+ if (row>=fNrows) {
+ row=0;
+ col++;
+ }
+ if (col>=fNcols) {
+ col=0;
+ level++;
+ }
+ }//end of loop over digits
+ delete fTracks;
+ fTracks = buf;
+}
+
+void AliSimDigits::CompresTrackBuffer1()
+{
+ //
+ //comress track according algorithm 1 (track ID comression independent to the digit compression)
+ //
+ fTrBufType = 1;
+
+ AliArrayI * buf = new AliArrayI; //create new buffer
+ buf->Set(fNrows*fNcols*fNlevel); //lets have the nearly the "worst case"
+ AliArrayI * index = new AliArrayI;
+ index->Set(fNcols*fNlevel);
+
+ Int_t icurrent=-1; //current index
+ Int_t izero; //number of zero
+ Int_t inum; //number of digits with the same current track ID
+ Int_t lastID =0; //last track ID
+ for (Int_t lev =0; lev<fNlevel; lev++){ //loop over levels
+ for (Int_t col = 0; col<fNcols; col++){ //loop over columns
+ izero = 0;
+ inum = 0;
+ lastID = 0;
+ (*index)[lev*fNcols+col]=icurrent+1;//set collumn pointer
+ Int_t ID; //current ID
+ for (Int_t row = 0; row< fNrows;row++){ //loop over rows
+ ID = GetTrackIDFast(row,col,lev);
+ if (ID <= 0) {
+ if ( inum> 0 ) { //if we have some tracks in buffer
+ icurrent++;
+ if ((icurrent+1)>=buf->fN) buf->Expand(icurrent*2);
+ (*buf)[icurrent] = inum;
+ icurrent++;
+ (*buf)[icurrent] = lastID;
+ inum = 0;
+ lastID = 0;
+ }
+ izero++;
+ }
+ else
+ if (ID != lastID)
+ if ( izero > 0 ) {
+ //if we have currently izero count of non tracks digits
+ icurrent++;
+ if (icurrent>=buf->fN) buf->Expand(icurrent*2);
+ (*buf)[icurrent]= -izero; //write how many under zero
+ inum++;
+ izero = 0;
+ lastID = ID;
+ }
+ else{
+ //if we change track ID from another track ID
+ icurrent++;
+ if ((icurrent+1)>=buf->fN) buf->Expand(icurrent*2);
+ (*buf)[icurrent] = inum;
+ icurrent++;
+ (*buf)[icurrent] = lastID;
+ lastID = ID;
+ inum = 1;
+ izero = 0;
+ }
+ else {
+ inum++;
+ }
+
+ }//end of loop over rows
+ if ( izero > 0 ) {
+ //if we have currently izero count of non tracks digits
+ icurrent++;
+ if (icurrent>=buf->fN) buf->Expand(icurrent*2);
+ (*buf)[icurrent]= -izero; //write how many under zero
+ }
+ if ( inum> 0 ) { //if we have some tracks in buffer
+ icurrent++;
+ if ((icurrent+1)>=buf->fN) buf->Expand(icurrent*2);
+ (*buf)[icurrent] = inum;
+ icurrent++;
+ (*buf)[icurrent] = ID;
+ }
+ }//end of loop over columns
+ }//end of loop over differnet track level
+ buf->Expand(icurrent+1);
+ delete fTracks;
+ fTracks = buf;
+ delete fTrIndex;
+ fTrIndex = index;
+}
+
+
+
+void AliSimDigits::ExpandTrackBuffer2()
+{
+ //
+ //comress track according algorithm 2 (track ID comression according digit compression)
+ fTrBufType = 0;
+}
+
+void AliSimDigits::CompresTrackBuffer2()
+{
+ //
+ //comress track according algorithm 2 (track ID comression according digit compression)
+ fTrBufType = 2;
+}
+
+
+Int_t AliSimDigits::GetTrackID2(Int_t row, Int_t column, Int_t level)
+{
+ //returnb track ID of digits - for buffer compresion 2
+ return -2;
+}
+
+
+
+AliH2F * AliSimDigits::DrawTracks( const char *option,Int_t level,
+ Float_t x1, Float_t x2, Float_t y1, Float_t y2)
+{
+ //
+ //draw digits in given array
+ //
+ //make digits histo
+ char ch[30];
+ sprintf(ch,"Track Segment_%d level %d ",GetID(),level );
+ if ( (fNrows<1)|| (fNcols<1)) {
+ return 0;
+ }
+ AliH2F * his = new AliH2F("Track histo",ch,fNrows,0,fNrows,fNcols,0,fNcols);
+ ExpandTrackBuffer();
+ //set histogram values
+ for (Int_t i = 0; i<fNrows;i++)
+ for (Int_t j = 0; j<fNcols;j++)
+ his->Fill(i,j,GetTrackIDFast(i,j,level));
+ if (x1>=0) {
+ AliH2F *h2fsub = his->GetSubrange2d(x1,x2,y1,y2);
+ delete his;
+ his=h2fsub;
+ }
+ if (his==0) return 0;
+ if (option!=0) his->Draw(option);
+ else his->Draw();
+ return his;
+}
+
+TClonesArray * AliSimDigits::GenerTPCClonesArray(TClonesArray * arr)
+{
+ //
+ //generate TClonnesArray of digits
+ //
+ TClonesArray * digits;
+ if (arr==0) digits=new TClonesArray("AliTPCdigit",300);
+ else digits = arr;
+ Int_t index = digits->GetEntriesFast();
+ for (Int_t row =0; row<fNrows; row++)
+ for (Int_t col =0; col<fNcols; col++){
+ Int_t amp = GetDigit(row,col);
+ if (amp>GetThreshold()){
+ AliTPCdigit dig;
+ dig.fPad = col;
+ dig.fTime = row;
+ dig.fSignal= amp;
+ dig.fPadRow =fSegmentID;
+ dig.fSector =fSegmentID;
+ dig.fTracks[0]= GetTrackID(row,col,0);
+ dig.fTracks[1]= GetTrackID(row,col,1);
+ dig.fTracks[2]= GetTrackID(row,col,2);
+ TClonesArray &ldigits = *digits;
+ new(ldigits[index++]) AliTPCdigit(dig);
+ }
+ }
+ return digits;
+}
+
--- /dev/null
+#ifndef ALISIMDIGITS_H
+#define ALISIMDIGITS_H
+/* Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
+ * See cxx source for full Copyright notice */
+
+/* $Id$ */
+
+////////////////////////////////////////////////
+// Manager class generaol Alice segment digits
+// segment is for example one pad row in TPC //
+////////////////////////////////////////////////
+#include "TError.h"
+#include "AliArrayI.h"
+#include "AliArrayS.h"
+class AliH2F;
+
+
+class AliSimDigits : public AliDigits{
+public:
+ AliSimDigits();
+ ~AliSimDigits();
+ void AllocateTrack(Int_t length); //construct empty buffer fTracks with size rows x column x length (number of tracks for one digit)
+ inline Int_t GetTrackIDFast(Int_t row, Int_t column,Int_t level); //return track ID at given row and collumn
+ inline void SetTrackIDFast(Int_t value,Int_t row, Int_t column,Int_t level); //set ID track at given row and collumn
+ virtual Int_t GetTrackID(Int_t row, Int_t column, Int_t level);
+ virtual void ExpandTrackBuffer(); //expand buffer to twodimensional array
+ virtual void CompresTrackBuffer(Int_t bufType); //compres buffer according buffertype algorithm
+ AliH2F * DrawTracks( const char *option=0,Int_t level=0,
+ Float_t x1=-1, Float_t x2=-1, Float_t y1=-1, Float_t y2=-1); //draw tracks
+ TClonesArray * GenerTPCClonesArray(TClonesArray * arr); //generate TClonnesArray of digits
+ //only for demonstration purpose
+public:
+ void InvalidateTrack();
+
+ Int_t GetTrackID1(Int_t row, Int_t column, Int_t level); //returnb track ID of digits - for buffer compresion 1
+ void ExpandTrackBuffer1(); //comress track according algorithm 1 (track ID comression independent to the digit compression)
+ void CompresTrackBuffer1(); //comress track according algorithm 1 (track ID comression independent to the digit compression)
+
+ Int_t GetTrackID2(Int_t row, Int_t column, Int_t level); //returnb track ID of digits - for buffer compresion 2
+ void ExpandTrackBuffer2(); //comress track according algorithm 2 (track ID comression according digit compression)
+ void CompresTrackBuffer2(); //comress track according algorithm 2 (track ID comression according digit compression)
+
+ AliArrayI * fTracks; //buffer of track index
+ AliArrayI * fTrIndex; //index position of column
+ Int_t fNlevel; //number of tracks etries for one digit
+ Int_t fTrBufType; //buffer type of the tracks
+ // Bool_t ClassError( ); //signalize class error
+ ClassDef(AliSimDigits,1)
+};
+
+
+
+Int_t AliSimDigits::GetTrackIDFast(Int_t row, Int_t column,Int_t level)
+{
+ //
+ //return track ID at given row and column
+ // return fTracks[level].At(fTrIndex[level][column]+row);
+ return fTracks->At(level*fNrows*fNcols+fNrows*column+row);
+}
+
+void AliSimDigits::SetTrackIDFast(Int_t value,Int_t row, Int_t column,Int_t level)
+{
+value+=2;
+ //set ID track at given row and collumn
+ // fTracks[level][fTrIndex[level][column]+row]=value;
+ if ( (row<0) || (row>=fNrows) || (column<0) || (column>=fNcols) )
+ ::Error("AliSimDigits::SetTrackIDFast", "row %d col %d out of bounds (size: %d x %d, this: 0x%08x)",
+ row, column, fNrows, fNcols, this);
+ if ( (level<0) || (level>=fNlevel)) ::Error("AliSimDigits::SetTrackIDFast", "index %d out of bounds", level);
+ (*fTracks)[level*fNrows*fNcols+fNrows*column+row]=value;
+}
+
+
+
+#endif
/*
$Log$
+Revision 1.17.2.2 2000/04/10 08:15:12 kowal2
+
+New, experimental data structure from M. Ivanov
+New tracking algorithm
+Different pad geometry for different sectors
+Digitization rewritten
+
+Revision 1.17.2.1 2000/04/10 07:56:53 kowal2
+Not used anymore - removed
+
+Revision 1.17 2000/01/19 17:17:30 fca
+Introducing a list of lists of hits -- more hits allowed for detector now
+
Revision 1.16 1999/11/05 09:29:23 fca
Accept only signals > 0
#include <fstream.h>
#include "AliMC.h"
-//MI change
+
#include "AliTPCParam.h"
-#include "AliTPCD.h"
#include "AliTPCPRF2D.h"
#include "AliTPCRF1D.h"
+#include "AliDigits.h"
+#include "AliSimDigits.h"
+
+#include "AliTPCDigitsArray.h"
+#include "AliCluster.h"
+#include "AliClusters.h"
+#include "AliTPCClustersRow.h"
+#include "AliTPCClustersArray.h"
fNsectors = 0;
fNtracks = 0;
fNclusters= 0;
-
- fDigParam= new AliTPCD();
- fDigits = fDigParam->GetArray();
+ //MI changes
+ fDigitsArray = 0;
+ fClustersArray = 0;
+ fTPCParam = 0;
}
//_____________________________________________________________________________
//
// Initialise arrays of hits and digits
fHits = new TClonesArray("AliTPChit", 176);
- gAlice->AddHitList(fHits);
- // fDigits = new TClonesArray("AliTPCdigit",10000);
- //MI change
- fDigParam= new AliTPCD;
- fDigits = fDigParam->GetArray();
-
- AliTPCParam *fTPCParam = &(fDigParam->GetParam());
-
+ //MI change
+ fDigitsArray = 0;
+ fClustersArray= 0;
+ fTPCParam = 0;
//
// Initialise counters
- //
fClusters = 0;
fTracks = 0;
- fNsectors = fTPCParam->GetNSector();
+ fNsectors = 0;
fNtracks = 0;
fNclusters= 0;
- fDigitsIndex = new Int_t[fNsectors+1];
+
//
fIshunt = 0;
//
delete fDigits;
delete fClusters;
delete fTracks;
- delete fDigParam;
- if (fDigitsIndex) delete [] fDigitsIndex;
+ if (fDigitsArray!=0) delete fDigitsArray;
+ if (fClustersArray!=0) delete fClustersArray;
+
+ if (fTPCParam) delete fTPCParam;
}
//_____________________________________________________________________________
//
// Add a simulated cluster copy to the list
//
- if(!fClusters) fClusters=new TClonesArray("AliTPCcluster",10000);
+ if(!fClusters) fClusters=new TClonesArray("AliTPCcluster",900000);
TClonesArray &lclusters = *fClusters;
new(lclusters[fNclusters++]) AliTPCcluster(c);
}
-//_____________________________________________________________________________
-void AliTPC::AddDigit(Int_t *tracks, Int_t *digits)
-{
- //
- // Add a TPC digit to the list
- //
- // TClonesArray &ldigits = *fDigits;
- //MI change
- TClonesArray &ldigits = *fDigParam->GetArray();
- new(ldigits[fNdigits++]) AliTPCdigit(tracks,digits);
-}
-
//_____________________________________________________________________________
void AliTPC::AddHit(Int_t track, Int_t *vol, Float_t *hits)
{
//_____________________________________________________________________________
void AliTPC::BuildGeometry()
{
+
//
// Build TPC ROOT TNode geometry for the event display
//
const Double_t kDegrad=TMath::Pi()/180;
const Double_t kRaddeg=180./TMath::Pi();
- AliTPCParam * fTPCParam = &(fDigParam->GetParam());
Float_t InnerOpenAngle = fTPCParam->GetInnerAngle();
Float_t OuterOpenAngle = fTPCParam->GetOuterAngle();
// inner sectors
- rl = fTPCParam->GetInSecLowEdge();
- ru = fTPCParam->GetInSecUpEdge();
+ rl = fTPCParam->GetInnerRadiusLow();
+ ru = fTPCParam->GetInnerRadiusUp();
for(i=0;i<nLo;i++) {
// Outer sectors
- rl = fTPCParam->GetOuSecLowEdge();
- ru = fTPCParam->GetOuSecUpEdge();
+ rl = fTPCParam->GetOuterRadiusLow();
+ ru = fTPCParam->GetOuterRadiusUp();
for(i=0;i<nHi;i++) {
sprintf(name,"US%2.2d",i);
Node->SetLineColor(kColorTPC);
fNodes->Add(Node);
}
+
+
}
}
//_____________________________________________________________________________
-static int FindProlongation(AliTPCtrack& t, const AliTPCSector *sec,
- int s, int rf=0)
+static Int_t FindProlongation(AliTPCtrack& t, const AliTPCSector *sec,
+ Int_t s, Int_t rf=0)
{
//-----------------------------------------------------------------
// This function tries to find a track prolongation.
//
// Origin: Iouri Belikov, CERN, Jouri.Belikov@cern.ch
//-----------------------------------------------------------------
- const int ROWS_TO_SKIP=int(0.5*sec->GetNRows());
+ const Int_t ROWS_TO_SKIP=(t<10) ? 10 : Int_t(0.5*sec->GetNRows());
const Float_t MAX_CHI2=12.;
- int try_again=ROWS_TO_SKIP;
+ Int_t try_again=ROWS_TO_SKIP;
Double_t alpha=sec->GetAlpha();
- int ns=int(2*TMath::Pi()/alpha+0.5);
+ Int_t ns=Int_t(2*TMath::Pi()/alpha+0.5);
- for (int nr=sec->GetRowNumber(t.GetX())-1; nr>=rf; nr--) {
+ for (Int_t nr=sec->GetRowNumber(t.GetX())-1; nr>=rf; nr--) {
Double_t x=sec->GetX(nr), ymax=sec->GetMaxY(nr);
if (!t.PropagateTo(x)) return 0;
}
if (row) {
- for (int i=row.Find(y-road); i<row; i++) {
+ for (Int_t i=row.Find(y-road); i<row; i++) {
AliTPCcluster* c=(AliTPCcluster*)(row[i]);
if (c->fY > y+road) break;
if (c->IsUsed()) continue;
}
if (cl) {
t.Update(cl,max_chi2);
- Double_t ll=TMath::Sqrt((1+t.GetTgl()*t.GetTgl())/
+ cl->fdEdX=sec->GetPadPitchWidth()*TMath::Sqrt((1+t.GetTgl()*t.GetTgl())/
(1-(t.GetC()*x-t.GetEta())*(t.GetC()*x-t.GetEta())));
- cl->fdEdX = cl->fQ/ll;
try_again=ROWS_TO_SKIP;
} else {
if (try_again==0) break;
}
return 1;
+
}
//_____________________________________________________________________________
-static void MakeSeeds(TObjArray& seeds,const AliTPCSector *sec, int max_sec,
-int i1, int i2)
+static void MakeSeeds(TObjArray& seeds,const AliTPCSector *sec, Int_t max_sec,
+Int_t i1, Int_t i2)
{
//-----------------------------------------------------------------
// This function creates track seeds.
// Origin: Iouri Belikov, CERN, Jouri.Belikov@cern.ch
//-----------------------------------------------------------------
TMatrix C(5,5); TVector x(5);
- double alpha=sec->GetAlpha(), shift=sec->GetAlphaShift();
- double cs=cos(alpha), sn=sin(alpha);
- for (int ns=0; ns<max_sec; ns++) {
- int nl=sec[(ns-1+max_sec)%max_sec][i2];
- int nm=sec[ns][i2];
- int nu=sec[(ns+1)%max_sec][i2];
+ Double_t alpha=sec->GetAlpha(), shift=sec->GetAlphaShift();
+ Double_t cs=cos(alpha), sn=sin(alpha);
+ for (Int_t ns=0; ns<max_sec; ns++) {
+ Int_t nl=sec[(ns-1+max_sec)%max_sec][i2];
+ Int_t nm=sec[ns][i2];
+ Int_t nu=sec[(ns+1)%max_sec][i2];
const AliTPCRow& r1=sec[ns][i1];
- for (int is=0; is < r1; is++) {
- double x1=sec->GetX(i1), y1=r1[is]->fY, z1=r1[is]->fZ;
- for (int js=0; js < nl+nm+nu; js++) {
+ for (Int_t is=0; is < r1; is++) {
+ Double_t x1=sec->GetX(i1), y1=r1[is]->fY, z1=r1[is]->fZ;
+ for (Int_t js=0; js < nl+nm+nu; js++) {
const AliTPCcluster *cl;
- int ks;
- double x2=sec->GetX(i2), y2, z2, tmp;
+ Int_t ks;
+ Double_t x2=sec->GetX(i2), y2, z2, tmp;
if (js<nl) {
ks=(ns-1+max_sec)%max_sec;
y2 =x2*sn+y2*cs; x2=tmp;
}
- double d=(x2-x1)*(0.-y2)-(0.-x2)*(y2-y1);
+ Double_t zz=z1 - z1/x1*(x1-x2);
+ if (TMath::Abs(zz-z2)>5) continue;
+
+ Double_t d=(x2-x1)*(0.-y2)-(0.-x2)*(y2-y1);
if (d==0.) {cerr<<"MakeSeeds warning: Straight seed !\n"; continue;}
+ Double_t x3=0., y3=0.;//gRandom->Gaus(0.,TMath::Sqrt(cl->fSigmaY2));
+
x(0)=y1;
x(1)=z1;
- x(2)=f1(x1,y1,x2,y2,0.,0.);
- x(3)=f2(x1,y1,x2,y2,0.,0.);
+ x(2)=f1(x1,y1,x2,y2,x3,y3);
+ x(3)=f2(x1,y1,x2,y2,x3,y3);
x(4)=f3(x1,y1,x2,y2,z1,z2);
if (TMath::Abs(x(2)*x1-x(3)) >= 0.999) continue;
Double_t a=asin(x(3));
Double_t zv=z1 - x(4)/x(2)*(a+asin(x(2)*x1-x(3)));
- if (TMath::Abs(zv)>33.) continue;
+ if (TMath::Abs(zv)>10.) continue;
TMatrix X(6,6); X=0.;
X(0,0)=r1[is]->fSigmaY2; X(1,1)=r1[is]->fSigmaZ2;
X(2,2)=cl->fSigmaY2; X(3,3)=cl->fSigmaZ2;
- X(4,4)=3./12.; X(5,5)=3./12.;
+ X(4,4)=cl->fSigmaY2; X(5,5)=cl->fSigmaZ2;
+ //X(4,4)=3./12.; X(5,5)=3./12.;
TMatrix F(5,6); F.UnitMatrix();
Double_t sy=sqrt(X(0,0)), sz=sqrt(X(1,1));
- F(2,0)=(f1(x1,y1+sy,x2,y2,0.,0.)-x(2))/sy;
- F(2,2)=(f1(x1,y1,x2,y2+sy,0.,0.)-x(2))/sy;
- F(2,4)=(f1(x1,y1,x2,y2,0.,0.+sy)-x(2))/sy;
- F(3,0)=(f2(x1,y1+sy,x2,y2,0.,0.)-x(3))/sy;
- F(3,2)=(f2(x1,y1,x2,y2+sy,0.,0.)-x(3))/sy;
- F(3,4)=(f2(x1,y1,x2,y2,0.,0.+sy)-x(3))/sy;
+ F(2,0)=(f1(x1,y1+sy,x2,y2,x3,y3)-x(2))/sy;
+ F(2,2)=(f1(x1,y1,x2,y2+sy,x3,y3)-x(2))/sy;
+ F(2,4)=(f1(x1,y1,x2,y2,x3,y3+sy)-x(2))/sy;
+ F(3,0)=(f2(x1,y1+sy,x2,y2,x3,y3)-x(3))/sy;
+ F(3,2)=(f2(x1,y1,x2,y2+sy,x3,y3)-x(3))/sy;
+ F(3,4)=(f2(x1,y1,x2,y2,x3,y3+sy)-x(3))/sy;
F(4,0)=(f3(x1,y1+sy,x2,y2,z1,z2)-x(4))/sy;
F(4,1)=(f3(x1,y1,x2,y2,z1+sz,z2)-x(4))/sz;
F(4,2)=(f3(x1,y1,x2,y2+sy,z1,z2)-x(4))/sy;
C.Mult(t,TMatrix(TMatrix::kTransposed,F));
AliTPCtrack *track=new AliTPCtrack(r1[is], x, C, x1, ns*alpha+shift);
- int rc=FindProlongation(*track,sec,ns,i2);
+ Int_t rc=FindProlongation(*track,sec,ns,i2);
if (rc<0 || *track<(i1-i2)/2) delete track;
else seeds.AddLast(track);
}
//-----------------------------------------------------------------
if (!fClusters) return;
- AliTPCParam *p=&fDigParam->GetParam();
+ AliTPCParam *p=fTPCParam;
AliTPCSector::SetParam(p);
- const int nis=p->GetNInnerSector()/2;
+ const Int_t nis=p->GetNInnerSector()/2;
AliTPCSSector *ssec=new AliTPCSSector[nis];
- int nrow_low=ssec->GetNRows();
+ Int_t nrow_low=ssec->GetNRows();
- const int nos=p->GetNOuterSector()/2;
+ const Int_t nos=p->GetNOuterSector()/2;
AliTPCLSector *lsec=new AliTPCLSector[nos];
- int nrow_up=lsec->GetNRows();
+ Int_t nrow_up=lsec->GetNRows();
- int ncl=fClusters->GetEntriesFast();
+ Int_t ncl=fClusters->GetEntriesFast();
while (ncl--) {
AliTPCcluster *c=(AliTPCcluster*)fClusters->UncheckedAt(ncl);
Int_t sec=c->fSector, row=c->fPadRow;
+
if (sec<nis*2) {
ssec[sec%nis][row].InsertCluster(c);
} else {
TObjArray seeds(20000);
- int nrows=nrow_low+nrow_up;
- int gap=int(0.125*nrows), shift=int(0.5*gap);
+ Int_t nrows=nrow_low+nrow_up;
+ Int_t gap=Int_t(0.125*nrows), shift=Int_t(0.5*gap);
MakeSeeds(seeds, lsec, nos, nrow_up-1, nrow_up-1-gap);
MakeSeeds(seeds, lsec, nos, nrow_up-1-shift, nrow_up-1-shift-gap);
seeds.Sort();
-
- int found=0;
- int nseed=seeds.GetEntriesFast();
-
- for (int s=0; s<nseed; s++) {
- AliTPCtrack& t=*((AliTPCtrack*)seeds.UncheckedAt(s));
- double alpha=t.GetAlpha();
+
+ Int_t found=0;
+ Int_t nseed=seeds.GetEntriesFast();
+
+ for (Int_t s=0; s<nseed; s++) {
+ AliTPCtrack *pt=(AliTPCtrack*)seeds.UncheckedAt(s), &t=*pt;
+ Double_t alpha=t.GetAlpha();
if (alpha > 2.*TMath::Pi()) alpha -= 2.*TMath::Pi();
if (alpha < 0. ) alpha += 2.*TMath::Pi();
- int ns=int(alpha/lsec->GetAlpha())%nos;
+ Int_t ns=Int_t(alpha/lsec->GetAlpha())%nos;
if (!FindProlongation(t,lsec,ns)) continue;
alpha=t.GetAlpha() + 0.5*ssec->GetAlpha() - ssec->GetAlphaShift();
if (alpha > 2.*TMath::Pi()) alpha -= 2.*TMath::Pi();
if (alpha < 0. ) alpha += 2.*TMath::Pi();
- ns=int(alpha/ssec->GetAlpha())%nis; //index of the inner sector needed
+ ns=Int_t(alpha/ssec->GetAlpha())%nis; //index of the inner sector needed
alpha=ns*ssec->GetAlpha() - t.GetAlpha();
if (!t.Rotate(alpha)) continue;
-
- if (!FindProlongation(t,ssec,ns)) continue;
- if (t < int(0.4*nrows)) continue;
+ if (!FindProlongation(t,ssec,ns)) continue;
- AddTrack(t);
- t.UseClusters();
- cerr<<found++<<'\r';
+ if (t >= Int_t(0.4*nrows)) {
+ AddTrack(t);
+ t.UseClusters();
+ cerr<<found++<<'\r';
+ }
+ delete pt;
}
delete[] ssec;
delete[] lsec;
+
}
//_____________________________________________________________________________
AliMedium(12,"CO2",10,0, ISXFLD, SXMGMX, 10., 999.,.1, .001, .001);
-
-
}
//_____________________________________________________________________________
struct Bin {
- const AliTPCdigit *dig;
- int idx;
- Bin() {dig=0; idx=-1;}
+ UShort_t q;
+ UInt_t mask;
+ Bin();
};
+Bin::Bin() {q=0; mask=0xFFFFFFFE;}
-struct PreCluster : public AliTPCcluster {
- const AliTPCdigit* summit; //pointer to the maximum digit of this precluster
- int idx; //index in AliTPC::fClusters
- int npeaks; //number of peaks in this precluster
- int ndigits; //number of digits in this precluster
- PreCluster();
+struct Peak {
+ Int_t k;
+ UInt_t mask;
};
-PreCluster::PreCluster() : AliTPCcluster() {npeaks=ndigits=0;}
+inline Bool_t IsMaximum(Int_t k, Int_t max, const Bin *bins) {
+ UShort_t q=bins[k].q;
+ if (q==1023) return kFALSE;
+ if (bins[k-max].q > q) return kFALSE;
+ if (bins[k-1 ].q > q) return kFALSE;
+ if (bins[k+max].q > q) return kFALSE;
+ if (bins[k+1 ].q > q) return kFALSE;
+ if (bins[k-max-1].q > q) return kFALSE;
+ if (bins[k+max-1].q > q) return kFALSE;
+ if (bins[k+max+1].q > q) return kFALSE;
+ if (bins[k-max+1].q > q) return kFALSE;
+ return kTRUE;
+}
+static void FindPeaks(Int_t k, Int_t max, Bin *bins, Peak *peaks, Int_t& n) {
+//if (n>=31) return;
+ if (n<31)
+ if (IsMaximum(k,max,bins)) {
+ peaks[n].k=k; peaks[n].mask=(2<<n);
+ n++;
+ }
+ bins[k].mask=0;
+ if (bins[k-max].mask&1) FindPeaks(k-max,max,bins,peaks,n);
+ if (bins[k-1 ].mask&1) FindPeaks(k-1 ,max,bins,peaks,n);
+ if (bins[k+max].mask&1) FindPeaks(k+max,max,bins,peaks,n);
+ if (bins[k+1 ].mask&1) FindPeaks(k+1 ,max,bins,peaks,n);
+}
-//_____________________________________________________________________________
-static void FindPreCluster(int i,int j,int maxj,Bin *bins,PreCluster &c)
-{
- //-----------------------------------------------------------------
- // This function looks for "preclusters".
- //
- // Origin: Iouri Belikov, CERN, Jouri.Belikov@cern.ch
- //-----------------------------------------------------------------
- Bin& b=bins[i*maxj+j];
- double q=(double)TMath::Abs(b.dig->fSignal);
+static void MarkPeak(Int_t k, Int_t max, Bin *bins, UInt_t m) {
+ UShort_t q=bins[k].q;
- if (b.idx >= 0 && b.idx != c.idx) {
- c.idx=b.idx;
- c.npeaks++;
- }
-
- if (q > TMath::Abs(c.summit->fSignal)) c.summit=b.dig;
-
+ bins[k].mask |= m;
+
+ if (bins[k-max].q <= q)
+ if ((bins[k-max].mask&m) == 0) MarkPeak(k-max,max,bins,m);
+ if (bins[k-1 ].q <= q)
+ if ((bins[k-1 ].mask&m) == 0) MarkPeak(k-1 ,max,bins,m);
+ if (bins[k+max].q <= q)
+ if ((bins[k+max].mask&m) == 0) MarkPeak(k+max,max,bins,m);
+ if (bins[k+1 ].q <= q)
+ if ((bins[k+1 ].mask&m) == 0) MarkPeak(k+1 ,max,bins,m);
+}
+
+static void MakeCluster(Int_t k,Int_t max,Bin *bins,UInt_t m,AliTPCcluster &c){
+ Float_t q=(Float_t)bins[k].q;
+ Int_t i=k/max, j=k-i*max;
c.fY += i*q;
c.fZ += j*q;
c.fSigmaY2 += i*i*q;
c.fSigmaZ2 += j*j*q;
c.fQ += q;
- c.ndigits++;
- b.dig = 0; b.idx = c.idx;
-
- if (bins[(i-1)*maxj+j].dig) FindPreCluster(i-1,j,maxj,bins,c);
- if (bins[i*maxj+(j-1)].dig) FindPreCluster(i,j-1,maxj,bins,c);
- if (bins[(i+1)*maxj+j].dig) FindPreCluster(i+1,j,maxj,bins,c);
- if (bins[i*maxj+(j+1)].dig) FindPreCluster(i,j+1,maxj,bins,c);
+ bins[k].mask = 0xFFFFFFFE;
+ if (bins[k-max].mask == m) MakeCluster(k-max,max,bins,m,c);
+ if (bins[k-1 ].mask == m) MakeCluster(k-1 ,max,bins,m,c);
+ if (bins[k+max].mask == m) MakeCluster(k+max,max,bins,m,c);
+ if (bins[k+1 ].mask == m) MakeCluster(k+1 ,max,bins,m,c);
}
//_____________________________________________________________________________
//
// Origin: Iouri Belikov, CERN, Jouri.Belikov@cern.ch
//-----------------------------------------------------------------
- AliTPCParam *par = &(fDigParam->GetParam());
-
- int inp=par->GetNPads(0, par->GetNRowLow()-1);
- int onp=par->GetNPads(par->GetNSector()-1,par->GetNRowUp() -1);
- const int MAXY=(inp>onp) ? inp+2 : onp+2;
- const int MAXTBKT=int((z_end+6*par->GetZSigma())/par->GetZWidth())+1;
- const int MAXZ=MAXTBKT+2;
- const int THRESHOLD=20;
-
- TTree *t=(TTree*)gDirectory->Get("TreeD0_Param1");
- t->GetBranch("Digits")->SetAddress(&fDigits);
- Int_t sectors_by_rows=(Int_t)t->GetEntries();
-
- int ncls=0;
-
+ AliTPCParam *par = fTPCParam;
+ const Int_t MAXZ=par->GetMaxTBin()+2;
+
+ TTree *t = (TTree *)gDirectory->Get("TreeD_75x40_100x60");
+ AliSimDigits digarr, *dummy=&digarr;
+ t->GetBranch("Segment")->SetAddress(&dummy);
+ Stat_t sectors_by_rows = t->GetEntries();
for (Int_t n=0; n<sectors_by_rows; n++) {
- if (!t->GetEvent(n)) continue;
- Bin *bins=new Bin[MAXY*MAXZ];
- AliTPCdigit *dig=(AliTPCdigit*)fDigits->UncheckedAt(0);
- int sec=dig->fSector, row=dig->fPadRow;
- int ndigits=fDigits->GetEntriesFast();
-
- int npads, sign;
+ t->GetEvent(n);
+ Int_t sec, row;
+ if (!par->AdjustSectorRow(digarr.GetID(),sec,row)) {
+ cerr<<"AliTPC warning: invalid segment ID ! "<<digarr.GetID()<<endl;
+ continue;
+ }
+
+ Float_t rx=par->GetPadRowRadii(sec,row);
+
+ Int_t npads, sign;
{
- int nis=par->GetNInnerSector(), nos=par->GetNOuterSector();
+ Int_t nis=par->GetNInnerSector(), nos=par->GetNOuterSector();
if (sec < nis) {
npads = par->GetNPadsLow(row);
sign = (sec < nis/2) ? 1 : -1;
}
}
- int ndig;
- for (ndig=0; ndig<ndigits; ndig++) {
- dig=(AliTPCdigit*)fDigits->UncheckedAt(ndig);
- int i=dig->fPad+1, j=dig->fTime+1;
- if (i > npads) {
- cerr<<"AliTPC::Digits2Clusters error: pad number is out of range ! ";
- cerr<<i<<' '<<npads<<endl;
- continue;
- }
- if (j > MAXTBKT) {
- cerr<<"AliTPC::Digits2Clusters error: time bucket is out of range ! ";
- cerr<<j<<' '<<MAXTBKT<<endl;
- continue;
+ const Int_t MAXBIN=MAXZ*(npads+2);
+ Bin *bins=new Bin[MAXBIN];
+
+ digarr.First();
+ do {
+ Short_t dig=digarr.CurrentDigit();
+ if (dig<=par->GetZeroSup()) continue;
+ Int_t j=digarr.CurrentRow()+1, i=digarr.CurrentColumn()+1;
+ bins[i*MAXZ+j].q=dig;
+ bins[i*MAXZ+j].mask=1;
+ } while (digarr.Next());
+
+ Int_t ncl=0;
+ for (Int_t i=0; i<MAXBIN; i++) {
+ if ((bins[i].mask&1) == 0) continue;
+ Peak peaks[32]; Int_t npeaks=0;
+ FindPeaks(i, MAXZ, bins, peaks, npeaks);
+
+ if (npeaks>30) continue;
+
+ Int_t k,l;
+ for (k=0; k<npeaks-1; k++){//mark adjacent peaks
+ if (peaks[k].k < 0) continue; //this peak is already removed
+ for (l=k+1; l<npeaks; l++) {
+ if (peaks[l].k < 0) continue; //this peak is already removed
+ Int_t ki=peaks[k].k/MAXZ, kj=peaks[k].k - ki*MAXZ;
+ Int_t li=peaks[l].k/MAXZ, lj=peaks[l].k - li*MAXZ;
+ Int_t di=TMath::Abs(ki - li);
+ Int_t dj=TMath::Abs(kj - lj);
+ if (di>1 || dj>1) continue;
+ if (bins[peaks[k].k].q > bins[peaks[l].k].q) {
+ peaks[l].mask=peaks[k].mask;
+ peaks[l].k*=-1;
+ } else {
+ peaks[k].mask=peaks[l].mask;
+ peaks[k].k*=-1;
+ break;
+ }
+ }
}
- if (dig->fSignal >= THRESHOLD) bins[i*MAXZ+j].dig=dig;
- if (i==1 || i==npads || j==1 || j==MAXTBKT) dig->fSignal*=-1;
- }
- int ncl=0;
- int i,j;
-
- for (i=1; i<MAXY-1; i++) {
- for (j=1; j<MAXZ-1; j++) {
- if (bins[i*MAXZ+j].dig == 0) continue;
- PreCluster c; c.summit=bins[i*MAXZ+j].dig; c.idx=ncls;
- FindPreCluster(i, j, MAXZ, bins, c);
- c.fY /= c.fQ;
- c.fZ /= c.fQ;
-
- double s2 = c.fSigmaY2/c.fQ - c.fY*c.fY;
- c.fSigmaY2 = s2 + 1./12.;
- c.fSigmaY2 *= par->GetPadPitchWidth()*par->GetPadPitchWidth();
- if (s2 != 0.) c.fSigmaY2 *= 0.17;
-
- s2 = c.fSigmaZ2/c.fQ - c.fZ*c.fZ;
- c.fSigmaZ2 = s2 + 1./12.;
- c.fSigmaZ2 *= par->GetZWidth()*par->GetZWidth();
- if (s2 != 0.) c.fSigmaZ2 *= 0.41;
-
- c.fY = (c.fY - 0.5 - 0.5*npads)*par->GetPadPitchWidth();
- c.fZ = par->GetZWidth()*c.fZ;
- c.fZ -= 3.*par->GetZSigma(); // PASA delay
- c.fZ = sign*(z_end - c.fZ);
-
- c.fSector=sec;
- c.fPadRow=row;
- c.fTracks[0]=c.summit->fTracks[0];
- c.fTracks[1]=c.summit->fTracks[1];
- c.fTracks[2]=c.summit->fTracks[2];
-
- if (c.summit->fSignal<0) {
- c.fSigmaY2 *= 25.;
- c.fSigmaZ2 *= 4.;
- }
-
- AddCluster(c); ncls++; ncl++;
+ for (k=0; k<npeaks; k++) {
+ MarkPeak(TMath::Abs(peaks[k].k), MAXZ, bins, peaks[k].mask);
}
- }
- for (ndig=0; ndig<ndigits; ndig++) {
- dig=(AliTPCdigit*)fDigits->UncheckedAt(ndig);
- int i=dig->fPad+1, j=dig->fTime+1;
- if (i > npads) {
- cerr<<"AliTPC::Digits2Clusters error: pad number is out of range ! ";
- cerr<<i<<' '<<npads<<endl;
- continue;
- }
- if (j > MAXTBKT) {
- cerr<<"AliTPC::Digits2Clusters error: time bucket is out of range ! ";
- cerr<<j<<' '<<MAXTBKT<<endl;
- continue;
+ for (k=0; k<npeaks; k++) {
+ if (peaks[k].k < 0) continue; //removed peak
+ AliTPCcluster c;
+ MakeCluster(peaks[k].k, MAXZ, bins, peaks[k].mask, c);
+ if (c.fQ < 5) continue; //noise cluster
+ c.fY /= c.fQ;
+ c.fZ /= c.fQ;
+
+ Double_t s2 = c.fSigmaY2/c.fQ - c.fY*c.fY;
+ c.fSigmaY2 = s2 + 1./12.;
+ c.fSigmaY2 *= par->GetPadPitchWidth(sec)*par->GetPadPitchWidth(sec);
+ if (s2 != 0.) {
+ c.fSigmaY2 *= 0.064*1.3*1.3;
+ if (sec<par->GetNInnerSector()) c.fSigmaY2 *= 1.44*1.44;
+ }
+
+ s2 = c.fSigmaZ2/c.fQ - c.fZ*c.fZ;
+ c.fSigmaZ2 = s2 + 1./12.;
+ c.fSigmaZ2 *= par->GetZWidth()*par->GetZWidth();
+ if (s2 != 0.) {
+ c.fSigmaZ2 *= 0.10*1.3*1.3;
+ if (sec<par->GetNInnerSector()) c.fSigmaZ2 *= 1.33*1.33;
+ }
+
+ c.fY = (c.fY - 0.5 - 0.5*npads)*par->GetPadPitchWidth(sec);
+ c.fZ = par->GetZWidth()*(c.fZ-1);
+ c.fZ -= 3.*par->GetZSigma(); // PASA delay
+ c.fZ = sign*(z_end - c.fZ);
+
+ if (rx<230./250.*TMath::Abs(c.fZ)) continue;
+
+ c.fSector=sec;
+ c.fPadRow=row;
+ Int_t ki=peaks[k].k/MAXZ, kj=peaks[k].k - ki*MAXZ;
+ c.fTracks[0]=digarr.GetTrackID(kj-1,ki-1,0);
+ c.fTracks[1]=digarr.GetTrackID(kj-1,ki-1,1);
+ c.fTracks[2]=digarr.GetTrackID(kj-1,ki-1,2);
+
+ c.fQ=bins[peaks[k].k].q;
+
+ if (ki==1 || ki==npads || kj==1 || kj==MAXZ-2) {
+ c.fSigmaY2 *= 25.;
+ c.fSigmaZ2 *= 4.;
+ }
+
+ AddCluster(c); ncl++;
}
- if (TMath::Abs(dig->fSignal)>=par->GetZeroSup()) bins[i*MAXZ+j].dig=dig;
}
-
- for (i=1; i<MAXY-1; i++) {
- for (j=1; j<MAXZ-1; j++) {
- if (bins[i*MAXZ+j].dig == 0) continue;
- PreCluster c; c.summit=bins[i*MAXZ+j].dig; c.idx=ncls;
- FindPreCluster(i, j, MAXZ, bins, c);
- if (c.ndigits < 2) continue; //noise cluster
- if (c.npeaks>1) continue; //overlapped cluster
- c.fY /= c.fQ;
- c.fZ /= c.fQ;
-
- double s2 = c.fSigmaY2/c.fQ - c.fY*c.fY;
- c.fSigmaY2 = s2 + 1./12.;
- c.fSigmaY2 *= par->GetPadPitchWidth()*par->GetPadPitchWidth();
- if (s2 != 0.) c.fSigmaY2 *= 0.04;
-
- s2 = c.fSigmaZ2/c.fQ - c.fZ*c.fZ;
- c.fSigmaZ2 = s2 + 1./12.;
- c.fSigmaZ2 *= par->GetZWidth()*par->GetZWidth();
- if (s2 != 0.) c.fSigmaZ2 *= 0.10;
-
- c.fY = (c.fY - 0.5 - 0.5*npads)*par->GetPadPitchWidth();
- c.fZ = par->GetZWidth()*c.fZ;
- c.fZ -= 3.*par->GetZSigma(); // PASA delay
- c.fZ = sign*(z_end - c.fZ);
-
- c.fSector=sec;
- c.fPadRow=row;
- c.fTracks[0]=c.summit->fTracks[0];
- c.fTracks[1]=c.summit->fTracks[1];
- c.fTracks[2]=c.summit->fTracks[2];
-
- if (c.summit->fSignal<0) {
- c.fSigmaY2 *= 25.;
- c.fSigmaZ2 *= 4.;
- }
- if (c.npeaks==0) {AddCluster(c); ncls++; ncl++;}
- else {
- new ((*fClusters)[c.idx]) AliTPCcluster(c);
- }
- }
- }
-
- cerr<<"sector, row, digits, clusters: "
- <<sec<<' '<<row<<' '<<ndigits<<' '<<ncl<<" \r";
-
- fDigits->Clear();
-
+ cerr<<"sector, row, compressed digits, clusters: "
+ <<sec<<' '<<row<<' '<<digarr.GetSize()<<' '<<ncl<<" \r";
+
delete[] bins;
}
}
-//_____________________________________________________________________________
-void AliTPC::ElDiff(Float_t *xyz)
-{
- //--------------------------------------------------
- // calculates the diffusion of a single electron
- //--------------------------------------------------
-
- //-----------------------------------------------------------------
- // Origin: Marek Kowalski IFJ, Krakow, Marek.Kowalski@ifj.edu.pl
- //-----------------------------------------------------------------
- AliTPCParam * fTPCParam = &(fDigParam->GetParam());
- Float_t driftl;
-
- Float_t z0=xyz[2];
-
- driftl=z_end-TMath::Abs(xyz[2]);
-
- if(driftl<0.01) driftl=0.01;
-
- // check the attachment
-
- driftl=TMath::Sqrt(driftl);
-
- // Float_t sig_t = driftl*diff_t;
- //Float_t sig_l = driftl*diff_l;
- Float_t sig_t = driftl*fTPCParam->GetDiffT();
- Float_t sig_l = driftl*fTPCParam->GetDiffL();
- xyz[0]=gRandom->Gaus(xyz[0],sig_t);
- xyz[1]=gRandom->Gaus(xyz[1],sig_t);
- xyz[2]=gRandom->Gaus(xyz[2],sig_l);
-
- if (TMath::Abs(xyz[2])>z_end){
- xyz[2]=TMath::Sign(z_end,z0);
- }
- if(xyz[2]*z0 < 0.){
- Float_t eps = 0.0001;
- xyz[2]=TMath::Sign(eps,z0);
- }
-}
-
//_____________________________________________________________________________
void AliTPC::Hits2Clusters()
{
// Origin: Marek Kowalski IFJ, Krakow, Marek.Kowalski@ifj.edu.pl
//-----------------------------------------------------------------
- AliTPCParam * fTPCParam = &(fDigParam->GetParam());
+ if(fTPCParam == 0){
+ printf("AliTPCParam MUST be created firstly\n");
+ return;
+ }
+
Float_t sigma_rphi,sigma_z,cl_rphi,cl_z;
//
TParticle *particle; // pointer to a given particle
TTree *TH = gAlice->TreeH();
Stat_t ntracks = TH->GetEntries();
- Particles=gAlice->Particles();
//------------------------------------------------------------
- // Loop over all sectors (72 sectors)
- // Sectors 0-35 are lower sectors, 0-17 z>0, 18-35 z<0
+ // Loop over all sectors (72 sectors for 20 deg
+ // segmentation for both lower and upper sectors)
+ // Sectors 0-35 are lower sectors, 0-17 z>0, 17-35 z<0
// Sectors 36-71 are upper sectors, 36-53 z>0, 54-71 z<0
//
// First cluster for sector 0 starts at "0"
//------------------------------------------------------------
-
-
- //
- int Nsectors=fDigParam->GetParam().GetNSector();
- for(Int_t isec=0; isec<Nsectors; isec++){
+
+ for(Int_t isec=0;isec<fTPCParam->GetNSector();isec++){
//MI change
- fTPCParam->AdjustAngles(isec,cph,sph);
+ fTPCParam->AdjustCosSin(isec,cph,sph);
//------------------------------------------------------------
// Loop over tracks
// to the particles
//
nhits=fHits->GetEntriesFast();
+ Particles=gAlice->Particles();
//
// Loop over hits
//
for(Int_t hit=0;hit<nhits;hit++){
tpcHit=(AliTPChit*)fHits->UncheckedAt(hit);
+ if (tpcHit->fQ == 0.) continue; //information about track (I.Belikov)
sector=tpcHit->fSector; // sector number
if(sector != isec) continue; //terminate iteration
ipart=tpcHit->fTrack;
if(cl_z < 0.) cl_z=2.5e-5;
//
- // smearing --> rotate sectors firstly,
+
+ //
+ // smearing --> rotate to the 1 (13) or to the 25 (49) sector,
// then the inaccuracy in a X-Y plane is only along Y (pad row)!
//
- Float_t xprim= tpcHit->fX*cph + tpcHit->fY*sph;
+ //Float_t xprim= tpcHit->fX*cph + tpcHit->fY*sph;
Float_t yprim=-tpcHit->fX*sph + tpcHit->fY*cph;
xyz[0]=gRandom->Gaus(yprim,TMath::Sqrt(sigma_rphi)); // y
- Double_t alpha=(sector < fTPCParam->GetNInnerSector()) ?
- fTPCParam->GetInnerAngle() : fTPCParam->GetOuterAngle();
- if (TMath::Abs(xyz[0]/xprim) > TMath::Tan(0.5*alpha)) xyz[0]=yprim;
xyz[1]=gRandom->Gaus(tpcHit->fZ,TMath::Sqrt(sigma_z)); // z
- if (TMath::Abs(xyz[1]) > 250) xyz[1]=tpcHit->fZ;
- xyz[2]=tpcHit->fQ+1;// q; let it be not equal to zero (Y.Belikov)
+ xyz[2]=tpcHit->fQ; // q
xyz[3]=sigma_rphi; // fSigmaY2
xyz[4]=sigma_z; // fSigmaZ2
-
- // and finally add the cluster
- Int_t tracks[5]={tpcHit->fTrack, -1, -1, sector, tpcHit->fPadRow};
+
+ Int_t tracks[5]={tpcHit->fTrack, -1, -1, sector, tpcHit->fPadRow};
AddCluster(xyz,tracks);
} // end of loop over hits
- } // end of loop over tracks
+ } // end of loop over tracks
-
- } // end of loop over sectors
+ } // end of loop over sectors
+
+} // end of function
+
+//_________________________________________________________________
+void AliTPC::Hits2ExactClustersSector(Int_t isec)
+{
+ //--------------------------------------------------------
+ //calculate exact cross point of track and given pad row
+ //resulting values are expressed in "digit" coordinata
+ //--------------------------------------------------------
+
+ //-----------------------------------------------------------------
+ // Origin: Marian Ivanov GSI Darmstadt, m.ivanov@gsi.de
+ //-----------------------------------------------------------------
+ //
+ if (fClustersArray==0){
+ return;
+ }
+ //
+ TParticle *particle; // pointer to a given particle
+ AliTPChit *tpcHit; // pointer to a sigle TPC hit
+ TClonesArray *Particles; //pointer to the particle list
+ Int_t sector,nhits;
+ Int_t ipart;
+ const Int_t cmaxhits=30000;
+ TVector * xxxx = new TVector(cmaxhits*4);
+ TVector & xxx = *xxxx;
+ Int_t maxhits = cmaxhits;
+ //construct array for each padrow
+ for (Int_t i=0; i<fTPCParam->GetNRow(isec);i++)
+ fClustersArray->CreateRow(isec,i);
+ //---------------------------------------------------------------
+ // Get the access to the tracks
+ //---------------------------------------------------------------
+
+ TTree *TH = gAlice->TreeH();
+ Stat_t ntracks = TH->GetEntries();
+ Particles=gAlice->Particles();
+ Int_t npart = Particles->GetEntriesFast();
+
+ //------------------------------------------------------------
+ // Loop over tracks
+ //------------------------------------------------------------
+ for(Int_t track=0;track<ntracks;track++){
+ ResetHits();
+ TH->GetEvent(track);
+ //
+ // Get number of the TPC hits and a pointer
+ // to the particles
+ //
+ nhits=fHits->GetEntriesFast();
+ //
+ // Loop over hits
+ //
+ Int_t currentIndex=0;
+ Int_t lastrow=-1; //last writen row
+ for(Int_t hit=0;hit<nhits;hit++){
+ tpcHit=(AliTPChit*)fHits->UncheckedAt(hit);
+ if (tpcHit==0) continue;
+ sector=tpcHit->fSector; // sector number
+ if(sector != isec) continue;
+ ipart=tpcHit->fTrack;
+ if (ipart<npart) particle=(TParticle*)Particles->UncheckedAt(ipart);
+
+ //find row number
+
+ Float_t x[3]={tpcHit->fX,tpcHit->fY,tpcHit->fZ};
+ Int_t index[3]={1,isec,0};
+ Int_t currentrow = fTPCParam->GetPadRow(x,index) ;
+ if (currentrow<0) continue;
+ if (lastrow<0) lastrow=currentrow;
+ if (currentrow==lastrow){
+ if ( currentIndex>=maxhits){
+ maxhits+=cmaxhits;
+ xxx.ResizeTo(4*maxhits);
+ }
+ xxx(currentIndex*4)=x[0];
+ xxx(currentIndex*4+1)=x[1];
+ xxx(currentIndex*4+2)=x[2];
+ xxx(currentIndex*4+3)=tpcHit->fQ;
+ currentIndex++;
+ }
+ else
+ if (currentIndex>2){
+ Float_t sumx=0;
+ Float_t sumx2=0;
+ Float_t sumx3=0;
+ Float_t sumx4=0;
+ Float_t sumy=0;
+ Float_t sumxy=0;
+ Float_t sumx2y=0;
+ Float_t sumz=0;
+ Float_t sumxz=0;
+ Float_t sumx2z=0;
+ Float_t sumq=0;
+ for (Int_t index=0;index<currentIndex;index++){
+ Float_t x,x2,x3,x4;
+ x=x2=x3=x4=xxx(index*4);
+ x2*=x;
+ x3*=x2;
+ x4*=x3;
+ sumx+=x;
+ sumx2+=x2;
+ sumx3+=x3;
+ sumx4+=x4;
+ sumy+=xxx(index*4+1);
+ sumxy+=xxx(index*4+1)*x;
+ sumx2y+=xxx(index*4+1)*x2;
+ sumz+=xxx(index*4+2);
+ sumxz+=xxx(index*4+2)*x;
+ sumx2z+=xxx(index*4+2)*x2;
+ sumq+=xxx(index*4+3);
+ }
+ Float_t CentralPad = (fTPCParam->GetNPads(isec,lastrow)-1)/2;
+ Float_t det=currentIndex*(sumx2*sumx4-sumx3*sumx3)-sumx*(sumx*sumx4-sumx2*sumx3)+
+ sumx2*(sumx*sumx3-sumx2*sumx2);
+
+ Float_t detay=sumy*(sumx2*sumx4-sumx3*sumx3)-sumx*(sumxy*sumx4-sumx2y*sumx3)+
+ sumx2*(sumxy*sumx3-sumx2y*sumx2);
+ Float_t detaz=sumz*(sumx2*sumx4-sumx3*sumx3)-sumx*(sumxz*sumx4-sumx2z*sumx3)+
+ sumx2*(sumxz*sumx3-sumx2z*sumx2);
+
+ Float_t detby=currentIndex*(sumxy*sumx4-sumx2y*sumx3)-sumy*(sumx*sumx4-sumx2*sumx3)+
+ sumx2*(sumx*sumx2y-sumx2*sumxy);
+ Float_t detbz=currentIndex*(sumxz*sumx4-sumx2z*sumx3)-sumz*(sumx*sumx4-sumx2*sumx3)+
+ sumx2*(sumx*sumx2z-sumx2*sumxz);
+
+ Float_t y=detay/det+CentralPad;
+ Float_t z=detaz/det;
+ Float_t by=detby/det; //y angle
+ Float_t bz=detbz/det; //z angle
+ sumy/=Float_t(currentIndex);
+ sumz/=Float_t(currentIndex);
+ AliCluster cl;
+ cl.fX=z;
+ cl.fY=y;
+ cl.fQ=sumq;
+ cl.fSigmaX2=bz;
+ cl.fSigmaY2=by;
+ cl.fTracks[0]=ipart;
+
+ AliTPCClustersRow * row = (fClustersArray->GetRow(isec,lastrow));
+ if (row!=0) row->InsertCluster(&cl);
+ currentIndex=0;
+ lastrow=currentrow;
+ } //end of calculating cluster for given row
+
+
+
+ } // end of loop over hits
+ } // end of loop over tracks
+ //write padrows to tree
+ for (Int_t ii=0; ii<fTPCParam->GetNRow(isec);ii++) {
+ fClustersArray->StoreRow(isec,ii);
+ fClustersArray->ClearRow(isec,ii);
+ }
+ xxxx->Delete();
+
}
-
+//__________________________________________________________________
void AliTPC::Hits2Digits()
{
-
//----------------------------------------------------
- // Loop over all sectors (72 sectors)
- // Sectors 0-35 are lower sectors, 0-17 z>0, 18-35 z<0
- // Sectors 36-71 are upper sectors, 36-53 z>0, 54-71 z<0
- //----
- int Nsectors=fDigParam->GetParam().GetNSector();
- for(Int_t isec=0;isec<Nsectors;isec++) Hits2DigitsSector(isec);
+ // Loop over all sectors
+ //----------------------------------------------------
+
+ if(fTPCParam == 0){
+ printf("AliTPCParam MUST be created firstly\n");
+ return;
+ }
+
+ for(Int_t isec=0;isec<fTPCParam->GetNSector();isec++) Hits2DigitsSector(isec);
+
}
// Get the access to the track hits
//-------------------------------------------------------
- AliTPCParam * fTPCParam = &(fDigParam->GetParam());
+
TTree *TH = gAlice->TreeH(); // pointer to the hits tree
Stat_t ntracks = TH->GetEntries();
// Only if there are any tracks...
//-------------------------------------------
-
- // TObjArrays for three neighouring pad-rows
-
- TObjArray **rowTriplet = new TObjArray* [3];
-
- // TObjArray-s for each pad-row
-
TObjArray **row;
-
- for (Int_t trip=0;trip<3;trip++){
- rowTriplet[trip]=new TObjArray;
- }
-
-
printf("*** Processing sector number %d ***\n",isec);
Int_t i;
- for (i=0;i<nrows;i++){
-
- // Triplets for i = 0 and i=1 are identical!
- // The same for i = nrows-1 and nrows!
+ if (fDigitsArray->GetTree()==0) fDigitsArray->MakeTree();
- if(i != 1 && i != nrows-1){
- MakeTriplet(i,rowTriplet,row);
- }
+ for (i=0;i<nrows;i++){
- DigitizeRow(i,isec,rowTriplet);
+ AliDigits * dig = fDigitsArray->CreateRow(isec,i);
- fDigParam->Fill();
+ DigitizeRow(i,isec,row);
- Int_t ndig=fDigParam->GetArray()->GetEntriesFast();
+ fDigitsArray->StoreRow(isec,i);
- printf("*** Sector, row, digits %d %d %d ***\n",isec,i,ndig);
+ Int_t ndig = dig->GetSize();
+
+ printf("*** Sector, row, compressed digits %d %d %d ***\n",isec,i,ndig);
+
+ fDigitsArray->ClearRow(isec,i);
- ResetDigits(); // reset digits for this row after storing them
-
+
} // end of the sector digitization
-
- // delete the last triplet
- for (i=0;i<3;i++) rowTriplet[i]->Delete();
-
+ for(i=0;i<nrows;i++){
+ row[i]->Delete();
+ }
+
delete [] row; // delete the array of pointers to TObjArray-s
} // ntracks >0
-} // end of Hits2Digits
-//_____________________________________________________________________________
-void AliTPC::MakeTriplet(Int_t row,
- TObjArray **rowTriplet, TObjArray **prow)
-{
- //------------------------------------------------------------------
- // Makes the "triplet" of the neighbouring pad-row for the
- // digitization including the cross-talk between the pad-rows
- //------------------------------------------------------------------
- //-----------------------------------------------------------------
- // Origin: Marek Kowalski IFJ, Krakow, Marek.Kowalski@ifj.edu.pl
- //-----------------------------------------------------------------
+} // end of Hits2DigitsSector
- AliTPCParam * fTPCParam = &(fDigParam->GetParam());
- Float_t gasgain = fTPCParam->GetGasGain();
- Int_t nTracks[3];
- Int_t nElements,nElectrons;
-
- TVector *pv;
- TVector *tv;
-
- //-------------------------------------------------------------------
- // pv is an "old" track, i.e. label + triplets of (x,y,z)
- // for each electron
- //
- //-------------------------------------------------------------------
-
-
- Int_t i1,i2;
- Int_t nel,nt;
-
- if(row == 0 || row == 1){
-
- // create entire triplet for the first AND the second row
-
- nTracks[0] = prow[0]->GetEntries();
- nTracks[1] = prow[1]->GetEntries();
- nTracks[2] = prow[2]->GetEntries();
-
- for(i1=0;i1<3;i1++){
- nt = nTracks[i1]; // number of tracks for this row
-
- for(i2=0;i2<nt;i2++){
- pv = (TVector*)prow[i1]->At(i2);
- TVector &v1 = *pv;
- nElements = pv->GetNrows();
- nElectrons = (nElements-1)/3;
-
- tv = new TVector(4*nElectrons+1); // create TVector for a modified track
- TVector &v2 = *tv;
- v2(0)=v1(0); //track label
-
- for(nel=0;nel<nElectrons;nel++){
- Int_t idx1 = nel*3;
- Int_t idx2 = nel*4;
- // Avalanche, including fluctuations
- Int_t aval = (Int_t) (-gasgain*TMath::Log(gRandom->Rndm()));
- v2(idx2+1)= v1(idx1+1);
- v2(idx2+2)= v1(idx1+2);
- v2(idx2+3)= v1(idx1+3);
- v2(idx2+4)= (Float_t)aval; // in number of electrons!
- } // end of loop over electrons
- //
- // Add this track to a row
- //
-
- rowTriplet[i1]->Add(tv);
-
-
- } // end of loop over tracks for this row
-
- prow[i1]->Delete(); // remove "old" tracks
- delete prow[i1]; // delete TObjArray for this row
- prow[i1]=0; // set pointer to NULL
-
- } // end of loop over row triplets
-
-
- }
- else{
-
- rowTriplet[0]->Delete(); // remove old lower row
-
- nTracks[0]=rowTriplet[1]->GetEntries(); // previous middle row
- nTracks[1]=rowTriplet[2]->GetEntries(); // previous upper row
- nTracks[2]=prow[row+1]->GetEntries(); // next row
-
-
- //-------------------------------------------
- // shift new tracks downwards
- //-------------------------------------------
-
- for(i1=0;i1<nTracks[0];i1++){
- pv=(TVector*)rowTriplet[1]->At(i1);
- rowTriplet[0]->Add(pv);
- }
-
- rowTriplet[1]->Clear(); // leave tracks on the heap!!!
-
- for(i1=0;i1<nTracks[1];i1++){
- pv=(TVector*)rowTriplet[2]->At(i1);
- rowTriplet[1]->Add(pv);
- }
-
- rowTriplet[2]->Clear(); // leave tracks on the heap!!!
-
- //---------------------------------------------
- // Create new upper row
- //---------------------------------------------
-
-
-
- for(i1=0;i1<nTracks[2];i1++){
- pv = (TVector*)prow[row+1]->At(i1);
- TVector &v1 = *pv;
- nElements = pv->GetNrows();
- nElectrons = (nElements-1)/3;
-
- tv = new TVector(4*nElectrons+1); // create TVector for a modified track
- TVector &v2 = *tv;
- v2(0)=v1(0); //track label
-
- for(nel=0;nel<nElectrons;nel++){
-
- Int_t idx1 = nel*3;
- Int_t idx2 = nel*4;
- // Avalanche, including fluctuations
- Int_t aval = (Int_t)
- (-gasgain*TMath::Log(gRandom->Rndm()));
-
- v2(idx2+1)= v1(idx1+1);
- v2(idx2+2)= v1(idx1+2);
- v2(idx2+3)= v1(idx1+3);
- v2(idx2+4)= (Float_t)aval; // in number of electrons!
- } // end of loop over electrons
-
- rowTriplet[2]->Add(tv);
-
- } // end of loop over tracks
-
- prow[row+1]->Delete(); // delete tracks for this row
- delete prow[row+1]; // delete TObjArray for this row
- prow[row+1]=0; // set a pointer to NULL
-
- }
-
-} // end of MakeTriplet
-//_____________________________________________________________________________
-void AliTPC::ExB(Float_t *xyz)
-{
- //------------------------------------------------
- // ExB at the wires and wire number calulation
- //------------------------------------------------
-
- //-----------------------------------------------------------------
- // Origin: Marek Kowalski IFJ, Krakow, Marek.Kowalski@ifj.edu.pl
- //-----------------------------------------------------------------
- AliTPCParam * fTPCParam = &(fDigParam->GetParam());
-
- Float_t x1=xyz[0];
- fTPCParam->GetWire(x1); //calculate nearest wire position
- Float_t dx=xyz[0]-x1;
- xyz[1]+=dx*fTPCParam->GetOmegaTau();
-
-} // end of ExB
//_____________________________________________________________________________
-void AliTPC::DigitizeRow(Int_t irow,Int_t isec,TObjArray **rowTriplet)
+void AliTPC::DigitizeRow(Int_t irow,Int_t isec,TObjArray **rows)
{
//-----------------------------------------------------------
// Single row digitization, coupling from the neighbouring
//-----------------------------------------------------------------
// Origin: Marek Kowalski IFJ, Krakow, Marek.Kowalski@ifj.edu.pl
+ // Modified: Marian Ivanov GSI Darmstadt, m.ivanov@gsi.de
//-----------------------------------------------------------------
- AliTPCParam * fTPCParam = &(fDigParam->GetParam());
- Float_t chipgain= fTPCParam->GetChipGain();
Float_t zerosup = fTPCParam->GetZeroSup();
Int_t nrows =fTPCParam->GetNRow(isec);
- const int MAXTBKT=
- int((z_end+6*fTPCParam->GetZSigma())/fTPCParam->GetZWidth())+1;
+ fCurrentIndex[1]= isec;
- Int_t nTracks[3];
- Int_t n_of_pads[3];
- Int_t IndexRange[4];
- Int_t i1;
- Int_t iFlag;
-
- //
- // iFlag = 0 -> inner row, iFlag = 1 -> the middle one, iFlag = 2 -> the outer one
- //
- nTracks[0]=rowTriplet[0]->GetEntries(); // lower row
- nTracks[1]=rowTriplet[1]->GetEntries(); // middle row
- nTracks[2]=rowTriplet[2]->GetEntries(); // upper row
-
-
- if(irow == 0){
- iFlag=0;
- n_of_pads[0]=fTPCParam->GetNPads(isec,0);
- n_of_pads[1]=fTPCParam->GetNPads(isec,1);
- }
- else if(irow == nrows-1){
- iFlag=2;
- n_of_pads[1]=fTPCParam->GetNPads(isec,irow-1);
- n_of_pads[2]=fTPCParam->GetNPads(isec,irow);
- }
- else {
- iFlag=1;
- for(i1=0;i1<3;i1++){
- n_of_pads[i1]=fTPCParam->GetNPads(isec,irow-1+i1);
- }
- }
-
+ Int_t n_of_pads = fTPCParam->GetNPads(isec,irow);
+ Int_t n_of_tbins = fTPCParam->GetMaxTBin();
+ Int_t IndexRange[4];
//
// Integrated signal for this row
// and a single track signal
- //
-
- TMatrix *m1 = new TMatrix(0,n_of_pads[iFlag]-1,0,MAXTBKT-1); // integrated
- TMatrix *m2 = new TMatrix(0,n_of_pads[iFlag]-1,0,MAXTBKT-1); // single
-
+ //
+ TMatrix *m1 = new TMatrix(0,n_of_pads,0,n_of_tbins); // integrated
+ TMatrix *m2 = new TMatrix(0,n_of_pads,0,n_of_tbins); // single
//
-
TMatrix &Total = *m1;
// Array of pointers to the label-signal list
- Int_t NofDigits = n_of_pads[iFlag]*MAXTBKT; // number of digits for this row
-
+ Int_t NofDigits = n_of_pads*n_of_tbins; // number of digits for this row
Float_t **pList = new Float_t* [NofDigits];
Int_t lp;
-
+ Int_t i1;
for(lp=0;lp<NofDigits;lp++)pList[lp]=0; // set all pointers to NULL
-
//
- // Straight signal and cross-talk, cross-talk is integrated over all
- // tracks and added to the signal at the very end
- //
-
-
- for (i1=0;i1<nTracks[iFlag];i1++){
-
- m2->Zero(); // clear single track signal matrix
-
- Float_t TrackLabel =
- GetSignal(rowTriplet[iFlag],i1,n_of_pads[iFlag],m2,m1,IndexRange);
-
- GetList(TrackLabel,n_of_pads[iFlag],m2,IndexRange,pList);
-
- }
-
- //
- // Cross talk from the neighbouring pad-rows
- //
-
- TMatrix *m3 = new TMatrix(0,n_of_pads[iFlag]-1,0,MAXTBKT-1); // cross-talk
-
- TMatrix &Cross = *m3;
-
- if(iFlag == 0){
-
- // cross-talk from the outer row only (first pad row)
-
- GetCrossTalk(0,rowTriplet[1],nTracks[1],n_of_pads,m3);
-
- }
- else if(iFlag == 2){
-
- // cross-talk from the inner row only (last pad row)
-
- GetCrossTalk(2,rowTriplet[1],nTracks[1],n_of_pads,m3);
-
- }
- else{
-
- // cross-talk from both inner and outer rows
-
- GetCrossTalk(3,rowTriplet[0],nTracks[0],n_of_pads,m3); // inner
- GetCrossTalk(4,rowTriplet[2],nTracks[2],n_of_pads,m3); //outer
+ //calculate signal
+ //
+ Int_t row1 = TMath::Max(irow-fTPCParam->GetNCrossRows(),0);
+ Int_t row2 = TMath::Min(irow+fTPCParam->GetNCrossRows(),nrows-1);
+ for (Int_t row= row1;row<=row2;row++){
+ Int_t nTracks= rows[row]->GetEntries();
+ for (i1=0;i1<nTracks;i1++){
+ fCurrentIndex[2]= row;
+ fCurrentIndex[3]=irow;
+ if (row==irow){
+ m2->Zero(); // clear single track signal matrix
+ Float_t TrackLabel = GetSignal(rows[row],i1,m2,m1,IndexRange);
+ GetList(TrackLabel,n_of_pads,m2,IndexRange,pList);
+ }
+ else GetSignal(rows[row],i1,0,m1,IndexRange);
+ }
}
-
- Total += Cross; // add the cross-talk
-
- //
- // Convert analog signal to ADC counts
- //
-
+
Int_t tracks[3];
- Int_t digits[5];
-
- for(Int_t ip=0;ip<n_of_pads[iFlag];ip++){
- for(Int_t it=0;it<MAXTBKT;it++){
+ AliDigits *dig = fDigitsArray->GetRow(isec,irow);
+ for(Int_t ip=0;ip<n_of_pads;ip++){
+ for(Int_t it=0;it<n_of_tbins;it++){
Float_t q = Total(ip,it);
- Int_t gi =it*n_of_pads[iFlag]+ip; // global index
+ Int_t gi =it*n_of_pads+ip; // global index
- q = gRandom->Gaus(q,fTPCParam->GetNoise()); // apply noise
- q *= (q_el*1.e15); // convert to fC
- q *= chipgain; // convert to mV
- q *= (adc_sat/dyn_range); // convert to ADC counts
+ q = gRandom->Gaus(q,fTPCParam->GetNoise()*fTPCParam->GetNoiseNormFac());
- if(q <zerosup) continue; // do not fill zeros
+ q = (Int_t)q;
+
+ if(q <=zerosup) continue; // do not fill zeros
if(q > adc_sat) q = adc_sat; // saturation
//
tracks[j1] = (pList[gi]) ?(Int_t)(*(pList[gi]+j1)) : -1;
}
- digits[0]=isec;
- digits[1]=irow;
- digits[2]=ip;
- digits[3]=it;
- digits[4]= (Int_t)q;
-
- // Add this digit
-
- AddDigit(tracks,digits);
+//Begin_Html
+/*
+ <A NAME="AliDigits"></A>
+ using of AliDigits object
+*/
+//End_Html
+ dig->SetDigitFast((Short_t)q,it,ip);
+ if (fDigitsArray->IsSimulated())
+ {
+ ((AliSimDigits*)dig)->SetTrackIDFast(tracks[0],it,ip,0);
+ ((AliSimDigits*)dig)->SetTrackIDFast(tracks[1],it,ip,1);
+ ((AliSimDigits*)dig)->SetTrackIDFast(tracks[2],it,ip,2);
+ }
+
} // end of loop over time buckets
} // end of lop over pads
delete m1;
delete m2;
- delete m3;
+ // delete m3;
} // end of DigitizeRow
+
//_____________________________________________________________________________
-Float_t AliTPC::GetSignal(TObjArray *p1, Int_t ntr, Int_t np, TMatrix *m1, TMatrix *m2,
+
+Float_t AliTPC::GetSignal(TObjArray *p1, Int_t ntr, TMatrix *m1, TMatrix *m2,
Int_t *IndexRange)
{
//-----------------------------------------------------------------
// Origin: Marek Kowalski IFJ, Krakow, Marek.Kowalski@ifj.edu.pl
+ // Modified: Marian Ivanov
//-----------------------------------------------------------------
TVector *tv;
- AliTPCParam * fTPCParam = &(fDigParam->GetParam());
- AliTPCPRF2D * fPRF2D = &(fDigParam->GetPRF2D());
- AliTPCRF1D * fRF = &(fDigParam->GetRF());
- const int MAXTBKT=
- int((z_end+6*fTPCParam->GetZSigma())/fTPCParam->GetZWidth())+1;
- //to make the code faster we put parameters to the stack
-
- Float_t zwidth = fTPCParam->GetZWidth();
- Float_t zwidthm1 =1./zwidth;
-
tv = (TVector*)p1->At(ntr); // pointer to a track
TVector &v = *tv;
Float_t label = v(0);
+ Int_t CentralPad = (fTPCParam->GetNPads(fCurrentIndex[1],fCurrentIndex[3])-1)/2;
- Int_t CentralPad = (np-1)/2;
- Int_t PadNumber;
Int_t nElectrons = (tv->GetNrows()-1)/4;
- Float_t range=((np-1)/2 + 0.5)*fTPCParam->GetPadPitchWidth(); // pad range
-
- range -= 0.5; // dead zone, 5mm from the edge, according to H.G. Fischer
-
- Float_t IneffFactor = 0.5; // inefficiency in the gain close to the edge, as above
-
-
- Float_t PadSignal[7]; // signal from a single electron
-
- TMatrix &signal = *m1;
- TMatrix &total = *m2;
-
-
IndexRange[0]=9999; // min pad
IndexRange[1]=-1; // max pad
IndexRange[2]=9999; //min time
IndexRange[3]=-1; // max time
+ // Float_t IneffFactor = 0.5; // inefficiency in the gain close to the edge, as above
+
+ TMatrix &signal = *m1;
+ TMatrix &total = *m2;
//
// Loop over all electrons
//
-
for(Int_t nel=0; nel<nElectrons; nel++){
- Int_t idx=nel*4;
- Float_t xwire = v(idx+1);
- Float_t y = v(idx+2);
- Float_t z = v(idx+3);
-
-
- Float_t absy=TMath::Abs(y);
-
- if(absy < 0.5*fTPCParam->GetPadPitchWidth()){
- PadNumber=CentralPad;
- }
- else if (absy < range){
- PadNumber=(Int_t) ((absy-0.5*fTPCParam->GetPadPitchWidth())/fTPCParam->GetPadPitchWidth()+1.);
- PadNumber=(Int_t) (TMath::Sign((Float_t)PadNumber, y)+CentralPad);
- }
- else continue; // electron out of pad-range , lost at the sector edge
+ Int_t idx=nel*4;
+ Float_t aval = v(idx+4);
+ Float_t eltoadcfac=aval*fTPCParam->GetTotalNormFac();
+ Float_t xyz[3]={v(idx+1),v(idx+2),v(idx+3)};
+ Int_t n = fTPCParam->CalcResponse(xyz,fCurrentIndex,fCurrentIndex[3]);
- Float_t aval = (absy<range-0.5) ? v(idx+4):v(idx+4)*IneffFactor;
-
-
- Float_t dist = y - (Float_t)(PadNumber-CentralPad)*fTPCParam->GetPadPitchWidth();
- for (Int_t i=0;i<7;i++){
- PadSignal[i]=fPRF2D->GetPRF(-dist+(i-3)*fTPCParam->GetPadPitchWidth(),xwire)*aval;
- PadSignal[i] *= fTPCParam->GetPadCoupling();
- }
-
- Int_t LeftPad = TMath::Max(0,PadNumber-3);
- Int_t RightPad = TMath::Min(np-1,PadNumber+3);
-
- Int_t pmin=LeftPad-PadNumber+3; // lower index of the pad_signal vector
- Int_t pmax=RightPad-PadNumber+3; // upper index
-
- Float_t z_drift = z*zwidthm1;
- Float_t z_offset = z_drift-(Int_t)z_drift;
-
- Int_t FirstBucket = (Int_t)z_drift; // numbering starts from "0"
-
-
- // loop over time bins (4 bins is enough - 3 sigma truncated Gaussian)
-
- for (Int_t i2=0;i2<4;i2++){
- Int_t TrueTime = FirstBucket+i2; // current time bucket
- Float_t dz = (Float_t(i2)+1.-z_offset)*zwidth;
- Float_t ampl = fRF->GetRF(dz);
- if( (TrueTime>MAXTBKT-1) ) break; // beyond the time range
-
- IndexRange[2]=TMath::Min(IndexRange[2],TrueTime); // min time
- IndexRange[3]=TMath::Max(IndexRange[3],TrueTime); // max time
-
- // loop over pads, from pmin to pmax
- for(Int_t i3=pmin;i3<=pmax;i3++){
- Int_t TruePad = LeftPad+i3-pmin;
- IndexRange[0]=TMath::Min(IndexRange[0],TruePad); // min pad
- IndexRange[1]=TMath::Max(IndexRange[1],TruePad); // max pad
- signal(TruePad,TrueTime)+=(PadSignal[i3]*ampl); // not converted to charge!!!
- total(TruePad,TrueTime)+=(PadSignal[i3]*ampl); // not converted to charge!!!
- } // end of pads loop
- } // end of time loop
+ if (n>0) for (Int_t i =0; i<n; i++){
+ Int_t *index = fTPCParam->GetResBin(i);
+ Int_t pad=index[1]+CentralPad; //in digit coordinates central pad has coordinate 0
+ if ( ( pad<(fTPCParam->GetNPads(fCurrentIndex[1],fCurrentIndex[3]))) && (pad>0)) {
+ Int_t time=index[2];
+ Float_t weight = fTPCParam->GetResWeight(i); //we normalise response to ADC channel
+ weight *= eltoadcfac;
+
+ if (m1!=0) signal(pad,time)+=weight;
+ total(pad,time)+=weight;
+ IndexRange[0]=TMath::Min(IndexRange[0],pad);
+ IndexRange[1]=TMath::Max(IndexRange[1],pad);
+ IndexRange[2]=TMath::Min(IndexRange[2],time);
+ IndexRange[3]=TMath::Max(IndexRange[3],time);
+ }
+ }
} // end of loop over electrons
-
+
return label; // returns track label when finished
}
// accept only the contribution larger than 500 electrons (1/2 s_noise)
- if(signal(ip,it)<500.) continue;
+ if(signal(ip,it)<0.5) continue;
Int_t GlobalIndex = it*np+ip; // GlobalIndex starts from 0!
-
}//end of GetList
//___________________________________________________________________
void AliTPC::MakeSector(Int_t isec,Int_t nrows,TTree *TH,
// Origin: Marek Kowalski IFJ, Krakow, Marek.Kowalski@ifj.edu.pl
//-----------------------------------------------------------------
- AliTPCParam * fTPCParam = &(fDigParam->GetParam());
+ Float_t gasgain = fTPCParam->GetGasGain();
Int_t i;
- Float_t xyz[3];
+ Float_t xyz[4];
AliTPChit *tpcHit; // pointer to a sigle TPC hit
row[i] = new TObjArray;
}
Int_t *n_of_electrons = new Int_t [nrows]; // electron counter for each row
- TVector **tr = new TVector* [nrows]; //pointers to the track vectors
+ TVector **tracks = new TVector* [nrows]; //pointers to the track vectors
//--------------------------------------------------------------------
// Loop over tracks, the "track" contains the full history
tpcHit = (AliTPChit*)fHits->UncheckedAt(hit); // get a pointer to a hit
Int_t sector=tpcHit->fSector; // sector number
- if(sector != isec) continue; //terminate iteration
+ if(sector != isec) continue;
currentTrack = tpcHit->fTrack; // track number
if(currentTrack != previousTrack){
for(i=0;i<nrows;i++){
if(previousTrack != -1){
if(n_of_electrons[i]>0){
- TVector &v = *tr[i];
+ TVector &v = *tracks[i];
v(0) = previousTrack;
- tr[i]->ResizeTo(3*n_of_electrons[i]+1); // shrink if necessary
- row[i]->Add(tr[i]);
+ tracks[i]->ResizeTo(4*n_of_electrons[i]+1); // shrink if necessary
+ row[i]->Add(tracks[i]);
}
else{
- delete tr[i]; // delete empty TVector
- tr[i]=0;
+ delete tracks[i]; // delete empty TVector
+ tracks[i]=0;
}
}
n_of_electrons[i]=0;
- tr[i] = new TVector(361); // TVectors for the next fTrack
+ tracks[i] = new TVector(481); // TVectors for the next fTrack
} // end of loop over rows
// Calculate the electron attachment probability
//---------------------------------------------------
- Float_t time = 1.e6*(z_end-TMath::Abs(tpcHit->fZ))/fTPCParam->GetDriftV();
+
+ Float_t time = 1.e6*(fTPCParam->GetZLength()-TMath::Abs(tpcHit->fZ))
+ /fTPCParam->GetDriftV();
// in microseconds!
Float_t AttProb = fTPCParam->GetAttCoef()*
fTPCParam->GetOxyCont()*time; // fraction!
//-----------------------------------------------
// Loop over electrons
//-----------------------------------------------
-
+ Int_t index[3];
+ index[1]=isec;
for(Int_t nel=0;nel<QI;nel++){
// skip if electron lost due to the attachment
if((gRandom->Rndm(0)) < AttProb) continue; // electron lost!
xyz[0]=tpcHit->fX;
xyz[1]=tpcHit->fY;
- xyz[2]=tpcHit->fZ;
- ElDiff(xyz); // Appply the diffusion
+ xyz[2]=tpcHit->fZ;
+ xyz[3]= (Float_t) (-gasgain*TMath::Log(gRandom->Rndm()));
+ index[0]=1;
+
+ TransportElectron(xyz,index); //MI change -august
Int_t row_number;
- fTPCParam->XYZtoCRXYZ(xyz,isec,row_number,3);
-
- //transform position to local coordinates
- //option 3 means that we calculate x position relative to
- //nearest pad row
-
- if ((row_number<0)||row_number>=fTPCParam->GetNRow(isec)) continue;
- ExB(xyz); // ExB effect at the sense wires
+ fTPCParam->GetPadRow(xyz,index); //MI change august
+ row_number = index[2];
+ //transform position to local digit coordinates
+ //relative to nearest pad row
+ if ((row_number<0)||row_number>=fTPCParam->GetNRow(isec)) continue;
n_of_electrons[row_number]++;
//----------------------------------
// Expand vector if necessary
//----------------------------------
if(n_of_electrons[row_number]>120){
- Int_t range = tr[row_number]->GetNrows();
- if(n_of_electrons[row_number] > (range-1)/3){
- tr[row_number]->ResizeTo(range+150); // Add 50 electrons
+ Int_t range = tracks[row_number]->GetNrows();
+ if((n_of_electrons[row_number])>(range-1)/4){
+
+ tracks[row_number]->ResizeTo(range+400); // Add 100 electrons
}
}
- TVector &v = *tr[row_number];
- Int_t idx = 3*n_of_electrons[row_number]-2;
+ TVector &v = *tracks[row_number];
+ Int_t idx = 4*n_of_electrons[row_number]-3;
- v(idx)= xyz[0]; // X
- v(idx+1)=xyz[1]; // Y (along the pad-row)
- v(idx+2)=xyz[2]; // Z
-
+ v(idx)= xyz[0]; // X - pad row coordinate
+ v(idx+1)=xyz[1]; // Y - pad coordinate (along the pad-row)
+ v(idx+2)=xyz[2]; // Z - time bin coordinate
+ v(idx+3)=xyz[3]; // avalanche size
} // end of loop over electrons
} // end of loop over hits
for(i=0;i<nrows;i++){
if(n_of_electrons[i]>0){
- TVector &v = *tr[i];
+ TVector &v = *tracks[i];
v(0) = previousTrack;
- tr[i]->ResizeTo(3*n_of_electrons[i]+1); // shrink if necessary
- row[i]->Add(tr[i]);
+ tracks[i]->ResizeTo(4*n_of_electrons[i]+1); // shrink if necessary
+ row[i]->Add(tracks[i]);
}
else{
- delete tr[i];
- tr[i]=0;
+ delete tracks[i];
+ tracks[i]=0;
}
}
- delete [] tr;
- delete [] n_of_electrons;
-
-} // end of MakeSector
-//_____________________________________________________________________________
-void AliTPC::GetCrossTalk (Int_t iFlag,TObjArray *p,Int_t ntracks,Int_t *npads,
- TMatrix *m)
-{
-
- //-------------------------------------------------------------
- // Calculates the cross-talk from one row (inner or outer)
- //-------------------------------------------------------------
-
- //-----------------------------------------------------------------
- // Origin: Marek Kowalski IFJ, Krakow, Marek.Kowalski@ifj.edu.pl
- //-----------------------------------------------------------------
-
- //
- // iFlag=2 & 3 --> cross-talk from the inner row
- // iFlag=0 & 4 --> cross-talk from the outer row
- //
- AliTPCParam * fTPCParam = &(fDigParam->GetParam());
- AliTPCPRF2D * fPRF2D = &(fDigParam->GetPRF2D());
- AliTPCRF1D * fRF = &(fDigParam->GetRF());
- const int MAXTBKT=
- int((z_end+6*fTPCParam->GetZSigma())/fTPCParam->GetZWidth())+1;
+ delete [] tracks;
+ delete [] n_of_electrons;
- //to make code faster
-
- Float_t zwidth = fTPCParam->GetZWidth();
- Float_t zwidthm1 =1/fTPCParam->GetZWidth();
-
- Int_t PadNumber;
- Float_t xwire;
-
- Int_t nPadsSignal; // for this pads the signal is calculated
- Float_t range; // sense wire range
- Int_t nPadsDiff;
-
- Float_t IneffFactor=0.5; // gain inefficiency close to the edges
-
- if(iFlag == 0){
- // 1-->0
- nPadsSignal = npads[1];
- range = ((npads[1]-1)/2 + 0.5)*fTPCParam->GetPadPitchWidth();
- nPadsDiff = (npads[1]-npads[0])/2;
- }
- else if (iFlag == 2){
- // 1-->2
- nPadsSignal = npads[2];
- range = ((npads[1]-1)/2 + 0.5)*fTPCParam->GetPadPitchWidth();
- nPadsDiff = 0;
- }
- else if (iFlag == 3){
- // 0-->1
- nPadsSignal = npads[1];
- range = ((npads[0]-1)/2 + 0.5)*fTPCParam->GetPadPitchWidth();
- nPadsDiff = 0;
- }
- else{
- // 2-->1
- nPadsSignal = npads[2];
- range = ((npads[2]-1)/2 + 0.5)*fTPCParam->GetPadPitchWidth();
- nPadsDiff = (npads[2]-npads[1])/2;
- }
-
- range-=0.5; // dead zone close to the edges
-
- TVector *tv;
- TMatrix &signal = *m;
-
- Int_t CentralPad = (nPadsSignal-1)/2;
- Float_t PadSignal[7]; // signal from a single electron
- // Loop over tracks
- for(Int_t nt=0;nt<ntracks;nt++){
- tv=(TVector*)p->At(nt); // pointer to a track
- TVector &v = *tv;
- Int_t nElectrons = (tv->GetNrows()-1)/4;
- // Loop over electrons
- for(Int_t nel=0; nel<nElectrons; nel++){
- Int_t idx=nel*4;
- xwire=v(idx+1);
-
- if (iFlag==0) xwire+=fTPCParam->GetPadPitchLength();
- if (iFlag==2) xwire-=fTPCParam->GetPadPitchLength();
- if (iFlag==3) xwire-=fTPCParam->GetPadPitchLength();
- if (iFlag==4) xwire+=fTPCParam->GetPadPitchLength();
-
- // electron acceptance for the cross-talk (only the closest wire)
-
- Float_t dxMax = fTPCParam->GetPadPitchLength()*0.5+fTPCParam->GetWWPitch();
- if(TMath::Abs(xwire)>dxMax) continue;
-
- Float_t y = v(idx+2);
- Float_t z = v(idx+3);
- Float_t absy=TMath::Abs(y);
-
- if(absy < 0.5*fTPCParam->GetPadPitchWidth()){
- PadNumber=CentralPad;
- }
- else if (absy < range){
- PadNumber=(Int_t) ((absy-0.5*fTPCParam->GetPadPitchWidth())/fTPCParam->GetPadPitchWidth() +1.);
- PadNumber=(Int_t) (TMath::Sign((Float_t)PadNumber, y)+CentralPad);
- }
- else continue; // electron out of sense wire range, lost at the sector edge
-
- Float_t aval = (absy<range-0.5) ? v(idx+4):v(idx+4)*IneffFactor;
-
- Float_t dist = y - (Float_t)(PadNumber-CentralPad)*fTPCParam->GetPadPitchWidth();
-
- for (Int_t i=0;i<7;i++){
- PadSignal[i]=fPRF2D->GetPRF(-dist+(i-3)*fTPCParam->GetPadPitchWidth(),xwire)*aval;
-
- PadSignal[i] *= fTPCParam->GetPadCoupling();
- }
- // real pad range
-
- Int_t LeftPad = TMath::Max(0,PadNumber-3);
- Int_t RightPad = TMath::Min(nPadsSignal-1,PadNumber+3);
-
- Int_t pmin=LeftPad-PadNumber+3; // lower index of the pad_signal vector
- Int_t pmax=RightPad-PadNumber+3; // upper index
-
-
- Float_t z_drift = z*zwidthm1;
- Float_t z_offset = z_drift-(Int_t)z_drift;
-
- Int_t FirstBucket = (Int_t)z_drift; // numbering starts from "0"
-
- for (Int_t i2=0;i2<4;i2++){
- Int_t TrueTime = FirstBucket+i2; // current time bucket
- Float_t dz = (Float_t(i2)+1.- z_offset)*zwidth;
- Float_t ampl = fRF->GetRF(dz);
- if((TrueTime>MAXTBKT-1)) break; // beyond the time range
-
-
- // loop over pads, from pmin to pmax
-
- for(Int_t i3=pmin;i3<pmax+1;i3++){
- Int_t TruePad = LeftPad+i3-pmin;
-
- if(TruePad<nPadsDiff || TruePad > nPadsSignal-nPadsDiff-1) continue;
-
- TruePad -= nPadsDiff;
- signal(TruePad,TrueTime)+=(PadSignal[i3]*ampl); // not converted to charge!
-
- } // end of loop over pads
- } // end of loop over time bins
-
- } // end of loop over electrons
-
- } // end of loop over tracks
-
-} // end of GetCrossTalk
+} // end of MakeSector
//_____________________________________________________________________________
// reset clusters
//
fNdigits = 0;
- // if (fDigits) fDigits->Clear();
- if (fDigParam->GetArray()!=0) fDigParam->GetArray()->Clear();
+ if (fDigits) fDigits->Clear();
fNclusters = 0;
if (fClusters) fClusters->Clear();
}
fMixtProp[2]=p3;
+}
+//_____________________________________________________________________________
+
+void AliTPC::TransportElectron(Float_t *xyz, Int_t *index)
+{
+ //
+ // electron transport taking into account:
+ // 1. diffusion,
+ // 2.ExB at the wires
+ // 3. nonisochronity
+ //
+ // xyz and index must be already transformed to system 1
+ //
+
+ fTPCParam->Transform1to2(xyz,index);
+
+ //add diffusion
+ Float_t driftl=xyz[2];
+ if(driftl<0.01) driftl=0.01;
+ driftl=TMath::Sqrt(driftl);
+ Float_t sig_t = driftl*(fTPCParam->GetDiffT());
+ Float_t sig_l = driftl*(fTPCParam->GetDiffL());
+ xyz[0]=gRandom->Gaus(xyz[0],sig_t);
+ xyz[1]=gRandom->Gaus(xyz[1],sig_t);
+ xyz[2]=gRandom->Gaus(xyz[2],sig_l);
+
+ // ExB
+
+ if (fTPCParam->GetMWPCReadout()==kTRUE){
+ Float_t x1=xyz[0];
+ fTPCParam->Transform2to2NearestWire(xyz,index);
+ Float_t dx=xyz[0]-x1;
+ xyz[1]+=dx*(fTPCParam->GetOmegaTau());
+ }
+ //add nonisochronity (not implemented yet)
+
}
//_____________________________________________________________________________
void AliTPC::Streamer(TBuffer &R__b)
R__b >> fNsectors;
R__b >> fNclusters;
R__b >> fNtracks;
- fDigitsIndex = new Int_t[fNsectors+1];
+
} else {
R__b.WriteVersion(AliTPC::IsA());
AliDetector::Streamer(R__b);
x[0]=par->GetPadRowRadii(fSector,fPadRow);
x[1]=fY;
x[2]=fZ;
- par->CRXYZtoXYZ(x,fSector,fPadRow,1);
- x[2]=fZ;
+ Float_t cs, sn, tmp;
+ par->AdjustCosSin(fSector,cs,sn);
+ tmp = x[0]*cs-x[1]*sn;
+ x[1]= x[0]*sn+x[1]*cs; x[0]=tmp;
}
//_____________________________________________________________________________
//
fX=hits[0]; // This is dummy code !
}
+//_________________________________________________________________________
AliTPCtrack::AliTPCtrack(const AliTPCcluster *c,const TVector& xx,
const TMatrix& CC, Double_t xref, Double_t alpha):
fX=t.fX;
fChi2=t.fChi2;
fAlpha=t.fAlpha;
- int n=t.fClusters.GetEntriesFast();
- for (int i=0; i<n; i++) fClusters.AddLast(t.fClusters.UncheckedAt(i));
+ Int_t n=t.fClusters.GetEntriesFast();
+ for (Int_t i=0; i<n; i++) fClusters.AddLast(t.fClusters.UncheckedAt(i));
}
//_____________________________________________________________________________
Int_t AliTPCtrack::Compare(TObject *o) {
//-----------------------------------------------------------------
- // This function compares tracks according to their curvature.
- //
+ // This function compares tracks according to the uncertainty of their
+ // position in Y.
// Origin: Iouri Belikov, CERN, Jouri.Belikov@cern.ch
//-----------------------------------------------------------------
AliTPCtrack *t=(AliTPCtrack*)o;
}
//_____________________________________________________________________________
-int AliTPCtrack::PropagateTo(Double_t xk,Double_t x0,Double_t rho,Double_t pm)
+Int_t AliTPCtrack::PropagateTo(Double_t xk,Double_t x0,Double_t rho,Double_t pm)
{
//-----------------------------------------------------------------
// This function propagates a track to a reference plane x=xk.
return 0;
}
- Double_t x1=fX, x2=x1+0.5*(xk-x1), dx=x2-x1, y1=x(0), z1=x(1);
+ Double_t x1=fX, x2=x1+(xk-x1), dx=x2-x1, y1=x(0), z1=x(1);
Double_t c1=x(2)*x1 - x(3), r1=sqrt(1.- c1*c1);
Double_t c2=x(2)*x2 - x(3), r2=sqrt(1.- c2*c2);
F(1,4)= dx*cc/cr;
TMatrix tmp(F,TMatrix::kMult,C);
C.Mult(tmp,TMatrix(TMatrix::kTransposed,F));
-
+
fX=x2;
-
+
//Multiple scattering******************
Double_t ey=x(2)*fX - x(3);
Double_t ex=sqrt(1-ey*ey);
Double_t p2=GetPt()*GetPt()*(1.+x(4)*x(4));
Double_t beta2=p2/(p2 + pm*pm);
Double_t d=sqrt((x1-fX)*(x1-fX)+(y1-x(0))*(y1-x(0))+(z1-x(1))*(z1-x(1)));
- d*=2.;
Double_t theta2=14.1*14.1/(beta2*p2*1e6)*d/x0*rho;
Q*=theta2;
C+=Q;
-
+
//Energy losses************************
Double_t dE=0.153e-3/beta2*(log(5940*beta2/(1-beta2)) - beta2)*d*rho;
if (x1 < x2) dE=-dE;
x(2)*=(1.- sqrt(p2+pm*pm)/p2*dE);
//x(3)*=(1.- sqrt(p2+pm*pm)/p2*dE);
-
- x1=fX; x2=xk; y1=x(0); z1=x(1);
- c1=x(2)*x1 - x(3); r1=sqrt(1.- c1*c1);
- c2=x(2)*x2 - x(3); r2=sqrt(1.- c2*c2);
-
- x(0) += dx*(c1+c2)/(r1+r2);
- x(1) += dx*(c1+c2)/(c1*r2 + c2*r1)*x(4);
-
- F.UnitMatrix();
- rr=r1+r2; cc=c1+c2; xx=x1+x2;
- F(0,2)= dx*(rr*xx + cc*(c1*x1/r1+c2*x2/r2))/(rr*rr);
- F(0,3)=-dx*(2*rr + cc*(c1/r1 + c2/r2))/(rr*rr);
- cr=c1*r2+c2*r1;
- F(1,2)= dx*x(4)*(cr*xx-cc*(r1*x2-c2*c1*x1/r1+r2*x1-c1*c2*x2/r2))/(cr*cr);
- F(1,3)=-dx*x(4)*(2*cr + cc*(c2*c1/r1-r1 + c1*c2/r2-r2))/(cr*cr);
- F(1,4)= dx*cc/cr;
- tmp.Mult(F,C);
- C.Mult(tmp,TMatrix(TMatrix::kTransposed,F));
-
- fX=x2;
-
+
return 1;
}
TMatrix K(C,TMatrix::kMult,Ht); K*=R;
TVector savex=x;
- x*=H; x-=m; x*=-1; x*=K; x+=savex;
+ x*=H; x-=m;
+
+ x*=-1; x*=K; x+=savex;
if (TMath::Abs(x(2)*fX-x(3)) >= 0.999) {
if (*this>4) cerr<<*this<<" AliTPCtrack warning: Filtering failed !\n";
x=savex;
TMatrix saveC=C;
C.Mult(K,tmp); C-=saveC; C*=-1;
-
+
fClusters.AddLast((AliTPCcluster*)c);
fChi2 += chisq;
}
//_____________________________________________________________________________
-int AliTPCtrack::Rotate(Double_t alpha)
+Int_t AliTPCtrack::Rotate(Double_t alpha)
{
//-----------------------------------------------------------------
// This function rotates this track.
//
// Origin: Iouri Belikov, CERN, Jouri.Belikov@cern.ch
//-----------------------------------------------------------------
- int num_of_clusters=fClusters.GetEntriesFast();
- for (int i=0; i<num_of_clusters; i++) {
+ Int_t num_of_clusters=fClusters.GetEntriesFast();
+ for (Int_t i=0; i<num_of_clusters; i++) {
//if (i<=14) continue;
AliTPCcluster *c=(AliTPCcluster*)fClusters.UncheckedAt(i);
c->Use();
}
//_____________________________________________________________________________
-struct S { int lab; int max; };
-int AliTPCtrack::GetLabel(int nrows) const
+struct S { Int_t lab; Int_t max; };
+Int_t AliTPCtrack::GetLabel(Int_t nrows) const
{
//-----------------------------------------------------------------
// This function returns the track label. If label<0, this track is fake.
//
// Origin: Iouri Belikov, CERN, Jouri.Belikov@cern.ch
//-----------------------------------------------------------------
- int num_of_clusters=fClusters.GetEntriesFast();
+ Int_t num_of_clusters=fClusters.GetEntriesFast();
S *s=new S[num_of_clusters];
- int i;
+ Int_t i;
for (i=0; i<num_of_clusters; i++) s[i].lab=s[i].max=0;
- int lab=123456789;
+ Int_t lab=123456789;
for (i=0; i<num_of_clusters; i++) {
AliTPCcluster *c=(AliTPCcluster*)fClusters.UncheckedAt(i);
lab=TMath::Abs(c->fTracks[0]);
- int j;
+ Int_t j;
for (j=0; j<num_of_clusters; j++)
if (s[j].lab==lab || s[j].max==0) break;
s[j].lab=lab;
s[j].max++;
}
- int max=0;
+ Int_t max=0;
for (i=0; i<num_of_clusters; i++)
if (s[i].max>max) {max=s[i].max; lab=s[i].lab;}
TMath::Abs(c->fTracks[2]) == lab ) max++;
}
- if (1.-float(max)/num_of_clusters > 0.10) return -lab;
+ if (1.-Float_t(max)/num_of_clusters > 0.10) return -lab;
- int tail=int(0.08*nrows);
+ Int_t tail=Int_t(0.08*nrows);
if (num_of_clusters < tail) return lab;
max=0;
lab == TMath::Abs(c->fTracks[1]) ||
lab == TMath::Abs(c->fTracks[2])) max++;
}
- if (max < int(0.5*tail)) return -lab;
+ if (max < Int_t(0.5*tail)) return -lab;
return lab;
}
//
// Origin: Iouri Belikov, CERN, Jouri.Belikov@cern.ch
//-----------------------------------------------------------------
- int ncl=fClusters.GetEntriesFast();
- int n=0;
+ Int_t ncl=fClusters.GetEntriesFast();
+ Int_t n=0;
Double_t *q=new Double_t[ncl];
- int i;
- for (i=0; i<ncl; i++) {
+ Int_t i;
+ for (i=1; i<ncl; i++) { //Shall I think of this "i=1" ? (I.Belikov)
AliTPCcluster *cl=(AliTPCcluster*)(fClusters.UncheckedAt(i));
- // if (cl->fdEdX > 3000) continue;
- if (cl->fdEdX <= 0) continue;
- q[n++]=cl->fdEdX;
+ q[n++]=TMath::Abs(cl->fQ)/cl->fdEdX;
+ if (cl->fSector<36) q[n-1]*=1.1;
}
//stupid sorting
- int swap;
+ Int_t swap;
do {
swap=0;
for (i=0; i<n-1; i++) {
}
} while (swap);
- int nl=int(low*n), nu=int(up *n);
+ Int_t nl=Int_t(low*n), nu=Int_t(up *n);
Double_t dedx=0.;
for (i=nl; i<=nu; i++) dedx += q[i];
dedx /= (nu-nl+1);
cerr<<"AliTPCRow::InsertCluster(): Too many clusters !\n"; return;
}
if (num_of_clusters==0) {clusters[num_of_clusters++]=c; return;}
- int i=Find(c->fY);
+ Int_t i=Find(c->fY);
memmove(clusters+i+1 ,clusters+i,(num_of_clusters-i)*sizeof(AliTPCcluster*));
clusters[i]=c; num_of_clusters++;
}
+//___________________________________________________________________
-int AliTPCRow::Find(Double_t y) const {
+Int_t AliTPCRow::Find(Double_t y) const {
//-----------------------------------------------------------------------
// Return the index of the nearest cluster
//
//-----------------------------------------------------------------------
if (y <= clusters[0]->fY) return 0;
if (y > clusters[num_of_clusters-1]->fY) return num_of_clusters;
- int b=0, e=num_of_clusters-1, m=(b+e)/2;
+ Int_t b=0, e=num_of_clusters-1, m=(b+e)/2;
for (; b<e; m=(b+e)/2) {
if (y > clusters[m]->fY) b=m+1;
else e=m;
}
return m;
}
+//________________________________________________________________________
////////////////////////////////////////////////
// Manager class for TPC //
////////////////////////////////////////////////
-
#include "AliDetector.h"
#include "AliHit.h"
#include "AliDigit.h"
-#include "AliTPCSecGeo.h"
#include "AliTPCParam.h"
#include <TMatrix.h>
#include <TTree.h>
class AliTPCcluster;
class AliTPCtrack;
class AliTPCParam;
-//MI changes
-class AliTPCD;
+
+class AliTPCDigitsArray;
+class AliTPCClustersArray;
class AliTPC : public AliDetector {
protected:
Int_t fNsectors; // Number of sectors in TPC
Int_t fNclusters; // Number of clusters in TPC
Int_t fNtracks; // Number of tracks in TPC
- Int_t *fClustersIndex; // Index for each sector in fClusters
- Int_t *fDigitsIndex; // Index for each sector in fDigits
+ TClonesArray *fClusters; // List of clusters for all sectors
+ TClonesArray *fTracks; // List of reconstructed tracks
+ //MI changes
+ AliTPCDigitsArray * fDigitsArray; //detector digit object
+ AliTPCClustersArray * fClustersArray; //detector cluster object
+ AliTPCParam *fTPCParam;
//MK changes
Int_t fMixtComp[3]; // drift gas components
Float_t fMixtProp[3]; // mixture proportions
- //
-
- TClonesArray *fClusters; // List of clusters for all sectors
- TClonesArray *fTracks; // List of reconstructed tracks
- //MI changes
- AliTPCD * fDigParam; //detector parameters
public:
AliTPC();
AliTPC(const char *name, const char *title);
virtual ~AliTPC();
virtual void AddCluster(Float_t*, Int_t*);
/*virtual*/void AddCluster(const AliTPCcluster&);
- virtual void AddDigit(Int_t*, Int_t*);
virtual void AddHit(Int_t, Int_t*, Float_t*);
virtual void AddTrack(Float_t*);
/*virtual*/void AddTrack(const AliTPCtrack&);
virtual void CreateGeometry() {}
virtual void CreateMaterials();
virtual void Hits2Clusters();
+ virtual void Hits2ExactClustersSector(Int_t isec); // MI change calculate "exact" cluster position
virtual void Hits2Digits(); //MI change
virtual void Hits2DigitsSector(Int_t isec); //MI change
virtual void Clusters2Tracks();
TClonesArray *Clusters() {return fClusters;}
TClonesArray *Tracks() {return fTracks;}
- Int_t *GetClustersIndex() {return fClustersIndex;}
- Int_t *GetDigitsIndex() {return fDigitsIndex;}
+
Int_t GetNsectors() {return fNsectors;}
virtual void MakeBranch(Option_t *opt=" ");
virtual void ResetDigits();
virtual void SetSecUps (Int_t s1,Int_t s2,Int_t s3,Int_t s4,Int_t s5, Int_t s6,
Int_t s7,Int_t s8,Int_t s9,Int_t s10, Int_t s11, Int_t s12);
virtual void SetSens(Int_t sens);
+
+ //MK changes
+
//MK changes
virtual void SetSide(Float_t side);
virtual void StepManager()=0;
virtual void DrawDetector() {}
- AliTPCD* GetDigParam() {return fDigParam;} //MI change8
- void SetDigParam(AliTPCD* param) {fDigParam=param;} //MI must think about it
+ AliTPCDigitsArray* GetDigitsArray() {return fDigitsArray;} //MI change
+ AliTPCClustersArray* GetClustersArray(){return fClustersArray;} //MI change
+ AliTPCParam *GetParam(){return fTPCParam;} // M.K, M.I changes
+ void SetParam(AliTPCParam *param){fTPCParam=param;} // M.K, M.I changes
+ void SetDigitsArray(AliTPCDigitsArray* param) {fDigitsArray=param;} //MI change
+ void SetClustersArray(AliTPCClustersArray *clusters) {fClustersArray = clusters;} //MI change
private:
//
- void ElDiff(Float_t *xyz);
- void MakeTriplet(Int_t row,TObjArray **rowTriplet,
- TObjArray **prow);
-
- void ExB(Float_t *xyz);
void DigitizeRow(Int_t irow,Int_t isec,TObjArray **rowTriplet);
- Float_t GetSignal(TObjArray *p1, Int_t ntr, Int_t np, TMatrix *m1, TMatrix *m2,
+ Float_t GetSignal(TObjArray *p1, Int_t ntr, TMatrix *m1, TMatrix *m2,
Int_t *IndexRange);
void GetList (Float_t label,Int_t np,TMatrix *m,Int_t *IndexRange,
Float_t **pList);
void MakeSector(Int_t isec,Int_t nrows,TTree *TH,Stat_t ntracks,TObjArray **row);
- void GetCrossTalk (Int_t iFlag,TObjArray *p,Int_t ntracks,Int_t *npads,
- TMatrix *m);
-
+ void TransportElectron(Float_t *xyz, Int_t *index);
+ Int_t fCurrentIndex[4];// index[0] indicates coordinate system,
+ // index[1] sector number,
+ // index[2] pad row number
+ // index[3] pad row number for which signal is calculated
ClassDef(AliTPC,2) // Time Projection Chamber class
};
Int_t fTracks[3];//labels of overlapped tracks
Int_t fSector; //sector number
Int_t fPadRow; //PadRow number
- Float_t fY; //Y of cluster
- Float_t fZ; //Z of cluster
- Float_t fQ; //Q of cluster (in ADC counts)
+ Float_t fY ; //Y of cluster
+ Float_t fZ ; //Z of cluster
+ Float_t fQ ; //Q of cluster (in ADC counts)
Float_t fdEdX; //dE/dX inside this cluster
Float_t fSigmaY2; //Sigma Y square of cluster
Float_t fSigmaZ2; //Sigma Z square of cluster
AliTPCcluster(Float_t *hits, Int_t*);
virtual ~AliTPCcluster() {;}
void Use() {fQ=-fQ;} //if fQ<0 cluster is already associated with a track
- int IsUsed() const {return (fQ<0) ? 1 : 0;}
+ Int_t IsUsed() const {return (fQ<0) ? 1 : 0;}
void GetXYZ(Float_t *x, const AliTPCParam *) const; //Get global x,y,z
Bool_t IsSortable() const;
Int_t Compare(TObject *o) ;
TObjArray fClusters; // clusters belonging to this track
Double_t fChi2; // total chi2 value for this track
public:
+ AliTPCtrack(): x(5), C(5,5), fClusters(200) {fAlpha=fX=fChi2=0.;}
AliTPCtrack(Float_t *hits);
AliTPCtrack(const AliTPCcluster *c, const TVector& xx, const TMatrix& CC,
Double_t xr, Double_t alpha);
AliTPCtrack(const AliTPCtrack& t);
Int_t Compare(TObject *o);
- int PropagateTo(Double_t xr,
- Double_t x0=28.94,Double_t rho=0.9e-3,Double_t pm=0.139);
+ Int_t PropagateTo(Double_t xr,
+ Double_t x0=28.94,Double_t rho=0.9e-3,Double_t pm=0.139);
void PropagateToVertex(
Double_t x0=36.66,Double_t rho=1.2e-3,Double_t pm=0.139);
void Update(const AliTPCcluster* c, Double_t chi2);
- int Rotate(Double_t angle);
+ Int_t Rotate(Double_t angle);
Bool_t IsSortable() const {return kTRUE;}
void UseClusters() const ;
Double_t GetPredictedChi2(const AliTPCcluster*) const ;
- int GetLabel(int nrows) const ;
+ Int_t GetLabel(Int_t nrows) const ;
void GetPxPyPz(Double_t&, Double_t&, Double_t&) const ;
Double_t GetdEdX(Double_t low, Double_t up) const ;
Double_t GetSigmaTgl2() const {return C(4,4);}
Double_t GetAlpha() const {return fAlpha;}
Double_t GetChi2() const {return fChi2;}
- operator int() const {return fClusters.GetEntriesFast();}
+ operator Int_t() const {return fClusters.GetEntriesFast();}
+ const AliTPCcluster *GetCluster(Int_t i) const {
+ return (const AliTPCcluster *)fClusters.UncheckedAt(i);
+ }
ClassDef(AliTPCtrack,1) // Time Projection Chamber reconstructed tracks
};
AliTPCRow() {num_of_clusters=0;}
void InsertCluster(const AliTPCcluster*);
- operator int() const {return num_of_clusters;}
- const AliTPCcluster* operator[](int i) const {return clusters[i];}
- int Find(Double_t y) const;
+ operator Int_t() const {return num_of_clusters;}
+ const AliTPCcluster* operator[](Int_t i) const {return clusters[i];}
+ Int_t Find(Double_t y) const;
};
class AliTPCSector {
AliTPCSector() { row = 0; num_of_rows=0; }
virtual ~AliTPCSector() { delete[] row; }
static void SetParam(AliTPCParam *p) { param=p; }
- AliTPCRow& operator[](int i) const { return *(row+i); }
- int GetNRows() const { return num_of_rows; }
- virtual Double_t GetX(int l) const = 0;
- virtual Double_t GetMaxY(int l) const = 0;
+ AliTPCRow& operator[](Int_t i) const { return *(row+i); }
+ Int_t GetNRows() const { return num_of_rows; }
+ virtual Double_t GetX(Int_t l) const = 0;
+ virtual Double_t GetMaxY(Int_t l) const = 0;
virtual Double_t GetAlpha() const = 0;
virtual Double_t GetAlphaShift() const = 0;
virtual Int_t GetRowNumber(Double_t x) const = 0;
+ virtual Double_t GetPadPitchWidth() const = 0;
};
class AliTPCSSector : public AliTPCSector {
row=new AliTPCRow[num_of_rows];
}
virtual ~AliTPCSSector() {}
- Double_t GetX(int l) const { return param->GetPadRowRadiiLow(l); }
- Double_t GetMaxY(int l) const { return GetX(l)*tan(0.5*GetAlpha()); }
+ Double_t GetX(Int_t l) const { return param->GetPadRowRadiiLow(l); }
+ Double_t GetMaxY(Int_t l) const { return GetX(l)*tan(0.5*GetAlpha()); }
Double_t GetAlpha() const {return param->GetInnerAngle();}
Double_t GetAlphaShift() const {return param->GetInnerAngleShift();}
+ Double_t GetPadPitchWidth() const {
+ return param->GetInnerPadPitchWidth();
+ }
Int_t GetRowNumber(Double_t x) const {
- Double_t r=param->GetInnerRadiusUp();
+ Double_t r=param->GetPadRowRadiiLow(param->GetNRowLow()-1);
if (x > r) return param->GetNRowLow();
- r=param->GetInnerRadiusLow();
+ r=param->GetPadRowRadiiLow(0);
if (x < r) return -1;
- return int((x-r)/param->GetPadPitchLength() + 0.5);
+ return Int_t((x-r)/param->GetInnerPadPitchLength() + 0.5);
}
};
row=new AliTPCRow[num_of_rows];
}
virtual ~AliTPCLSector() {}
- Double_t GetX(int l) const { return param->GetPadRowRadiiUp(l); }
- Double_t GetMaxY(int l) const { return GetX(l)*tan(0.5*GetAlpha()); }
+ Double_t GetX(Int_t l) const { return param->GetPadRowRadiiUp(l); }
+ Double_t GetMaxY(Int_t l) const { return GetX(l)*tan(0.5*GetAlpha()); }
Double_t GetAlpha() const {return param->GetOuterAngle();}
Double_t GetAlphaShift() const {return param->GetOuterAngleShift();}
+ Double_t GetPadPitchWidth() const {
+ return param->GetOuterPadPitchWidth();
+ }
Int_t GetRowNumber(Double_t x) const {
- Double_t r=param->GetOuterRadiusUp();
+ Double_t r=param->GetPadRowRadiiUp(param->GetNRowUp()-1);
if (x > r) return param->GetNRowUp();
- r=param->GetOuterRadiusLow();
+ r=param->GetPadRowRadiiUp(0);
if (x < r) return -1;
- return int((x-r)/param->GetPadPitchLength() + 0.5);
+ return Int_t((x-r)/param->GetOuterPadPitchLength() + 0.5);
}
};
--- /dev/null
+/**************************************************************************
+ * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
+ * *
+ * Author: The ALICE Off-line Project. *
+ * Contributors are mentioned in the code where appropriate. *
+ * *
+ * Permission to use, copy, modify and distribute this software and its *
+ * documentation strictly for non-commercial purposes is hereby granted *
+ * without fee, provided that the above copyright notice appears in all *
+ * copies and that both the copyright notice and this permission notice *
+ * appear in the supporting documentation. The authors make no claims *
+ * about the suitability of this software for any purpose. It is *
+ * provided "as is" without express or implied warranty. *
+ **************************************************************************/
+
+/*
+$Log$
+Revision 1.1.4.2 2000/04/10 11:34:02 kowal2
+
+Clusters handling in a new data structure
+
+*/
+
+
+///////////////////////////////////////////////////////////////////////////////
+// //
+// Time Projection Chamber clusters objects //
+//
+// Origin: Marian Ivanov , GSI Darmstadt
+// //
+// //
+// //
+///////////////////////////////////////////////////////////////////////////////
+#include "AliTPC.h"
+#include "AliTPCCluster.h"
+#include "TClonesArray.h"
+#include "TDirectory.h"
+
+
+const Int_t kDefSize = 1; //defalut size
+
+
+ClassImp(AliTPCClustersRow)
+
+
+//*****************************************************************************
+//
+//_____________________________________________________________________________
+AliTPCClustersRow::AliTPCClustersRow()
+{
+ //
+ //default constructor
+ fNclusters=0;
+ fClusters = new TClonesArray("AliTPCcluster",kDefSize);
+}
+//_____________________________________________________________________________
+AliTPCClustersRow::AliTPCClustersRow(Int_t size)
+{
+ fNclusters=0;
+ fClusters = new TClonesArray("AliTPCcluster",size);
+}
+
+//_____________________________________________________________________________
+const AliTPCcluster* AliTPCClustersRow::operator[](Int_t i)
+{
+ //
+ // return cluster at internal position i
+ //
+ if (fClusters==0) return 0;
+ void * cl = fClusters->UncheckedAt(i);
+ if (cl==0) return 0;
+ return (AliTPCcluster*)cl;
+}
+//_____________________________________________________________________________
+void AliTPCClustersRow::Sort()
+{
+ // sort cluster
+ if (fClusters) fClusters->Sort();
+}
+
+//_____________________________________________________________________________
+void AliTPCClustersRow::InsertCluster(const AliTPCcluster * c)
+{
+ //
+ // Add a simulated cluster copy to the list
+ //
+ if(!fClusters) fClusters=new TClonesArray("AliTPCcluster",1000);
+ TClonesArray &lclusters = *fClusters;
+ new(lclusters[fNclusters++]) AliTPCcluster(*c);
+}
+
+//_____________________________________________________________________________
+Int_t AliTPCClustersRow::Find(Double_t y) const
+{
+ //
+ // return index of cluster nearest to given y position
+ //
+ AliTPCcluster* cl;
+ cl=(AliTPCcluster*)fClusters->UncheckedAt(0);
+ if (y <= cl->fY) return 0;
+ cl=(AliTPCcluster*)fClusters->UncheckedAt(fNclusters-1);
+ if (y > cl->fY) return fNclusters;
+ //if (y <= clusters[0]->fY) return 0;
+ //if (y > clusters[num_of_clusters-1]->fY) return num_of_clusters;
+ Int_t b=0, e=fNclusters-1, m=(b+e)/2;
+ // Int_t b=0, e=num_of_clusters-1, m=(b+e)/2;
+ for (; b<e; m=(b+e)/2) {
+ cl = (AliTPCcluster*)fClusters->UncheckedAt(m);
+ if (y > cl->fY) b=m+1;
+ // if (y > clusters[m]->fY) b=m+1;
+ else e=m;
+ }
+ return m;
+}
+
+
+//_____________________________________________________________________________
+
+ClassImp(AliTPCClustersArray)
+
+AliTPCClustersArray::AliTPCClustersArray()
+{
+ fParam = 0;
+}
+
+AliTPCClustersArray::~AliTPCClustersArray()
+{
+ //
+ //object is only owner of fParam
+ //
+ if (fParam) delete fParam;
+}
+
+const AliTPCClustersRow * AliTPCClustersArray::GetRow(Int_t sector,Int_t row)
+{
+ //
+ //return clusters ((AliTPCClustersRow *) per given sector and padrow
+ //
+ if (fParam==0) return 0;
+ Int_t index = fParam->GetIndex(sector,row);
+ return (AliTPCClustersRow *)(*this)[index];
+}
+
+Bool_t AliTPCClustersArray::LoadRow(Int_t sector,Int_t row)
+{
+ //
+ //return clusters ((AliTPCClustersRow *) per given sector and padrow
+ //
+ if (fParam==0) return 0;
+ Int_t index = fParam->GetIndex(sector,row);
+ return LoadSegment(index);
+}
+
+Bool_t AliTPCClustersArray::StoreRow(Int_t sector,Int_t row)
+{
+ //
+ //return clusters ((AliTPCClustersRow *) per given sector and padrow
+ //
+ if (fParam==0) return 0;
+ Int_t index = fParam->GetIndex(sector,row);
+ StoreSegment(index);
+ return kTRUE;
+}
+
+
+
+Bool_t AliTPCClustersArray::Setup(AliTPCParam *param)
+{
+ //
+ //setup function to adjust array parameters
+ //
+ if (param==0) return kFALSE;
+ fParam = new AliTPCParam(*param);
+ return MakeArray(fParam->GetNRowsTotal());
+}
--- /dev/null
+#ifndef TPCClusters_H
+#define TPCClusters_H
+/* Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
+ * See cxx source for full Copyright notice */
+
+/* $Id$ */
+
+////////////////////////////////////////////////
+// Manager class for TPC clusters //
+////////////////////////////////////////////////
+
+#include "AliDetector.h"
+#include "AliHit.h"
+#include "AliDigit.h"
+#include "AliSegmentArray.h"
+#include "AliTPCParam.h"
+
+#include <TMatrix.h>
+#include <TTree.h>
+#include <TClonesArray.h>
+
+
+class TClonesArray;
+class TObjArray;
+
+
+class AliTPCClustersRow : public AliSegmentID{
+public:
+ AliTPCClustersRow();
+ AliTPCClustersRow(Int_t size);
+ void InsertCluster(const AliTPCcluster* c ); //insert copy of cluster
+ const AliTPCcluster* operator[](Int_t i);
+ Int_t Find(Double_t y) const; //find nearest cluster in y direction
+ void Sort();
+public:
+ TClonesArray * fClusters;
+ Int_t fNclusters;
+ ClassDef(AliTPCClustersRow,1)
+};
+
+
+class AliTPCClustersArray : public AliSegmentArray {
+public:
+ AliTPCClustersArray();
+ ~AliTPCClustersArray();
+ const AliTPCClustersRow * GetRow(Int_t sector,Int_t row);
+ Bool_t LoadRow(Int_t sector,Int_t row);
+ Bool_t StoreRow(Int_t sector,Int_t row);
+ Bool_t Setup(AliTPCParam *param);
+ //construct array according parameters in fParam
+ const AliTPCParam & GetParam() {return *fParam;}
+private:
+ AliSegmentID * NewSegment(){ return (AliSegmentID*)new AliTPCClustersRow;}
+ AliTPCParam * fParam; //pointer to TPC parameters
+ //AliTPCClustersRow ** fRow; //pointer to array of pointers to cluster row
+ ClassDef(AliTPCClustersArray,1)
+};
+
+#endif
+
--- /dev/null
+/**************************************************************************
+ * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
+ * *
+ * Author: The ALICE Off-line Project. *
+ * Contributors are mentioned in the code where appropriate. *
+ * *
+ * Permission to use, copy, modify and distribute this software and its *
+ * documentation strictly for non-commercial purposes is hereby granted *
+ * without fee, provided that the above copyright notice appears in all *
+ * copies and that both the copyright notice and this permission notice *
+ * appear in the supporting documentation. The authors make no claims *
+ * about the suitability of this software for any purpose. It is *
+ * provided "as is" without express or implied warranty. *
+ **************************************************************************/
+
+/*
+$Log$
+Revision 1.1.4.2 2000/04/10 11:34:02 kowal2
+
+Clusters handling in a new data structure
+
+*/
+
+///////////////////////////////////////////////////////////////////////////////
+// //
+// Time Projection Chamber clusters objects //
+//
+// Origin: Marian Ivanov , GSI Darmstadt
+// //
+// //
+// //
+///////////////////////////////////////////////////////////////////////////////
+#include "AliTPC.h"
+#include "AliTPCParam.h"
+#include "AliSegmentArray.h"
+#include "AliCluster.h"
+#include "AliClusters.h"
+#include "AliClustersArray.h"
+#include "AliTPCClustersRow.h"
+
+#include "AliTPCClustersArray.h"
+#include "TClonesArray.h"
+#include "TDirectory.h"
+
+
+
+//_____________________________________________________________________________
+
+ClassImp(AliTPCClustersArray)
+
+AliTPCClustersArray::AliTPCClustersArray()
+{
+ fParam = 0;
+ SetClass("AliTPCClustersRow");
+}
+
+AliTPCClustersArray::~AliTPCClustersArray()
+{
+ //
+ //object is only owner of fParam
+ //
+ if (fParam) delete fParam;
+}
+
+
+
+AliTPCClustersRow * AliTPCClustersArray::GetRow(Int_t sector,Int_t row)
+{
+ //
+ //return clusters ((AliTPCClustersRow *) per given sector and padrow
+ //
+ if (fParam==0) return 0;
+ Int_t index = ((AliTPCParam*)fParam)->GetIndex(sector,row);
+ return (AliTPCClustersRow *)(*this)[index];
+}
+
+AliTPCClustersRow * AliTPCClustersArray::CreateRow(Int_t sector, Int_t row)
+{
+ //
+ //create digits row
+ //
+ //if row just exist - delete it
+ AliTPCParam * param = (AliTPCParam*)fParam;
+ Int_t index = param->GetIndex(sector,row);
+ AliTPCClustersRow * clusters = (AliTPCClustersRow *)(*this)[index];
+ if (clusters !=0) delete clusters;
+
+ clusters = (AliTPCClustersRow *) AddSegment(index);
+ if (clusters == 0) return 0;
+ return clusters;
+}
+
+AliTPCClustersRow * AliTPCClustersArray::LoadRow(Int_t sector,Int_t row)
+{
+ //
+ //return clusters ((AliTPCClustersRow *) per given sector and padrow
+ //
+ if (fParam==0) return 0;
+ Int_t index = ((AliTPCParam*)fParam)->GetIndex(sector,row);
+ return ( AliTPCClustersRow *) LoadSegment(index);
+}
+
+Bool_t AliTPCClustersArray::StoreRow(Int_t sector,Int_t row)
+{
+ //
+ //return clusters ((AliTPCClustersRow *) per given sector and padrow
+ //
+ if (fParam==0) return 0;
+ Int_t index = ((AliTPCParam*)fParam)->GetIndex(sector,row);
+ StoreSegment(index);
+ return kTRUE;
+}
+
+Bool_t AliTPCClustersArray::ClearRow(Int_t sector,Int_t row)
+{
+ //
+ //return clusters ((AliTPCDigitsRow *) per given sector and padrow
+ //
+ if (fParam==0) return 0;
+ Int_t index = ((AliTPCParam*)fParam)->GetIndex(sector,row);
+ ClearSegment(index);
+ return kTRUE;
+}
+
+
+
+Bool_t AliTPCClustersArray::Setup(AliDetectorParam *param)
+{
+ //
+ //setup function to adjust array parameters
+ //
+ if (param==0) return kFALSE;
+ fParam = param;
+ return MakeArray(((AliTPCParam*)fParam)->GetNRowsTotal());
+
+}
+Bool_t AliTPCClustersArray::Update()
+{
+ //
+ //setup function to adjust array parameters
+ //
+ if (fParam ==0 ) return kFALSE;
+ if (fTree!=0) return MakeDictionary( ((AliTPCParam*)fParam)->GetNRowsTotal()) ;
+ ((AliTPCParam*)fParam)->Update();
+ return MakeArray(((AliTPCParam*)fParam)->GetNRowsTotal());
+}
+
+
+/*
+void AliTPCClustersArray::MakeTree()
+{
+ // AliSegmentID segment;
+ if (fClusterType==0) {
+ Error("AliTPCCLustersArray", "cluster type isn't adjusted");
+ return;
+ }
+ AliClusters * psegment = (AliClusters *)NewSegment();
+ psegment->SetClass(fClusterType->GetName());
+ psegment->SetArray(100);
+ if (fTree) delete fTree;
+ fTree = new TTree("Segment Tree","Tree with segments");
+ fBranch = fTree->Branch("Segment",psegment->IsA()->GetName(),&psegment,64000,1);
+ delete psegment;
+}
+*/
+AliSegmentID * AliTPCClustersArray::NewSegment()
+{
+ //
+ //create object according class information
+ if (fClusterType==0) {
+ Error("AliTPCCLustersArray", "cluster type isn't adjusted");
+ return 0;
+ }
+ AliSegmentID *segment=AliSegmentArray::NewSegment();
+ ((AliTPCClustersRow*)segment)->SetClass(fClusterType->GetName());
+ ((AliTPCClustersRow*)segment)->SetArray(100);
+ return segment;
+}
--- /dev/null
+#ifndef ALITPCCLUSTERSARRAY_H
+#define ALITPCCLUSTERSARRAY_H
+/* Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
+ * See cxx source for full Copyright notice */
+
+/* $Id$ */
+
+////////////////////////////////////////////////
+// Manager class for TPC clusters //
+////////////////////////////////////////////////
+
+#include "AliDetector.h"
+#include "AliHit.h"
+#include "AliDigit.h"
+#include "AliSegmentArray.h"
+#include "AliClustersArray.h"
+#include "AliTPCParam.h"
+
+#include <TMatrix.h>
+#include <TTree.h>
+#include <TClonesArray.h>
+#include <TClass.h>
+
+class TClonesArray;
+class TObjArray;
+class AliTPCClustersRow;
+//class TClass;
+
+class AliTPCClustersArray : public AliClustersArray {
+public:
+ AliTPCClustersArray();
+ ~AliTPCClustersArray();
+ AliTPCClustersRow * GetRow(Int_t sector,Int_t row);
+ AliTPCClustersRow * CreateRow(Int_t sector, Int_t row); //
+ AliTPCClustersRow * LoadRow(Int_t sector,Int_t row);
+ Bool_t StoreRow(Int_t sector,Int_t row);
+ Bool_t ClearRow(Int_t sector,Int_t row);
+ Bool_t Setup(AliDetectorParam *param);
+ //construct array according parameters in fParam
+ Bool_t Update(); //blabla
+ AliSegmentID * NewSegment(); //create new segment - AliTPCClustersRow
+protected:
+ //void MakeTree();
+
+private:
+ ClassDef(AliTPCClustersArray,1)
+};
+
+#endif //ALITPCCLUSTERSARRAY_H
--- /dev/null
+/**************************************************************************
+ * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
+ * *
+ * Author: The ALICE Off-line Project. *
+ * Contributors are mentioned in the code where appropriate. *
+ * *
+ * Permission to use, copy, modify and distribute this software and its *
+ * documentation strictly for non-commercial purposes is hereby granted *
+ * without fee, provided that the above copyright notice appears in all *
+ * copies and that both the copyright notice and this permission notice *
+ * appear in the supporting documentation. The authors make no claims *
+ * about the suitability of this software for any purpose. It is *
+ * provided "as is" without express or implied warranty. *
+ **************************************************************************/
+
+///////////////////////////////////////////////////////////////////////////////
+// //
+// Time Projection Chamber AliTPCClusterRow objects
+// - clusters for given segment of TPC //
+//
+// Origin: Marian Ivanov , GSI Darmstadt
+// //
+// //
+///////////////////////////////////////////////////////////////////////////////
+#include "AliTPC.h"
+#include "AliCluster.h"
+#include "AliClusters.h"
+#include "AliTPCClustersRow.h"
+#include "TDirectory.h"
+
+
+const Int_t kDefSize = 1; //defalut size
+
+
+ClassImp(AliTPCClustersRow)
+
+
+//*****************************************************************************
+//
+//_____________________________________________________________________________
+AliTPCClustersRow::AliTPCClustersRow()
+{
+ //
+ //default constructor
+ fNclusters=0;
+}
+
+//_____________________________________________________________________________
+//AliTPCClustersRow::AliTPCClustersRow(Int_t size)
+//{
+// fNclusters=0;
+// fClusters = new TClonesArray("AliTPCcluster",size);
+//}
+
--- /dev/null
+#ifndef ALITPCCLUSTERROW_H
+#define ALITPCCLUSTERROW_H
+/* Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
+ * See cxx source for full Copyright notice */
+
+/* $Id$ */
+
+////////////////////////////////////////////////
+// Manager class for TPC clusters //
+////////////////////////////////////////////////
+
+#include "AliDetector.h"
+#include "AliSegmentArray.h"
+#include "AliClusters.h"
+
+
+#include <TClonesArray.h>
+
+
+class TClonesArray;
+class TObjArray;
+
+
+class AliTPCClustersRow : public AliClusters{
+public:
+ AliTPCClustersRow();
+
+public:
+
+ ClassDef(AliTPCClustersRow,1)
+};
+#endif //ALITPCCLUSTERROW_H
+++ /dev/null
-/**************************************************************************
- * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
- * *
- * Author: The ALICE Off-line Project. *
- * Contributors are mentioned in the code where appropriate. *
- * *
- * Permission to use, copy, modify and distribute this software and its *
- * documentation strictly for non-commercial purposes is hereby granted *
- * without fee, provided that the above copyright notice appears in all *
- * copies and that both the copyright notice and this permission notice *
- * appear in the supporting documentation. The authors make no claims *
- * about the suitability of this software for any purpose. It is *
- * provided "as is" without express or implied warranty. *
- **************************************************************************/
-
-/*
-$Log$
-*/
-
-//-----------------------------------------------------------------------------
-//
-// Origin: Marian Ivanov, Uni. of Bratislava, ivanov@fmph.uniba.sk
-//
-// Implementation of class AliTPCD
-//
-//-----------------------------------------------------------------------------
-
-#include <TMath.h>
-#include "AliTPCParam.h"
-#include "AliTPCRF1D.h"
-#include "AliTPCPRF2D.h"
-#include "AliTPCD.h"
-#include "TClonesArray.h"
-#include "TClass.h"
-#include "TBranchClones.h"
-#include "TTree.h"
-#include "TDirectory.h"
-
-
-
-// other include files follow here
-
-
-ClassImp(AliTPCD)
- //_____________________________________________________________
-AliTPCD::AliTPCD(Text_t * name,
- AliTPCParam * param, AliTPCPRF2D* prf, AliTPCRF1D* prfz)
-{
- //construct new object's or accept objects sent to constructor
- //AliTPCD handle sent object and is repsonsible for
- //deleting it
-
-//Begin_Html
-/*
-<img src="picts/alitpcd.gif">
-*/
-//End_Html
- SetName(name);
- if ((param!=0) &&
- ( (param->IsA()->InheritsFrom("AliTPCParam")==kTRUE ) ))
- fParam=param;
- else
- fParam= new AliTPCParam;
- if ( (prf!=0) && (prf->IsA()->InheritsFrom("AliTPCPRF2D")==kTRUE) )
- fPRF=prf;
- else
- fPRF = new AliTPCPRF2D;
- if ( (prfz!=0) && (prfz->IsA()->InheritsFrom("AliTPCRF1D")==kTRUE) )
- fRF=prfz;
- else
- fRF = new AliTPCRF1D(kTRUE);
- fDigits = new TClonesArray("AliTPCdigit",5000);
- fpthis=this;
-}
-
-AliTPCD::~AliTPCD()
-{
- if (fParam!=0) fParam->Delete();
- if (fPRF!=0) fPRF->Delete();
- if (fRF!=0) fRF->Delete();
- if (fDigits!=0) fDigits->Delete();
-}
-
-
-Bool_t AliTPCD::SetTree(Int_t nevent, TDirectory *dir )
-{
- char treeName[100];
- // Get Hits Tree header from file
- sprintf(treeName,"TreeD%d_%s",nevent,GetName());
- fTreeD = (TTree*)dir->Get(treeName);
- if (fTreeD == 0) return kFALSE;
- //set Digit branch
- TBranch *b = fTreeD->GetBranch("Digits");
- if (b==0) return kFALSE;
- b->SetAddress(&fDigits);
- return kTRUE;
-}
-
-
-Bool_t AliTPCD::MakeTree(Int_t nevent)
-{
- char treeName[100];
- // Get Hits Tree header from file
- sprintf(treeName,"TreeD%d_%s",nevent,GetName());
- fTreeD = new TTree(treeName,treeName);
- if (fTreeD == 0) return kFALSE;
- //set Digit branch
- TBranch *b = fTreeD->Branch("Digits",&fDigits,40000);
- if (b==0) return kFALSE;
- b->SetAddress(&fDigits);
-
- return kTRUE;
-}
-
-void AliTPCD::Fill()
-{
- if (fTreeD!=0) fTreeD->Fill();
-}
-
-
-
-
-
-void AliTPCD::Streamer(TBuffer &R__b)
-{
- // Stream an object of class AliTPCD.
- if (R__b.IsReading()) {
- Version_t R__v = R__b.ReadVersion(); if (R__v) { }
- TNamed::Streamer(R__b);
- if (fParam!=0) {
- fParam->Delete();
- fParam = new AliTPCParam;
- }
- if (fPRF!=0) {
- fPRF->Delete();
- fPRF = new AliTPCPRF2D;
- }
- if (fRF!=0) {
- fRF->Delete();
- fRF = new AliTPCRF1D;
- }
- if (fTreeD!=0) {
- fRF->Delete();
- fRF = new AliTPCRF1D;
- }
- R__b >>fParam;
- R__b >>fPRF;
- R__b >>fRF;
- SetTree();
- } else {
- R__b.WriteVersion(AliTPCD::IsA());
- TNamed::Streamer(R__b);
- R__b <<fParam;
- R__b <<fPRF;
- R__b <<fRF;
- if (fTreeD!=0) fTreeD->Write();
- }
-}
+++ /dev/null
-#ifndef ALITPCD_H
-#define ALITPCD_H
-/* Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
- * See cxx source for full Copyright notice */
-
-/* $Id$ */
-
-// include files and class forward declarations
-
-
-// Documentation
-/**
- * Object with the TPC parameters
- *
- *
- *
- */
-#include "TNamed.h"
-#include "TTree.h"
-class AliTPCPRF2D;
-class AliTPCRF1D;
-class AliTPCParam;
-class TClonesArray;
-class TTree;
-class TDirectory;
-R__EXTERN TDirectory * gDirectory;
-//class TBranch;
-
-class AliTPCD : public TNamed{
-
-public:
- AliTPCD(
- Text_t * name ="DIGIT",
- AliTPCParam *param=0,
- AliTPCPRF2D *prf=0,
- AliTPCRF1D *prfz=0);
- ~AliTPCD();
-
-public:
-
- AliTPCParam & GetParam() {return *fParam;}
- //give us reference to the parameters
- AliTPCPRF2D & GetPRF2D() {return *fPRF;}
- //give us reference to 2-dimensional pad response function object
- //this is responsible for respnse in x and y dimension
- AliTPCRF1D & GetRF() {return *fRF;}
- //give us reference to 1 dimensionl response
- //this is responsible for z-direction
- TClonesArray * GetArray() {return fDigits;}
- //return reference for digits array
-
- TTree * GetTree() { return fTreeD;}
- //return refeence to actual tree
- Bool_t SetTree(Int_t nevent=0, TDirectory *dir = gDirectory);
- //map tree from given directory
- Bool_t MakeTree(Int_t nevent=0);
- //map tree from given directory
- void Fill();
-
-protected:
-
-public:
- AliTPCParam * fParam; //geometry and gas parameters object
- AliTPCPRF2D * fPRF; //x and y pad response function object
- AliTPCRF1D * fRF; //z (time) response function object
- TClonesArray *fDigits; //aray of tpc Digits
- TTree *fTreeD; //tree
-private:
- AliTPCD *fpthis; //pointer to object
- ClassDef(AliTPCD,2)
-};
-
-
-#endif /* ALITPCD_H */
--- /dev/null
+void AliTPCDigitDisplay(int sec, int row, int lab=-1,
+ int max_t_chan=500, float min_t=0., float max_t=500.,
+ int max_p_chan=150, float min_p=0., float max_p=150.)
+{
+// Dynamically link some shared libs
+ if (gClassTable->GetID("AliRun") < 0) {
+ gROOT->LoadMacro("loadlibs.C");
+ loadlibs();
+ }
+
+// Connect the Root Galice file containing Geometry, Kine and Hits
+ TFile *f = (TFile*)gROOT->GetListOfFiles()->FindObject("galice.root");
+ if (f) f->Close();
+ //f = new TFile("galice.root");
+ f = TFile::Open("rfio:galice.root");
+
+ AliTPCParam *par=(AliTPCParam *)f.Get("75x40_100x60");
+
+ char s[80];
+ sprintf(s,"Sector %d Row %d\n",sec,row);
+ TH2F *h = new TH2F("h",s,max_t_chan,min_t,max_t,max_p_chan,min_p,max_p);
+
+ TTree *t=(TTree*)f.Get("TreeD_75x40_100x60");
+ AliSimDigits dummy, *digit=&dummy;
+ t->GetBranch("Segment")->SetAddress(&digit);
+ for (int i=0; i<t->GetEntries(); i++) {
+ t->GetEvent(i);
+ int ss,rr;
+ par->AdjustSectorRow(digit->GetID(),ss,rr);
+ if (ss==sec && rr==row) goto ok;
+ }
+ return;
+
+ok:
+ int imax=0, jmax=0, qmax=0;
+ digit->First();
+ do {
+ Short_t dig=digit->CurrentDigit();
+ int i=digit->CurrentRow(), j=digit->CurrentColumn();
+ if (lab >= 0) {
+ int lab0=digit->GetTrackID(i,j,0);
+ int lab1=digit->GetTrackID(i,j,1);
+ int lab2=digit->GetTrackID(i,j,2);
+ if (lab0!=lab) if (lab1!=lab) if (lab2!=lab) continue;
+ if (dig>qmax) {imax=i; jmax=j; qmax=dig;}
+ cerr<<lab0<<' '<<lab1<<' '<<lab2<<endl;
+ }
+ h->Fill(i,j,dig);
+ } while (digit->Next());
+ if (qmax>0) {cerr<<"Peak (time,pad,q) : "<<imax<<' '<<jmax<<' '<<qmax<<endl;}
+
+ h->SetMaximum(100);
+ gStyle->SetOptStat(0);
+ TCanvas *c1=new TCanvas("c1","TPC digits display",0,0,1110,680);
+ TPad *p1=new TPad("p1","",0,0,1,0.5);
+ p1->Draw();
+ TPad *p2=new TPad("p2","",0,0.5,1,1);
+ p2->Draw();
+ p2->cd();
+ h->Draw("lego");
+ p1->cd();
+ h->Draw("colz");
+}
+
--- /dev/null
+/**************************************************************************
+ * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
+ * *
+ * Author: The ALICE Off-line Project. *
+ * Contributors are mentioned in the code where appropriate. *
+ * *
+ * Permission to use, copy, modify and distribute this software and its *
+ * documentation strictly for non-commercial purposes is hereby granted *
+ * without fee, provided that the above copyright notice appears in all *
+ * copies and that both the copyright notice and this permission notice *
+ * appear in the supporting documentation. The authors make no claims *
+ * about the suitability of this software for any purpose. It is *
+ * provided "as is" without express or implied warranty. *
+ **************************************************************************/
+
+/*
+$Log$
+Revision 1.1.4.2 2000/04/10 11:37:42 kowal2
+
+Digits handling in a new data structure
+
+*/
+
+///////////////////////////////////////////////////////////////////////////////
+// //
+// Time Projection Chamber clusters objects //
+//
+// Origin: Marian Ivanov , GSI Darmstadt
+// //
+// //
+// //
+///////////////////////////////////////////////////////////////////////////////
+#include "AliTPCParam.h"
+#include "AliTPCParam.h"
+#include "AliTPCRF1D.h"
+#include "AliTPCPRF2D.h"
+
+#include "TObjArray.h"
+#include "AliSegmentID.h"
+#include "AliSegmentArray.h"
+
+#include "AliArrayI.h"
+#include "AliArrayS.h"
+
+
+#include "AliDigits.h"
+#include "AliSimDigits.h"
+#include "AliDigitsArray.h"
+#include "AliTPCDigitsArray.h"
+//#include "TClonesArray.h"
+#include "TDirectory.h"
+
+
+
+//_____________________________________________________________________________
+
+ClassImp(AliTPCDigitsArray)
+
+AliTPCDigitsArray::AliTPCDigitsArray(Bool_t sim)
+{
+ //
+ //default constructor
+ fParam = 0;
+ fBSim = sim;
+ if ( sim == kTRUE) SetClass("AliSimDigits");
+ else
+ SetClass("AliDigits");
+ fParam = 0;
+ // fPRF = 0;
+ //fRF = 0;
+ fCompression = 1;
+ fTrackLevel = 3;
+}
+
+AliTPCDigitsArray::~AliTPCDigitsArray()
+{
+ //
+
+ //
+}
+
+AliDigits * AliTPCDigitsArray::CreateRow(Int_t sector, Int_t row)
+{
+ //
+ //create digits row
+ //
+ //if row just exist - delete it
+ AliTPCParam * param = (AliTPCParam*)fParam;
+ Int_t index = param->GetIndex(sector,row);
+ AliDigits * dig = (AliDigits *)(*this)[index];
+ if (dig !=0) delete dig;
+
+ dig = (AliDigits *) AddSegment(index);
+ if (dig == 0) return 0;
+ dig->Allocate(param->GetMaxTBin(),param->GetNPads(sector,row));
+ if (fBSim == kTRUE) ((AliSimDigits*) dig)->AllocateTrack(fTrackLevel);
+ return dig;
+}
+
+
+AliDigits * AliTPCDigitsArray::GetRow(Int_t sector,Int_t row)
+{
+ //
+ //return clusters ((AliTPCDigitsRow *) per given sector and padrow
+ //
+ if (fParam==0) return 0;
+ Int_t index = ((AliTPCParam*)fParam)->GetIndex(sector,row);
+ return (AliDigits *)(*this)[index];
+}
+
+AliDigits * AliTPCDigitsArray::LoadRow(Int_t sector,Int_t row)
+{
+ //
+ //return clusters ((AliTPCDigitsRow *) per given sector and padrow
+ //
+ if (fParam==0) return 0;
+ Int_t index = ((AliTPCParam*)fParam)->GetIndex(sector,row);
+ return (AliDigits *)LoadSegment(index);
+}
+
+Bool_t AliTPCDigitsArray::StoreRow(Int_t sector,Int_t row)
+{
+ //
+ //return clusters ((AliTPCDigitsRow *) per given sector and padrow
+ //
+ AliTPCParam * param = (AliTPCParam*)fParam;
+ if (fParam==0) return 0;
+ Int_t index = param->GetIndex(sector,row);
+ ( (AliDigits *)At(index))->CompresBuffer(fCompression,param->GetZeroSup());
+ if (fBSim == kTRUE) ( (AliSimDigits *)At(index))->CompresTrackBuffer(1);
+ StoreSegment(index);
+ return kTRUE;
+}
+
+Bool_t AliTPCDigitsArray::ClearRow(Int_t sector,Int_t row)
+{
+ //
+ //return clusters ((AliTPCDigitsRow *) per given sector and padrow
+ //
+ if (fParam==0) return 0;
+ Int_t index = ((AliTPCParam*)fParam)->GetIndex(sector,row);
+ ClearSegment(index);
+ return kTRUE;
+}
+
+
+
+Bool_t AliTPCDigitsArray::Setup(AliDetectorParam *param)
+{
+ //
+ //setup function to adjust array parameters
+ //
+ if (param==0) return kFALSE;
+ if (fParam !=0) delete fParam;
+ // fParam = new AliTPCParam((AliTPCParam&)(*param));
+ fParam = param;
+ return MakeArray(((AliTPCParam*)fParam)->GetNRowsTotal());
+}
+
+Bool_t AliTPCDigitsArray::Update()
+{
+ //
+ //setup function to adjust array parameters
+ //
+ if (fParam ==0 ) return kFALSE;
+ if (fTree!=0) return MakeDictionary( ((AliTPCParam*)fParam)->GetNRowsTotal()) ;
+ ((AliTPCParam*)fParam)->Update();
+ return MakeArray(((AliTPCParam*)fParam)->GetNRowsTotal());
+}
--- /dev/null
+#ifndef ALITPCDIGITSARRAY_H
+#define ALITPCDIGITSARRAY_H
+/* Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
+ * See cxx source for full Copyright notice */
+
+/* $Id$ */
+
+////////////////////////////////////////////////
+// Manager class for TPC clusters //
+////////////////////////////////////////////////
+
+#include "AliDetector.h"
+#include "AliHit.h"
+#include "AliDigits.h"
+#include "AliSegmentArray.h"
+#include "AliDigitsArray.h"
+#include "AliTPCParam.h"
+
+#include <TMatrix.h>
+#include <TTree.h>
+#include <TClonesArray.h>
+
+
+class TClonesArray;
+class TObjArray;
+class AliTPCPRF2D;
+class AliTPCRF1D;
+
+class AliTPCDigitsArray : public AliDigitsArray {
+public:
+ AliTPCDigitsArray(Bool_t sim=kTRUE);
+ ~AliTPCDigitsArray();
+ AliDigits * GetRow(Int_t sector,Int_t row); //return pointer to row from array
+ AliDigits * CreateRow(Int_t sector, Int_t row); //
+ AliDigits * LoadRow(Int_t sector,Int_t row);
+ Bool_t StoreRow(Int_t sector,Int_t row);
+ Bool_t ClearRow(Int_t sector,Int_t row);
+ Bool_t Setup(AliDetectorParam *param);
+
+ Bool_t IsSimulated(){return fBSim;}
+ Bool_t Update(); //
+private:
+ //AliTPCPRF2D * fPRF; //x and y pad response function object
+ //AliTPCRF1D * fRF; //z (time) response function object
+ Bool_t fBSim; //signalize if we have digits with track ID
+ Int_t fCompression; //default compression for AliDigits - used in storing
+ Int_t fTrackLevel; //default level for track ID storing
+ ClassDef(AliTPCDigitsArray,1)
+};
+
+#endif //ALITPCCLUSTERSARRAY_H
+++ /dev/null
-void AliTPCDigitsDisplay(int sec, int row,
- int max_t_chan=500, float min_t=0., float max_t=500.,
- int max_p_chan=200, float min_p=0., float max_p=200.)
-{
-// Dynamically link some shared libs
- if (gClassTable->GetID("AliRun") < 0) {
- gROOT->LoadMacro("loadlibs.C");
- loadlibs();
- } else {
- delete gAlice;
- gAlice=0;
- }
-
-// Connect the Root Galice file containing Geometry, Kine and Hits
- TFile *f = (TFile*)gROOT->GetListOfFiles()->FindObject("galice.root");
- if (f) f->Close();
- f = new TFile("galice.root");
-
- TClonesArray *fDigits=new TClonesArray("AliTPCdigit",10000);
- TTree *t=(TTree*)f->Get("TreeD0_Param1");
- t->GetBranch("Digits")->SetAddress(&fDigits);
- Int_t sectors_by_rows=(Int_t)t->GetEntries();
- for (Int_t n=0; n<sectors_by_rows; n++) {
- if (!t->GetEvent(n)) continue;
- AliTPCdigit *dig=(AliTPCdigit*)fDigits->UncheckedAt(0);
-
- if (sec < dig->fSector) break;
- if (sec != dig->fSector) continue;
- if (row != dig->fPadRow) continue;
-
- char s[80];
- sprintf(s,"Sector %d Row %d\n",sec,row);
- TH2F *h = new TH2F("h",s,max_t_chan,min_t,max_t,max_p_chan,min_p,max_p);
- Int_t ndigits=fDigits->GetEntriesFast();
- for (Int_t ndig=0; ndig<ndigits; ndig++) {
- dig=(AliTPCdigit*)fDigits->UncheckedAt(ndig);
- if (dig->fSignal < 0) continue; //cluster finder threshold
- h->Fill(dig->fTime,dig->fPad,dig->fSignal);
- }
- h->SetMaximum(200);
- gStyle->SetOptStat(0);
- TCanvas *c1=new TCanvas("c1","TPC digits display",0,0,1110,680);
- TPad *p1=new TPad("p1","",0,0,1,0.5);
- p1->Draw();
- TPad *p2=new TPad("p2","",0,0.5,1,1);
- p2->Draw();
- p2->cd();
- h->Draw("lego");
- p1->cd();
- h->Draw("colz");
- }
-}
-
--- /dev/null
+/**************************************************************************
+ * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
+ * *
+ * Author: The ALICE Off-line Project. *
+ * Contributors are mentioned in the code where appropriate. *
+ * *
+ * Permission to use, copy, modify and distribute this software and its *
+ * documentation strictly for non-commercial purposes is hereby granted *
+ * without fee, provided that the above copyright notice appears in all *
+ * copies and that both the copyright notice and this permission notice *
+ * appear in the supporting documentation. The authors make no claims *
+ * about the suitability of this software for any purpose. It is *
+ * provided "as is" without express or implied warranty. *
+ **************************************************************************/
+
+/*
+$Log$
+Revision 1.1.4.2 2000/04/10 11:37:42 kowal2
+
+Digits handling in a new data structure
+
+*/
+
+//-----------------------------------------------------------------------------
+//
+//
+// Author: Marian Ivanov
+//
+// Implementation of class TTPCDigitsH
+//
+//-----------------------------------------------------------------------------
+////////////////////////////////////////////////
+// Manager class for AliTPCDigitsH //
+////////////////////////////////////////////////
+
+#include <iostream.h>
+#include "TMath.h"
+// other include files follow here
+#include "TFile.h"
+//*KEEP,TFile.
+#include "TROOT.h"
+#include "TGraph.h"
+#include "AliRun.h"
+#include "AliDisplay.h"
+#include "TPad.h"
+#include "TCanvas.h"
+#include "TCanvasImp.h"
+#include "TPaveText.h"
+//*KEEP,TH1.
+#include "TH1.h"
+//*KEEP,TH2
+#include "AliH2F.h"
+//*KEEP,TF2.
+#include "TF2.h"
+//*KEEP,TClonesArray,T=C++.
+#include "TClonesArray.h"
+#include "TTree.h"
+//GALICE includes
+#include "GParticle.h"
+#include "AliTPC.h"
+#include "AliTPCParam.h"
+#include "AliTPCD.h"
+#include "AliTPCDigitsH.h"
+
+
+R__EXTERN TSystem * gSystem;
+R__EXTERN AliRun * gAlice;
+
+
+
+ClassImp(AliTPCDigitsH)
+
+AliTPCDigitsH::AliTPCDigitsH()
+{
+//Begin_Html
+/*
+<img src="gif/TPCDigitsH.gif">
+*/
+//End_Html
+
+ fsec = 1;
+ frow = 1;
+ fpad = 1;
+ fTimeN = 500;
+ fTimeStart = 0;
+ fTimeStop = 500;
+ fOccuN =25;
+ fbDelHisto = kFALSE;
+ fEventN = 0; //event nuber connected to digit tree
+ fThreshold = 5;
+
+ fParticles = 0;
+ fDigits= 0;
+
+ fDParam =0;
+
+ fbIOState = kFALSE;
+ fbDigState = kFALSE;
+}
+
+AliTPCDigitsH::~AliTPCDigitsH()
+{
+
+}
+
+AliTPCDigitsH::AliTPCDigitsH(const AliTPCDigitsH &)
+{
+}
+
+AliTPCDigitsH & AliTPCDigitsH::operator = (const AliTPCDigitsH &)
+{
+ return *this;
+}
+void AliTPCDigitsH::SetDParam(AliTPCD * dig)
+{
+ if (dig!=0)
+ {
+ fDParam =dig;
+ fTPCParam = &(fDParam->GetParam());
+ }
+ else
+ {
+ fTPCParam = 0;
+ fDParam =0;
+ }
+}
+
+AliTPCParam *& AliTPCDigitsH::GetParam()
+{
+ return fTPCParam;
+}
+
+
+void AliTPCDigitsH::CloseFiles()
+{
+ if (fin)
+ {
+ fin->Close();
+ //try
+ // {
+ delete fin;
+ // // }
+ // //catch(...)
+ // // {
+ // cout<<"FIN Delete error. Contact autor of root \n";
+ // };
+ fin = 0;
+ };
+ if (fout)
+ {
+ fout->Close();
+ //try
+ //{
+ // delete fout;
+ //}
+ // catch(...)
+ //{
+ // cout<<"Out Delete error. Contact autor of root \n";
+ //};
+ fout =0;
+ };
+ fbIOState = kFALSE;
+ fbDigState = kFALSE;
+}
+
+Bool_t AliTPCDigitsH::SetIO(const char * inFile, const char* outFile )
+{
+ /// Set input and output file
+ /// control permisions and so on
+ /// if all is OK then set flag fbIOState = kTRUE
+ fbIOState = kFALSE;
+ TString s1=inFile;
+ TString s2=outFile;
+ // important ---- it close previious open file if this file exist
+ if (fin)
+ {
+ if (fin == fout) fout = NULL;
+ fin->Close();
+ // try
+ //{
+ delete fin;
+ //}
+ //catch(...)
+ //{
+ // cout<<"Fin Delete error. Contact autor of root \n";
+ //};
+ fin = 0;
+ };
+ // important ---- it close previous open file if this file exist
+ if (fout)
+ {
+ fout->Close();
+ //try
+ //{
+ delete fout;
+ //}
+ //catch(...)
+ //{
+ // cout<<"Fout Delete error. Contact autor of root \n";
+ //};
+ fout = 0;
+ };
+
+ //close the files if exist in root enviroment
+ TFile *file = (TFile*)gROOT->GetListOfFiles()->FindObject((char*)inFile);
+ if (file) file->Close();
+ file = (TFile*)gROOT->GetListOfFiles()->FindObject((char*)outFile);
+ if (file) file->Close();
+ //if input file is the output file
+ if (s1 == s2 )
+ {
+ if (gSystem->AccessPathName((char*)inFile, kWritePermission ) == kFALSE)
+ fin = new TFile((char*)inFile,"UPDATE","trees with digits");
+ if (!(fin))
+ {
+ cout<<"Input file couldn't be open for writing \n";
+ cout<<"Loook if the file exiest or if you have permision to write \n";
+ return kFALSE;
+ }
+ else
+ {
+ fout = fin;
+ fbIOState = kTRUE;
+ return kTRUE;
+ }
+ }
+ //open input file
+ if (gSystem->AccessPathName((char*)inFile, kReadPermission ) == kFALSE)
+ fin = new TFile((char*)inFile,"UPDATE","trees with digits");
+ else
+ {
+ cout<<"Input file couldn't be open\n";
+ cout<<"Maybe the file is not open \n";
+ return kFALSE ;
+ }
+ if (!(fin))
+ {
+ cout<<"Input file couldn't be open\n";
+ cout<<"Probably not root file \n";
+ return kFALSE ;
+ }
+
+ //open output file
+ if (gSystem->AccessPathName((char*)outFile, kWritePermission) == kFALSE)
+ fout = new TFile((char *)outFile,"UPDATE");
+ else
+ fout = new TFile((char *)outFile,"NEW");
+
+ if (!(fout))
+ {
+ cout<<"Output file couldn't be open\n";
+ return kFALSE ;
+ }
+ //if input and output file is OK set state variable to true
+ fbIOState = kTRUE;
+ return kTRUE;
+}
+
+Bool_t AliTPCDigitsH::SetEventN(Int_t EventN=0)
+{
+ if (!(fin))
+ {
+ cout<<"Warning: Input file not open !!! \n";
+ return kFALSE;
+ }
+ fin->cd();
+ if (EventN>-1) fEventN = EventN;
+ fParticles = 0;
+ if (gAlice)
+ {
+ delete gAlice;
+ gAlice =0;
+ }
+ gAlice = (AliRun*) fin->Get("gAlice");
+ if (gAlice == 0 )
+ cout<<" Warning : AliRun objects not found in input file \n.";
+ else
+ {
+ gAlice->GetEvent(fEventN);
+ fParticles = gAlice->Particles();
+ }
+ if (fParticles == 0)
+ return kFALSE;
+ else
+ return kTRUE;
+}
+
+
+
+Bool_t AliTPCDigitsH::SetTree(Int_t eventn )
+{
+ fbDigState = kFALSE;
+ ftree = 0;
+ if ( fbIOState == kFALSE)
+ {
+ cout<<"IO files not adjusted \n FIX IT!!!";
+ return kFALSE;
+ }
+ fin->cd();
+ if (fDParam->SetTree(eventn)==0){
+ fbDigState = kFALSE;
+ cout<<"Input tree doesn't exist !!! \n";
+ return kFALSE;
+ }
+ fDigits = fDParam->GetArray();
+ ftree = fDParam->GetTree();
+ fbDigState=kTRUE;
+ return kTRUE;
+}
+
+void AliTPCDigitsH::SetSecRowTime(Int_t sec , Int_t row , Int_t TimeN, Float_t TimeStart, Float_t TimeStop )
+{
+ fsec = sec;
+ frow = row;
+ fTimeN =TimeN;
+ fTimeStart = TimeStart;
+ fTimeStop = TimeStop;
+}
+
+void AliTPCDigitsH::SetParticles(Int_t sec = -1, Int_t row = -1 ,
+ Int_t size1 = 30000,Int_t size2=300,
+ Bool_t all=kTRUE )
+{
+ if (sec>0) fsec = sec;
+ if (row>-1) frow =row;
+ char s[80];
+ char sh[80];
+ // create particles histograms
+ sprintf(s,"Sector %d Row %d\n",fsec,frow);
+ sprintf(sh,"Particles%d_%d",fsec,frow);
+ fHParticles = new TH1F(sh,s,size1,4,size1);
+
+ sprintf(s,"Sector %d Row %d\n",fsec,frow);
+ sprintf(sh,"All particles%d_%d",fsec,frow);
+ fHAllP = new TH1F(sh,s,200,1,25);
+
+ sprintf(s,"Sector %d Row %d\n",fsec,frow);
+ sprintf(sh,"Secondary Particles%d_%d",fsec,frow);
+ fHSecondaryP = new TH1F(sh,s,200,1,25);
+
+ if (!(fin))
+ {
+ cout<<"Input file not open, open file before \n";
+ }
+ else
+{
+ fin->cd();
+ Int_t sectors_by_rows=(Int_t)ftree->GetEntries();
+ GParticle * particle;
+ // loop over all sectors and rows
+ for (Int_t n=0; n<sectors_by_rows; n++)
+ {
+ if (!ftree->GetEvent(n)) continue;
+ AliTPCdigit *dig=(AliTPCdigit*)fDigits->UncheckedAt(0);
+ if (fsec < dig->fSector) break;
+ if (fsec != dig->fSector) continue;
+ if (frow != dig->fPadRow) continue;
+
+ Int_t ndigits=fDigits->GetEntriesFast();
+ //loop over all digits in sector pad
+ for (Int_t ndig=0; ndig<ndigits; ndig++)
+ {
+ Float_t x,y;
+ dig=(AliTPCdigit*)fDigits->UncheckedAt(ndig);
+ fHParticles->Fill(dig->fTracks[0]);
+ // get pointer to particle information and fill All and secondary histo
+ particle = (GParticle*) fParticles->UncheckedAt(dig->fTracks[0]);
+ fHAllP->Fill(particle->GetKF());
+ // Int_t id = particle->GetKF();
+ x = (Float_t)particle->GetVx();
+ y = (Float_t)particle->GetVy();
+ if ( (x*x+y*y ) > 1 )
+ fHSecondaryP->Fill(particle->GetKF());
+ if (all==kTRUE)
+ {
+ fHParticles->Fill(dig->fTracks[1]);
+ particle = (GParticle*) fParticles->UncheckedAt(dig->fTracks[1]);
+ fHAllP->Fill(particle->GetKF());
+ x = (Float_t)particle->GetVx();
+ y = (Float_t)particle->GetVy();
+ if ( (x*x+y*y ) > 1 )
+ fHSecondaryP->Fill(particle->GetKF());
+ fHParticles->Fill(dig->fTracks[2]);
+ particle = (GParticle*) fParticles->UncheckedAt(dig->fTracks[2]);
+ fHAllP->Fill(particle->GetKF());
+ x = (Float_t)particle->GetVx();
+ y = (Float_t)particle->GetVy();
+ if ( (x*x+y*y ) > 1 )
+ fHSecondaryP->Fill(particle->GetKF());
+ }
+ }
+ }
+ //make histogram with multiplicity
+ char s[80];
+ char sh[80];
+ if (all==kTRUE)
+ sprintf(s,"Number of AliDigits over threshold per one track in sector %d Row %d\n (all three most important track recorded)",fsec,frow);
+ else
+ sprintf(s,"Number of AliDigits over threshold per sector %d Row %d\n (only most important track)",fsec,frow);
+ sprintf(sh,"His_%d_%d",fsec,frow);
+ fHPartMultiplicity = new TH1F(sh,s,size2,1,size2);
+ for (Int_t i=1;i<size1;i++)
+ {
+ Int_t mul=Int_t(fHParticles->GetBinContent(i));
+ if (mul>0) fHPartMultiplicity->Fill(mul);
+ }
+ if (fout)
+ {
+ fout->cd();
+ fHParticles->Write();
+ fHPartMultiplicity->Write();
+ //fHSecondaryP->Write();
+ //fHAllP->Write();
+ }
+ }
+}
+
+
+void AliTPCDigitsH::Anal()
+{
+ if (fbIOState == kFALSE)
+ {
+ cout<<"Input output problem. \n Do you initialize IO files ? \n";
+ return;
+ }
+ if (fbDigState == kFALSE)
+ {
+ cout<<"Input file doesn't enhalt selected tree \n";
+ return;
+ }
+ fout->cd();
+
+//if we dont want let histogram in memory then we delete old histogram
+ if ( (fH2Digit) && (fbDelHisto == kTRUE) )
+ {
+ // try
+ //{
+ // delete fH2Digit;
+ //}
+ // catch(...)
+ //{
+ // cout<<"Delete error. Contact autor of root \n";
+ //};
+ fH2Digit = 0;
+ }
+ char s[80];
+ char sh[80];
+ sprintf(s,"Sector %d Row %d\n",fsec,frow);
+ sprintf(sh,"h%d_%d",fsec,frow);
+
+ if ( (fout) && (fbDelHisto == kFALSE) )
+ {
+ fH2Digit = (AliH2F *) fout->Get(sh);
+ if (fH2Digit) return;
+ }
+
+ Int_t n_of_pads =fTPCParam->GetNPads(fsec,frow);
+
+ fH2Digit = new AliH2F(sh, s, fTimeN, fTimeStart, fTimeStop, n_of_pads, 0, n_of_pads-1);
+
+ if (!(fout))
+ {
+ cout<<"Input file not open, open file before \n";
+ }
+ else
+ {
+ //fin->cd();
+ Int_t sectors_by_rows=(Int_t)ftree->GetEntries();
+ //loop over all sectors and rows
+ for (Int_t n=0; n<sectors_by_rows; n++) {
+ if (!ftree->GetEvent(n)) continue;
+ AliTPCdigit *dig=(AliTPCdigit*)fDigits->UncheckedAt(0);
+ if (fsec < dig->fSector) break;
+ if (fsec != dig->fSector) continue;
+ if (frow != dig->fPadRow) continue;
+
+ Int_t ndigits=fDigits->GetEntriesFast();
+ //loop over all digits in sector pad
+ for (Int_t ndig=0; ndig<ndigits; ndig++) {
+ dig=(AliTPCdigit*)fDigits->UncheckedAt(ndig);
+ fH2Digit->Fill(dig->fTime,dig->fPad,dig->fSignal);
+ }
+ }
+ if (fout) fout->cd();
+ fH2Digit->Write();
+ }
+
+}
+void AliTPCDigitsH::Draw(Option_t * opt1 ="cont1" , Option_t * opt2 = "error",
+ Option_t * opt3 = "L" )
+{
+ TString o1 = opt1;
+ o1.ToLower();
+
+ TString o2 = opt2;
+ o2.ToLower();
+
+ TString o3 = opt3;
+ o3.ToLower();
+
+ fcanvas = new TCanvas("dh","Digits Histograms",700,900);
+
+ if (fTitle)
+ {
+ // try
+ //{
+ //delete fTitle;
+ //}
+ // catch(...)
+ //{
+ // cout<<"Delete error. Contact autor of root \n";
+ //};
+ fTitle = 0;
+ }
+ fTitle = new TPaveText(0.2,0.96,0.8,0.995);
+ fTitle->AddText("Occupancy calculation for TPC");
+ fTitle->Draw();
+
+ fpad1 = new TPad("pad1","",0.05,0.7,0.95,0.95,21);
+ fpad1->Draw();
+ fpad2 = new TPad("pad2","",0.05,0.4,0.95,0.65,21);
+ fpad2->Draw();
+ fpad3 = new TPad("pad3","",0.05,0.05,0.95,0.35,21);
+ fpad3->Draw();
+
+ fpad1->cd();
+ // pad1->TPaveText::title.SetSize(0.1);
+ if (fH2Digit)
+ {
+ fH2DigitBW->Draw(o1);
+ fH2DigitBW->SetXTitle("time bin");
+ fH2DigitBW->SetYTitle("pad number");
+ }
+ fpad2->cd();
+ fH1Occu->Fit("pol0");
+ if (fH1Occu)
+ {
+ fH1Occu->Draw(o2);
+ fH1Occu->SetXTitle("time bin");
+ fH1Occu->SetYTitle("occupancy");
+ }
+ fpad3->cd();
+ if (fH1Digit)
+ {
+ fH1Digit->Draw(o3);
+ fH1Digit->SetXTitle("time bin");
+ fH1Digit->SetYTitle("ADC amplitude ");
+ }
+
+};
+
+void AliTPCDigitsH::DeleteHisto(const Text_t *namecycle)
+{
+ if (fout) fout->Delete(namecycle);
+}
+
+void AliTPCDigitsH::SetHisto(Int_t pad = 1 )
+{
+
+ Int_t n_of_pads = fTPCParam->GetNPads(fsec,frow);
+ if (pad > (n_of_pads-1))
+ {
+ cout<<"Pad number is greater then actula number of pads in thi row \n";
+ cout<<"Noch einmal \n";
+ return;
+ }
+
+ fpad = pad;
+ Anal();
+
+ // if ( (fH1Digit) && (fbDelHisto == kTRUE))
+ // {
+ // try
+ // {
+ // // delete fH1Digit;
+ // }
+ // catch(...)
+ // {
+ // cout<<"Delete error. Contact autor of root \n";
+ // };
+ // fH1Digit = 0;
+ // }
+
+ char s[80];
+ char sh[80];
+ sprintf(s,"example sector %d Row %d Pad %d",fsec,frow,fpad);
+ sprintf(sh,"h%d_%d_%d",fsec,frow,fpad);
+ fH2DigitBW = new AliH2F("bw", "", fTimeN, fTimeStart, fTimeStop, n_of_pads, 0, n_of_pads-1);
+ fH1Digit = new TH1F(sh,s,fTimeN,fTimeStart,fTimeStop);
+
+ for (Int_t i = 0;i<fTimeN;i++)
+ {
+ Int_t index = fH2Digit->GetBin(i,pad);
+ Float_t weight = fH2Digit->GetBinContent(index);
+ fH1Digit->Fill(i,weight);
+ };
+
+
+ sprintf(s,"Occupancy in sector %d Row %d threshold = %d",fsec,frow,fThreshold);
+ sprintf(sh,"hoccu%d_%d_%d",fsec,frow,fpad);
+ fH1Occu = new TH1F(sh,s,fOccuN,fTimeStart,fTimeStop);
+
+ for (Int_t i = 0;i<fOccuN;i++)
+ {
+ Int_t over =0;
+ Int_t all =0;
+ for (int itime = i*(fTimeN/fOccuN); itime<(i+1)*(fTimeN/fOccuN);itime++)
+ {
+ for (Int_t ipad = 0; ipad < n_of_pads; ipad++)
+ {
+ Int_t index = fH2Digit->GetBin(itime,ipad);
+ if ( (ipad>3) && ((ipad+3)<n_of_pads)){
+ all++;
+ if (fH2Digit->GetBinContent(index) >fThreshold) over++ ;
+ }
+ if (fH2Digit->GetBinContent(index) >fThreshold)
+ fH2DigitBW->Fill(itime,ipad,1);
+ else
+ fH2DigitBW->Fill(itime,ipad,0);
+ }
+ }
+ Float_t occu = ((Float_t)over) /((Float_t) (all));
+ // Float_t time = ((fTimeStop-fTimeStart)/fOccuN)*i+fTimeStart;
+
+ fH1Occu->SetBinContent(i,occu);
+ // Int_t index = fH1Occu->GetBin(i);
+ Float_t error = sqrt( ((Float_t) ((over)/25+1)) )/((Float_t)(all)/25.);
+ fH1Occu->SetBinError(i,error);
+
+ };
+
+
+}
+
+
+
+void AliTPCDigitsH::Streamer(TBuffer & R__b)
+{
+ if (R__b.IsReading()) {
+ // Version_t R__v = R__b.ReadVersion();
+ } else {
+ R__b.WriteVersion(AliTPCDigitsH::IsA());
+ }
+}
--- /dev/null
+#ifndef TTPCDIGITSH_H
+#define TTPCDIGITSH_H
+/* Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
+ * See cxx source for full Copyright notice */
+
+/* $Id$ */
+
+////////////////////////////////////////////////
+// Manager class for AliTPCDigitsH //
+////////////////////////////////////////////////
+
+
+// include files and class forward declarations
+
+class TFile;
+class TH2F;
+class AliH2F;
+class TH1F;
+class TPaveText;
+class TPad;
+class TCanvas;
+class AliTPCParam;
+class AliTPCD;
+class TClonesArray;
+class TTree;
+#include "TObject.h"
+#include "TUnixSystem.h"
+
+class AliTPCDigitsH :public TObject{
+public:
+ ~AliTPCDigitsH();
+ AliTPCDigitsH(const AliTPCDigitsH &);
+ AliTPCDigitsH();
+ AliTPCDigitsH & operator = (const AliTPCDigitsH &);
+ AliTPCD * GetDParam() {return fDParam;}
+ void SetDParam(AliTPCD * dig);
+ AliTPCParam *& GetParam();
+ //get tpc parameters
+ TFile * GetIn() {return fin;}
+ TFile * GetOut() {return fout;}
+ void Anal(); //get two dimensional histogram time*pad*amplitude for given
+ void SetSecRowTime(Int_t sec , Int_t row = 1,
+ Int_t TimeN = 500 ,
+ Float_t TimeStart = 0, Float_t TimeStop = 500);
+ //set section row and timing histogram
+ //ranges and calculate histograms
+ void SetHisto( Int_t pad = 1 );
+ virtual void Draw(Option_t * opt1 ="cont1" , Option_t * opt2 = "error",
+ Option_t * opt3 = "L" );
+
+ void CloseFiles(); //close input and output file
+ void DeleteHisto(const Text_t *namecycle); //
+
+ Bool_t SetIO(const char * inFile, const char* outFile);
+ Bool_t SetTree(Int_t eventn =0 );
+ void SetParticles(Int_t sec = -1, Int_t row = -1 ,
+ Int_t size1 = 30000,Int_t size2=300,
+ Bool_t all=1 );
+ Bool_t SetEventN(Int_t EventN=0); //set event number connected to analisys
+
+ void SetbDelHisto(Bool_t bDelHisto) { fbDelHisto = bDelHisto;} //
+ void SetThreshold(Int_t threshold = 10 ) { fThreshold = threshold ;} //
+ /////////////
+ AliH2F & GetHis1() { return *fH2Digit;}
+ AliH2F & GetHisBW() { return *fH2DigitBW;}
+ TH1F & GetHis2() { return *fH1Digit;}
+ TH1F & GetHis3() { return *fH1Occu;}
+ TPad & GetPad1() {return *fpad1;}
+ TPad & GetPad2() {return *fpad2;}
+ TPad & GetPad3() {return *fpad3;}
+ TCanvas &GetCanvas(){return *fcanvas;}
+protected:
+
+private:
+ TFile *fin; //input TTRE file with digits
+ TFile *fout; //output file
+ TPad * fpad1;
+ TPad * fpad2;
+ TPad * fpad3;
+ TCanvas * fcanvas;
+ AliTPCParam * fTPCParam;
+ AliTPCD *fDParam;
+ Bool_t fbIOState;
+ //state of Input and Output file : kTRUE if all is OK
+ Bool_t fbDigState;
+ //state of Input digits tree kTRUE if ftree point to valid digit tree
+ TClonesArray *fDigits; //pointer to digits object used inanal
+ TClonesArray *fParticles; //pointer to particles array
+ TTree *ftree; //pointer to tree with digits
+ Int_t fsec; //actual sector of TPC
+ Int_t frow; //actual row of TPC
+ Int_t fpad; //actual pad
+ Int_t fEventN; //event number connected to
+ Int_t fTimeN; //division number of the time
+ Float_t fTimeStart,fTimeStop; //start and stop time for histograms
+ Int_t fOccuN; //time division for occupancy calculating
+ TPaveText * fTitle; //
+ Int_t fThreshold; //treshold for the ocupancy definition
+ Bool_t fbDelHisto; //swith which tell if we want to delete produced histogram
+
+ AliH2F *fH2Digit; //two dimensional histogram - sector row
+ AliH2F *fH2DigitBW; //black and white histogram over treshold
+ TH1F *fH1Digit; //one dimensional histogram sector row pad
+ TH1F *fH1Occu; //occupancy graph
+ TH1F *fHParticles; //histogram of particles contributing to digits
+ TH1F *fHPartMultiplicity;
+ //histogram of particles multiplicity
+ TH1F *fHAllP; //histogram with accepted time bin for all particles
+ TH1F *fHSecondaryP;
+ //histogram with accepted time bin for secondary particles
+
+ ClassDef(AliTPCDigitsH,1)
+};
+#endif /* TTPCDIGITSH_H */
-
void AliTPCHits2Digits(const char * name= "pokusD_")
{
}
//names of trees
+
const char * inFile = "galice.root";
// const * char ident= "TreeD1par_";
AliTPCPRF2D &prf = paramd->GetPRF2D();
AliTPCRF1D & rf = paramd->GetRF();
- param.SetPadLength(2.0);
- param.SetPadWidth(0.3);
+ param.SetPadLength(2.05);
+ param.SetPadWidth(0.35);
param.SetPadPitchLength(2.05);
param.SetPadPitchWidth(0.35);
param.SetNWires(5);
param.SetNoise(500);
param.SetGasGain(1.e4);
param.SetChipGain(24);
- param.SetSectorAngles(20.,0.,20.,0.);
- param.SetInnerRadiusLow(83.9);
- param.SetInnerRadiusUp(141.3);
+ param.SetSectorAngles(40.,0.,20.,10.);
+ param.SetInnerRadiusLow(83.7);
+ param.SetInnerRadiusUp(132.9);
param.SetOuterRadiusLow(146.9);
param.SetOuterRadiusUp(249.4);
- param.SetTSample(1.9e-7);
- param.SetTSigma(1.5e-7/2.35);
- param.SetInSecLowEdge(81.6);
- param.SetInSecUpEdge(143.6);
- param.SetOuSecLowEdge(144.2);
- param.SetOuSecUpEdge(252.1);
- param.SetEdge(1.5);
- param.SetDeadZone(1.15);
param.Update();
//Set z (time) response function
rf.SetGauss(param.GetZSigma(),param.GetZWidth(),0.4);
rf.Update();
//Set two dimensional pad response function
- TFile f("$(ALICE_ROOT)/TPC/AliTPCprf2d.root");
+ TFile f("TPC/AliTPCprf2d.root");
// prf.Read("prf_205035_Gati_062074_d03");
prf.Read("prf_205035_Gati_062074_d03");
f.Close();
prf.Dump();
printf("**********Digit object dump end********************\n");
- TPC->Hits2DigitsSector(1);
- TPC->Hits2DigitsSector(2);
- TPC->Hits2DigitsSector(3);
- TPC->Hits2DigitsSector(1+18);
- TPC->Hits2DigitsSector(2+18);
- TPC->Hits2DigitsSector(3+18);
- TPC->Hits2DigitsSector(1+36);
- TPC->Hits2DigitsSector(2+36);
- TPC->Hits2DigitsSector(3+36);
- TPC->Hits2DigitsSector(1+36+18);
- TPC->Hits2DigitsSector(2+36+18);
- TPC->Hits2DigitsSector(3+36+18);
+ TPC->Hits2DigitsSector(0);
file->cd();
/*
$Log$
+Revision 1.3.8.2 2000/04/10 08:40:46 kowal2
+
+Small changes by M. Ivanov, improvements of algorithms
+
+Revision 1.3.8.1 2000/04/10 07:56:53 kowal2
+Not used anymore - removed
+
+Revision 1.3 1999/10/05 17:15:46 fca
+Minor syntax for the Alpha OSF
+
Revision 1.2 1999/09/29 09:24:34 fca
Introduction of the Copyright and cvs Log
*/
///////////////////////////////////////////////////////////////////////////////
-// AliTPCPRF2D - //
+// AliTPCPRF2D - //
// Pad response function object in two dimesions //
// This class contains the basic functions for the //
// calculation of PRF according generic charge distribution //
// Origin: Marian Ivanov, Uni. of Bratislava, ivanov@fmph.uniba.sk //
// //
///////////////////////////////////////////////////////////////////////////////
+
+
#include "TMath.h"
#include "AliTPCPRF2D.h"
#include "TF2.h"
#include "TH2.h"
#include "TPaveText.h"
#include "TText.h"
+//
extern TStyle * gStyle;
static Double_t funGauss2D(Double_t *x, Double_t * par)
{
+//Gauss function -needde by the generic function object
return ( TMath::Exp(-(x[0]*x[0])/(2*par[0]*par[0]))*
TMath::Exp(-(x[1]*x[1])/(2*par[1]*par[1])));
static Double_t funCosh2D(Double_t *x, Double_t * par)
{
+ //Cosh function -needde by the generic function object
return ( 1/(TMath::CosH(3.14159*x[0]/(2*par[0]))*
TMath::CosH(3.14159*x[1]/(2*par[1]))));
}
static Double_t funGati2D(Double_t *x, Double_t * par)
{
- //par[1] = is equal to k3X
- //par[0] is equal to pad wire distance
+ //Gati function -needde by the generic function object
Float_t K3=par[1];
Float_t K3R=TMath::Sqrt(K3);
Float_t K2=(TMath::Pi()/2)*(1-K3R/2.);
return res;
}
-
-///////////////////////////////////////////////////////////////////////////
-///////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////
AliTPCPRF2D::AliTPCPRF2D()
{
+ //default constructor for response function object
ffcharge = 0;
fNPRF =NPRF ;
fSigmaX = 0;
+ fSigmaY = 0;
fGRF = 0;
fkNorm = 1;
- forigsigmaY=0;
- forigsigmaX=0;
+ fOrigSigmaY=0;
+ fOrigSigmaX=0;
fNdiv = 5;
+ //set daault angels
+ fChargeAngle = 0;
+ fCosAngle = 0;
//chewron default values
SetPad(0.8,0.8);
SetChevron(0.2,0.0,1.0);
SetY(-0.2,0.2,2);
- // SetGauss(0.22,0.22,1);
}
AliTPCPRF2D::~AliTPCPRF2D()
Float_t AliTPCPRF2D::GetPRF(Float_t xin, Float_t yin, Bool_t inter)
{
- if (ffcharge==0) return 0;
- // Float_t y=Float_t(fNYdiv-1)*(yin-fY1)/(fY2-fY1);
+ //function which return pad response
+ //for the charge in distance xin
+ //return cubic aproximation of PRF or PRF at nearest virtual wire
+ if (ffcharge==0) return 0;
//transform position to "wire position"
Float_t y=fDYtoWire*(yin-fY1);
if (fNYdiv == 1) y=fY1;
c=K-d;
Float_t dy=y-Float_t(i);
Float_t res = a+b*dy+c*dy*dy+d*dy*dy*dy;
- //Float_t res = z1*(1-dy)+z2*dy;
return res;
}
+ return 0.;
}
Float_t AliTPCPRF2D::GetPRFActiv(Float_t xin)
{
- //x xin DStep unit
- //return splaine aproximaton
+ //GEt response function on given charege line
+ //return spline aproximaton
Float_t x = (xin*fDStepM1)+fNPRF/2;
Int_t i = Int_t(x);
Float_t AliTPCPRF2D::GetGRF(Float_t xin, Float_t yin)
{
+ //function which returnoriginal charge distribution
+ //this function is just normalised for fKnorm
if (fGRF != 0 )
return fkNorm*fGRF->Eval(xin,yin)/fInteg;
else
void AliTPCPRF2D::SetParam( TF2 * GRF, Float_t kNorm,
Float_t sigmaX, Float_t sigmaY)
{
+ //adjust parameters of the original charge distribution
+ //and pad size parameters
if (fGRF !=0 ) fGRF->Delete();
fGRF = GRF;
fkNorm = kNorm;
if (sigmaX ==0) sigmaX=(fWidth+fK*fHeightS)/sqrt12;
if (sigmaY ==0) sigmaY=(fWidth+fK*fHeightS)/sqrt12;
- forigsigmaX=sigmaX;
- forigsigmaY=sigmaY;
+ fOrigSigmaX=sigmaX;
+ fOrigSigmaY=sigmaY;
fDStep = TMath::Sqrt(sigmaX*sigmaX+fWidth*fWidth/6.)/10.;
- // Update();
sprintf(fType,"User");
}
void AliTPCPRF2D::SetGauss(Float_t sigmaX, Float_t sigmaY,
Float_t kNorm)
{
+ //
+ // set parameters for Gauss generic charge distribution
+ //
fkNorm = kNorm;
if (fGRF !=0 ) fGRF->Delete();
fGRF = new TF2("fun",funGauss2D,-5.,5.,-5.,5.,4);
funParam[1]=sigmaY;
funParam[2]=fK;
funParam[3]=fHeightS;
- forigsigmaX=sigmaX;
- forigsigmaY=sigmaY;
+ fOrigSigmaX=sigmaX;
+ fOrigSigmaY=sigmaY;
fGRF->SetParameters(funParam);
fDStep = TMath::Sqrt(sigmaX*sigmaX+fWidth*fWidth/6.)/10.;
//by default I set the step as one tenth of sigma
- //Update();
sprintf(fType,"Gauss");
}
void AliTPCPRF2D::SetCosh(Float_t sigmaX, Float_t sigmaY,
Float_t kNorm)
-{
+{
+ // set parameters for Cosh generic charge distribution
+ //
fkNorm = kNorm;
if (fGRF !=0 ) fGRF->Delete();
fGRF = new TF2("fun", funCosh2D,-5.,5.,-5.,5.,4);
funParam[2]=fK;
funParam[3]=fHeightS;
fGRF->SetParameters(funParam);
- forigsigmaX=sigmaX;
- forigsigmaY=sigmaY;
+ fOrigSigmaX=sigmaX;
+ fOrigSigmaY=sigmaY;
fDStep = TMath::Sqrt(sigmaX*sigmaX+fWidth*fWidth/6.)/10.;
//by default I set the step as one tenth of sigma
- //Update();
sprintf(fType,"Cosh");
}
Float_t padDistance,
Float_t kNorm)
{
+ // set parameters for Gati generic charge distribution
+ //
fkNorm = kNorm;
if (fGRF !=0 ) fGRF->Delete();
fGRF = new TF2("fun", funGati2D,-5.,5.,-5.,5.,5);
funParam[3]=fHeightS;
funParam[4]=K3Y;
fGRF->SetParameters(funParam);
- forigsigmaX=padDistance;
- forigsigmaY=padDistance;
+ fOrigSigmaX=padDistance;
+ fOrigSigmaY=padDistance;
fDStep = TMath::Sqrt(padDistance*padDistance+fWidth*fWidth/6.)/10.;
//by default I set the step as one tenth of sigma
- //Update();
sprintf(fType,"Gati");
}
void AliTPCPRF2D::Update()
{
- for (Int_t i=0; i<fNYdiv; i++){
- if (fNYdiv == 1) fActualY = fY1;
+ //
+ //update fields with interpolated values for
+ //PRF calculation
+
+ if ( fGRF == 0 ) return;
+ //initialize interpolated values to 0
+ Int_t i;
+ //Float_t x;
+ for (i =0; i<fNPRF*fNYdiv;i++) ffcharge[i] = 0;
+ //firstly calculate total integral of charge
+
+ ////////////////////////////////////////////////////////
+ //I'm waiting for normal integral
+ //in this moment only sum
+ Float_t x2= 4*fOrigSigmaX;
+ Float_t y2= 4*fOrigSigmaY;
+ Float_t dx = fOrigSigmaX/Float_t(fNdiv*6);
+ Float_t dy = fOrigSigmaY/Float_t(fNdiv*6);
+ Int_t nx = Int_t(0.5+x2/dx);
+ Int_t ny = Int_t(0.5+y2/dy);
+ Int_t ix,iy;
+ fInteg = 0;
+ Double_t dInteg =0;
+ for (ix=-nx;ix<=nx;ix++)
+ for ( iy=-ny;iy<=ny;iy++)
+ dInteg+=fGRF->Eval(Float_t(ix)*dx,Float_t(iy)*dy)*dx*dy;
+ /////////////////////////////////////////////////////
+ fInteg =dInteg;
+ if ( fInteg == 0 ) fInteg = 1;
+
+ for (i=0; i<fNYdiv; i++){
+ if (fNYdiv == 1) fCurrentY = fY1;
else
- fActualY = fY1+Float_t(i)*(fY2-fY1)/Float_t(fNYdiv-1);
+ fCurrentY = fY1+Double_t(i)*(fY2-fY1)/Double_t(fNYdiv-1);
fcharge = &(ffcharge[i*fNPRF]);
Update1();
}
+ //calculate conversion coefitient to convert position to virtual wire
+ fDYtoWire=Float_t(fNYdiv-1)/(fY2-fY1);
+ fDStepM1=1/fDStep;
+ UpdateSigma();
}
void AliTPCPRF2D::Update1()
{
- //initialize to 0
-
-
+ //
+ //update fields with interpolated values for
+ //PRF calculation for given charge line
Int_t i;
- Float_t x;
- for (i =0; i<fNPRF;i++) fcharge[i] = 0;
- if ( fGRF == 0 ) return;
- ////////////////////////////////////////////////////////
- //I'm waiting for normal integral
- //in this moment only sum
- Float_t x2= 4*forigsigmaX;
- Float_t y2= 4*forigsigmaY;
- Float_t dx = forigsigmaX/Float_t(fNdiv*6);
- Float_t dy = forigsigmaY/Float_t(fNdiv*6);
- fInteg = 0;
- for (x=0.;x<x2;x+=dx)
- for (Float_t y=0;y<y2;y+=dy) fInteg+=fGRF->Eval(x,y)*dx*dy;
- fInteg*=4;
- /////////////////////////////////////////////////////
-
-
- if ( fInteg == 0 ) fInteg = 1;
-
+ Double_t x,dx,ddx,ddy,dddx,dddy;
+ Double_t cos = TMath::Cos(fChargeAngle);
+ Double_t sin = TMath::Sin(fChargeAngle);
+
//integrate charge over pad for different distance of pad
for (i =0; i<fNPRF;i++)
- { //x in cm fWidth in cm
+ {
+ //x in cm fWidth in cm
//calculate integral
- Float_t xch = fDStep * (Float_t)(i-fNPRF/2);
- Float_t k=1;
+ Double_t xch = fDStep * (Double_t)(i-fNPRF/2);
+ Double_t k=1;
fcharge[i]=0;
- for (Float_t y=-fHeightFull/2.-fShiftY;
+
+ for (Double_t y=-fHeightFull/2.-fShiftY; //loop over chevron steps
y<fHeightFull/2.;y+=fHeightS){
- Float_t y2=TMath::Min((y+fHeightS),Float_t(fHeightFull/2.));
- Float_t y1=TMath::Max((y),Float_t(-fHeightFull/2.));
- Float_t x1;
+ Double_t y2=TMath::Min((y+fHeightS),Double_t(fHeightFull/2.));
+ Double_t y1=TMath::Max((y),Double_t(-fHeightFull/2.));
+ Double_t x1;
if (k>0)
x1 = (y2-y1)*fK-(fWidth+fK*fHeightS)/2.;
else
x1 =-(fWidth+fK*fHeightS)/2. ;
- Float_t x2=x1+fWidth;
+ Double_t x2=x1+fWidth;
if (y2>y1) {
- if ((x2-x1)*fNdiv<forigsigmaX) dx=(x2-x1);
+ if ((x2-x1)*fNdiv<fOrigSigmaX) dx=(x2-x1);
else{
- dx= forigsigmaX/Float_t(fNdiv);
- dx = (x2-x1)/Float_t(Int_t(3+(x2-x1)/dx));
+ dx= fOrigSigmaX/Double_t(fNdiv);
+ dx = (x2-x1)/Double_t(Int_t(3.5+(x2-x1)/dx));
}
- Float_t dy;
- if ((y2-y1)*fNdiv<forigsigmaY) dy=(y2-y1);
+ Double_t dy;
+ if ((y2-y1)*fNdiv<fOrigSigmaY) dy=(y2-y1);
else{
- dy= forigsigmaY/Float_t(fNdiv);
- dy = (y2-y1)/Float_t(Int_t(3+(y2-y1)/dy));
+ dy= fOrigSigmaY/Double_t(fNdiv);
+ dy = (y2-y1)/Double_t(Int_t(3.5+(y2-y1)/dy));
}
+ //integrate between x1 x2 and y1 y2
+ for (x=x1;x<x2+dx/2.;x+=dx)
+ for (Double_t y=y1;y<y2+dy/2.;y+=dy){
+ if ( (y>(fCurrentY-(4.0*fOrigSigmaY))) &&
+ (y<(fCurrentY+(4.0*fOrigSigmaY)))){
+ Double_t xt=x-k*fK*(y-y1);
+ if ((TMath::Abs(xch-xt)<4*fOrigSigmaX)){
+
+ ddx = xch-(xt+dx/2.);
+ ddy = fCurrentY-(y+dy/2.);
+ dddx = cos*ddx-sin*ddy;
+ dddy = sin*ddx+cos*ddy;
+ Double_t z0=fGRF->Eval(dddx,dddy); //middle point
+
+ ddx = xch-(xt+dx/2.);
+ ddy = fCurrentY-(y);
+ dddx = cos*ddx-sin*ddy;
+ dddy = sin*ddx+cos*ddy;
+ Double_t z1=fGRF->Eval(dddx,dddy); //point down
+
+ ddx = xch-(xt+dx/2.);
+ ddy = fCurrentY-(y+dy);
+ dddx = cos*ddx-sin*ddy;
+ dddy = sin*ddx+cos*ddy;
+ Double_t z3=fGRF->Eval(dddx,dddy); //point up
+
+ ddx = xch-(xt);
+ ddy = fCurrentY-(y+dy/2.);
+ dddx = cos*ddx-sin*ddy;
+ dddy = sin*ddx+cos*ddy;
+ Double_t z2=fGRF->Eval(dddx,dddy); //point left
+
+ ddx = xch-(xt+dx);
+ ddy = fCurrentY-(y+dy/2.);
+ dddx = cos*ddx-sin*ddy;
+ dddy = sin*ddx+cos*ddy;
+ Double_t z4=fGRF->Eval(dddx,dddy); //point right
- for (x=x1;x<x2;x+=dx)
- for (Float_t y=y1;y<y2;y+=dy){
- if ( (y>(fActualY-(4.0*forigsigmaY))) &&
- (y<(fActualY+(4.0*forigsigmaY)))){
- Float_t xt=x-k*fK*(y-y1);
- if ((TMath::Abs(xch-xt)<4*forigsigmaX)){
-
- Float_t z0=fGRF->Eval(xch-(xt+dx/2.),fActualY-(y+dy/2.));
-
- Float_t z1=fGRF->Eval(xch-(xt+dx/2.),fActualY-y);
- Float_t z2=fGRF->Eval(xch-xt,fActualY-(y+dy/2.));
- Float_t z3=fGRF->Eval(xch-(xt-dx/2.),fActualY-y);
- Float_t z4=fGRF->Eval(xch-xt,fActualY-(y-dy/2.));
if (z0<0) z0=0;
if (z1<0) z1=0;
if (z2<0) z2=0;
if (z3<0) z3=0;
if (z4<0) z4=0;
-
- // Float_t a=(z1-z3)/2;
- // Float_t b=(z2-z4)/2;
- Float_t c= (z3+z1-2*z0)/2.;
- Float_t d= (z2+z4-2*z0)/2.;
- Float_t z= (z0+c/12.+d/12.);
-
- //Float_t z= fGRF->Eval(xch-xt,fActualY-y);
- if (z>0.) fcharge[i]+=z*dx*dy/fInteg;
+
+ Double_t c= (z3+z1-2*z0)/2.;
+ Double_t d= (z2+z4-2*z0)/2.;
+ Double_t z= (z0+c/12.+d/12.);
+
+ if (z>0.) fcharge[i]+=fkNorm*z*dx*dy/fInteg;
}
}
}
k*=-1;
}
};
-
- fSigmaX = 0;
+
+}
+
+void AliTPCPRF2D::UpdateSigma()
+{
+ //
+ //calulate effective sigma X and sigma y of PRF
+ fMeanX = 0;
+ fMeanY = 0;
+ fSigmaX = 0;
+ fSigmaY = 0;
+
Float_t sum =0;
- Float_t mean=0;
- for (x =-fNPRF*fDStep; x<fNPRF*fDStep;x+=fDStep)
- { //x in cm fWidth in cm
- Float_t weight = GetPRFActiv(x);
- fSigmaX+=x*x*weight;
- mean+=x*weight;
- sum+=weight;
+ Int_t i;
+ Float_t x,y;
+
+ for (i=-1; i<=fNYdiv; i++){
+ if (fNYdiv == 1) y = fY1;
+ else
+ y = fY1+Float_t(i)*(fY2-fY1)/Float_t(fNYdiv-1);
+ for (x =-fNPRF*fDStep; x<fNPRF*fDStep;x+=fDStep)
+ {
+ //x in cm fWidth in cm
+ Float_t weight = GetPRF(x,y);
+ fSigmaX+=x*x*weight;
+ fSigmaY+=y*y*weight;
+ fMeanX+=x*weight;
+ fMeanY+=y*weight;
+ sum+=weight;
};
+ }
if (sum>0){
- mean/=sum;
- fSigmaX = TMath::Sqrt(fSigmaX/sum-mean*mean);
+ fMeanX/=sum;
+ fMeanY/=sum;
+ fSigmaX = TMath::Sqrt(fSigmaX/sum-fMeanX*fMeanX);
+ fSigmaY = TMath::Sqrt(fSigmaY/sum-fMeanY*fMeanY);
}
else fSigmaX=0;
- //calculate conversion coefitient to convert position to virtual wire
- fDYtoWire=Float_t(fNYdiv-1)/(fY2-fY1);
- fDStepM1=1/fDStep;
}
+
void AliTPCPRF2D::Streamer(TBuffer &R__b)
{
// Stream an object of class AliTPCPRF2D
Version_t R__v = R__b.ReadVersion(); if (R__v) { }
TObject::Streamer(R__b);
//read chewron parameters
- R__b >> fSigmaX;
R__b >> fHeightFull;
R__b >> fHeightS;
R__b >> fShiftY;
R__b >> fWidth;
R__b >> fK;
- R__b >> fActualY;
- //read charge parameters
- R__b >> fType[0];
- R__b >> fType[1];
- R__b >> fType[2];
- R__b >> fType[3];
- R__b >> fType[4];
- R__b >> forigsigmaX;
- R__b >> forigsigmaY;
+ R__b >> fSigmaX;
+ R__b >> fSigmaY;
+ R__b >> fMeanX;
+ R__b >> fMeanY;
+ //read charge parameters
+ R__b.ReadFastArray(fType,5);
+ R__b >> fOrigSigmaX;
+ R__b >> fOrigSigmaY;
R__b >> fkNorm;
R__b >> fK3X;
R__b >> fK3Y;
R__b >> fPadDistance;
- R__b >> fInteg;
-
+ R__b >> fInteg;
//read functions
if (fGRF!=0) {
- delete [] fGRF;
+ fGRF->Delete();
fGRF=0;
}
if (strncmp(fType,"User",3)==0){
if (strncmp(fType,"Cosh",3)==0)
fGRF = new TF2("fun",funCosh2D,-5.,5.,-5.,5.,4);
if (strncmp(fType,"Gati",3)==0)
- fGRF = new TF2("fun",funGati2D,-5.,5.,-5.,5.,5);
-
+ fGRF = new TF2("fun",funGati2D,-5.,5.,-5.,5.,5);
//read interpolation parameters
R__b >>fY1;
R__b >>fY2;
R__b.WriteVersion(AliTPCPRF2D::IsA());
TObject::Streamer(R__b);
//write chewron parameters
- R__b << fSigmaX;
R__b << fHeightFull;
R__b << fHeightS;
R__b << fShiftY;
R__b << fWidth;
R__b << fK;
- R__b << fActualY;
+ R__b << fSigmaX;
+ R__b << fSigmaY;
+ R__b << fMeanX;
+ R__b << fMeanY;
//write charge parameters
- R__b << fType[0];
- R__b << fType[1];
- R__b << fType[2];
- R__b << fType[3];
- R__b << fType[4];
-
- R__b << forigsigmaX;
- R__b << forigsigmaY;
+ R__b.WriteFastArray(fType,5);
+ R__b << fOrigSigmaX;
+ R__b << fOrigSigmaY;
R__b << fkNorm;
R__b << fK3X;
R__b << fK3Y;
void AliTPCPRF2D::DrawX(Float_t x1 ,Float_t x2,Float_t y, Bool_t inter)
{
+ //draw pad response function at interval <x1,x2> at given y position
if (fGRF==0) return ;
const Int_t N=100;
char s[100];
TPad * pad2 = new TPad("pad2PRF","",0.05,0.22,0.95,0.60,21);
pad2->Draw();
- // pad1->cd();
- //pad2->cd();
gStyle->SetOptFit(1);
gStyle->SetOptStat(0);
sprintf(s,"PRF response function for chevron pad");
TH1F * hPRFc = new TH1F("hPRFc",s,N+1,x1,x2);
Float_t x=x1;
Float_t y1;
- // Float_t y2;
for (Float_t i = 0;i<N+1;i++)
{
comment->AddText(s);
sprintf(s,"Y position: %2.2f ",y);
comment->AddText(s);
- sprintf(s,"Sigma x of original distribution: %2.2f ",forigsigmaX);
+ sprintf(s,"Sigma x of original distribution: %2.2f ",fOrigSigmaX);
comment->AddText(s);
- sprintf(s,"Sigma y of original distribution: %2.2f ",forigsigmaY);
+ sprintf(s,"Sigma y of original distribution: %2.2f ",fOrigSigmaY);
comment->AddText(s);
sprintf(s,"Type of original distribution: %s ",fType);
comment->AddText(s);
comment->AddText(s);
sprintf(s,"Overlap factor: %2.2f",fK*fHeightS/fWidth);
comment->AddText(s);
- sprintf(s,"Sigma x of original distribution: %2.2f ",forigsigmaX);
+ sprintf(s,"Sigma x of original distribution: %2.2f ",fOrigSigmaX);
comment->AddText(s);
- sprintf(s,"Sigma y of original distribution: %2.2f ",forigsigmaY);
+ sprintf(s,"Sigma y of original distribution: %2.2f ",fOrigSigmaY);
comment->AddText(s);
sprintf(s,"Type of original distribution: %s ",fType);
comment->AddText(s);
Float_t dy=(y2-y1)/Float_t(Ny) ;
Float_t x,y,z,ddx;
// Float_t y2;
- for ( x = x1;x<(x2+dx/2.);x+=dx)
- for(y = y1;y<=(y2+dx/2.);y+=dy)
+ for ( x = x1;x<(x2+3.1*dx);x+=dx)
+ for(y = y1;y<(y2+3.1*dx);y+=dy)
{
Float_t sumx=0;
Float_t sum=0;
- for (Float_t padx=-fWidth;padx<(fWidth*1.1);padx+=fWidth)
+ for (Int_t i=-3;i<=3;i++)
+ // for (Float_t padx=-fWidth;padx<(fWidth*1.1);padx+=fWidth)
{
- z = GetPRF(x-padx,y,inter);
+ Float_t padx=Float_t(i)*fWidth;
+ z = GetPRF(x-padx,y,inter);
if (z>thr){
sum+=z;
sumx+=z*padx;
comment->AddText(s);
sprintf(s,"Overlap factor: %2.2f",fK*fHeightS/fWidth);
comment->AddText(s);
- sprintf(s,"Sigma x of original distribution: %2.2f ",forigsigmaX);
+ sprintf(s,"Sigma x of original distribution: %2.2f ",fOrigSigmaX);
comment->AddText(s);
- sprintf(s,"Sigma y of original distribution: %2.2f ",forigsigmaY);
+ sprintf(s,"Sigma y of original distribution: %2.2f ",fOrigSigmaY);
comment->AddText(s);
sprintf(s,"Type of original distribution: %s ",fType);
comment->AddText(s);
* See cxx source for full Copyright notice */
/* $Id$ */
-
////////////////////////////////////////////////
-// Manager class for AliTPCPRF2D //
+// Manager class for AliTPCPRF2D //
////////////////////////////////////////////////
#include "TObject.h"
#include "TMath.h"
class TF2;
-class TArrayF;
+class TArrayF;
class AliTPCPRF2D : public TObject {
public :
AliTPCPRF2D();
~AliTPCPRF2D();
-
+ void Update(); //recalculate tables for charge calculation
Float_t GetGRF(Float_t xin, Float_t yin);
//return generic response function in xin
Float_t GetPRF(Float_t xin, Float_t yin, Bool_t inter=kFALSE);
//return PRF in point xin,yin
- void SetY(Float_t y1, Float_t y2, Int_t nYdiv) ;
void DrawX(Float_t x1, Float_t x2,Float_t y, Bool_t inter=kFALSE);
//draw one dimensional response for
//fixed y
// void DrawY(Float_t y1, Float_t y2,Float_t x);
//draw one dimensional response for fixed x
- void Draw(Option_t *) {}
void Draw(Float_t x1, Float_t x2, Float_t y1, Float_t y2,
Bool_t inter=kFALSE, Int_t Nx=20, Int_t Ny=20);
//draw two dimensional PRF
Float_t thr=0);
//draw distortion of COG method
//we suppose threshold equal to thr
-
+
+ void SetPad(Float_t width, Float_t height);
+ //set base chevron parameters
+ void SetChevron(Float_t hstep, Float_t shifty, Float_t fac);
+ //set chevron parameters
+ void SetChParam(Float_t width, Float_t height,
+ Float_t hstep, Float_t shifty, Float_t fac);
+ //set all geometrical parameters
+ void SetY(Float_t y1, Float_t y2, Int_t nYdiv) ;
+ void SetChargeAngle(Float_t angle){fChargeAngle = angle;} //set angle of pad and charge distribution
+ //axes
void SetGauss(Float_t sigmaX,Float_t sigmaY , Float_t kNorm=1);
//adjust PRF with GAUSIAN as generic GRF
//if direct = kTRUE then it does't convolute distribution
Float_t kNorm=1);
void SetParam(TF2 * GRF,Float_t kNorm,
Float_t sigmaX=0, Float_t sigmaY=0);
- void SetPad(Float_t width, Float_t height);
- //set base chevron parameters
- void SetChevron(Float_t hstep, Float_t shifty, Float_t fac);
- //set chevron parameters
- void SetChParam(Float_t width, Float_t height,
- Float_t hstep, Float_t shifty, Float_t fac);
- //set all geometrical parameters
void SetNdiv(Int_t Ndiv){fNdiv=Ndiv;}
- void Update();
+ Float_t GetSigmaX() const {return fSigmaX;}
+ Float_t GetSigmaY() const {return fSigmaY;}
+
+
protected:
- void Update1();
+ void Update1();
+ void UpdateSigma(); //recalculate sigma of PRF
Float_t GetPRFActiv(Float_t xin); //return PRF in point xin and actual y
- Float_t * fcharge; // field with PRF
- Float_t fY1;
- Float_t fY2;
- Int_t fNYdiv;
+ Float_t * fcharge; //field with PRF
+ Float_t fY1; //position of first "virtual" vire
+ Float_t fY2; //position of last virtual vire
+ Int_t fNYdiv; //number of wires
Float_t * ffcharge; //pointer to array of arrays
private:
+
+ //chevron parameters
+ Float_t fHeightFull; //height of the full pad
+ Float_t fHeightS; //height of the one step
+ Float_t fShiftY; //shift of the step
+ Float_t fWidth; //width of the pad
+ Float_t fK; //k factor of the chewron
+
Double_t funParam[5];//parameters of used charge function
Int_t fNPRF; //number of interpolations point
Int_t fNdiv; //number of division to calculate integral
Float_t fInteg; //integral of GRF on +- infinity
TF2 * fGRF; //charge distribution function
- Float_t fK3X;
- Float_t fK3Y;
- Float_t fPadDistance;
+ Float_t fK3X; //KX parameter (only for Gati parametrization)
+ Float_t fK3Y; //KY parameter (only for Gati parametrisation)
+ Float_t fPadDistance; //pad anode distnce (only for Gati parametrisation)
+
+ Float_t fOrigSigmaX; //sigma of original distribution;
+ Float_t fOrigSigmaY; //sigma of original distribution;
+ Float_t fChargeAngle;//'angle' of charge distribution refernce system to pad reference system
+ Float_t fCosAngle; //'angle' of the pad assymetry
- Float_t forigsigmaX;//sigma of original distribution;
- Float_t forigsigmaY;//sigma of original distribution;
- Float_t fSigmaX; //sigma of PAD response function
+ Float_t fSigmaX; //sigma X of PAD response function
+ Float_t fSigmaY; //sigma Y of PAD response function
+ Float_t fMeanX; //mean X value
+ Float_t fMeanY; //mean Y value
//calculated during update
- //chewron parameters
- Float_t fHeightFull; //height of the full pad
- Float_t fHeightS; //height of the one step
- Float_t fShiftY; //shift of the step
- Float_t fWidth; //width of the pad
- Float_t fK; //k factor of the chewron
- Float_t fActualY; //in reality we calculate PRF only for
- //one fixed y
- char fType[5]; //charge type
- //to make calculation faster we reduce division
- Float_t fDYtoWire; //used to make PRF calculation faster in GetPRF
- Float_t fDStepM1; //used in GetPRFActiv
+
+
+ char fType[5]; //charge type
+ Float_t fCurrentY; //in reality we calculate PRF only for one fixed y
+ Float_t fDYtoWire; //! used to make PRF calculation faster in GetPRF
+ Float_t fDStepM1; //! used in GetPRFActiv to make calculation faster
ClassDef(AliTPCPRF2D,1)
};
/*
$Log$
+Revision 1.7.8.2 2000/04/10 08:44:51 kowal2
+
+New transformations added
+Different pad and pad-rows geometries for different sectors
+
+Revision 1.7.8.1 2000/04/10 07:56:53 kowal2
+Not used anymore - removed
+
+Revision 1.7 1999/10/08 13:10:35 fca
+Values in SetDefault are in radiants
+
Revision 1.6 1999/10/08 06:27:59 fca
Defaults updated
#include <iostream.h>
#include <TMath.h>
#include <TObject.h>
-#include "AliTPCSecGeo.h"
+#include <TRandom.h>
#include <AliTPCParam.h>
ClassImp(AliTPCParam)
-const static Int_t kMaxRows=600;
-
-
-// default values
-const static Int_t kMaxTBin =512;
-
-
-const static Float_t kInnerRadiusLow = 83.9;
-const static Float_t kOuterRadiusLow = 146.9;
-const static Float_t kInnerRadiusUp = 141.3;
-const static Float_t kOuterRadiusUp = 249.4;
-
-const static Float_t kInnerAngle = 0.34906585; // 20 degrees
-const static Float_t kInnerAngleShift = 0;
-const static Float_t kOuterAngle = 0.34906585; // 20 degrees
-const static Float_t kOuterAngleShift = 0;
-
-const static Float_t kPadPitchLength = 2.05;
-const static Float_t kPadPitchWidth = 0.35;
-const static Float_t kPadLength = 2.05;
-const static Float_t kPadWidth = 0.35;
-
-// Number of wires per pad and wire-wire pitch
-const static Int_t knWires = 5;
+const static Int_t kMaxRows=600;
+//
+//sector default parameters
+//
+const static Float_t kInnerRadiusLow = 81.6;
+const static Float_t kOuterRadiusLow = 144.2;
+const static Float_t kInnerRadiusUp = 143.6;
+const static Float_t kOuterRadiusUp = 252.1;
+const static Float_t kInnerAngle = 20; // 20 degrees
+const static Float_t kInnerAngleShift = 10;
+const static Float_t kOuterAngle = 20; // 20 degrees
+const static Float_t kOuterAngleShift = 10;
+const static Float_t kInnerFrameSpace = 1.5;
+const static Float_t kOuterFrameSpace = 1.5;
+const static Float_t kInnerWireMount = 1.15;
+const static Float_t kOuterWireMount = 1.15;
+const static Float_t kZLength =250.;
+const static Int_t kGeometryType = 0; //straight rows
+//
+//wires default parameters
+//
+const static Int_t kNInnerWiresPerPad = 5;
+const static Int_t kInnerDummyWire = 2;
+const static Float_t kInnerOffWire = 0.5;
+const static Int_t kNOuterWiresPerPad = 5;
+const static Int_t kOuterDummyWire = 2;
+const static Float_t kOuterOffWire = 0.5;
+//
+//pad default parameters
+//
+const static Float_t kInnerPadPitchLength = 2.05;
+const static Float_t kInnerPadPitchWidth = 0.35;
+const static Float_t kInnerPadLength = 2.05;
+const static Float_t kInnerPadWidth = 0.35;
+const static Float_t kOuterPadPitchLength = 2.05;
+const static Float_t kOuterPadPitchWidth = 0.35;
+const static Float_t kOuterPadLength = 2.05;
+const static Float_t kOuterPadWidth = 0.35;
+const static Bool_t kBMWPCReadout = kTRUE; //MWPC readout - another possibility GEM
+const static Int_t kNCrossRows = 1; //number of rows to cross-talk
+
+//
+//gas default parameters
+//
const static Float_t kDiffT = 2.2e-2;
-const static Float_t kDiffL = 2.2e-2;
+const static Float_t kDiffL = 2.2e-2;
+const static Float_t kGasGain = 2.e4;
const static Float_t kDriftV =2.85e6;
-
const static Float_t kOmegaTau = 0.145;
const static Float_t kAttCoef = 250.;
const static Float_t kOxyCont = 5.e-6;
-
-
-const static Float_t kChipGain = 12;
-const static Float_t kGasGain = 2e4;
-const static Float_t kTSample = 2.e-7; //TSAMPLE
-const static Float_t kTFWHM = 2.5e-7; //fwhm of charge distribution
-
-const static Float_t kNoise = 1000; //default noise = 1000 el
-const static Int_t kZeroSup=5;
+//
+//electornic default parameters
+//
const static Float_t kPadCoupling=0.5;
+const static Int_t kZeroSup=5;
+const static Float_t kNoise = 1000;
+const static Float_t kChipGain = 12;
+const static Float_t kChipNorm = 0.4;
+const static Float_t kTSample = 2.e-7;
+const static Float_t kTFWHM = 1.9e-7; //fwhm of charge distribution
+const static Int_t kMaxTBin =512;
+const static Int_t kADCSat =1024;
+const static Float_t kADCDynRange =2000.;
+//
+//
+//
+const static Float_t kBField =0.2;
+const static Float_t kNPrimLoss =10.9;
+const static Float_t kNTotalLoss =39.9;
//
-const static Float_t kEdgeSectorSpace = 1.15;
+//transformation coeficients
+//
const static Float_t kDegtoRad = 0.01745329251994;
const static Float_t kRadtoDeg = 57.29577951309;
-
+//
+//response constants
+//
+const static Int_t kNResponseMax=100;
+const static Float_t kResponseThreshold=0.01;
//___________________________________________
AliTPCParam::AliTPCParam()
{
- //constructor set the default parameters
+ //
+ //constructor sets the default parameters
+ //
+
+ fResponseBin = 0;
+ fResponseWeight = 0;
+ fRotAngle = 0;
SetDefault();
}
-
-void AliTPCParam::SetSectorAngles(Float_t innerangle, Float_t innershift, Float_t outerangle,
- Float_t outershift, Bool_t inDegree)
+AliTPCParam::~AliTPCParam()
{
//
- // set opening angles
- fInnerAngle = innerangle; //opening angle of Inner sector
- fInnerAngleShift = innershift; //shift of first inner sector center to the 0
- fOuterAngle = outerangle; //opening angle of outer sector
- fOuterAngleShift = outershift; //shift of first sector center to the 0
- if (inDegree==kTRUE){
- fInnerAngle *=kDegtoRad;
- fInnerAngleShift *=kDegtoRad;
- fOuterAngle *=kDegtoRad;
- fOuterAngleShift *=kDegtoRad;
- }
+ //destructor deletes some dynamicaly alocated variables
+ //
+
+ if (fResponseBin!=0) delete [] fResponseBin;
+ if (fResponseWeight!=0) delete [] fResponseWeight;
+ if (fRotAngle !=0) delete [] fRotAngle;
+
}
-void AliTPCParam::CRXYZtoXYZ(Float_t *xyz,
- const Int_t §or, const Int_t & padrow, Int_t option) const
-{
- //transform relative coordinates to absolute
- Bool_t rel = ( (option&2)!=0);
- Float_t row_first;
- row_first = (sector<=fNInnerSector) ? fPadRowLow[0] : fPadRowUp[0];
- if (rel==kTRUE) //if the position is relative to pad row
+
+
+Int_t AliTPCParam::Transform0to1(Float_t *xyz, Int_t * index) const
+{
+ //
+ // calculates sector number (index[1], undefined on input)
+ // xyz intact
+ //
+
+ Float_t angle,x1;
+ Int_t sector;
+ Float_t r = TMath::Sqrt(xyz[0]*xyz[0]+xyz[1]*xyz[1]);
+ if ((xyz[0]==0)&&(xyz[1]==0)) angle = 0.;
+ else
{
- xyz[0]+=row_first;
- xyz[0]+=(Int_t) padrow*fPadPitchLength;
- }
-
- xyz[2]=z_end-xyz[2];
- if (sector<fNInnerSector) {
- if ( sector>=(fNInnerSector>>1)) xyz[2]*=-1.;
- } else {
- if ( (sector-fNInnerSector) >= (fNOuterSector>>1) ) xyz[2]*=-1;
- }
+ angle =TMath::ASin(xyz[1]/r);
+ if (xyz[0]<0) angle=TMath::Pi()-angle;
+ if ( (xyz[0]>0) && (xyz[1]<0) ) angle=2*TMath::Pi()+angle;
+ }
- Float_t x1=xyz[0];
- Float_t y1=xyz[1];
+ sector=Int_t((angle-fInnerAngleShift)/fInnerAngle);
+
Float_t cos,sin;
- AdjustAngles(sector,cos,sin);
- xyz[0]= x1*cos - y1*sin;
- xyz[1]= x1*sin + y1*cos;
-}
+ AdjustCosSin(sector,cos,sin);
+ x1=xyz[0]*cos + xyz[1]*sin;
-void AliTPCParam::XYZtoCRXYZ(Float_t *xyz,
- Int_t §or, Int_t & padrow, Int_t option)
-{
- //transform global position to the position relative to the sector padrow
- //if option=0 X calculate absolute calculate sector
- //if option=1 X absolute use input sector
- //if option=2 X relative to pad row calculate sector
- //if option=3 X relative use input sector
- //!!!!!!!!! WE start to calculate rows from row = 0
-
- Bool_t rel = ( (option&2)!=0);
- //option 0 and 2 means that we don't have information about sector
- //we calculate sector
- if ((option&1)==0){
- Float_t angle;
- Float_t r = TMath::Sqrt(xyz[0]*xyz[0]+xyz[1]*xyz[1]);
- if ((xyz[0]==0)&&(xyz[1]==0)) angle = 0;
- else
- {
- angle =TMath::ASin(xyz[1]/r);
- if (xyz[0]<0) angle=TMath::Pi()-angle;
- if ( (xyz[0]>0) && (xyz[1]<0) ) angle=2*TMath::Pi()+angle;
- }
- //transform global position to the position relative to the sector padrow
- //fistly calculate xyz[0] radius for lover sector
- //bacause in this moment we dont know in which sector we are
- sector=Int_t((angle-fInnerAngleShift)/fInnerAngle);
- Float_t x1;
- Float_t y1;
- //firstly we suppose that we are in inner sector
- Float_t cos,sin;
- AdjustAngles(sector,cos,sin);
-
- x1=xyz[0]*cos + xyz[1]*sin;
- y1=-xyz[0]*sin + xyz[1]*cos;
- if (x1>fOuterRadiusLow)
- {
- sector=Int_t((angle-fOuterAngleShift)/fOuterAngle)+fNInnerSector;
- AdjustAngles(sector,cos,sin);
- x1=xyz[0]*cos + xyz[1]*sin;
- y1=-xyz[0]*sin + xyz[1]*cos;
- if (xyz[2]<0) sector+=(fNOuterSector>>1);
- }
+ if (x1>fOuterRadiusLow)
+ {
+ sector=Int_t((angle-fOuterAngleShift)/fOuterAngle)+fNInnerSector;
+ if (xyz[2]<0) sector+=(fNOuterSector>>1);
+ }
else
if (xyz[2]<0) sector+=(fNInnerSector>>1);
+ index[1]=sector; // calculated sector number
+ index[0]=1; // indicates system after transformation
+ return sector;
+}
- if (x1<fOuterRadiusLow)
- padrow =Int_t( (x1-fPadRowLow[0])/fPadPitchLength+0.5);
- else
- padrow = Int_t( (x1-fPadRowUp[0])/fPadPitchLength+0.5);
- if (rel==kTRUE)
- if (x1<fOuterRadiusLow) x1-=padrow*fPadPitchLength+fPadRowLow[0];
- else
- x1-=padrow*fPadPitchLength+fPadRowUp[0];
- xyz[0]=x1;
- xyz[1]=y1;
- xyz[2]=z_end-TMath::Abs(xyz[2]);
- } //endif we don't have information about sector
- else{
- //if we have information about sector
- Float_t cos,sin;
- AdjustAngles(sector,cos,sin);
- Float_t x1;
- Float_t y1;
- //rotate to given sector
- x1=xyz[0]*cos + xyz[1]*sin;
- y1=-xyz[0]*sin + xyz[1]*cos;
- //calculate pad row number
- if (sector<fNInnerSector) {
- padrow =Int_t( (x1-fPadRowLow[0])/fPadPitchLength+1.5)-1;
+Bool_t AliTPCParam::Transform(Float_t *xyz, Int_t *index, Int_t* oindex)
+{
+ //transformation from input coodination system to output coordination system
+ switch (index[0]){
+ case 0:
+ break;
+ };
+
+ return kFALSE;
+
+}
+
+Int_t AliTPCParam::GetPadRow(Float_t *xyz, Int_t *index) const
+{
+ //
+ //calculates pad row of point xyz - transformation to system 8 (digit system)
+ //
+ Int_t system = index[0];
+ if (0==system) {
+ Transform0to1(xyz,index);
+ system=1;
+ }
+ if (1==system) {
+ Transform1to2(xyz,index);
+ system=2;
+ }
+
+ if (fGeometryType==0){ //straight row
+ if (2==system) {
+ Transform2to3(xyz,index);
+ system=3;
+ }
+ if (3==system) {
+ Transform3to4(xyz,index);
+ system=4;
}
- else {
- padrow =Int_t( (x1-fPadRowUp[0])/fPadPitchLength+1.5)-1;
+ if (4==system) {
+ Transform4to8(xyz,index);
+ system=8;
}
- //if we store relative position calculate position relative to pad row
- if (rel==kTRUE){
- if (sector<fNInnerSector)
- x1-=padrow*fPadPitchLength+fPadRowLow[0];
- else
- x1-=padrow*fPadPitchLength+fPadRowUp[0];
- }
- xyz[0]=x1;
- xyz[1]=y1;
- xyz[2]=z_end-TMath::Abs(xyz[2]);
+ if (8==system) {
+ index[0]=8;
+ return index[2];
+ }
}
+
+ if (fGeometryType==1){ //cylindrical geometry
+ if (2==system) {
+ Transform2to5(xyz,index);
+ system=5;
+ }
+ if (5==system) {
+ Transform2to3(xyz,index);
+ system=6;
+ }
+ if (6==system) {
+ Transform3to4(xyz,index);
+ system=7;
+ }
+ if (8==system) {
+ index[0]=8;
+ return index[2];
+ }
+ }
+ index[0]=system;
+ return -1; //if no reasonable system
}
-void AliTPCParam::CRYZtoTimePad(const Float_t &y, const Float_t &z,
- Float_t &time, Float_t &pad,
- Int_t sector, Int_t padrow)
+void AliTPCParam::SetSectorAngles(Float_t innerangle, Float_t innershift, Float_t outerangle,
+ Float_t outershift)
{
- //transform position in cm to position in time slices and pads
- Float_t nofpads = GetNPads(sector,padrow);
- Float_t padc=(nofpads+1)/2; // this is the "central" pad for a row
- pad = y/(fPadPitchWidth)+padc;
- time=z/fZWidth;
+ //
+ // set opening angles
+ fInnerAngle = innerangle; //opening angle of Inner sector
+ fInnerAngleShift = innershift; //shift of first inner sector center to the 0
+ fOuterAngle = outerangle; //opening angle of outer sector
+ fOuterAngleShift = outershift; //shift of first sector center to the 0
+ fInnerAngle *=kDegtoRad;
+ fInnerAngleShift *=kDegtoRad;
+ fOuterAngle *=kDegtoRad;
+ fOuterAngleShift *=kDegtoRad;
}
-void AliTPCParam::CRTimePadtoYZ(Float_t &y, Float_t &z,
- const Float_t &time, const Float_t &pad,
- Int_t sector, Int_t padrow)
+
+Float_t AliTPCParam::GetInnerAngle() const
{
- //transform position in time slices and pads to cm
- Float_t nofpads = GetNPads(sector,padrow);
- Float_t padc=(nofpads+1)/2; // this is the "central" pad for a row
- y=(pad-padc)*fPadPitchWidth;
- z=time*fZWidth;
+ //return angle
+ return fInnerAngle;
+
}
-Int_t AliTPCParam::GetWire(Float_t & x)
-{
- //
- //return wire number of pad for electron at relative position x
- //to the center of the pad
- //and adjust x to the wire position
- //we suppose that if the wire number is even the center wire
- //is at center of pad
- //
- Float_t xrel= x/fWWPitch;
- if ((fnWires&1)==0) xrel+=1;
- else xrel+=0.5;
- Int_t nw=Int_t(xrel);
- if (xrel<0) nw-=1;
-
- x=(nw*fWWPitch);
- if ((fnWires&1)==0) x-=fWWPitch/2.;
- return nw;
+Float_t AliTPCParam::GetInnerAngleShift() const
+{
+ //return angle
+ return fInnerAngleShift;
}
+Float_t AliTPCParam::GetOuterAngle() const
+{
+ //return angle
+ return fOuterAngle;
+}
+Float_t AliTPCParam::GetOuterAngleShift() const
+{
+ //return angle
+
+ return fOuterAngleShift;
+}
+
Int_t AliTPCParam::GetIndex(Int_t sector, Int_t row)
{
//give index of the given sector and pad row
//no control if the sectors and rows are reasonable !!!
//
- if (sector<fNInnerSector) return sector*fnRowLow+row;
- return (fNInnerSector*fnRowLow)+(sector-fNInnerSector)*fnRowUp+row;
+ if (sector<fNInnerSector) return sector*fNRowLow+row;
+ return (fNInnerSector*fNRowLow)+(sector-fNInnerSector)*fNRowUp+row;
}
-Bool_t AliTPCParam::AdjustSectorRow(Int_t index, Int_t & sector, Int_t &row)
+Bool_t AliTPCParam::AdjustSectorRow(Int_t index, Int_t & sector, Int_t &row) const
{
//
//return sector and padrow for given index
- //if index is reasonable return true else return false
+ //if index is reasonable returns true else return false
//
if ( (index<0) || (index>fNtRows)) return kFALSE;
- Int_t outindex = fNInnerSector*fnRowLow;
+ Int_t outindex = fNInnerSector*fNRowLow;
if (index<outindex) {
- sector = index/fnRowLow;
- row = index - sector*fnRowLow;
+ sector = index/fNRowLow;
+ row = index - sector*fNRowLow;
return kTRUE;
}
index-= outindex;
- sector = index/fnRowUp;
- row = index - sector*fnRowUp;
+ sector = index/fNRowUp;
+ row = index - sector*fNRowUp;
+ sector += fNInnerSector;
return kTRUE;
}
-
-
-Int_t AliTPCParam::GetPadRow(Int_t isec, Float_t &x)
+void AliTPCParam::SetDefault()
{
//
- //return the pad row for given x (transformed)
+ //set default parameters
//
- Float_t row_first=GetPadRowRadii(isec,0);
- Int_t row = Int_t(( x-row_first+1.5*fPadPitchLength)/fPadPitchLength)-1;
- //Int_t will make from -0.5 0 but we want to make -1 so we add and after substract 1
- x -=row* fPadPitchLength+row_first;
- if ( (row<0)||(row>=GetNRow(isec))) return -1;
- else return row;
-}
-
-void AliTPCParam::SetDefault()
-{
- //set default TPC param
fbStatus = kFALSE;
- //set sector parameters
- fInnerRadiusLow = kInnerRadiusLow;
- fOuterRadiusLow = kOuterRadiusLow;
- fInnerRadiusUp = kInnerRadiusUp;
- fOuterRadiusUp = kOuterRadiusUp;
- SetSectorAngles(kInnerAngle,kInnerAngleShift, kOuterAngle, kOuterAngleShift,kFALSE);
- // set default pad size and shape
- fPadPitchLength = kPadPitchLength;
- fPadPitchWidth = kPadPitchWidth;
- fPadLength = kPadLength;
- fPadWidth = kPadWidth;
//
- fnWires = knWires;
- fWWPitch= kPadPitchLength/Float_t(knWires);
- fDiffT = kDiffT;
- fDiffL = kDiffL;
- fOmegaTau = kOmegaTau;
- fOxyCont = kOxyCont;
- fAttCoef = kAttCoef;
- fNoise = kNoise;
- fChipGain = kChipGain;
- fGasGain = kGasGain;
- fZeroSup= kZeroSup;
- fPadCoupling= kPadCoupling;
- fTSample =kTSample;
- fTSigma =kTFWHM/2.35;
- fDriftV=kDriftV;
- fMaxTBin = kMaxTBin;
- fbStatus = Update();
-}
-
-void AliTPCParam::AdjustAngles(Int_t isec, Float_t &cos, Float_t &sin) const
-{
+ //set sector parameters
+ //
+ SetInnerRadiusLow(kInnerRadiusLow);
+ SetOuterRadiusLow(kOuterRadiusLow);
+ SetInnerRadiusUp(kInnerRadiusUp);
+ SetOuterRadiusUp(kOuterRadiusUp);
+ SetInnerFrameSpace(kInnerFrameSpace);
+ SetOuterFrameSpace(kOuterFrameSpace);
+ SetInnerWireMount(kInnerWireMount);
+ SetOuterWireMount(kOuterWireMount);
+ SetSectorAngles(kInnerAngle,kInnerAngleShift,kOuterAngle,kOuterAngleShift);
+ SetZLength(kZLength);
+ SetGeometryType(kGeometryType);
+ //
+ //set wire parameters
+ //
+ SetInnerNWires(kNInnerWiresPerPad);
+ SetInnerDummyWire(kInnerDummyWire);
+ SetInnerOffWire(kInnerOffWire);
+ SetOuterNWires(kNOuterWiresPerPad);
+ SetOuterDummyWire(kOuterDummyWire);
+ SetOuterOffWire(kOuterOffWire);
+ //
+ //set pad parameter
//
- //set cosinus and sinus of rotation angles for sector isec
+ SetInnerPadPitchLength(kInnerPadPitchLength);
+ SetInnerPadPitchWidth(kInnerPadPitchWidth);
+ SetInnerPadLength(kInnerPadLength);
+ SetInnerPadWidth(kInnerPadWidth);
+ SetOuterPadPitchLength(kOuterPadPitchLength);
+ SetOuterPadPitchWidth(kOuterPadPitchWidth);
+ SetOuterPadLength(kOuterPadLength);
+ SetOuterPadWidth(kOuterPadWidth);
+ SetMWPCReadout(kBMWPCReadout);
+ SetNCrossRows(kNCrossRows);
//
- cos=fRotAngle[isec*2];
- sin=fRotAngle[isec*2+1];
+ //set gas paremeters
+ //
+ SetDiffT(kDiffT);
+ SetDiffL(kDiffL);
+ SetGasGain(kGasGain);
+ SetDriftV(kDriftV);
+ SetOmegaTau(kOmegaTau);
+ SetAttCoef(kAttCoef);
+ SetOxyCont(kOxyCont);
+ //
+ //set electronivc parameters
+ //
+ SetPadCoupling(kPadCoupling);
+ SetZeroSup(kZeroSup);
+ SetNoise(kNoise);
+ SetChipGain(kChipGain);
+ SetChipNorm(kChipNorm);
+ SetTSample(kTSample);
+ SetTFWHM(kTFWHM);
+ SetMaxTBin(kMaxTBin);
+ SetADCSat(kADCSat);
+ SetADCDynRange(kADCDynRange);
+ //set magnetic field
+ SetBField(kBField);
+ SetNPrimLoss(kNPrimLoss);
+ SetNTotalLoss(kNTotalLoss);
+ //
+ //set response parameters
+ //
+ SetNResponseMax(kNResponseMax);
+ SetResponseThreshold(kResponseThreshold);
}
+
Bool_t AliTPCParam::Update()
{
Int_t i,j; //loop variables because HP
//-----------------Sector section------------------------------------------
//calclulate number of sectors
- fNInnerSector = Int_t(4*TMath::Pi()/fInnerAngle+0.2); // number of inner sectors - factor 0.2 to don't
- //be influnced by inprecision
+ fNInnerSector = Int_t(4*TMath::Pi()/fInnerAngle+0.2);
+ // number of inner sectors - factor 0.2 to don't be influnced by inprecision
if (fNInnerSector%2) return kFALSE;
fNOuterSector = Int_t(4*TMath::Pi()/fOuterAngle+0.2);
if (fNOuterSector%2) return kFALSE;
fNSector = fNInnerSector+fNOuterSector;
+
+ if (fRotAngle!=0) delete [] fRotAngle;
+ fRotAngle = new Float_t[4*fNSector];
//calculate sin and cosine of rotations angle
//sectors angles numbering from 0
- j=fNInnerSector;
+
+ j=fNInnerSector*2;
Float_t angle = fInnerAngleShift;
- for (i=0; i<fNInnerSector*2; i+=2, j+=2 , angle +=fInnerAngle){
+ for (i=0; j<fNInnerSector*4; i+=4, j+=4 , angle +=fInnerAngle){
fRotAngle[i]=TMath::Cos(angle);
fRotAngle[i+1]=TMath::Sin(angle);
fRotAngle[j] = fRotAngle[i];
fRotAngle[j+1] = fRotAngle[i+1];
+ fRotAngle[i+2] =angle;
+ fRotAngle[j+2] =angle;
}
angle = fOuterAngleShift;
- j=(fNInnerSector+fNOuterSector/2)*2;
- for (i=fNInnerSector*2; i<fNSector*2; i+=2,j+=2, angle +=fOuterAngle){
+ j=(fNInnerSector+fNOuterSector/2)*4;
+ for (i=fNInnerSector*4; j<fNSector*4; i+=4,j+=4, angle +=fOuterAngle){
fRotAngle[i]=TMath::Cos(angle);
fRotAngle[i+1]=TMath::Sin(angle);
fRotAngle[j] = fRotAngle[i];
fRotAngle[j+1] = fRotAngle[i+1];
+ fRotAngle[i+2] =angle;
+ fRotAngle[j+2] =angle;
}
+ fZWidth = fTSample*fDriftV;
+ fTotalNormFac = fPadCoupling*fChipNorm*q_el*1.e15*fChipGain*fADCSat/fADCDynRange;
+ fNoiseNormFac = q_el*1.e15*fChipGain*fADCSat/fADCDynRange;
+ //wire section
+ Int_t nwire;
+ Float_t wspace; //available space for wire
+ Float_t dummyspace; //dummyspace for wire
+
+ fInnerWWPitch = Float_t((Double_t)fInnerPadPitchLength/(Double_t)fNInnerWiresPerPad);
+ wspace =fInnerRadiusUp-fInnerRadiusLow-2*fInnerOffWire;
+ nwire = Int_t(wspace/fInnerWWPitch);
+ wspace = Float_t(nwire)*fInnerWWPitch;
+ dummyspace =(fInnerRadiusUp-fInnerRadiusLow-wspace)/2.;
+ fRInnerFirstWire = fInnerRadiusLow+dummyspace;
+ fRInnerLastWire = fRInnerFirstWire+fInnerWWPitch*(Float_t)(nwire);
+
+ fOuterWWPitch = Float_t((Double_t)fOuterPadPitchLength/(Double_t)fNOuterWiresPerPad);
+ wspace =fOuterRadiusUp-fOuterRadiusLow-2*fOuterOffWire;
+ nwire = Int_t(wspace/fOuterWWPitch);
+ wspace = Float_t(nwire)*fOuterWWPitch;
+ dummyspace =(fOuterRadiusUp-fOuterRadiusLow-wspace)/2.;
+ fROuterFirstWire = fOuterRadiusLow+dummyspace;
+ fROuterLastWire = fROuterFirstWire+fOuterWWPitch*(Float_t)(nwire);
- //----------------PAD section------------------------------------
- //recalculate and check some geometric parameters
- if (0.001>fPadPitchLength){
- cout<<"ERROR !!! Small pad pitch length \n"<<flush;
- return kFALSE;
- }
- if (fPadPitchLength<fPadLength) {
- cout<<"ERROR !!! Pitch length smaller then length of pad \n"<<flush;
- return kFALSE;
- }
- fnRowUp = Int_t((0.01+fOuterRadiusUp-fOuterRadiusLow)/fPadPitchLength)+1;
- if ( kMaxRows<fnRowUp) fnRowUp = kMaxRows;
- if (1>fnRowUp) return kFALSE;
-
- fnRowLow = Int_t((0.01+fInnerRadiusUp-fInnerRadiusLow)/fPadPitchLength)+1;
- if ( kMaxRows<fnRowLow) fnRowUp = kMaxRows;
- if (1>fnRowLow) return kFALSE;
- // adjust upper sectors pad row positions and pad numbers
- for (i = 0;i<fnRowUp;i++)
- {
- Float_t x = fOuterRadiusLow +fPadPitchLength*(Float_t)i;
- //Float_t y = x*2*tan(alpha_up/2)-kEdgeSectorSpace;
- Float_t y = (x-0.5*fPadPitchLength)*tan(fOuterAngle/2)-kEdgeSectorSpace
- -fPadPitchWidth/2.;
- fPadRowUp[i] = x;
- fnPadsUp[i] = 1+2*(Int_t)(y/fPadPitchWidth) ;
-
- }
- // adjust lower sectors pad row positions and pad numbers
- for (i = 0;i<fnRowLow;i++)
- {
- Float_t x = fInnerRadiusLow +fPadPitchLength*(Float_t)i;
- // Float_t y = x*2*tan(alpha_low/2)-kEdgeSectorSpace;
- Float_t y = (x-0.5*fPadPitchLength)*tan(fInnerAngle/2)-kEdgeSectorSpace
- -fPadPitchWidth/2.;
- fPadRowLow[i] = x;
- fnPadsLow[i] = 1+2*(Int_t)(y/fPadPitchWidth) ;
-
- }
-
- //that variable are not writen to the file there are calculated
//
- fWWPitch= fPadPitchLength/Float_t(fnWires);
- fZWidth = fTSample*fDriftV;
- fNtRows = fNInnerSector*fnRowLow+fNOuterSector*fnRowUp;
+ //response data
+ //
+ if (fResponseBin==0) delete [] fResponseBin;
+ if (fResponseWeight==0) delete [] fResponseBin;
+ fResponseBin = new Int_t[3*fNResponseMax];
+ fResponseWeight = new Float_t[fNResponseMax];
+
fbStatus = kTRUE;
return kTRUE;
}
Int_t AliTPCParam::GetNRowLow() const
{
//get the number of pad rows in low sector
- return fnRowLow;
+ return fNRowLow;
}
Int_t AliTPCParam::GetNRowUp() const
{
//get the number of pad rows in up sector
- return fnRowUp;
+ return fNRowUp;
}
Float_t AliTPCParam::GetPadRowRadiiLow(Int_t irow) const
{
//get the pad row (irow) radii
- if ( !(irow<0) && (irow<fnRowLow) )
+ if ( !(irow<0) && (irow<fNRowLow) )
return fPadRowLow[irow];
else
return 0;
Float_t AliTPCParam::GetPadRowRadiiUp(Int_t irow) const
{
//get the pad row (irow) radii
- if ( !(irow<0) && (irow<fnRowUp) )
+ if ( !(irow<0) && (irow<fNRowUp) )
return fPadRowUp[irow];
else
return 0;
Int_t AliTPCParam::GetNPadsLow(Int_t irow) const
{
//get the number of pads in row irow
- if ( !(irow<0) && (irow<fnRowLow) )
- return fnPadsLow[irow];
+ if ( !(irow<0) && (irow<fNRowLow) )
+ return fNPadsLow[irow];
else
return 0;
}
Int_t AliTPCParam::GetNPadsUp(Int_t irow) const
{
//get the number of pads in row irow
- if ( !(irow<0) && (irow<fnRowUp) )
- return fnPadsUp[irow];
+ if ( !(irow<0) && (irow<fNRowUp) )
+ return fNPadsUp[irow];
else
return 0;
}
if (R__b.IsReading()) {
Version_t R__v = R__b.ReadVersion(); if (R__v) { }
- TObject::Streamer(R__b);
+ AliDetectorParam::Streamer(R__b);
if (R__v < 2) return;
- //sector parameters
- R__b >> fInnerRadiusLow;
- R__b >> fInnerRadiusUp;
- R__b >> fOuterRadiusLow;
- R__b >> fOuterRadiusUp;
- R__b >> fInnerAngle;
- R__b >> fInnerAngleShift;
- R__b >> fOuterAngle;
- R__b >> fOuterAngleShift;
- //pad parameters
- R__b >> fPadPitchLength;
- R__b >> fPadPitchWidth;
- R__b >> fPadLength;
- R__b >> fPadWidth;
-
- R__b >> fnWires;
- //gas parameters
- R__b >>fDiffT;
- R__b >>fDiffL;
- R__b >>fGasGain;
- R__b >>fDriftV;
- R__b >>fOmegaTau;
- R__b >>fOxyCont;
- R__b >>fAttCoef;
-
- R__b >>fPadCoupling;
- R__b >>fZeroSup;
- R__b >>fNoise;
- R__b >>fChipGain;
-
- R__b >>fTSample;
- R__b >>fTSigma;
- //
- Update();
+ //---------------------------------------------------------------------
+ // ALICE TPC sector geometry
+ //--------------------------------------------------------------------
+ R__b >> fInnerRadiusLow; // lower radius of inner sector-IP
+ R__b >> fInnerRadiusUp; // upper radius of inner sector-IP
+ R__b >> fOuterRadiusUp; // upper radius of outer sector-IP
+ R__b >> fOuterRadiusLow; // lower radius of outer sector-IP
+ R__b >> fInnerAngle; //opening angle of Inner sector
+ R__b >> fInnerAngleShift; //shift of first inner sector center to the 0
+ R__b >> fOuterAngle; //opening angle of outer sector
+ R__b >> fOuterAngleShift; //shift of first sector center to the 0
+ R__b >> fInnerFrameSpace; //spce for inner frame in the phi direction
+ R__b >> fOuterFrameSpace; //spce for outer frame in the phi direction
+ R__b >> fInnerWireMount;
+ R__b >> fOuterWireMount;
+ //R__b >> fNInnerSector; //!number of inner sectors - calculated
+ //R__b >> fNOuterSector; //!number of outer sectors -calculated
+ //R__b >> fNSector; //! total number of sectors -calculated
+ R__b >> fZLength; //length of the drift region of the TPC
+ //R__b.ReadFastArray(fRotAngle,fNSector*4); // sin and cos of rotation angles for
+ R__b >> fGeometryType; //type of geometry -0 straight rows
+ // diferent sectors
+ //---------------------------------------------------------------------
+ // ALICE TPC wires geometry
+ //--------------------------------------------------------------------
+ R__b >> fNInnerWiresPerPad;// Number of wires per pad
+ //R__b >> fInnerWWPitch; // pitch between wires in inner sector - calculated
+ R__b >> fInnerDummyWire; //number of wires without pad readout
+ R__b >> fInnerOffWire;//oofset of first wire to the begining of the sector
+ //R__b >> fRInnerFirstWire; //position of the first wire -calculated
+ //R__b >> fRInnerLastWire; //position of the last wire -calculated
+ R__b >> fNOuterWiresPerPad;// Number of wires per pad
+ //R__b >> fOuterWWPitch; // pitch between wires in outer sector - calculated
+ R__b >> fOuterDummyWire; //number of wires without pad readout
+ R__b >> fOuterOffWire;//oofset of first wire to the begining of the sector
+ //R__b >> fROuterFirstWire; //position of the first wire -calulated
+ //R__b >> fROuterLastWire; //position of the last wire -calculated
+ //---------------------------------------------------------------------
+ // ALICE TPC pad parameters
+ //--------------------------------------------------------------------
+ R__b >> fInnerPadPitchLength; //Inner pad pitch length
+ R__b >> fInnerPadPitchWidth; //Inner pad pitch width
+ R__b >> fInnerPadLength; //Inner pad length
+ R__b >> fInnerPadWidth; //Inner pad width
+ R__b >> fOuterPadPitchLength; //Outer pad pitch length
+ R__b >> fOuterPadPitchWidth; //Outer pad pitch width
+ R__b >> fOuterPadLength; //Outer pad length
+ R__b >> fOuterPadWidth; //Outer pad width
+ R__b >> fBMWPCReadout; //indicate wire readout
+ R__b >> fNCrossRows; //number of pad rows to crostalk
+ R__b >> fNRowLow; // number of pad rows per low sector
+ R__b >> fNRowUp; // number of pad rows per sector up
+ //R__b >> fPadRowLow[600]; // Lower sector, pad row radii
+ //R__b >> fPadRowUp[600]; // Upper sector, pad row radii
+ //R__b >> fNPadsLow[600]; // Lower sector, number of pads per row
+ //R__b >> fNPadsUp[600]; // Upper sector, number of pads per row
+ //---------------------------------------------------------------------
+ // ALICE TPC Gas Parameters
+ //--------------------------------------------------------------------
+ R__b >> fDiffT; //tangencial diffusion constant
+ R__b >> fDiffL; //longutudinal diffusion constant
+ R__b >> fGasGain; //gas gain constant
+ R__b >> fDriftV; //drift velocity constant
+ R__b >> fOmegaTau; //omega tau ExB coeficient
+ R__b >> fAttCoef; //attachment coefitients
+ R__b >> fOxyCont; //oxygen content
+ //---------------------------------------------------------------------
+ // ALICE TPC Electronics Parameters
+ //--------------------------------------------------------------------
+ R__b >> fPadCoupling; //coupling factor ration of anode signal
+ //and total pads signal
+ R__b >> fZeroSup; //zero suppresion constant
+ R__b >> fNoise; //noise sigma constant
+ R__b >> fChipGain; //preamp shaper constant
+ R__b >> fChipNorm; //preamp shaper normalisation
+ R__b >> fTSample; // sampling time
+ R__b >> fZWidth; //derived value calculated using TSample and driftw
+ R__b >> fTSigma; // width of the Preamp/Shaper function
+ R__b >> fMaxTBin; //maximum time bin number
+ R__b >> fADCSat; //saturation value of ADC (10 bits)
+ R__b >> fADCDynRange; // input dynamic range (mV)
+ //--------------------------------------------------------
} else {
R__b.WriteVersion(AliTPCParam::IsA());
- TObject::Streamer(R__b);
- R__b << fInnerRadiusLow;
- R__b << fInnerRadiusUp;
- R__b << fOuterRadiusLow;
- R__b << fOuterRadiusUp;
- R__b << fInnerAngle;
- R__b << fInnerAngleShift;
- R__b << fOuterAngle;
- R__b << fOuterAngleShift;
-
- R__b << fPadPitchLength;
- R__b << fPadPitchWidth;
- R__b << fPadLength;
- R__b << fPadWidth;
-
- R__b << fnWires;
-
- R__b <<fDiffT;
- R__b <<fDiffL;
- R__b <<fGasGain;
- R__b <<fDriftV;
- R__b <<fOmegaTau;
- R__b <<fOxyCont;
- R__b <<fAttCoef;
-
-
- R__b <<fPadCoupling;
- R__b <<fZeroSup;
- R__b <<fNoise;
- R__b <<fChipGain;
+ AliDetectorParam::Streamer(R__b);
+ //---------------------------------------------------------------------
+ // ALICE TPC sector geometry
+ //--------------------------------------------------------------------
+ R__b << fInnerRadiusLow; // lower radius of inner sector-IP
+ R__b << fInnerRadiusUp; // upper radius of inner sector-IP
+ R__b << fOuterRadiusUp; // upper radius of outer sector-IP
+ R__b << fOuterRadiusLow; // lower radius of outer sector-IP
+ R__b << fInnerAngle; //opening angle of Inner sector
+ R__b << fInnerAngleShift; //shift of first inner sector center to the 0
+ R__b << fOuterAngle; //opening angle of outer sector
+ R__b << fOuterAngleShift; //shift of first sector center to the 0
+ R__b << fInnerFrameSpace; //spce for inner frame in the phi direction
+ R__b << fOuterFrameSpace; //spce for outer frame in the phi direction
+ R__b << fInnerWireMount;
+ R__b << fOuterWireMount;
+ //R__b << fNInnerSector; //!number of inner sectors - calculated
+ //R__b << fNOuterSector; //!number of outer sectors -calculated
+ //R__b << fNSector; //! total number of sectors -calculated
+ R__b << fZLength; //length of the drift region of the TPC
+ //R__b.WriteFastArray(fRotAngle,fNSector*4); // sin and cos of rotation angles for
+ R__b << fGeometryType; //type of geometry -0 straight rows
- R__b <<fTSample;
- R__b <<fTSigma;
+ // diferent sectors
+ //---------------------------------------------------------------------
+ // ALICE TPC wires geometry
+ //--------------------------------------------------------------------
+ R__b << fNInnerWiresPerPad;// Number of wires per pad
+ // R__b << fInnerWWPitch; // pitch between wires in inner sector - calculated
+ R__b << fInnerDummyWire; //number of wires without pad readout
+ R__b << fInnerOffWire;//oofset of first wire to the begining of the sector
+ //R__b << fRInnerFirstWire; //position of the first wire -calculated
+ //R__b << fRInnerLastWire; //position of the last wire -calculated
+ R__b << fNOuterWiresPerPad;// Number of wires per pad
+ //R__b << fOuterWWPitch; // pitch between wires in outer sector - calculated
+ R__b << fOuterDummyWire; //number of wires without pad readout
+ R__b << fOuterOffWire;//oofset of first wire to the begining of the sector
+ //R__b << fROuterFirstWire; //position of the first wire -calulated
+ //R__b << fROuterLastWire; //position of the last wire -calculated
+ //---------------------------------------------------------------------
+ // ALICE TPC pad parameters
+ //--------------------------------------------------------------------
+ R__b << fInnerPadPitchLength; //Inner pad pitch length
+ R__b << fInnerPadPitchWidth; //Inner pad pitch width
+ R__b << fInnerPadLength; //Inner pad length
+ R__b << fInnerPadWidth; //Inner pad width
+ R__b << fOuterPadPitchLength; //Outer pad pitch length
+ R__b << fOuterPadPitchWidth; //Outer pad pitch width
+ R__b << fOuterPadLength; //Outer pad length
+ R__b << fOuterPadWidth; //Outer pad width
+ R__b << fBMWPCReadout; //indicate wire readout
+ R__b << fNCrossRows; // number of rows to cross talk
+ R__b << fNRowLow; // number of pad rows per low sector
+ R__b << fNRowUp; // number of pad rows per sector up
+ // R__b << fPadRowLow[600]; // Lower sector, pad row radii
+ //R__b << fPadRowUp[600]; // Upper sector, pad row radii
+ //R__b << fNPadsLow[600]; // Lower sector, number of pads per row
+ //R__b << fNPadsUp[600]; // Upper sector, number of pads per row
+ //---------------------------------------------------------------------
+ // ALICE TPC Gas Parameters
+ //--------------------------------------------------------------------
+ R__b << fDiffT; //tangencial diffusion constant
+ R__b << fDiffL; //longutudinal diffusion constant
+ R__b << fGasGain; //gas gain constant
+ R__b << fDriftV; //drift velocity constant
+ R__b << fOmegaTau; //omega tau ExB coeficient
+ R__b << fAttCoef; //attachment coefitients
+ R__b << fOxyCont; //oxygen content
+ //---------------------------------------------------------------------
+ // ALICE TPC Electronics Parameters
+ //--------------------------------------------------------------------
+ R__b << fPadCoupling; //coupling factor ration of anode signal
+ //and total pads signal
+ R__b << fZeroSup; //zero suppresion constant
+ R__b << fNoise; //noise sigma constant
+ R__b << fChipGain; //preamp shaper constant
+ R__b << fChipNorm; //preamp shaper normalisation
+ R__b << fTSample; // sampling time
+ R__b << fZWidth; //derived value calculated using TSample and driftw
+ R__b << fTSigma; // width of the Preamp/Shaper function
+ R__b << fMaxTBin; //maximum time bin number
+ R__b << fADCSat; //saturation value of ADC (10 bits)
+ R__b << fADCDynRange; // input dynamic range (mV)
}
}
// Manager class for TPC parameters //
////////////////////////////////////////////////
-#include "TObject.h"
+#include "AliDetectorParam.h"
+#include "TMath.h"
// the last things from AliTPCSecGeo
-//const Float_t z_end = 250.;
-//const Float_t alpha_low=0.523598775; // 30 degrees
-//const Float_t alpha_up=0.261799387; // 15 degrees
-//const Float_t q_el = 1.602e-19; // elementary charge
-//const Float_t adc_sat = 1023; // dynamic range (10 bits)
-//const Float_t dyn_range = 2000.; // output dynamic range (mV)
-
+const Float_t z_end = 250.;
+const Float_t alpha_low=0.34906585; // 20 degrees
+const Float_t alpha_up=0.34906585; // 20 degrees
+const Float_t q_el = 1.602e-19; // elementary charge
+const Float_t adc_sat = 1023; // dynamic range (10 bits)
+const Float_t dyn_range = 2000.; // output dynamic range (mV)
+//
-class AliTPCParam : public TObject {
+class AliTPCParam : public AliDetectorParam {
//////////////////////////////////////////////////////
//////////////////////////////////////////////////////
//ALITPCParam object to be possible change
//geometry and some other parameters of TPC
- //used by AliTPC and AliTPCSector
+ //used by AliTPC and AliTPCSector
+
public:
AliTPCParam();
- virtual ~AliTPCParam() {;} //dummy destructor
+ virtual ~AliTPCParam();
- void XYZtoCRXYZ(Float_t *xyz,
- Int_t §or, Int_t &padrow, Int_t option=3);
+ virtual Bool_t Transform(Float_t *xyz, Int_t *index, Int_t* oindex);
+ //transformation from input coodination system to output coordination system
+ Int_t Transform0to1(Float_t *xyz, Int_t *index) const;
+ //trasforamtion from global to global - adjust index[0] sector
+ //return value is equal to sector corresponding to global position
+ inline void Transform1to2(Float_t *xyz, Int_t *index) const;
+ //transformation to rotated coordinata
+ inline void Transform2to1(Float_t *xyz, Int_t *index) const;
+ //transformation from rotated coordinata to global coordinata
+ inline void Transform2to2(Float_t *xyz, Int_t *index, Int_t *oindex) const;
+ //transform rotated coordinata of one sector to rotated
+ //coordinata relative to another sector
+ inline Float_t Transform2to2NearestWire(Float_t *xyz, Int_t *index) const;
+ //round x position to nearest wire
+ inline Int_t Transform2to3(Float_t *xyz, Int_t *index) const;
+ //calulate coresponding index[2] -pad row for straight rows
+ //does not change xyz[]
+ //return pad - row
+ inline void Transform3to4(Float_t *xyz, Int_t *index) const;
+ //valid only for straight rows straight rows
+ //calculate xyz[0] position relative to given index
+ //return pad - row
+ inline void Transform4to3(Float_t *xyz, Int_t *index) const;
+ //valid only for straight rows straight rows
+ //transform xyz[0] position relative to given index
+ inline void Transform2to5( Float_t *xyz, Int_t *index) const;
+ //transform [x,y,z] to [r,rphi,z]
+ inline void Transform5to2(Float_t *xyz, Int_t *index) const;
+ //transform [r,rphi,z] coordinata to [x,y,z]
+ inline void Transform4to8(Float_t *xyz, Int_t *index) const;
+ //transform xyz coordinata to 'digit' coordinata
+ inline void Transform8to4(Float_t *xyz, Int_t *index) const;
+ //transform 'digit' coordinata to xyz coordinata
+ inline void Transform6to8(Float_t *xyz, Int_t *index) const;
+ //transform dr,f coordinata to 'digit' coordinata
+ inline void Transform8to6(Float_t *xyz, Int_t *index) const;
+ //transform 'digit' coordinata to dr,f coordinata
+
+ virtual Int_t Transform2toPadRow(Float_t *xyz, Int_t *index) const{return 0;}
+ //transform rotated to
+
+ virtual Int_t GetPadRow(Float_t *xyz, Int_t *index) const ;
+ //return pad row of point xyz - xyz is given in coordinate system -(given by index)
+ //output system is 3 for straight row and 7 for cylindrical row
+ virtual void XYZtoCRXYZ(Float_t *xyz,
+ Int_t §or, Int_t &padrow, Int_t option=3){;}
//transform global position to the position relative to the sector padrow
//if option=0 X calculate absolute calculate sector
//if option=1 X absolute use input sector
//if option=2 X relative to pad row calculate sector
//if option=3 X relative use input sector
- void CRXYZtoXYZ(Float_t *xyz,
- const Int_t §or, const Int_t & padrow, Int_t option=3) const;
+ virtual void CRXYZtoXYZ(Float_t *xyz,
+ const Int_t §or, const Int_t & padrow, Int_t option=3) const {;}
//transform relative position to the gloabal position
- void CRTimePadtoYZ(Float_t &y, Float_t &z,
- const Float_t &time, const Float_t &pad,
- Int_t sector, Int_t padrow );
+ virtual void CRTimePadtoYZ(Float_t &y, Float_t &z,
+ const Float_t &time, const Float_t &pad,
+ Int_t sector, Int_t padrow ){;}
//transform position in digit units (time slices and pads) to "normal"
//units (cm)
- void CRYZtoTimePad(const Float_t &y, const Float_t &z,
- Float_t &time, Float_t &pad,
- Int_t sector, Int_t padrow);
- //transform position in cm to position in digit unit
+ virtual void CRYZtoTimePad(const Float_t &y, const Float_t &z,
+ Float_t &time, Float_t &pad,
+ Int_t sector, Int_t padrow){;}
+ //transform position in cm to position in digit unit
+ virtual Int_t CalcResponse(Float_t* x, Int_t * index, Int_t row){return 0;}
+ //calculate bin response as function of the input position -x and the weight
+ //if row -pad row is equal -1 calculate response for each pad row
+ //otherwise it calculate only in given pad row
+ //return number of valid response bin
+ virtual void SetDefault(); //set defaut TPCparam
+ virtual Bool_t Update(); //recalculate and check geometric parameters
+ Bool_t GetStatus(); //get information about object consistency
+ Int_t GetIndex(Int_t sector, Int_t row); //give index of the given sector and pad row
+ Int_t GetNSegmentsTotal() const {return fNtRows;}
Double_t GetLowMaxY(Int_t irow) const {return irow*0.;}
Double_t GetUpMaxY(Int_t irow) const {return irow*0;}
- //additional geometrical function
- Int_t GetPadRow(Int_t isec, Float_t &x);
- //return pad row for given sector and position x
- //if res=-1 it is out of sector
-
- Int_t GetWire(Float_t &x);
- Int_t GetIndex(Int_t sector, Int_t row); //give index of the given sector and pad row
- Bool_t AdjustSectorRow(Int_t index, Int_t & sector, Int_t &row); //return sector and padrow
+ //additional geometrical function - for Belikov
+
+ Bool_t AdjustSectorRow(Int_t index, Int_t & sector, Int_t &row) const; //return sector and padrow
//for given index
- Int_t GetNRowsTotal(){return fNtRows;} //get total nuber of rows
- void SetDefault(); //set defaut TPCparam
- Bool_t Update(); //recalculate and check geometric parameters
- Bool_t GetStatus(); //get information about object consistency
+ inline void AdjustCosSin(Int_t isec, Float_t &cos, Float_t &sin) const;
+ //set cosinus and sinus of rotation angles for sector isec
+ inline Float_t GetAngle(Int_t isec) const;
+ //
+ //set sector parameters
+ //
+ void SetInnerRadiusLow(Float_t InnerRadiusLow ) { fInnerRadiusLow=InnerRadiusLow;}
+ void SetOuterRadiusLow(Float_t OuterRadiusLow ) { fOuterRadiusLow=OuterRadiusLow;}
+ void SetInnerRadiusUp(Float_t InnerRadiusUp) { fInnerRadiusUp= InnerRadiusUp;}
+ void SetOuterRadiusUp(Float_t OuterRadiusUp) { fOuterRadiusUp= OuterRadiusUp;}
+ void SetSectorAngles(Float_t innerangle, Float_t innershift, Float_t outerangle,
+ Float_t outershift);
+ void SetInnerFrameSpace(Float_t frspace) {fInnerFrameSpace = frspace;}
+ void SetOuterFrameSpace(Float_t frspace) {fOuterFrameSpace = frspace;}
+ void SetInnerWireMount(Float_t fmount) {fInnerWireMount = fmount;}
+ void SetOuterWireMount(Float_t fmount) {fOuterWireMount = fmount;}
+ void SetZLength(Float_t zlength) {fZLength = zlength;}
+ void SetGeometryType(Int_t type) {fGeometryType = type;}
+ //
+ //set wire parameters
+ //
+ void SetInnerNWires(Int_t nWires){ fNInnerWiresPerPad=nWires;}
+ void SetInnerDummyWire(Int_t dummy) {fInnerDummyWire = dummy;}
+ void SetInnerOffWire(Float_t offset) {fInnerOffWire =offset;}
+ void SetOuterNWires(Int_t nWires){ fNOuterWiresPerPad=nWires;}
+ void SetOuterDummyWire(Int_t dummy) {fOuterDummyWire = dummy;}
+ void SetOuterOffWire(Float_t offset) {fOuterOffWire =offset;}
+ //
+ //set pad parameter
+ //
+ void SetInnerPadPitchLength(Float_t PadPitchLength){ fInnerPadPitchLength=PadPitchLength;}
+ void SetInnerPadPitchWidth(Float_t PadPitchWidth){ fInnerPadPitchWidth = PadPitchWidth;}
+ void SetInnerPadLength(Float_t PadLength){ fInnerPadLength=PadLength;}
+ void SetInnerPadWidth(Float_t PadWidth) { fInnerPadWidth=PadWidth;}
+ void SetOuterPadPitchLength(Float_t PadPitchLength){ fOuterPadPitchLength=PadPitchLength;}
+ void SetOuterPadPitchWidth(Float_t PadPitchWidth){ fOuterPadPitchWidth = PadPitchWidth;}
+ void SetOuterPadLength(Float_t PadLength){ fOuterPadLength=PadLength;}
+ void SetOuterPadWidth(Float_t PadWidth) { fOuterPadWidth=PadWidth;}
+ void SetMWPCReadout(Bool_t type) {fBMWPCReadout = type;}
+ void SetNCrossRows(Int_t rows){fNCrossRows = rows;}
+ //
+ //set gas paremeters
+ //
+ void SetDiffT(Float_t DiffT){ fDiffT= DiffT;}
+ void SetDiffL(Float_t DiffL){ fDiffL=DiffL;}
+ void SetGasGain(Float_t GasGain){ fGasGain=GasGain;}
+ void SetDriftV(Float_t DriftV){ fDriftV= DriftV;}
+ void SetOmegaTau(Float_t OmegaTau){ fOmegaTau=OmegaTau;}
+ void SetAttCoef(Float_t AttCoef){ fAttCoef=AttCoef;}
+ void SetOxyCont(Float_t OxyCont){ fOxyCont=OxyCont;}
+ //
+ //set electronivc parameters
+ //
+ void SetPadCoupling(Float_t PadCoupling){ fPadCoupling=PadCoupling;}
+ void SetZeroSup(Int_t ZeroSup) { fZeroSup=ZeroSup;}
+ void SetNoise(Float_t Noise ) { fNoise= Noise;}
+ void SetChipGain(Float_t ChipGain){ fChipGain= ChipGain;}
+ void SetChipNorm(Float_t ChipNorm){ fChipNorm= ChipNorm;}
+ void SetTSample(Float_t TSample) { fTSample=TSample;}
+ void SetTFWHM(Float_t fwhm) { fTSigma=fwhm/2.35;}
+ void SetMaxTBin(Int_t maxtbin) { fMaxTBin = maxtbin;}
+ void SetADCSat(Int_t adcsat) { fADCSat = adcsat;}
+ void SetADCDynRange(Float_t adcdynrange) {fADCDynRange = adcdynrange;}
+ //
+ //set response parameters
+ //
+ void SetNResponseMax(Int_t max) { fNResponseMax = max;}
+ void SetResponseThreshold(Int_t threshold) {fResponseThreshold = threshold;}
+ //
+ //get sector parameters
+ //
+ Float_t GetInnerRadiusLow() const {return fInnerRadiusLow;}
+ Float_t GetInnerRadiusUp() const {return fInnerRadiusUp;}
+ Float_t GetOuterRadiusLow() const {return fOuterRadiusLow;}
+ Float_t GetOuterRadiusUp() const {return fOuterRadiusUp;}
+ Float_t GetInnerFrameSpace() const {return fInnerFrameSpace;}
+ Float_t GetOuterFrameSpace() const {return fOuterFrameSpace;}
+ Float_t GetInnerWireMount() const {return fInnerWireMount;}
+ Float_t GetOuterWireMount() const {return fOuterWireMount;}
+ Float_t GetInnerAngle() const ;
+ Float_t GetInnerAngleShift() const ;
+ Float_t GetOuterAngle() const ;
+ Float_t GetOuterAngleShift() const ;
+ Int_t GetNInnerSector() const {return fNInnerSector;}
+ Int_t GetNOuterSector() const {return fNOuterSector;}
+ Int_t GetNSector() const {return fNSector;}
+ Float_t GetZLength() const {return fZLength;}
+ Int_t GetGeometryType() const {return fGeometryType;}
+
+ //
+ //get wires parameter
+ //
+ Int_t GetInnerNWires() const {return fNInnerWiresPerPad;}
+ Float_t GetInnerWWPitch() const {return fInnerWWPitch;}
+ Int_t GetInnerDummyWire() const {return fInnerDummyWire;}
+ Float_t GetInnerOffWire() const {return fInnerOffWire;}
+ Float_t GetRInnerFirstWire() const {return fRInnerFirstWire;}
+ Float_t GetRInnerLastWire() const {return fRInnerLastWire;}
+ Int_t GetOuterNWires() const {return fNOuterWiresPerPad;}
+ Float_t GetOuterWWPitch() const {return fOuterWWPitch;}
+ Int_t GetOuterDummyWire() const {return fOuterDummyWire;}
+ Float_t GetOuterOffWire() const {return fOuterOffWire;}
+ Float_t GetROuterFirstWire() const {return fROuterFirstWire;}
+ Float_t GetROuterLastWire() const {return fROuterLastWire;}
+ Float_t GetWWPitch(Int_t isector = 0) const {
+ return ( (isector < fNInnerSector) ? fInnerWWPitch :fOuterWWPitch);}
+ //
+ //get pad parameters
+ //
+ Float_t GetInnerPadPitchLength() const {return fInnerPadPitchLength;}
+ Float_t GetInnerPadPitchWidth() const {return fInnerPadPitchWidth;}
+ Float_t GetInnerPadLength() const {return fInnerPadLength;}
+ Float_t GetInnerPadWidth() const {return fInnerPadWidth;}
+ Float_t GetOuterPadPitchLength() const {return fOuterPadPitchLength;}
+ Float_t GetOuterPadPitchWidth() const {return fOuterPadPitchWidth;}
+ Float_t GetOuterPadLength() const {return fOuterPadLength;}
+ Float_t GetOuterPadWidth() const {return fOuterPadWidth;}
+ Bool_t GetMWPCReadout() const {return fBMWPCReadout;}
+ Int_t GetNCrossRows() const {return fNCrossRows;}
+ Float_t GetPadPitchWidth(Int_t isector = 0) const {
+ return ( (isector < fNInnerSector) ? fInnerPadPitchWidth :fOuterPadPitchWidth);}
+ Float_t GetPadPitchLength(Int_t isector = 0) const {
+ return ( (isector < fNInnerSector) ? fInnerPadPitchLength :fOuterPadPitchLength);}
- void AdjustAngles(Int_t isec, Float_t &cos, Float_t &sin) const;
- //set cosinus and sinus of rotation angles for sector isec
Int_t GetNRowLow() const; //get the number of pad rows in low sector
Int_t GetNRowUp() const; //get the number of pad rows in up sector
- Int_t GetNRow(Int_t isec) {return ((isec<fNInnerSector) ? fnRowLow:fnRowUp);}
- //get the nuber of pad row in given sector
+ Int_t GetNRow(Int_t isec) const {return ((isec<fNInnerSector) ? fNRowLow:fNRowUp);}
+ Int_t GetNRowsTotal(){return fNtRows;} //get total nuber of rows
Float_t GetPadRowRadiiLow(Int_t irow) const; //get the pad row (irow) radii
Float_t GetPadRowRadiiUp(Int_t irow) const; //get the pad row (irow) radii
Float_t GetPadRowRadii(Int_t isec,Int_t irow) const {
return ( (isec < fNInnerSector) ?GetPadRowRadiiLow(irow):GetPadRowRadiiUp(irow));}
- //retrun raii of the pad row irow in sector i
+ //retrun radii of the pad row irow in sector i
Int_t GetNPadsLow(Int_t irow) const; //get the number of pads in row irow
Int_t GetNPadsUp(Int_t irow) const; //get the number of pads in row irow
- Int_t GetNPads(Int_t isector,Int_t irow){
- return ( (isector < fNInnerSector) ?GetNPadsLow(irow) : GetNPadsUp(irow));}
- //get the number of pads in given sector and row
- // Int_t GetNPads(Int_t isector, Int_t irow) const;
- //get the number of pads in sector isector and row irow
-
- void SetInnerRadiusLow(Float_t InnerRadiusLow ) { fInnerRadiusLow=InnerRadiusLow;}
- void SetOuterRadiusLow(Float_t OuterRadiusLow ){ fOuterRadiusLow=OuterRadiusLow;}
- void SetInnerRadiusUp(Float_t InnerRadiusUp){ fInnerRadiusUp= InnerRadiusUp;}
- void SetOuterRadiusUp(Float_t OuterRadiusUp){ fOuterRadiusUp= OuterRadiusUp;}
-
- void SetSectorAngles(Float_t innerangle, Float_t innershift, Float_t outerangle,
- Float_t outershift,Bool_t inDegree=kTRUE);
-
- void SetInSecLowEdge(Float_t isle){fInSecLowEdge=isle;}
- void SetInSecUpEdge(Float_t isue){fInSecUpEdge=isue;}
- void SetOuSecLowEdge(Float_t osle){fOuSecLowEdge=osle;}
- void SetOuSecUpEdge(Float_t osue){fOuSecUpEdge=osue;}
-
- void SetEdge(Float_t edge){fEdge = edge;}
- void SetDeadZone(Float_t zone){fDeadZone = zone;}
-
-
- void SetPadPitchLength(Float_t PadPitchLength){ fPadPitchLength=PadPitchLength;}
- void SetPadPitchWidth(Float_t PadPitchWidth){ fPadPitchWidth = PadPitchWidth;}
- void SetPadLength(Float_t PadLength){ fPadLength=PadLength;}
- void SetPadWidth(Float_t PadWidth) { fPadWidth=PadWidth;}
- void SetDiffT(Float_t DiffT){ fDiffT= DiffT;}
- void SetDiffL(Float_t DiffL){ fDiffL=DiffL;}
- void SetDriftV(Float_t DriftV){ fDriftV= DriftV;}
- void SetOmegaTau(Float_t OmegaTau){ fOmegaTau=OmegaTau;}
- void SetAttCoef(Float_t AttCoef){ fAttCoef=AttCoef;}
- void SetOxyCont(Float_t OxyCont){ fOxyCont=OxyCont;}
+ Int_t GetNPads(Int_t isector,Int_t irow) const{
+ return ( (isector < fNInnerSector) ?GetNPadsLow(irow) : GetNPadsUp(irow));}
+ //
+ //get GAS parameters
+ //
+ Float_t GetDiffT() const {return fDiffT;}
+ Float_t GetDiffL() const {return fDiffL;}
+ Float_t GetGasGain() const {return fGasGain;}
+ Float_t GetDriftV() const {return fDriftV;}
+ Float_t GetOmegaTau() const {return fOmegaTau;}
+ Float_t GetAttCoef() const {return fAttCoef;}
+ Float_t GetOxyCont() const {return fOxyCont;}
+ //
+ //get Electronic parameters
+ //
+ Float_t GetPadCoupling() const {return fPadCoupling;}
+ Int_t GetZeroSup() const {return fZeroSup;}
+ Float_t GetNoise() const {return fNoise;}
+ Float_t GetChipGain() const {return fChipGain;}
+ Float_t GetChipNorm() const {return fChipNorm;}
+ Float_t GetTSample() const {return fTSample;}
+ Float_t GetZWidth() const {return fZWidth;}
+ Float_t GetTFWHM() const {return fTSigma*2.35;}
+ Float_t GetZSigma() const {return fTSigma*fDriftV;}
+ virtual Float_t GetZOffset() {return 3*fTSigma*fDriftV;}
+ Int_t GetMaxTBin() const {return fMaxTBin;}
+ Int_t GetADCSat() const {return fADCSat;}
+ Float_t GetADCDynRange() const {return fADCDynRange;}
+ Float_t GetTotalNormFac() const {return fTotalNormFac;}
+ Float_t GetNoiseNormFac() const {return fNoiseNormFac;}
+ //
+ // get response data
+ //
+ inline Int_t * GetResBin(Int_t i);
+ //return response bin i - bin given by padrow [0] pad[1] timebin[2]
+ inline Float_t GetResWeight(Int_t i);
+ //return weight of response bin i
+protected :
- void SetNoise(Float_t Noise ){ fNoise= Noise;}
- void SetChipGain(Float_t ChipGain){ fChipGain= ChipGain;}
- void SetGasGain(Float_t GasGain){ fGasGain=GasGain;}
- void SetTSample(Float_t TSample){ fTSample=TSample;}
- void SetTSigma(Float_t Sigma){ fTSigma=Sigma;}
- void SetPadCoupling(Float_t PadCoupling){ fPadCoupling=PadCoupling;}
- void SetNWires(Int_t nWires){ fnWires=nWires;}
- void SetWWPitch(Float_t WWPitch){ fWWPitch=WWPitch;}
- void SetZeroSup(Int_t ZeroSup){ fZeroSup=ZeroSup;}
-
- Float_t GetInnerRadiusLow(){return fInnerRadiusLow;}
- Float_t GetOuterRadiusLow(){return fOuterRadiusLow;}
- Float_t GetInnerRadiusUp(){return fInnerRadiusUp;}
- Float_t GetOuterRadiusUp(){return fOuterRadiusUp;}
-
- Float_t GetInnerAngle(){return fInnerAngle;}
- Float_t GetInnerAngleShift(){return fInnerAngleShift;}
- Float_t GetOuterAngle(){return fOuterAngle;}
- Float_t GetOuterAngleShift(){return fOuterAngleShift;}
- Int_t GetNInnerSector(){return fNInnerSector;}
- Int_t GetNOuterSector(){return fNOuterSector;}
- Int_t GetNSector(){return fNSector;}
-
- Float_t GetInSecLowEdge(){return fInSecLowEdge;}
- Float_t GetInSecUpEdge(){return fInSecUpEdge;}
- Float_t GetOuSecLowEdge(){return fOuSecLowEdge;}
- Float_t GetOuSecUpEdge(){return fOuSecUpEdge;}
-
- Float_t GetEdge(){return fEdge;}
- Float_t GetDeadZone(){return fDeadZone;}
-
- Float_t GetPadPitchLength(){return fPadPitchLength;}
- Float_t GetPadPitchWidth(){return fPadPitchWidth;}
- Float_t GetPadLength(){return fPadLength;}
- Float_t GetPadWidth() {return fPadWidth;}
- Float_t GetDiffT(){return fDiffT;}
- Float_t GetDiffL(){return fDiffL;}
- Float_t GetDriftV(){return fDriftV;}
- Float_t GetOmegaTau(){return fOmegaTau;}
- Float_t GetAttCoef(){return fAttCoef;}
- Float_t GetOxyCont(){return fOxyCont;}
-
- Float_t GetNoise(){return fNoise;}
- Float_t GetChipGain(){return fChipGain;}
- Float_t GetGasGain(){return fGasGain;}
- Float_t GetTSample(){return fTSample;}
- Float_t GetTSigma(){return fTSigma;}
- Float_t GetZWidth(){return fZWidth;}
- Float_t GetZSigma(){return fTSigma*fDriftV;}
- Float_t GetPadCoupling(){return fPadCoupling;}
- Int_t GetNWires(){return fnWires;}
- Float_t GetWWPitch(){return fWWPitch;}
- Int_t GetZeroSup(){return fZeroSup;}
- Int_t GetMaxTBin(){return fMaxTBin;}
-
-private :
Bool_t fbStatus; //indicates consistency of the data
//---------------------------------------------------------------------
// ALICE TPC sector geometry
+ //--------------------------------------------------------------------
+ Float_t fInnerRadiusLow; // lower radius of inner sector-IP
+ Float_t fInnerRadiusUp; // upper radius of inner sector-IP
+ Float_t fOuterRadiusUp; // upper radius of outer sector-IP
+ Float_t fOuterRadiusLow; // lower radius of outer sector-IP
+ Float_t fInnerAngle; //opening angle of Inner sector
+ Float_t fInnerAngleShift; //shift of first inner sector center to the 0
+ Float_t fOuterAngle; //opening angle of outer sector
+ Float_t fOuterAngleShift; //shift of first sector center to the 0
+ Float_t fInnerFrameSpace; //space for inner frame in the phi direction
+ Float_t fOuterFrameSpace; //space for outer frame in the phi direction
+ Float_t fInnerWireMount; //space for wire mount, inner sector
+ Float_t fOuterWireMount; //space for wire mount, outer sector
+ Int_t fNInnerSector; //!number of inner sectors -calculated
+ Int_t fNOuterSector; //!number of outer sectors -calculated
+ Int_t fNSector; //! total number of sectors -calculated
+ Float_t fZLength; //length of the drift region of the TPC
+ Float_t *fRotAngle; // sin and cos of rotation angles for
+ // diferent sectors -calculated
+ Int_t fGeometryType; //type of geometry -0 straight rows
+ //1-cylindrical
+ //---------------------------------------------------------------------
+ // ALICE TPC wires geometry - for GEM we can consider that it is gating
//--------------------------------------------------------------------
-
- Float_t fInnerRadiusLow; // lower radius of inner sector
- Float_t fOuterRadiusLow; // lower radius of outer sector
- Float_t fInnerRadiusUp; // upper radius of inner sector
- Float_t fOuterRadiusUp; // upper radius of outer sector
-
- Float_t fInnerAngle; //opening angle of Inner sector
- Float_t fInnerAngleShift; //shift of first inner sector center to the 0
- Float_t fOuterAngle; //opening angle of outer sector
- Float_t fOuterAngleShift; //shift of first sector center to the 0
-
- Int_t fNInnerSector; //!number of inner sectors
- Int_t fNOuterSector; //!number of outer sectors
- Int_t fNSector; //! total number of sectors
-
- Float_t fInSecLowEdge; // inner sector lower edge
- Float_t fInSecUpEdge; // inner sector upper edge
- Float_t fOuSecLowEdge; // outer sector lower edge
- Float_t fOuSecUpEdge; // outer sector upper edge
-
- Float_t fEdge; // thickness of the sector edge
- Float_t fDeadZone; // dead zone due to the sector mounting etc.
-
+ Int_t fNInnerWiresPerPad; // Number of wires per pad
+ Float_t fInnerWWPitch; // pitch between wires in inner sector - calculated
+ Int_t fInnerDummyWire; //number of wires without pad readout
+ Float_t fInnerOffWire; //oofset of first wire to the begining of the sector
+ Float_t fRInnerFirstWire; //position of the first wire -calculated
+ Float_t fRInnerLastWire; //position of the last wire -calculated
+ Int_t fNOuterWiresPerPad; // Number of wires per pad
+ Float_t fOuterWWPitch; // pitch between wires in outer sector -calculated
+ Int_t fOuterDummyWire; //number of wires without pad readout
+ Float_t fOuterOffWire; //oofset of first wire to the begining of the sector
+ Float_t fROuterFirstWire; //position of the first wire -calulated
+ Float_t fROuterLastWire; //position of the last wire -calculated
//---------------------------------------------------------------------
// ALICE TPC pad parameters
//--------------------------------------------------------------------
- Float_t fPadPitchLength; //pad pitch length
- Float_t fPadPitchWidth; //pad pitch width
- Float_t fPadLength; //pad length
- Float_t fPadWidth; //pad width
-
-
- Int_t fnRowLow; // number of pad rows per low sector
- Int_t fnRowUp; // number of pad rows per sector up
- Float_t fPadRowLow[600]; // Lower sector, pad row radii
- Float_t fPadRowUp[600]; // Upper sector, pad row radii
- Int_t fnPadsLow[600]; // Lower sector, number of pads per row
- Int_t fnPadsUp[600]; // Upper sector, number of pads per row
- Float_t fRotAngle[200]; // sin and cos of rotation angles for
- // diferent sectors
-
- Int_t fnWires; // Number of wires per pad
- Float_t fWWPitch; // pitch between wires
+ Float_t fInnerPadPitchLength; //Inner pad pitch length
+ Float_t fInnerPadPitchWidth; //Inner pad pitch width
+ Float_t fInnerPadLength; //Inner pad length
+ Float_t fInnerPadWidth; //Inner pad width
+ Float_t fOuterPadPitchLength; //Outer pad pitch length
+ Float_t fOuterPadPitchWidth; //Outer pad pitch width
+ Float_t fOuterPadLength; //Outer pad length
+ Float_t fOuterPadWidth; //Outer pad width
+ Bool_t fBMWPCReadout; //indicate wire readout - kTRUE or GEM readout -kFALSE
+ Int_t fNCrossRows; //number of rows to crostalk calculation
+
+ Int_t fNRowLow; //number of pad rows per low sector -calculated
+ Int_t fNRowUp; //number of pad rows per sector up -calculated
+ Int_t fNtRows; //total number of rows in TPC -calculated
+ Float_t fPadRowLow[600]; //Lower sector, pad row radii -calculated
+ Float_t fPadRowUp[600]; //Upper sector, pad row radii -calculated
+ Int_t fNPadsLow[600]; //Lower sector, number of pads per row -calculated
+ Int_t fNPadsUp[600]; //Upper sector, number of pads per row -calculated
//---------------------------------------------------------------------
// ALICE TPC Gas Parameters
//--------------------------------------------------------------------
Float_t fDiffT; //tangencial diffusion constant
Float_t fDiffL; //longutudinal diffusion constant
Float_t fGasGain; //gas gain constant
- Float_t fDriftV; //drift velocity constant
+ Float_t fDriftV; //drift velocity constant
Float_t fOmegaTau; //omega tau ExB coeficient
Float_t fAttCoef; //attachment coefitients
Float_t fOxyCont; //oxygen content
//--------------------------------------------------------------------
Float_t fPadCoupling; //coupling factor ration of anode signal
//and total pads signal
- Int_t fZeroSup; //zero suppresion constant
- Float_t fNoise; //noise sigma constant
- Float_t fChipGain; //preamp shaper constant
- Float_t fTSample; // sampling time
- Float_t fZWidth; //derived value calculated using TSample and driftw
- Float_t fTSigma; // width of the Preamp/Shaper function
- Int_t fMaxTBin; //maximum time bin number
- //--------------------------------------------------------
- //
- Int_t fNtRows; //total number of rows in TPC
+ Int_t fZeroSup; //zero suppresion constant
+ Float_t fNoise; //noise sigma constant
+ Float_t fChipGain; //preamp shaper constant
+ Float_t fChipNorm; //preamp shaper normalisation
+ Float_t fTSample; //sampling time
+ Float_t fZWidth; //derived value calculated using TSample and driftw -computed
+ Float_t fTSigma; //width of the Preamp/Shaper function
+ Int_t fMaxTBin; //maximum time bin number
+ Int_t fADCSat; //saturation value of ADC (10 bits)
+ Float_t fADCDynRange; //input dynamic range (mV)
+ Float_t fTotalNormFac; //full normalisation factor - calculated
+ Float_t fNoiseNormFac; //normalisation factor to transform noise in electron to ADC channel
+
+
+protected:
+ //---------------------------------------------------------------------
+ // ALICE TPC response data
+ //---------------------------------------------------------------------
+ Int_t fNResponseMax; //maximal dimension of response
+ Float_t fResponseThreshold; //threshold for accepted response
+ Int_t fCurrentMax; //current maximal dimension -calulated
+ Int_t *fResponseBin; //array with bins -calulated
+ Float_t *fResponseWeight; //array with response -calulated
+
ClassDef(AliTPCParam,2) //parameter object for set:TPC
};
+
+inline Int_t * AliTPCParam::GetResBin(Int_t i)
+{
+ //return response bin i - bin given by padrow [0] pad[1] timebin[2]
+ if (i<fCurrentMax) return &fResponseBin[i*3];
+ else return 0;
+};
+
+inline Float_t AliTPCParam::GetResWeight(Int_t i)
+{
+ //return weight of response bin i
+ if (i<fCurrentMax) return fResponseWeight[i];
+ else return 0;
+}
+
/////////////////////////////////////////////////////////////////////////////
//
//---------------------------------------------------------------------
//
//
// Sigma rphi
-/*const Float_t a_rphi=0.41818e-2;
+const Float_t a_rphi=0.41818e-2;
const Float_t b_rphi=0.17460e-4;
const Float_t c_rphi=0.30993e-2;
const Float_t d_rphi=0.41061e-3;
const Float_t ac_z=0.19081;
const Float_t bc_z=0.55938e-3;
const Float_t cc_z=0.30428;
-*/
+
+
+
+void AliTPCParam::AdjustCosSin(Int_t isec, Float_t &cos, Float_t &sin) const
+{
+ //
+ //set cosinus and sinus of rotation angles for sector isec
+ //
+ cos=fRotAngle[isec*4];
+ sin=fRotAngle[isec*4+1];
+}
+
+Float_t AliTPCParam::GetAngle(Int_t isec) const
+{
+ //
+ //return rotation angle of given sector
+ //
+ return fRotAngle[isec*4+2];
+}
+
+
+inline void AliTPCParam::Transform1to2(Float_t *xyz, Int_t *index) const
+{
+ //transformation to rotated coordinates
+ //we must have information about sector!
+
+ //rotate to given sector
+ Float_t cos,sin;
+ AdjustCosSin(index[1],cos,sin);
+ Float_t x1=xyz[0]*cos + xyz[1]*sin;
+ Float_t y1=-xyz[0]*sin + xyz[1]*cos;
+ xyz[0]=x1;
+ xyz[1]=y1;
+ xyz[2]=fZLength-TMath::Abs(xyz[2]);
+ index[0]=2;
+}
+
+inline void AliTPCParam::Transform2to1(Float_t *xyz, Int_t *index) const
+{
+ //
+ //transformation from rotated coordinates to global coordinates
+ //
+ Float_t cos,sin;
+ AdjustCosSin(index[1],cos,sin);
+ Float_t x1=xyz[0]*cos - xyz[1]*sin;
+ Float_t y1=xyz[0]*sin + xyz[1]*cos;
+ xyz[0]=x1;
+ xyz[1]=y1;
+ xyz[2]=fZLength-xyz[2];
+ if (index[1]<fNInnerSector)
+ if ( index[1]>=(fNInnerSector>>1)) xyz[2]*=-1.;
+ else
+ if ( (index[1]-fNInnerSector) > (fNOuterSector>>1) ) xyz[2]*=-1;
+ index[0]=1;
+}
+
+inline void AliTPCParam::Transform2to2(Float_t *xyz, Int_t *index, Int_t *oindex) const
+{
+ //transform rotated coordinats of one sector to rotated
+ //coordinates relative to another sector
+ Transform2to1(xyz,index);
+ Transform1to2(xyz,oindex);
+ index[0]=2;
+ index[1]=oindex[1];
+}
+
+inline Float_t AliTPCParam::Transform2to2NearestWire(Float_t *xyz, Int_t *index) const
+{
+ //
+ // asigns the x-position of the closest wire to xyz[0], return the
+ // electron to closest wire distance
+ //
+ Float_t xnew,dx;
+ if (index[1]<fNInnerSector) {
+ xnew = fRInnerFirstWire+TMath::Nint((xyz[0]-fRInnerFirstWire)/fInnerWWPitch)*fInnerWWPitch;
+ }
+ else {
+ xnew = fROuterFirstWire+TMath::Nint((xyz[0]-fROuterFirstWire)/fOuterWWPitch)*fOuterWWPitch;
+ }
+ dx = xnew-xyz[0];
+ xyz[0]=xnew;
+ return dx;
+}
+
+inline Int_t AliTPCParam::Transform2to3(Float_t *xyz, Int_t *index) const
+{
+ //
+ //calulates coresponding pad row number, sets index[2] for straight rows
+ //does not change xyz[] information
+ //valid only for straight row
+ //
+ if (index[1]<fNInnerSector)
+ index[2] =TMath::Nint((xyz[0]-fPadRowLow[0])/fInnerPadPitchLength);
+ else
+ index[2] = TMath::Nint((xyz[0]-fPadRowUp[0])/fOuterPadPitchLength);
+ index[0]=3;
+ return index[2];
+}
+
+inline void AliTPCParam::Transform3to4(Float_t *xyz, Int_t *index) const
+{
+ //
+ //valid only for straight rows straight rows
+ //calculate xyz[0] position relative to given index
+ //
+ if (index[1]<fNInnerSector)
+ xyz[0] -=index[2]*fInnerPadPitchLength+fPadRowLow[0];
+ else
+ xyz[0] -=index[2]*fOuterPadPitchLength+fPadRowUp[0];
+ index[0] =4;
+}
+
+inline void AliTPCParam::Transform4to3(Float_t *xyz, Int_t *index) const
+{
+ //
+ //valid only for straight rows
+ //transforms relative xyz[0] to the global one within given sector
+ //
+ if (index[1]<fNInnerSector)
+ xyz[0] +=index[2]*fInnerPadPitchLength+fPadRowLow[0];
+ else
+ xyz[0] +=index[2]*fOuterPadPitchLength+fPadRowUp[0];
+ index[0] =3;
+}
+
+
+inline void AliTPCParam::Transform2to5( Float_t *xyz, Int_t *index) const
+{
+ //
+ //transform [x,y,z] to [r,phi,z]
+ //
+ Float_t angle;
+ Float_t r = TMath::Sqrt(xyz[0]*xyz[0]+xyz[1]*xyz[1]);
+ if ((xyz[0]==0)&&(xyz[1]==0)) angle = 0;
+ else
+ {
+ angle =TMath::ASin(xyz[1]/r);
+ if (xyz[0]<0) angle=TMath::Pi()-angle;
+ if ( (xyz[0]>0) && (xyz[1]<0) ) angle=2*TMath::Pi()+angle;
+ }
+ xyz[0]=r;
+ xyz[1]=angle;
+ index[0]=5;
+}
+
+inline void AliTPCParam::Transform5to2( Float_t *xyz, Int_t *index) const
+{
+ //
+ //transform [r,rphi,z] to [x,y,z]
+ //
+ Float_t r = xyz[0];
+ Float_t angle= xyz[1];
+ xyz[0]=r*TMath::Cos(angle);
+ xyz[1]=r*TMath::Sin(angle);
+ index[0]=2;
+}
+
+inline void AliTPCParam::Transform4to8(Float_t *xyz, Int_t *index) const
+{
+ //
+ //transform xyz coordinates to 'digit' coordinates
+ //
+ if (index[1]<fNInnerSector) {
+ xyz[0]/=fInnerPadPitchLength;
+ xyz[1]/=fInnerPadPitchWidth;
+ xyz[2]/=fZWidth;
+ }
+ else{
+ xyz[0]/=fOuterPadPitchLength;
+ xyz[1]/=fOuterPadPitchWidth;
+ xyz[2]/=fZWidth;
+ }
+ index[0]=8;
+}
+
+inline void AliTPCParam::Transform8to4(Float_t *xyz, Int_t *index) const
+{
+ //
+ //transforms 'digit' coordinates to xyz coordinates
+ //
+ if (index[1]<fNInnerSector) {
+ xyz[0]*=fInnerPadPitchLength;
+ xyz[1]*=fInnerPadPitchWidth;
+ xyz[2]*=fZWidth;
+ }
+ else{
+ xyz[0]*=fOuterPadPitchLength;
+ xyz[1]*=fOuterPadPitchWidth;
+ xyz[2]*=fZWidth;
+ }
+ index[0]=4;
+}
+
+inline void AliTPCParam::Transform6to8(Float_t *xyz, Int_t *index) const
+{
+ //
+ //transforms cylindrical xyz coordinates to 'digit' coordinates
+ //
+
+ if (index[1]<fNInnerSector) {
+ xyz[0]/=fInnerPadPitchLength;
+ xyz[1]*=xyz[0]/fInnerPadPitchWidth;
+ xyz[2]/=fZWidth;
+ }
+ else{
+ xyz[0]/=fOuterPadPitchLength;
+ xyz[1]*=xyz[0]/fOuterPadPitchWidth;
+ xyz[2]/=fZWidth;
+ }
+ index[0]=8;
+}
+
+inline void AliTPCParam::Transform8to6(Float_t *xyz, Int_t *index) const
+{
+ //
+ //transforms 'digit' coordinates to cylindrical xyz coordinates
+ //
+
+ if (index[1]<fNInnerSector) {
+ xyz[0]*=fInnerPadPitchLength;
+ xyz[1]/=xyz[0]/fInnerPadPitchWidth;
+ xyz[2]*=fZWidth;
+ }
+ else{
+ xyz[0]*=fOuterPadPitchLength;
+ xyz[1]/=xyz[0]/fOuterPadPitchWidth;
+ xyz[2]*=fZWidth;
+ }
+ index[0]=6;
+}
--- /dev/null
+/**************************************************************************
+ * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
+ * *
+ * Author: The ALICE Off-line Project. *
+ * Contributors are mentioned in the code where appropriate. *
+ * *
+ * Permission to use, copy, modify and distribute this software and its *
+ * documentation strictly for non-commercial purposes is hereby granted *
+ * without fee, provided that the above copyright notice appears in all *
+ * copies and that both the copyright notice and this permission notice *
+ * appear in the supporting documentation. The authors make no claims *
+ * about the suitability of this software for any purpose. It is *
+ * provided "as is" without express or implied warranty. *
+ **************************************************************************/
+
+/*
+$Log$
+Revision 1.1.4.2 2000/04/10 11:36:13 kowal2
+
+New Detector parameters handling class
+
+*/
+
+///////////////////////////////////////////////////////////////////////
+// Manager and of geomety classes for set: TPC //
+// //
+// !sectors are numbered from 0 //
+// !pad rows are numbered from 0 //
+//
+// 27.7. - AliTPCPaaramSr object for TPC
+// TPC with straight pad rows
+// Origin: Marian Ivanov, Uni. of Bratislava, ivanov@fmph.uniba.sk //
+// //
+///////////////////////////////////////////////////////////////////////
+
+
+#include <iostream.h>
+#include <TMath.h>
+#include <TObject.h>
+#include <AliTPCParamCR.h>
+
+
+
+ClassImp(AliTPCParamCR)
+const static Int_t kMaxRows=600;
+const static Float_t kEdgeSectorSpace = 2.5;
+
+AliTPCParamCR::AliTPCParamCR()
+{
+ //
+ //constructor set the default parameters
+ fInnerPRF=0;
+ fOuterPRF=0;
+ fTimeRF = 0;
+ fFacSigma = Float_t(2.);
+ SetDefault();
+ Update();
+}
+
+AliTPCParamCR::~AliTPCParamCR()
+{
+ //
+ //destructor destroy some dynmicaly alocated variables
+ if (fInnerPRF != 0) delete fInnerPRF;
+ if (fOuterPRF != 0) delete fOuterPRF;
+ if (fTimeRF != 0) delete fTimeRF;
+}
+
+void AliTPCParamCR::SetDefault()
+{
+ //set default TPC param
+ fbStatus = kFALSE;
+ AliTPCParam::SetDefault();
+}
+
+Int_t AliTPCParamCR::CalcResponse(Float_t* xyz, Int_t * index)
+{
+ //
+ //calculate bin response as function of the input position -x
+ //return number of valid response bin
+ //
+ //we suppose that coordinata is expressed in float digits
+ // it's mean coordinate system 8
+ //xyz[0] - float padrow xyz[1] is float pad (center pad is number 0) and xyz[2] is float time bin
+ if ( (fInnerPRF==0)||(fOuterPRF==0)||(fTimeRF==0) ){
+ Error("AliTPCParamCR", "response function were not adjusted");
+ return -1;
+ }
+
+ Float_t sfpadrow; // sigma of response function
+ Float_t sfpad; // sigma of
+ Float_t sftime= fFacSigma*fTimeRF->GetSigma()/fZWidth; //3 sigma of time response
+ if (index[1]<fNInnerSector){
+ sfpadrow =fFacSigma*fInnerPRF->GetSigmaY()/fInnerPadPitchLength;
+ sfpad =fFacSigma*fInnerPRF->GetSigmaX()/fInnerPadPitchWidth;
+ }else{
+ sfpadrow =fFacSigma*fOuterPRF->GetSigmaY()/fOuterPadPitchLength;
+ sfpad =fFacSigma*fOuterPRF->GetSigmaX()/fOuterPadPitchWidth;
+ }
+
+ Int_t fpadrow = TMath::Nint(xyz[0]-sfpadrow); //"first" padrow
+ Int_t fpad = TMath::Nint(xyz[1]-sfpad); //first pad
+ Int_t ftime = TMath::Nint(xyz[2]+fTimeRF->GetOffset()-sftime); // first time
+ Int_t lpadrow = TMath::Min(TMath::Nint(xyz[0]+sfpadrow),fpadrow+19); //"last" padrow
+ Int_t lpad = TMath::Min(TMath::Nint(xyz[1]+sfpad),fpad+19); //last pad
+ Int_t ltime = TMath::Min(TMath::Nint(xyz[2]+fTimeRF->GetOffset()+sftime),ftime+19); // last time
+
+ Float_t padres[20][20]; //I don't expect bigger number of bins
+ Float_t timeres[20];
+ //calculate padresponse function
+ Int_t padrow;
+ for (padrow = fpadrow;padrow<=lpadrow;padrow++)
+ for (Int_t pad = fpad;pad<=lpad;pad++){
+ Float_t dy = (xyz[0]-Float_t(padrow));
+ Float_t dx = (xyz[1]-Float_t(pad));
+ if (index[1]<fNInnerSector)
+ padres[padrow-fpadrow][pad-fpad]=fInnerPRF->GetPRF(dx*fInnerPadPitchWidth,dy*fInnerPadPitchLength);
+ else
+ padres[padrow-fpadrow][pad-fpad]=fOuterPRF->GetPRF(dx*fOuterPadPitchWidth,dy*fOuterPadPitchLength);
+ }
+ //calculate time response function
+
+ Int_t time;
+ for (time = ftime;time<=ltime;time++) timeres[time-ftime]= fTimeRF->GetRF((xyz[2]-Float_t(time))*fZWidth);
+
+ //write over threshold values to stack
+ Int_t cindex3=-1;
+ Int_t cindex=0;
+ Float_t cweight = 0;
+ for (padrow = fpadrow;padrow<=lpadrow;padrow++)
+ for (Int_t pad = fpad;pad<=lpad;pad++)
+ for (time = ftime;time<=ltime;time++){
+ cweight = timeres[time-ftime]*padres[padrow-fpadrow][pad-fpad];
+ if (cweight>fResponseThreshold) {
+ fResponseBin[++cindex3]=padrow;
+ fResponseBin[++cindex3]=pad;
+ fResponseBin[++cindex3]=time;
+ fResponseWeight[++cindex]=cweight;
+ }
+ }
+ fCurrentMax=cindex;
+ return fCurrentMax;
+}
+
+void AliTPCParamCR::CRXYZtoXYZ(Float_t *xyz,
+ const Int_t §or, const Int_t & padrow, Int_t option) const
+{
+ //transform relative coordinates to absolute
+ Bool_t rel = ( (option&2)!=0);
+ Int_t index[2]={sector,padrow};
+ if (rel==kTRUE) Transform4to3(xyz,index);//if the position is relative to pad row
+ Transform2to1(xyz,index);
+}
+
+void AliTPCParamCR::XYZtoCRXYZ(Float_t *xyz,
+ Int_t §or, Int_t & padrow, Int_t option) const
+{
+ //transform global position to the position relative to the sector padrow
+ //if option=0 X calculate absolute calculate sector
+ //if option=1 X absolute use input sector
+ //if option=2 X relative to pad row calculate sector
+ //if option=3 X relative use input sector
+ //!!!!!!!!! WE start to calculate rows from row = 0
+ Int_t index[2];
+ Bool_t rel = ( (option&2)!=0);
+
+ //option 0 and 2 means that we don't have information about sector
+ if ((option&1)==0) Transform0to1(xyz,index); //we calculate sector number
+ else
+ index[0]=sector;
+ Transform1to2(xyz,index);
+ Transform2to3(xyz,index);
+ //if we store relative position calculate position relative to pad row
+ if (rel==kTRUE) Transform3to4(xyz,index);
+ sector = index[0];
+ padrow = index[1];
+}
+
+
+
+Bool_t AliTPCParamCR::Update()
+{
+
+ //
+ // update some calculated parameter which must be updated after changing "base"
+ // parameters
+ // for example we can change size of pads and according this recalculate number
+ // of pad rows, number of of pads in given row ....
+ Int_t i;
+ if (AliTPCParam::Update()==kFALSE) return kFALSE;
+ fbStatus = kFALSE;
+
+ // adjust lower sectors pad row positions and pad numbers
+ fNRowLow = (Int_t(1.0001*(fRInnerLastWire-fRInnerFirstWire)/fInnerWWPitch)
+ -2*fInnerDummyWire)/fNInnerWiresPerPad;
+ if ( kMaxRows<fNRowLow) fNRowUp = kMaxRows;
+ if (1>fNRowLow) return kFALSE;
+ Float_t firstpad = fRInnerFirstWire+(fInnerDummyWire-0.5)*fInnerWWPitch
+ +fInnerPadPitchLength/2.;
+
+ for (i = 0;i<fNRowLow;i++)
+ {
+ Float_t x = firstpad +fInnerPadPitchLength*(Float_t)i;
+ Float_t y = (x-0.5*fInnerPadPitchLength)*tan(fInnerAngle/2.)-fInnerFrameSpace-
+ fInnerPadPitchWidth/2.;
+ fPadRowLow[i] = x;
+ fNPadsLow[i] = 1+2*(Int_t)(y/fInnerPadPitchWidth) ;
+ }
+
+ // adjust upper sectors pad row positions and pad numbers
+ fNRowUp = (Int_t((fROuterLastWire-fROuterFirstWire+0.001)/fOuterWWPitch)
+ -2*fOuterDummyWire)/fNOuterWiresPerPad;
+ if ( kMaxRows<fNRowUp) fNRowUp = kMaxRows;
+ if (1>fNRowUp) return kFALSE;
+ firstpad = fROuterFirstWire+(fOuterDummyWire-0.5)*fOuterWWPitch
+ +fOuterPadPitchLength/2.;
+
+ for (i = 0;i<fNRowUp;i++)
+ {
+ Float_t x = firstpad + fOuterPadPitchLength*(Float_t)i;
+ Float_t y = (x-0.5*fOuterPadPitchLength)*tan(fOuterAngle/2.)-fOuterFrameSpace-
+ fInnerPadPitchWidth/2.;
+ fPadRowUp[i] = x;
+ fNPadsUp[i] = 1+2*(Int_t)(y/fOuterPadPitchWidth) ;
+ }
+ fNtRows = fNInnerSector*fNRowLow+fNOuterSector*fNRowUp;
+ return kTRUE;
+}
+
+
+
+void AliTPCParamCR::Streamer(TBuffer &R__b)
+{
+ // Stream an object of class AliTPC.
+
+ if (R__b.IsReading()) {
+ Version_t R__v = R__b.ReadVersion(); if (R__v) { }
+ // TObject::Streamer(R__b);
+ AliTPCParam::Streamer(R__b);
+ // if (R__v < 2) return;
+ Update();
+ } else {
+ R__b.WriteVersion(AliTPCParamCR::IsA());
+ //TObject::Streamer(R__b);
+ AliTPCParam::Streamer(R__b);
+ }
+}
+
+
+
+
--- /dev/null
+#ifndef TPCParamCR_H
+#define TPCParamCR_H
+/* Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
+ * See cxx source for full Copyright notice */
+
+/* $Id$ */
+
+////////////////////////////////////////////////
+// Manager class for TPC parameters //
+////////////////////////////////////////////////
+#include "AliTPCPRF2D.h"
+#include "AliTPCRF1D.h"
+#include "AliTPCParam.h"
+
+class AliTPCParamCR : public AliTPCParam {
+public:
+ AliTPCParamCR();
+ virtual ~AliTPCParamCR();
+ Int_t CalcResponse(Float_t* x, Int_t * index);
+ //calculate bin response as function of the input position -x
+ //return number of valid response bin
+
+ void XYZtoCRXYZ(Float_t *xyz,
+ Int_t §or, Int_t &padrow, Int_t option=3) const;
+ //transform global position to the position relative to the sector padrow
+ //if option=0 X calculate absolute calculate sector
+ //if option=1 X absolute use input sector
+ //if option=2 X relative to pad row calculate sector
+ //if option=3 X relative use input sector
+
+ void CRXYZtoXYZ(Float_t *xyz,
+ const Int_t §or, const Int_t & padrow, Int_t option=3) const;
+ //transform relative position to the gloabal position
+ Bool_t Update(); //recalculate and check geometric parameters
+ void SetDefault(); //set default parameters
+ void SetInnerPRF(AliTPCPRF2D * prf) {fInnerPRF = prf;}
+ void SetOuterPRF(AliTPCPRF2D * prf) {fOuterPRF = prf;}
+ void SetTimeRF(AliTPCRF1D * timerf) {fTimeRF = timerf;}
+
+ AliTPCPRF2D * GetInnerPRF() const {return fInnerPRF;}
+ AliTPCPRF2D * GetOuterPRF() const {return fOuterPRF;}
+ AliTPCRF1D * GetTimeRF() const {return fTimeRF;}
+protected:
+ AliTPCPRF2D * fInnerPRF; //pad response function object for inner sector
+ AliTPCPRF2D * fOuterPRF; //pad response function object for inner sector
+ AliTPCRF1D * fTimeRF; //time response function object
+ Float_t fFacSigma; //factor-how many sigma of response I accept
+ ClassDef(AliTPCParamCR,1) //parameter object for set:TPC
+};
+
+#endif
--- /dev/null
+/**************************************************************************
+ * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
+ * *
+ * Author: The ALICE Off-line Project. *
+ * Contributors are mentioned in the code where appropriate. *
+ * *
+ * Permission to use, copy, modify and distribute this software and its *
+ * documentation strictly for non-commercial purposes is hereby granted *
+ * without fee, provided that the above copyright notice appears in all *
+ * copies and that both the copyright notice and this permission notice *
+ * appear in the supporting documentation. The authors make no claims *
+ * about the suitability of this software for any purpose. It is *
+ * provided "as is" without express or implied warranty. *
+ **************************************************************************/
+
+/*
+$Log$
+Revision 1.1.4.2 2000/04/10 11:36:13 kowal2
+
+New Detector parameters handling class
+
+*/
+
+///////////////////////////////////////////////////////////////////////
+// Manager and of geomety classes for set: TPC //
+// //
+// !sectors are numbered from 0 //
+// !pad rows are numbered from 0 //
+//
+// 27.7. - AliTPCPaaramSr object for TPC
+// TPC with straight pad rows
+// Origin: Marian Ivanov, Uni. of Bratislava, ivanov@fmph.uniba.sk //
+// //
+///////////////////////////////////////////////////////////////////////
+
+
+#include <iostream.h>
+#include <TMath.h>
+#include <TObject.h>
+#include <AliTPCParamSR.h>
+
+
+
+ClassImp(AliTPCParamSR)
+const static Int_t kMaxRows=600;
+const static Float_t kEdgeSectorSpace = 2.5;
+const static Float_t kFacSigmaPadRow=2.;
+const static Float_t kFacSigmaPad=3.;
+const static Float_t kFacSigmaTime=3.;
+
+
+AliTPCParamSR::AliTPCParamSR()
+{
+ //
+ //constructor set the default parameters
+ fInnerPRF=0;
+ fOuterPRF=0;
+ fTimeRF = 0;
+ fFacSigmaPadRow = Float_t(kFacSigmaPadRow);
+ fFacSigmaPad = Float_t(kFacSigmaPad);
+ fFacSigmaTime = Float_t(kFacSigmaTime);
+
+
+ SetDefault();
+ Update();
+}
+
+AliTPCParamSR::~AliTPCParamSR()
+{
+ //
+ //destructor destroy some dynmicaly alocated variables
+ if (fInnerPRF != 0) delete fInnerPRF;
+ if (fOuterPRF != 0) delete fOuterPRF;
+ if (fTimeRF != 0) delete fTimeRF;
+}
+
+void AliTPCParamSR::SetDefault()
+{
+ //set default TPC param
+ fbStatus = kFALSE;
+ AliTPCParam::SetDefault();
+}
+
+Int_t AliTPCParamSR::CalcResponse(Float_t* xyz, Int_t * index, Int_t row)
+{
+ //
+ //calculate bin response as function of the input position -x
+ //return number of valid response bin
+ //
+ //we suppose that coordinate is expressed in float digits
+ // it's mean coordinate system 8
+ //xyz[0] - float padrow xyz[1] is float pad (center pad is number 0) and xyz[2] is float time bin
+ if ( (fInnerPRF==0)||(fOuterPRF==0)||(fTimeRF==0) ){
+ Error("AliTPCParamSR", "response function was not adjusted");
+ return -1;
+ }
+
+ Float_t sfpadrow; // sigma of response function
+ Float_t sfpad; // sigma of
+ Float_t sftime= fFacSigmaTime*fTimeRF->GetSigma()/fZWidth; //3 sigma of time response
+ if (index[1]<fNInnerSector){
+ sfpadrow =fFacSigmaPadRow*fInnerPRF->GetSigmaY()/fInnerPadPitchLength;
+ sfpad =fFacSigmaPad*fInnerPRF->GetSigmaX()/fInnerPadPitchWidth;
+ }else{
+ sfpadrow =fFacSigmaPadRow*fOuterPRF->GetSigmaY()/fOuterPadPitchLength;
+ sfpad =fFacSigmaPad*fOuterPRF->GetSigmaX()/fOuterPadPitchWidth;
+ }
+
+ Int_t fpadrow = TMath::Max(TMath::Nint(index[2]+xyz[0]-sfpadrow),0); //"first" padrow
+ Int_t fpad = TMath::Nint(xyz[1]-sfpad); //first pad
+ Int_t ftime = TMath::Max(TMath::Nint(xyz[2]+GetZOffset()/GetZWidth()-sftime),0); // first time
+ Int_t lpadrow = TMath::Min(TMath::Nint(index[2]+xyz[0]+sfpadrow),fpadrow+19); //"last" padrow
+ lpadrow = TMath::Min(GetNRow(index[1])-1,lpadrow);
+ Int_t lpad = TMath::Min(TMath::Nint(xyz[1]+sfpad),fpad+19); //last pad
+ Int_t ltime = TMath::Min(TMath::Nint(xyz[2]+GetZOffset()/GetZWidth()+sftime),ftime+19); // last time
+ ltime = TMath::Min(ltime,GetMaxTBin()-1);
+
+ if (row>=0) { //if we are interesting about given pad row
+ if (fpadrow<=row) fpadrow =row;
+ else
+ return 0;
+ if (lpadrow>=row) lpadrow = row;
+ else
+ return 0;
+ }
+
+
+ Float_t padres[20][20]; //I don't expect bigger number of bins
+ Float_t timeres[20];
+ Int_t cindex3=0;
+ Int_t cindex=0;
+ Float_t cweight = 0;
+ if (fpadrow>=0) {
+ //calculate padresponse function
+ Int_t padrow, pad;
+ for (padrow = fpadrow;padrow<=lpadrow;padrow++)
+ for (pad = fpad;pad<=lpad;pad++){
+ Float_t dy = (-xyz[0]+Float_t(index[2]-padrow));
+ Float_t dx = (-xyz[1]+Float_t(pad));
+ if (index[1]<fNInnerSector)
+ padres[padrow-fpadrow][pad-fpad]=fInnerPRF->GetPRF(dx*fInnerPadPitchWidth,dy*fInnerPadPitchLength);
+ else
+ padres[padrow-fpadrow][pad-fpad]=fOuterPRF->GetPRF(dx*fOuterPadPitchWidth,dy*fOuterPadPitchLength); }
+ //calculate time response function
+ Int_t time;
+ for (time = ftime;time<=ltime;time++)
+ timeres[time-ftime]= fTimeRF->GetRF((-xyz[2]+Float_t(time))*fZWidth);
+ //write over threshold values to stack
+ for (padrow = fpadrow;padrow<=lpadrow;padrow++)
+ for (pad = fpad;pad<=lpad;pad++)
+ for (time = ftime;time<=ltime;time++){
+ cweight = timeres[time-ftime]*padres[padrow-fpadrow][pad-fpad];
+ if (cweight>fResponseThreshold) {
+ fResponseBin[cindex3]=padrow;
+ fResponseBin[cindex3+1]=pad;
+ fResponseBin[cindex3+2]=time;
+ cindex3+=3;
+ fResponseWeight[cindex]=cweight;
+ cindex++;
+ }
+ }
+ }
+ fCurrentMax=cindex;
+ return fCurrentMax;
+}
+
+void AliTPCParamSR::TransformTo8(Float_t *xyz, Int_t *index) const
+{
+ //
+ // transformate point to digit coordinate
+ //
+ if (index[0]==0) Transform0to1(xyz,index);
+ if (index[0]==1) Transform1to2(xyz,index);
+ if (index[0]==2) Transform2to3(xyz,index);
+ if (index[0]==3) Transform3to4(xyz,index);
+ if (index[0]==4) Transform4to8(xyz,index);
+}
+
+void AliTPCParamSR::TransformTo2(Float_t *xyz, Int_t *index) const
+{
+ //
+ //transformate point to rotated coordinate
+ //
+ //we suppose that
+ if (index[0]==0) Transform0to1(xyz,index);
+ if (index[0]==1) Transform1to2(xyz,index);
+ if (index[0]==4) Transform4to3(xyz,index);
+ if (index[0]==8) { //if we are in digit coordinate system transform to global
+ Transform8to4(xyz,index);
+ Transform4to3(xyz,index);
+ }
+}
+
+void AliTPCParamSR::CRXYZtoXYZ(Float_t *xyz,
+ const Int_t §or, const Int_t & padrow, Int_t option) const
+{
+ //transform relative coordinates to absolute
+ Bool_t rel = ( (option&2)!=0);
+ Int_t index[2]={sector,padrow};
+ if (rel==kTRUE) Transform4to3(xyz,index);//if the position is relative to pad row
+ Transform2to1(xyz,index);
+}
+
+void AliTPCParamSR::XYZtoCRXYZ(Float_t *xyz,
+ Int_t §or, Int_t & padrow, Int_t option) const
+{
+ //transform global position to the position relative to the sector padrow
+ //if option=0 X calculate absolute calculate sector
+ //if option=1 X absolute use input sector
+ //if option=2 X relative to pad row calculate sector
+ //if option=3 X relative use input sector
+ //!!!!!!!!! WE start to calculate rows from row = 0
+ Int_t index[2];
+ Bool_t rel = ( (option&2)!=0);
+
+ //option 0 and 2 means that we don't have information about sector
+ if ((option&1)==0) Transform0to1(xyz,index); //we calculate sector number
+ else
+ index[0]=sector;
+ Transform1to2(xyz,index);
+ Transform2to3(xyz,index);
+ //if we store relative position calculate position relative to pad row
+ if (rel==kTRUE) Transform3to4(xyz,index);
+ sector = index[0];
+ padrow = index[1];
+}
+
+Float_t AliTPCParamSR::GetPrimaryLoss(Float_t *x, Int_t *index, Float_t *angle)
+{
+ //
+ //
+ Float_t padlength=GetPadPitchLength(index[1]);
+ Float_t a1=TMath::Sin(angle[0]);
+ a1*=a1;
+ Float_t a2=TMath::Sin(angle[1]);
+ a2*=a2;
+ Float_t length =padlength*TMath::Sqrt(1+a1+a2);
+ return length*fNPrimLoss;
+}
+
+Float_t AliTPCParamSR::GetTotalLoss(Float_t *x, Int_t *index, Float_t *angle)
+{
+ //
+ //
+ Float_t padlength=GetPadPitchLength(index[1]);
+ Float_t a1=TMath::Sin(angle[0]);
+ a1*=a1;
+ Float_t a2=TMath::Sin(angle[1]);
+ a2*=a2;
+ Float_t length =padlength*TMath::Sqrt(1+a1+a2);
+ return length*fNTotalLoss;
+
+}
+
+
+void AliTPCParamSR::GetClusterSize(Float_t *x, Int_t *index, Float_t *angle, Int_t mode, Float_t *sigma)
+{
+ //
+ //return cluster sigma2 (x,y) for particle at position x
+ // in this case x coordinata is in drift direction
+ //and y in pad row direction
+ //we suppose that input coordinate system is digit system
+
+ Float_t xx;
+ Float_t lx[3] = {x[0],x[1],x[2]};
+ Int_t li[3] = {index[0],index[1],index[2]};
+ TransformTo2(lx,li);
+ // Float_t sigmadiff;
+ sigma[0]=0;
+ sigma[1]=0;
+
+ xx = lx[2]; //calculate drift length in cm
+ if (xx>0) {
+ sigma[0]+= xx*GetDiffL()*GetDiffL();
+ sigma[1]+= xx*GetDiffT()*GetDiffT();
+ }
+
+
+ //sigma[0]=sigma[1]=0;
+ if (GetTimeRF()!=0) sigma[0]+=GetTimeRF()->GetSigma()*GetTimeRF()->GetSigma();
+ if ( (index[1]<fNInnerSector) &&(GetInnerPRF()!=0))
+ sigma[1]+=GetInnerPRF()->GetSigmaX()*GetInnerPRF()->GetSigmaX();
+ if ( (index[1]>=fNInnerSector) && (GetOuterPRF()!=0))
+ sigma[1]+=GetOuterPRF()->GetSigmaX()*GetOuterPRF()->GetSigmaX();
+
+
+ sigma[0]/= GetZWidth()*GetZWidth();
+ sigma[1]/=GetPadPitchWidth(index[0])*GetPadPitchWidth(index[0]);
+}
+
+
+
+
+void AliTPCParamSR::GetSpaceResolution(Float_t *x, Int_t *index, Float_t *angle,
+ Float_t amplitude, Int_t mode, Float_t *sigma)
+{
+ //
+ //
+ //
+
+}
+Float_t AliTPCParamSR::GetAmp(Float_t *x, Int_t *index, Float_t *angle)
+{
+ //
+ //
+ //
+ return 0;
+}
+
+Float_t * AliTPCParamSR::GetAnglesAccMomentum(Float_t *x, Int_t * index, Float_t* momentum, Float_t *angle)
+{
+ //
+ //calculate angle of track to padrow at given position
+ // for given magnetic field and momentum of the particle
+ //
+
+ TransformTo2(x,index);
+ AliDetectorParam::GetAnglesAccMomentum(x,index,momentum,angle);
+ Float_t addangle = TMath::ASin(x[1]/GetPadRowRadii(index[1],index[2]));
+ angle[1] +=addangle;
+ return angle;
+}
+
+
+Bool_t AliTPCParamSR::Update()
+{
+
+ //
+ // update some calculated parameter which must be updated after changing "base"
+ // parameters
+ // for example we can change size of pads and according this recalculate number
+ // of pad rows, number of of pads in given row ....
+ Int_t i;
+ if (AliTPCParam::Update()==kFALSE) return kFALSE;
+ fbStatus = kFALSE;
+
+ // adjust lower sectors pad row positions and pad numbers
+ fNRowLow = (Int_t(1.001+((fRInnerLastWire-fRInnerFirstWire)/fInnerWWPitch))
+ -2*fInnerDummyWire)/fNInnerWiresPerPad;
+ if ( kMaxRows<fNRowLow) fNRowUp = kMaxRows;
+ if (1>fNRowLow) return kFALSE;
+
+ //Float_t firstpad = fRInnerFirstWire+(fInnerDummyWire-0.5)*fInnerWWPitch
+ // +fInnerPadPitchLength/2.;
+ Float_t lastpad = fRInnerLastWire-(fInnerDummyWire-0.5)*fInnerWWPitch
+ -fInnerPadPitchLength/2.;
+ Float_t firstpad = lastpad-Float_t(fNRowLow-1)*fInnerPadPitchLength;
+
+ for (i = 0;i<fNRowLow;i++)
+ {
+ Float_t x = firstpad +fInnerPadPitchLength*(Float_t)i;
+ Float_t y = (x-0.5*fInnerPadPitchLength)*tan(fInnerAngle/2.)-fInnerWireMount-
+ fInnerPadPitchWidth/2.;
+ fPadRowLow[i] = x;
+ fNPadsLow[i] = 1+2*(Int_t)(y/fInnerPadPitchWidth) ;
+ }
+
+ // adjust upper sectors pad row positions and pad numbers
+ fNRowUp = (Int_t(1.001+((fROuterLastWire-fROuterFirstWire)/fOuterWWPitch))
+ -2*fOuterDummyWire)/fNOuterWiresPerPad;
+ if ( kMaxRows<fNRowUp) fNRowUp = kMaxRows;
+ if (1>fNRowUp) return kFALSE;
+ firstpad = fROuterFirstWire+(fOuterDummyWire-0.5)*fOuterWWPitch
+ +fOuterPadPitchLength/2.;
+
+ for (i = 0;i<fNRowUp;i++)
+ {
+ Float_t x = firstpad + fOuterPadPitchLength*(Float_t)i;
+ Float_t y = (x-0.5*fOuterPadPitchLength)*tan(fOuterAngle/2.)-fOuterWireMount-
+ fInnerPadPitchWidth/2.;
+ fPadRowUp[i] = x;
+ fNPadsUp[i] = 1+2*(Int_t)(y/fOuterPadPitchWidth) ;
+ }
+ fNtRows = fNInnerSector*fNRowLow+fNOuterSector*fNRowUp;
+ return kTRUE;
+}
+
+
+
+void AliTPCParamSR::Streamer(TBuffer &R__b)
+{
+ // Stream an object of class AliTPC.
+
+ if (R__b.IsReading()) {
+ Version_t R__v = R__b.ReadVersion(); if (R__v) { }
+ // TObject::Streamer(R__b);
+ AliTPCParam::Streamer(R__b);
+ // if (R__v < 2) return;
+ Update();
+ } else {
+ R__b.WriteVersion(AliTPCParamSR::IsA());
+ //TObject::Streamer(R__b);
+ AliTPCParam::Streamer(R__b);
+ }
+}
+
+
+
+
--- /dev/null
+#ifndef TPCParamSR_H
+#define TPCParamSR_H
+/* Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
+ * See cxx source for full Copyright notice */
+
+/* $Id$ */
+
+////////////////////////////////////////////////
+// Manager class for TPC parameters //
+////////////////////////////////////////////////
+#include "AliTPCPRF2D.h"
+#include "AliTPCRF1D.h"
+#include "AliTPCParam.h"
+
+class AliTPCParamSR : public AliTPCParam {
+public:
+ AliTPCParamSR();
+ virtual ~AliTPCParamSR();
+ Int_t CalcResponse(Float_t* x, Int_t * index, Int_t row);
+ //calculate bin response as function of the input position -x
+ //return number of valid response bin
+
+ void XYZtoCRXYZ(Float_t *xyz,
+ Int_t §or, Int_t &padrow, Int_t option=3) const;
+ //transform global position to the position relative to the sector padrow
+ //if option=0 X calculate absolute calculate sector
+ //if option=1 X absolute use input sector
+ //if option=2 X relative to pad row calculate sector
+ //if option=3 X relative use input sector
+
+ void CRXYZtoXYZ(Float_t *xyz,
+ const Int_t §or, const Int_t & padrow, Int_t option=3) const;
+ //transform relative position to the gloabal position
+ void TransformTo8(Float_t *xyz, Int_t *index) const;
+ void TransformTo2(Float_t *xyz, Int_t *index) const;
+ Bool_t Update(); //recalculate and check geometric parameters
+ void SetDefault(); //set default parameters
+ void SetInnerPRF(AliTPCPRF2D * prf) {fInnerPRF = prf;}
+ void SetOuterPRF(AliTPCPRF2D * prf) {fOuterPRF = prf;}
+ void SetTimeRF(AliTPCRF1D * timerf) {fTimeRF = timerf;}
+
+ AliTPCPRF2D * GetInnerPRF() const {return fInnerPRF;}
+ AliTPCPRF2D * GetOuterPRF() const {return fOuterPRF;}
+ AliTPCRF1D * GetTimeRF() const {return fTimeRF;}
+ void SetFacSigmaPadRow(Float_t fac) {fFacSigmaPadRow=fac;}
+ void SetFacSigmaPad(Float_t fac) {fFacSigmaPad=fac;}
+ void SetFacSigmaTime(Float_t fac) {fFacSigmaTime=fac;}
+
+ virtual Float_t GetPrimaryLoss(Float_t *x, Int_t *index, Float_t *angle);
+ virtual Float_t GetTotalLoss(Float_t *x, Int_t *index, Float_t *angle);
+
+ virtual void GetClusterSize(Float_t *x, Int_t *index, Float_t *angle, Int_t mode, Float_t *sigma);
+ virtual void GetSpaceResolution(Float_t *x, Int_t *index, Float_t *angle, Float_t amplitude, Int_t mode,Float_t *sigma);
+ virtual Float_t GetAmp(Float_t *x, Int_t *index, Float_t *angle);
+ virtual Float_t * GetAnglesAccMomentum(Float_t *x, Int_t * index, Float_t* momentum, Float_t *angle);
+
+protected:
+ AliTPCPRF2D * fInnerPRF; //pad response function object for inner sector
+ AliTPCPRF2D * fOuterPRF; //pad response function object for inner sector
+ AliTPCRF1D * fTimeRF; //time response function object
+ Float_t fFacSigmaPadRow; //factor-how many sigma of response I accept
+ Float_t fFacSigmaPad;
+ Float_t fFacSigmaTime;
+ ClassDef(AliTPCParamSR,1) //parameter object for set:TPC
+};
+
+#endif
+
+
+
+
+
+
/*
$Log$
+Revision 1.4.8.2 2000/04/10 08:53:09 kowal2
+
+Updates by M. Ivanov
+
+
+Revision 1.4 1999/09/29 09:24:34 fca
+Introduction of the Copyright and cvs Log
+
*/
//-----------------------------------------------------------------------------
// Declaration of class AliTPCRF1D
//
//-----------------------------------------------------------------------------
+
#include "TMath.h"
#include "AliTPCRF1D.h"
#include "TF2.h"
static Double_t funGauss(Double_t *x, Double_t * par)
{
+ //Gauss function -needde by the generic function object
return TMath::Exp(-(x[0]*x[0])/(2*par[0]*par[0]));
}
static Double_t funCosh(Double_t *x, Double_t * par)
{
+ //Cosh function -needde by the generic function object
return 1/TMath::CosH(3.14159*x[0]/(2*par[0]));
}
static Double_t funGati(Double_t *x, Double_t * par)
{
- //par[1] = is equal to k3
- //par[0] is equal to pad wire distance
+ //Gati function -needde by the generic function object
Float_t K3=par[1];
Float_t K3R=TMath::Sqrt(K3);
Float_t K2=(TMath::Pi()/2)*(1-K3R/2.);
return res;
}
-
-
-
-///////////////////////////////////////////////////////////////////////////
-///////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////
-AliTPCRF1D * gRF1D;
ClassImp(AliTPCRF1D)
AliTPCRF1D::AliTPCRF1D(Bool_t direct,Int_t np,Float_t step)
{
+ //default constructor for response function object
fDirect=direct;
fNRF = np;
fcharge = new Float_t[fNRF];
fDSTEPM1=1./step;
fSigma = 0;
- gRF1D = this;
fGRF = 0;
fkNorm = 0.5;
fpadWidth = 3.5;
AliTPCRF1D::~AliTPCRF1D()
{
- if (fcharge!=0) delete fcharge;
+ if (fcharge!=0) delete [] fcharge;
if (fGRF !=0 ) fGRF->Delete();
}
Float_t AliTPCRF1D::GetRF(Float_t xin)
{
- //x xin DSTEP unit
+ //function which return response
+ //for the charge in distance xin
//return linear aproximation of RF
Float_t x = TMath::Abs((xin-fOffset)*fDSTEPM1)+fNRF/2;
Int_t i1=Int_t(x);
Float_t AliTPCRF1D::GetGRF(Float_t xin)
{
+ //function which returnoriginal charge distribution
+ //this function is just normalised for fKnorm
if (fGRF != 0 )
return fkNorm*fGRF->Eval(xin)/fInteg;
else
void AliTPCRF1D::SetParam( TF1 * GRF,Float_t padwidth,
Float_t kNorm, Float_t sigma)
{
+ //adjust parameters of the original charge distribution
+ //and pad size parameters
fpadWidth = padwidth;
fGRF = GRF;
fkNorm = kNorm;
void AliTPCRF1D::SetGauss(Float_t sigma, Float_t padWidth,
Float_t kNorm)
{
- // char s[120];
+ //
+ // set parameters for Gauss generic charge distribution
+ //
fpadWidth = padWidth;
fkNorm = kNorm;
if (fGRF !=0 ) fGRF->Delete();
forigsigma=sigma;
fGRF->SetParameters(funParam);
fDSTEPM1 = 10./TMath::Sqrt(sigma*sigma+fpadWidth*fpadWidth/12);
- //by default I set the step as one tenth of sigma
- // Update();
+ //by default I set the step as one tenth of sigma
sprintf(fType,"Gauss");
}
void AliTPCRF1D::SetCosh(Float_t sigma, Float_t padWidth,
Float_t kNorm)
{
- // char s[120];
+ //
+ // set parameters for Cosh generic charge distribution
+ //
fpadWidth = padWidth;
fkNorm = kNorm;
if (fGRF !=0 ) fGRF->Delete();
forigsigma=sigma;
fDSTEPM1 = 10./TMath::Sqrt(sigma*sigma+fpadWidth*fpadWidth/12);
//by default I set the step as one tenth of sigma
- // Update();
sprintf(fType,"Cosh");
}
void AliTPCRF1D::SetGati(Float_t K3, Float_t padDistance, Float_t padWidth,
Float_t kNorm)
{
- // char s[120];
+ //
+ // set parameters for Gati generic charge distribution
+ //
fpadWidth = padWidth;
fkNorm = kNorm;
if (fGRF !=0 ) fGRF->Delete();
forigsigma=padDistance;
fDSTEPM1 = 10./TMath::Sqrt(padDistance*padDistance+fpadWidth*fpadWidth/12);
//by default I set the step as one tenth of sigma
- // Update();
sprintf(fType,"Gati");
}
void AliTPCRF1D::Draw(Float_t x1,Float_t x2,Int_t N)
{
+ //
+ //Draw prf in selected region <x1,x2> with nuber of diviision = n
+ //
char s[100];
TCanvas * c1 = new TCanvas("canRF","Pad response function",700,900);
c1->cd();
void AliTPCRF1D::Update()
{
- //initialize to 0
+ //
+ //update fields with interpolated values for
+ //PRF calculation
+
+ //at the begining initialize to 0
for (Int_t i =0; i<fNRF;i++) fcharge[i] = 0;
if ( fGRF == 0 ) return;
fInteg = fGRF->Integral(-5*forigsigma,5*forigsigma,funParam,0.00001);
void AliTPCRF1D::Streamer(TBuffer &R__b)
{
- // Stream an object of class AliTPC.
+ // Stream an object of class AliTPCRF1D.
if (R__b.IsReading()) {
Version_t R__v = R__b.ReadVersion(); if (R__v) { }
R__b >> fOffset;
//read functions
if (fGRF!=0) {
- delete fGRF;
+ delete [] fGRF;
fGRF=0;
}
if (strncmp(fType,"User",3)==0){
R__b <<fDSTEPM1;
R__b <<fNRF;
R__b.WriteFastArray(fcharge,fNRF);
- R__b.WriteFastArray(funParam,5);
-
-
-
+ R__b.WriteFastArray(funParam,5);
}
}
/* $Id$ */
////////////////////////////////////////////////
-// Manager class for AliTPCRF1D //
+// Manager class for AliTPCRF1D //
////////////////////////////////////////////////
//adjust RF with general function
void SetOffset(Float_t xoff) {fOffset=xoff;}
//set offset value
+ Float_t GetOffset(){return fOffset;}
Float_t GetPadWidth(){ return fpadWidth;};
//return pad width
Float_t GetSigma(){return fSigma;}
//return estimated sigma of RF
- void Draw(Option_t*) {}
void Draw(Float_t x1=-3 ,Float_t x2 =3.,Int_t N = 200);
//draw RF it don't delete histograms after drawing
/// it's on user !!!!
+++ /dev/null
-#ifndef TPCSecGeo_H
-#define TPCSecGeo_H
-/* Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
- * See cxx source for full Copyright notice */
-
-/* $Id$ */
-
-//Some things from the old AliTPCSecGeo
-
-const Float_t z_end = 250.;
-
-const Float_t q_el = 1.602e-19; // elementary charge
-const Float_t adc_sat = 1023; // dynamic range (10 bits)
-const Float_t dyn_range = 2000.; // output dynamic range (mV)
-
-/////////////////////////////////////////////////////////////////////////////
-//
-//---------------------------------------------------------------------
-// ALICE TPC Cluster Parameters
-//--------------------------------------------------------------------
-//
-//
-// Sigma rphi
-const Float_t a_rphi=0.41818e-2;
-const Float_t b_rphi=0.17460e-4;
-const Float_t c_rphi=0.30993e-2;
-const Float_t d_rphi=0.41061e-3;
-// Sigma z
-const Float_t a_z=0.39614e-2;
-const Float_t b_z=0.22443e-4;
-const Float_t c_z=0.51504e-1;
-// Cluster width in rphi
-const Float_t ac_rphi=0.18322;
-const Float_t bc_rphi=0.59551e-3;
-const Float_t cc_rphi=0.60952e-1;
-// Cluster width in z
-const Float_t ac_z=0.19081;
-const Float_t bc_z=0.55938e-3;
-const Float_t cc_z=0.30428;
-//
-
-#define TPCSecGeo_H
-
-#endif
void AliTPCTestClustering() {
- const char *pname="Param1";
- const char *tname="TreeD0_Param1";
+ const char *pname="75x40_100x60";
+ const char *tname="TreeD_75x40_100x60";
// Dynamically link some shared libs
+
if (gClassTable->GetID("AliRun") < 0) {
gROOT->LoadMacro("loadlibs.C");
loadlibs();
// Connect the Root Galice file containing Geometry, Kine and Hits
TFile *file = (TFile*)gROOT->GetListOfFiles()->FindObject("galice.root");
if (!file) file = new TFile("galice.root");
+ //if (!file) file = TFile::Open("rfio:galice.root");
// Get AliRun object from file or create it if not on file
if (!gAlice) {
int ver=TPC->IsVersion();
cerr<<"TPC version "<<ver<<" has been found !\n";
- AliTPCD *dig=(AliTPCD*)file->Get(pname);
- if (dig!=0) TPC->SetDigParam(dig);
+ AliTPCParam *dig=(AliTPCParam *)file->Get(pname);
+ if (dig!=0) TPC->SetParam(dig);
else cerr<<"Warning: default TPC parameters will be used !\n";
switch (ver) {
int n=c->GetEntriesFast();
cerr<<"Number of clusters "<<n<<" \n";
- AliTPCParam *par=&TPC->GetDigParam()->GetParam();
Float_t x[3];
TPolyMarker3D *pm=new TPolyMarker3D(n);
for (int i=0; i<n; i++) {
AliTPCcluster *cl=(AliTPCcluster *)c->UncheckedAt(i);
- cl->GetXYZ(x,par);
+ cl->GetXYZ(x,dig);
Double_t xx=x[0], yy=x[1], zz=x[2];
pm->SetPoint(i,xx,yy,zz);
}
+struct GoodTrack {
+ Int_t lab;
+ Int_t code;
+ Float_t px,py,pz;
+ Float_t x,y,z;
+};
+Int_t good_tracks(GoodTrack *gt, Int_t max);
+
void AliTPCTestTracking() {
- const char *pname="Param1";
- const char *tname="TreeD0_Param1";
+ const char *pname="75x40_100x60";
// Dynamically link some shared libs
+
if (gClassTable->GetID("AliRun") < 0) {
gROOT->LoadMacro("loadlibs.C");
loadlibs();
// Connect the Root Galice file containing Geometry, Kine and Hits
TFile *file = (TFile*)gROOT->GetListOfFiles()->FindObject("galice.root");
if (!file) file = new TFile("galice.root");
+ //if (!file) file = TFile::Open("rfio:galice.root");
// Get AliRun object from file or create it if not on file
if (!gAlice) {
gAlice->GetEvent(0);
- TClonesArray *particles=gAlice->Particles();
- int np=particles->GetEntriesFast();
- int *good=new int[np];
- for (int ii=0; ii<np; ii++) good[ii]=0;
-
AliTPC *TPC = (AliTPC*)gAlice->GetDetector("TPC");
- int ver=TPC->IsVersion();
+ Int_t ver=TPC->IsVersion();
cerr<<"TPC version "<<ver<<" has been found !\n";
- AliTPCD *digp= (AliTPCD*)file->Get(pname);
- if (digp!=0) TPC->SetDigParam(digp);
+ AliTPCParam *digp= (AliTPCParam*)file->Get(pname);
+ if (digp!=0) TPC->SetParam(digp);
else cerr<<"Warning: default TPC parameters will be used !\n";
- int nrow_up=TPC->GetDigParam()->GetParam().GetNRowUp();
- int nrows=TPC->GetDigParam()->GetParam().GetNRowLow()+nrow_up;
- int zero=TPC->GetDigParam()->GetParam().GetZeroSup();
- int gap=int(0.125*nrows);
- int good_number=int(0.4*nrows);
+ Int_t nrow_up=TPC->GetParam()->GetNRowUp();
+ Int_t nrows=TPC->GetParam()->GetNRowLow()+nrow_up;
switch (ver) {
case 1:
cerr<<"Making clusters...\n";
TPC->Hits2Clusters();
- TClonesArray *clusters=TPC->Clusters();
- if (!clusters) {cerr<<"No clusters found !\n"; return;}
- int n=clusters->GetEntriesFast();
- cerr<<"Number of clusters "<<n<<" \n";
-
- cerr<<"Marking \"good\" tracks... \n";
- for (int i=0; i<n; i++) {
- AliTPCcluster *c=(AliTPCcluster*)clusters->UncheckedAt(i);
- int lab=c->fTracks[0];
- if (lab<0) continue; //noise cluster
- lab=TMath::Abs(lab);
- int row=c->fPadRow;
- if (row==nrow_up-1 ) good[lab]|=0x1000;
- if (row==nrow_up-1-gap) good[lab]|=0x800;
- good[lab]++;
- }
-
break;
case 2:
cerr<<"Looking for clusters...\n";
TPC->Digits2Clusters();
- TClonesArray *clusters=TPC->Clusters();
- if (!clusters) {cerr<<"No clusters found !\n"; return;}
- int n=clusters->GetEntriesFast();
- cerr<<"Number of clusters "<<n<<" \n";
-
- cerr<<"Marking \"good\" tracks... \n";
- TTree *TD=gDirectory->Get(tname);
- TClonesArray *digits=TPC->Digits();
- TD->GetBranch("Digits")->SetAddress(&digits);
-
- int *count = new int[np];
- int i;
- for (i=0; i<np; i++) count[i]=0;
- int sectors_by_rows=(int)TD->GetEntries();
- for (i=0; i<sectors_by_rows; i++) {
- if (!TD->GetEvent(i)) continue;
- int row;
- int ndigits=digits->GetEntriesFast();
- int j;
- for (j=0; j<ndigits; j++) {
- AliTPCdigit *dig = (AliTPCdigit*)digits->UncheckedAt(j);
- int idx0=dig->fTracks[0];
- int idx1=dig->fTracks[1];
- int idx2=dig->fTracks[2];
- row=dig->fPadRow;
- if (idx0>=0 && dig->fSignal>=zero) count[idx0]+=1;
- if (idx1>=0 && dig->fSignal>=zero) count[idx1]+=1;
- if (idx2>=0 && dig->fSignal>=zero) count[idx2]+=1;
- }
- for (j=0; j<np; j++) {
- if (count[j]>1) {
- int ks;
- if (row==nrow_up-1 ) good[j]|=0x1000;
- if (row==nrow_up-1-gap) good[j]|=0x800;
- good[j]++;
- }
- count[j]=0;
- }
- }
- delete[] count;
-
break;
default:
cerr<<"Invalid TPC version !\n";
return;
}
+ TClonesArray *clusters=TPC->Clusters();
+ Int_t n=clusters->GetEntriesFast();
+ cerr<<"Number of clusters "<<n<<" \n";
+
cerr<<"Looking for tracks...\n";
+ TStopwatch timer;
TPC->Clusters2Tracks();
- int nt=0;
+ timer.Stop(); timer.Print();
+ Int_t nt=0;
TClonesArray *tracks=TPC->Tracks();
if (tracks) nt=tracks->GetEntriesFast();
cerr<<"Number of found tracks "<<nt<<endl;
/////////////////////////////////////////////////////////////////////////
+ GoodTrack gt[7000];
+ Int_t ngood=0;
+ ifstream in("good_tracks");
+ if (in) {
+ cerr<<"Reading good tracks...\n";
+ while (in>>gt[ngood].lab>>gt[ngood].code
+ >>gt[ngood].px >>gt[ngood].py>>gt[ngood].pz
+ >>gt[ngood].x >>gt[ngood].y >>gt[ngood].z) {
+ ngood++;
+ cerr<<ngood<<'\r';
+ if (ngood==7000) {
+ cerr<<"Too many good tracks !\n";
+ break;
+ }
+ }
+ if (!in.eof()) cerr<<"Read error (good_tracks) !\n";
+ } else {
+ cerr<<"Marking good tracks (this will take a while)...\n";
+ ngood=good_tracks(gt,7000);
+ ofstream out("good_tracks");
+ if (out) {
+ for (Int_t ngd=0; ngd<ngood; ngd++)
+ out<<gt[ngd].lab<<' '<<gt[ngd].code<<' '
+ <<gt[ngd].px <<' '<<gt[ngd].py<<' '<<gt[ngd].pz<<' '
+ <<gt[ngd].x <<' '<<gt[ngd].y <<' '<<gt[ngd].z <<endl;
+ } else cerr<<"Can not open file (good_tracks) !\n";
+ out.close();
+ }
+ cerr<<"Number of good tracks : "<<ngood<<endl;
+
cerr<<"Doing comparison...\n";
- TH1F *hp=new TH1F("hp","PHI resolution",50,-100.,100.); hp->SetFillColor(4);
- TH1F *hl=new TH1F("hl","LAMBDA resolution",50,-100,100); hl->SetFillColor(4);
+ TH1F *hp=new TH1F("hp","PHI resolution",50,-20.,20.); hp->SetFillColor(4);
+ TH1F *hl=new TH1F("hl","LAMBDA resolution",50,-20,20);hl->SetFillColor(4);
TH1F *hpt=new TH1F("hpt","Relative Pt resolution",30,-10.,10.);
hpt->SetFillColor(2);
- TH1F *hd=new TH1F("hd","Impact parameter distribution ",30,0,25);
- hd->SetFillColor(6);
+ TH1F *hmpt=new TH1F("hmpt","Relative Pt resolution (pt>4GeV/c)",30,-60,60);
+ hmpt->SetFillColor(6);
- TH1F *hgood=new TH1F("hgood","Good tracks",20,0,10);
- TH1F *hfound=new TH1F("hfound","Found tracks",20,0,10);
- TH1F *hfake=new TH1F("hfake","Fake tracks",20,0,10);
- TH1F *hg=new TH1F("hg","",20,0,10); //efficiency for good tracks
+ TH1F *hgood=new TH1F("hgood","Good tracks",20,0,7);
+ TH1F *hfound=new TH1F("hfound","Found tracks",20,0,7);
+ TH1F *hfake=new TH1F("hfake","Fake tracks",20,0,7);
+ TH1F *hg=new TH1F("hg","",20,0,7); //efficiency for good tracks
hg->SetLineColor(4); hg->SetLineWidth(2);
- TH1F *hf=new TH1F("hf","Efficiency for fake tracks",20,0,10);
+ TH1F *hf=new TH1F("hf","Efficiency for fake tracks",20,0,7);
hf->SetFillColor(1); hf->SetFillStyle(3013); hf->SetLineWidth(2);
- TH1F *he =new TH1F("he","dE/dX for pions with 0.4<p<0.5 GeV/c",50,0.,500.);
- TH2F *hep=new TH2F("hep","dE/dX vs momentum",50,0.,2.,50,0.,500.);
-
- for (int i=0; i<np; i++) {
- TParticle *p = (TParticle*)particles->UncheckedAt(i);
- if (p->GetFirstMother()>=0) continue; //secondary particle
- if (good[i] < 0x1000+0x800+2+good_number) continue;
- Double_t ptg=p->Pt(),pxg=p->Px(),pyg=p->Py(),pzg=p->Pz();
- if (ptg<0.100) continue;
- if (fabs(pzg/ptg)>0.999) continue;
+ TH1F *he =new TH1F("he","dE/dX for pions with 0.4<p<0.5 GeV/c",50,0.,100.);
+ TH2F *hep=new TH2F("hep","dE/dX vs momentum",50,0.,2.,50,0.,200.);
- //cout<<i<<endl;
+ while (ngood--) {
+ Int_t lab=gt[ngood].lab,tlab;
+ Float_t ptg=
+ TMath::Sqrt(gt[ngood].px*gt[ngood].px + gt[ngood].py*gt[ngood].py);
hgood->Fill(ptg);
- int found=0;
- for (int j=0; j<nt; j++) {
- AliTPCtrack *track=(AliTPCtrack*)tracks->UncheckedAt(j);
- int lab=track->GetLabel(nrows);
- if (fabs(lab)!=i) continue;
-
- found=1;
-
- Double_t xk=76.;
- track->PropagateTo(xk);
- xk-=0.11;
- track->PropagateTo(xk,42.7,2.27); //C
- xk-=26.;
- track->PropagateTo(xk,36.2,1.98e-3); //C02
- xk-=0.051;
- track->PropagateTo(xk,42.7,2.27); //C
- xk-=25.;
- track->PropagateTo(xk,36.7,1.29e-3);//Air
- xk-=0.4; // +
- track->PropagateTo(xk,21.82,2.33);//ITS+beam_pipe+etc (approximately)
-
- track->PropagateToVertex(); //comparison should be done at the vertex
-
- if (lab==i) hfound->Fill(ptg);
- else { hfake->Fill(ptg); cerr<<lab<<" fake\n";}
- Double_t px,py,pz,pt=fabs(track->GetPt());track->GetPxPyPz(px,py,pz);
- Double_t phig=TMath::ATan(pyg/pxg);
- Double_t phi =TMath::ATan(py /px );
- hp->Fill((phi - phig)*1000.);
- Double_t lamg=TMath::ATan(pzg/ptg);
- Double_t lam =TMath::ATan(pz /pt );
- hl->Fill((lam - lamg)*1000.);
- hpt->Fill((pt - ptg)/ptg*100.);
- Double_t x=track->GetX(), y=track->GetY(), z=track->GetZ();
- hd->Fill(sqrt(x*x + y*y + z*z)*10.);
-
- Double_t mom=track->GetP();
- Double_t dedx=track->GetdEdX(0.05,0.80)/
- digp->GetParam().GetPadPitchLength();
-
- hep->Fill(mom,dedx,1.);
- if (p->GetPdgCode()==211 || p->GetPdgCode()==-211)
- if (mom>0.4 && mom<0.5)
- he->Fill(dedx,1.);
-
- break;
+
+ AliTPCtrack *track;
+ Int_t i;
+ for (i=0; i<nt; i++) {
+ track=(AliTPCtrack*)tracks->UncheckedAt(i);
+ tlab=track->GetLabel(nrows);
+ if (lab==TMath::Abs(tlab)) break;
}
- if (!found) cerr<<"Track number "<<i<<" was not found !\n";
- }
+ if (i==nt) {
+ cerr<<"Track "<<lab<<" was not found !\n";
+ continue;
+ }
+ Double_t xk=gt[ngood].x;//digp->GetPadRowRadii(0,0);
+ track->PropagateTo(xk);
- delete[] good;
+ if (lab==tlab) hfound->Fill(ptg);
+ else { hfake->Fill(ptg); cerr<<lab<<" fake\n";}
+
+ Double_t px,py,pz,pt=fabs(track->GetPt());track->GetPxPyPz(px,py,pz);
+
+ if (TMath::Abs(gt[ngood].code)==11 && ptg>4.) {
+ hmpt->Fill((1/pt - 1/ptg)/(1/ptg)*100.);
+ } else {
+ Float_t phig=TMath::ATan2(gt[ngood].py,gt[ngood].px);
+ Float_t phi =TMath::ATan2(py,px );
+ hp->Fill((phi - phig)*1000.);
- Stat_t ngood =hgood->GetEntries(); cerr<<"Good tracks "<<ngood<<endl;
- Stat_t nfound=hfound->GetEntries();
- if (ngood!=0)
- cerr<<"Integral efficiency is about "<<nfound/ngood*100.<<" %\n";
+ Float_t lamg=TMath::ATan2(gt[ngood].pz,ptg);
+ Float_t lam =TMath::ATan2(pz ,pt );
+ hl->Fill((lam - lamg)*1000.);
+
+ hpt->Fill((1/pt - 1/ptg)/(1/ptg)*100.);
+ }
+ Float_t mom=track->GetP();
+ Float_t dedx=track->GetdEdX(0.05,0.70);
+ hep->Fill(mom,dedx,1.);
+ if (TMath::Abs(gt[ngood].code)==211)
+ if (mom>0.4 && mom<0.5) {
+ he->Fill(dedx,1.);
+ }
+ }
+
+ Stat_t ng=hgood->GetEntries(); cerr<<"Good tracks "<<ng<<endl;
+ Stat_t nf=hfound->GetEntries();
+ if (ng!=0)
+ cerr<<"Integral efficiency is about "<<nf/ng*100.<<" %\n";
gStyle->SetOptStat(111110);
gStyle->SetOptFit(1);
TPad *p4=new TPad("p4","",0.5,0,1,0.3); p4->Draw();
p4->cd(); p4->SetFillColor(42); p4->SetFrameFillColor(10);
- hd->SetXTitle("(mm)"); hd->Draw(); c1->cd();
+ hmpt->SetXTitle("(%)"); hmpt->Fit("gaus"); c1->cd();
TPad *p5=new TPad("p5","",0,0.6,1,1); p5->Draw(); p5->cd();
p5->SetFillColor(41); p5->SetFrameFillColor(10);
hg->SetXTitle("Pt (GeV/c)");
hg->Draw();
- TLine *line1 = new TLine(0,1.0,2,1.0); line1->SetLineStyle(4);
+ TLine *line1 = new TLine(0,1.0,7,1.0); line1->SetLineStyle(4);
line1->Draw("same");
- TLine *line2 = new TLine(0,0.9,2,0.9); line2->SetLineStyle(4);
+ TLine *line2 = new TLine(0,0.9,7,0.9); line2->SetLineStyle(4);
line2->Draw("same");
hf->SetFillColor(1);
hep->SetXTitle("p (Gev/c)"); hep->SetYTitle("dE/dX (Arb. Units)");
hep->Draw(); c1->cd();
+}
+
+Int_t good_tracks(GoodTrack *gt, Int_t max) {
+ const char *tname="TreeD_75x40_100x60";
+
+ Int_t nt=0;
+
+ AliTPC *TPC = (AliTPC*)gAlice->GetDetector("TPC");
+ Int_t ver=TPC->IsVersion();
+ AliTPCParam *digp= (AliTPCParam*)TPC->GetParam();
+
+ Int_t nrow_up=TPC->GetParam()->GetNRowUp();
+ Int_t nrows=TPC->GetParam()->GetNRowLow()+nrow_up;
+ Int_t zero=TPC->GetParam()->GetZeroSup();
+ Int_t gap=Int_t(0.125*nrows);
+ Int_t good_number=Int_t(0.4*nrows);
+
+ //gAlice->GetEvent(0);
+ TClonesArray *particles=gAlice->Particles();
+ Int_t np=particles->GetEntriesFast();
+ Int_t *good=new Int_t[np];
+ for (Int_t ii=0; ii<np; ii++) good[ii]=0;
+
+ switch (ver) {
+ case 1:
+ TClonesArray *clusters=TPC->Clusters();
+ Int_t n=0;
+ if (clusters) n=clusters->GetEntriesFast();
+ for (Int_t i=0; i<n; i++) {
+ AliTPCcluster *c=(AliTPCcluster*)clusters->UncheckedAt(i);
+ Int_t lab=c->fTracks[0];
+ if (lab<0) continue; //noise cluster
+ lab=TMath::Abs(lab);
+ Int_t sec=c->fSector, row=c->fPadRow;
+ if (sec>=digp->GetNInnerSector())
+ if (row==nrow_up-1 ) good[lab]|=0x1000;
+ if (sec>=digp->GetNInnerSector())
+ if (row==nrow_up-1-gap) good[lab]|=0x800;
+ good[lab]++;
+ }
+ break;
+ case 2:
+ TTree *TD=(TTree*)gDirectory->Get(tname);
+ AliSimDigits da, *digits=&da;
+ TD->GetBranch("Segment")->SetAddress(&digits);
+ Int_t *count = new Int_t[np];
+ Int_t i;
+ for (i=0; i<np; i++) count[i]=0;
+ Int_t sectors_by_rows=(Int_t)TD->GetEntries();
+ for (i=0; i<sectors_by_rows; i++) {
+ if (!TD->GetEvent(i)) continue;
+ Int_t sec,row;
+ digp->AdjustSectorRow(digits->GetID(),sec,row);
+ cerr<<sec<<' '<<row<<" \r";
+ digits->First();
+ while (digits->Next()) {
+ Int_t it=digits->CurrentRow(), ip=digits->CurrentColumn();
+ Short_t dig = digits->GetDigit(it,ip);
+ Int_t idx0=digits->GetTrackID(it,ip,0);
+ Int_t idx1=digits->GetTrackID(it,ip,1);
+ Int_t idx2=digits->GetTrackID(it,ip,2);
+ if (idx0>=0 && dig>=zero) count[idx0]+=1;
+ if (idx1>=0 && dig>=zero) count[idx1]+=1;
+ if (idx2>=0 && dig>=zero) count[idx2]+=1;
+ }
+ for (Int_t j=0; j<np; j++) {
+ if (count[j]>1) {
+ if (sec>=digp->GetNInnerSector())
+ if (row==nrow_up-1 ) good[j]|=0x1000;
+ if (sec>=digp->GetNInnerSector())
+ if (row==nrow_up-1-gap) good[j]|=0x800;
+ good[j]++;
+ }
+ count[j]=0;
+ }
+ }
+ delete[] count;
+ break;
+ default:
+ cerr<<"Invalid TPC version !\n";
+ return;
+ }
+
+ TTree *TH=gAlice->TreeH();
+ TClonesArray *hits=TPC->Hits();
+ Int_t npart=TH->GetEntries();
+
+ while (npart--) {
+ TPC->ResetHits();
+ TH->GetEvent(npart);
+ Int_t nhits=hits->GetEntriesFast();
+ if (nhits==0) continue;
+ AliTPChit *hit;
+ Int_t j;
+ for (j=0; j<nhits-1; j++) {
+ hit=(AliTPChit*)hits->UncheckedAt(j);
+ if (hit->fQ==0.) break;
+ }
+ if (j==nhits-1) continue;
+ AliTPChit *hit1=(AliTPChit*)hits->UncheckedAt(j+1);
+ if (hit1->fQ != 0.) continue;
+ Int_t i=hit->fTrack;
+ TParticle *p = (TParticle*)particles->UncheckedAt(i);
+ if (p->GetFirstMother()>=0) continue; //secondary particle
+ if (good[i] < 0x1000+0x800+2+good_number) continue;
+ if (p->Pt()<0.100) continue;
+ if (TMath::Abs(p->Pz()/p->Pt())>0.999) continue;
+
+ gt[nt].lab=i;
+ gt[nt].code=p->GetPdgCode();
+//**** px py pz - in global coordinate system, x y z - in local !
+ gt[nt].px=hit->fX; gt[nt].py=hit->fY; gt[nt].pz=hit->fZ;
+ Float_t cs,sn; digp->AdjustCosSin(hit1->fSector,cs,sn);
+ gt[nt].x = hit1->fX*cs + hit1->fY*sn;
+ gt[nt].y =-hit1->fX*sn + hit1->fY*cs;
+ gt[nt].z = hit1->fZ;
+ nt++;
+
+ cerr<<i<<" \r";
+ if (nt==max) {cerr<<"Too many good tracks !\n"; break;}
+ }
+ delete[] good;
+ return nt;
}
/*
$Log$
+Revision 1.13.8.2 2000/04/10 08:33:44 kowal2
+
+Updated readout chambers
+
+Revision 1.13.8.1 2000/04/10 07:56:53 kowal2
+Not used anymore - removed
+
+Revision 1.13 1999/11/04 17:28:06 fca
+Correct barrel part of HV Degrader
+
Revision 1.12 1999/10/08 06:27:23 fca
Corrected bug in the HV degrader geometry, thanks to G.Tabary
#include "AliRun.h"
#include <iostream.h>
#include <fstream.h>
-
#include "AliMC.h"
#include "AliConst.h"
#include "AliTPCParam.h"
-#include "AliTPCD.h"
+#include "AliTPCDigitsArray.h"
ClassImp(AliTPCv0)
{
//
// Creation of the TPC coarse geometry (version 0)
- // Origin Marek Kowalski Crakow
+ // Origin Marek Kowalski Cracow
//
//Begin_Html
/*
*/
//End_Html
- AliTPCParam * fTPCParam = &(fDigParam->GetParam());
Int_t *idtmed = fIdtmed->GetArray();
Int_t nOuterSector = fTPCParam->GetNOuterSector()/2;
- Float_t InSecLowEdge = fTPCParam->GetInSecLowEdge();
- Float_t InSecUpEdge = fTPCParam->GetInSecUpEdge();
+ Float_t InSecLowEdge = fTPCParam->GetInnerRadiusLow();
+ Float_t InSecUpEdge = fTPCParam->GetInnerRadiusUp();
- Float_t OuSecLowEdge = fTPCParam->GetOuSecLowEdge();
- Float_t OuSecUpEdge = fTPCParam->GetOuSecUpEdge();
+ Float_t OuSecLowEdge = fTPCParam->GetOuterRadiusLow();
+ Float_t OuSecUpEdge = fTPCParam->GetOuterRadiusUp();
Float_t SecThick = 2.225; // Al
- Float_t edge = fTPCParam->GetEdge();
// S (Inner) sectors
- dm[0] = InSecLowEdge*TMath::Tan(0.5*InnerOpenAngle)-edge;
- dm[1] = InSecUpEdge*TMath::Tan(0.5*InnerOpenAngle)-edge;
+ Float_t LowEdge = fTPCParam->GetInnerFrameSpace();
+
+ dm[0] = InSecLowEdge*TMath::Tan(0.5*InnerOpenAngle)-LowEdge;
+ dm[1] = InSecUpEdge*TMath::Tan(0.5*InnerOpenAngle)-LowEdge;
dm[2] = SecThick;
dm[3] = 0.5*(InSecUpEdge-InSecLowEdge);
// L (Outer) sectors
- dm[0] = OuSecLowEdge*TMath::Tan(0.5*OuterOpenAngle)-edge;
- dm[1] = OuSecUpEdge*TMath::Tan(0.5*OuterOpenAngle)-edge;
+ Float_t UpEdge = fTPCParam->GetOuterFrameSpace();
+
+ dm[0] = OuSecLowEdge*TMath::Tan(0.5*OuterOpenAngle)-UpEdge;
+ dm[1] = OuSecUpEdge*TMath::Tan(0.5*OuterOpenAngle)-UpEdge;
dm[2] = SecThick;
dm[3] = 0.5*(OuSecUpEdge-OuSecLowEdge);
////////////////////////////////////////////////
// Version 0 for TPC //
////////////////////////////////////////////////
+
#include "AliTPC.h"
/*
$Log$
+Revision 1.15.8.2 2000/04/10 08:29:48 kowal2
+
+Different pad geometry for different sectors
+Updated readouch chambers geometry
+
+Revision 1.15.8.1 2000/04/10 07:56:53 kowal2
+Not used anymore - removed
+
+Revision 1.15 1999/11/04 17:28:07 fca
+Correct barrel part of HV Degrader
+
Revision 1.14 1999/10/08 06:27:23 fca
Corrected bug in the HV degrader geometry, thanks to G.Tabary
#include "AliConst.h"
#include "AliTPCParam.h"
-#include "AliTPCD.h"
+#include "AliTPCDigitsArray.h"
ClassImp(AliTPCv1)
*/
//End_Html
- AliTPCParam * fTPCParam = &(fDigParam->GetParam());
Int_t *idtmed = fIdtmed->GetArray();
Int_t nOuterSector = fTPCParam->GetNOuterSector()/2;
- Float_t InSecLowEdge = fTPCParam->GetInSecLowEdge();
- Float_t InSecUpEdge = fTPCParam->GetInSecUpEdge();
+ Float_t InSecLowEdge = fTPCParam->GetInnerRadiusLow();
+ Float_t InSecUpEdge = fTPCParam->GetInnerRadiusUp();
- Float_t OuSecLowEdge = fTPCParam->GetOuSecLowEdge();
- Float_t OuSecUpEdge = fTPCParam->GetOuSecUpEdge();
+ Float_t OuSecLowEdge = fTPCParam->GetOuterRadiusLow();
+ Float_t OuSecUpEdge = fTPCParam->GetOuterRadiusUp();
Float_t SecThick = 2.225; // Al
- Float_t edge = fTPCParam->GetEdge();
-
// S (Inner) sectors
- dm[0] = InSecLowEdge*TMath::Tan(0.5*InnerOpenAngle)-edge;
- dm[1] = InSecUpEdge*TMath::Tan(0.5*InnerOpenAngle)-edge;
+ Float_t LowEdge = fTPCParam->GetInnerFrameSpace();
+
+ dm[0] = InSecLowEdge*TMath::Tan(0.5*InnerOpenAngle)-LowEdge;
+ dm[1] = InSecUpEdge*TMath::Tan(0.5*InnerOpenAngle)-LowEdge;
dm[2] = 0.5*SecThick;
dm[3] = 0.5*(InSecUpEdge-InSecLowEdge);
// L (Outer) sectors
- dm[0] = OuSecLowEdge*TMath::Tan(0.5*OuterOpenAngle)-edge;
- dm[1] = OuSecUpEdge*TMath::Tan(0.5*OuterOpenAngle)-edge;
+ Float_t UpEdge = fTPCParam->GetOuterFrameSpace();
+
+ dm[0] = OuSecLowEdge*TMath::Tan(0.5*OuterOpenAngle)-UpEdge;
+ dm[1] = OuSecUpEdge*TMath::Tan(0.5*OuterOpenAngle)-UpEdge;
dm[2] = 0.5*SecThick;
dm[3] = 0.5*(OuSecUpEdge-OuSecLowEdge);
Float_t r1,r2,zz;
Float_t StripThick = 0.01; // 100 microns
- Float_t dead = fTPCParam->GetDeadZone();
+ Float_t dead;
gMC->Gsvolu("TSST", "TRD1", idtmed[4], dm, 0);
// S-sector
+ dead = fTPCParam->GetInnerWireMount();
+
for (ns = 0; ns < fTPCParam->GetNRowLow(); ns++) {
r1 = fTPCParam->GetPadRowRadiiLow(ns);
dm[7] = 250.;
+ dead = fTPCParam->GetOuterWireMount();
+
Float_t xx = dead/TMath::Tan(0.5*OuterOpenAngle);
for(ns=0;ns<fTPCParam->GetNRowUp();ns++){
gMC->Gsatt("TPCO","SEEN",1);
gMC->Gsatt("TPOV","SEEN",1);
gMC->Gsatt("TPVD","SEEN",1);
- //
+
gMC->Gdopt("hide", "on");
gMC->Gdopt("shad", "on");
gMC->Gsatt("*", "fill", 7);
Int_t vol[2];
TLorentzVector p;
TClonesArray &lhits = *fHits;
-
- AliTPCParam *fTPCParam = &(fDigParam->GetParam());
//
vol[1]=copy-1; // row
id=gMC->CurrentVolOffID(1,copy);
vol[0]=copy+fTPCParam->GetNInnerSector()-1; // sector
+
+ //I.Belikov's modification
+ if (vol[1]==0) {
+ gMC->TrackMomentum(p);
+ hits[0]=p[0];
+ hits[1]=p[1];
+ hits[2]=p[2];
+ hits[3]=0.; // this hit has no energy loss
+ new(lhits[fNhits++]) AliTPChit(fIshunt,gAlice->CurrentTrack(),vol,hits);
+
+ gMC->TrackPosition(p);
+ hits[0]=p[0];
+ hits[1]=p[1];
+ hits[2]=p[2];
+ hits[3]=0.; // this hit has no energy loss
+ new(lhits[fNhits++]) AliTPChit(fIshunt,gAlice->CurrentTrack(),vol,hits);
+ }
+ //end of I.Belikov's modification
} else if(id==fIdSens2) {
// S
vol[1]=copy-1; // row
id=gMC->CurrentVolOffID(1,copy); // sector
vol[0]=copy-1;
+
+ //I.Belikov's modification
+ if (vol[1]==0) {
+ gMC->TrackMomentum(p);
+ hits[0]=p[0];
+ hits[1]=p[1];
+ hits[2]=p[2];
+ hits[3]=0.; // this hit has no energy loss
+ new(lhits[fNhits++]) AliTPChit(fIshunt,gAlice->CurrentTrack(),vol,hits);
+
+ gMC->TrackPosition(p);
+ hits[0]=p[0];
+ hits[1]=p[1];
+ hits[2]=p[2];
+ hits[3]=0.; // this hit has no energy loss
+ new(lhits[fNhits++]) AliTPChit(fIshunt,gAlice->CurrentTrack(),vol,hits);
+ }
+ //end of I.Belikov's modification
+
} else return;
gMC->TrackPosition(p);
for(i=0;i<3;++i) hits[i]=p[i];
- hits[3]=0;
+ hits[3]=1; //I'd like to have something positive here (I.Belikov)
new(lhits[fNhits++]) AliTPChit(fIshunt,gAlice->CurrentTrack(),vol,hits);
}
}
////////////////////////////////////////////////
// Version 1 for TPC //
////////////////////////////////////////////////
+
#include "AliTPC.h"
/*
$Log$
+Revision 1.19.8.2 2000/04/10 08:31:52 kowal2
+
+Different geometry for different sectors
+Updated readout chambers
+Some modifications to StepManager by J.Belikov
+
+Revision 1.19.8.1 2000/04/10 07:56:53 kowal2
+Not used anymore - removed
+
+Revision 1.19 1999/11/04 17:28:07 fca
+Correct barrel part of HV Degrader
+
Revision 1.18 1999/10/14 16:52:08 fca
Only use PDG codes and not GEANT ones
#include <TMath.h>
#include "AliTPCv2.h"
-#include "AliTPCD.h"
+#include "AliTPCDigitsArray.h"
#include "AliRun.h"
#include "AliConst.h"
#include "AliPDG.h"
*/
//End_Html
- AliTPCParam * fTPCParam = &(fDigParam->GetParam());
Int_t *idtmed = fIdtmed->GetArray();
Float_t z_side = dm[2]; // 1/2 of the side gas thickness
- //-----------------------------------------------------------
+ //------------------------------------------------------------
// Readout chambers , 25% of X0, I use Al as the material
- //-----------------------------------------------------------
+ //------------------------------------------------------------
Float_t InnerOpenAngle = fTPCParam->GetInnerAngle();
Float_t OuterOpenAngle = fTPCParam->GetOuterAngle();
Float_t InnerAngleShift = fTPCParam->GetInnerAngleShift();
Float_t OuterAngleShift = fTPCParam->GetOuterAngleShift();
- Float_t InSecLowEdge = fTPCParam->GetInSecLowEdge();
- Float_t InSecUpEdge = fTPCParam->GetInSecUpEdge();
+ Float_t InSecLowEdge = fTPCParam->GetInnerRadiusLow();
+ Float_t InSecUpEdge = fTPCParam->GetInnerRadiusUp();
- Float_t OuSecLowEdge = fTPCParam->GetOuSecLowEdge();
- Float_t OuSecUpEdge = fTPCParam->GetOuSecUpEdge();
+ Float_t OuSecLowEdge = fTPCParam->GetOuterRadiusLow();
+ Float_t OuSecUpEdge = fTPCParam->GetOuterRadiusUp();
Float_t SecThick = 2.225; // Al
- Float_t edge = fTPCParam->GetEdge();
+ Float_t LowEdge = fTPCParam->GetInnerFrameSpace();
// S (Inner) sectors
- dm[0] = InSecLowEdge*TMath::Tan(0.5*InnerOpenAngle)-edge;
- dm[1] = InSecUpEdge*TMath::Tan(0.5*InnerOpenAngle)-edge;
+ dm[0] = InSecLowEdge*TMath::Tan(0.5*InnerOpenAngle)-LowEdge;
+ dm[1] = InSecUpEdge*TMath::Tan(0.5*InnerOpenAngle)-LowEdge;
dm[2] = 0.5*SecThick;
dm[3] = 0.5*(InSecUpEdge-InSecLowEdge);
// L (Outer) sectors
- dm[0] = OuSecLowEdge*TMath::Tan(0.5*OuterOpenAngle)-edge;
- dm[1] = OuSecUpEdge*TMath::Tan(0.5*OuterOpenAngle)-edge;
+ Float_t UpEdge = fTPCParam->GetOuterFrameSpace();
+
+ dm[0] = OuSecLowEdge*TMath::Tan(0.5*OuterOpenAngle)-UpEdge;
+ dm[1] = OuSecUpEdge*TMath::Tan(0.5*OuterOpenAngle)-UpEdge;
dm[2] = 0.5*SecThick;
dm[3] = 0.5*(OuSecUpEdge-OuSecLowEdge);
Float_t r1,r2,zz;
Float_t StripThick = 0.01; // 100 microns
- Float_t dead = fTPCParam->GetDeadZone();
+ Float_t dead;
gMC->Gsvolu("TSST", "TRD1", idtmed[4], dm, 0);
dm[2] = 0.5*(250. - 0.002);
dm[3] = 0.5 * StripThick;
+ dead= fTPCParam->GetInnerWireMount();
+
for (ns = 0; ns < fTPCParam->GetNRowLow(); ns++) {
Float_t rmax = dm[6];
Float_t r1,r2;
- Float_t dead = fTPCParam->GetDeadZone();
+ Float_t dead = fTPCParam->GetOuterWireMount();
Float_t StripThick = 0.01; // 100 microns
const Float_t prim = 14.35; // number of primary collisions per 1 cm
const Float_t poti = 20.77e-9; // first ionization potential for Ne/CO2
const Float_t w_ion = 35.97e-9; // energy for the ion-electron pair creation
-
- // const Float_t prim = 17.65;
- // const Float_t poti = 19.02e-9;
- // const Float_t w_ion = 33.06e-9;
const Float_t big = 1.e10;
Int_t vol[2];
TClonesArray &lhits = *fHits;
TLorentzVector pos;
-
- AliTPCParam *fTPCParam = &(fDigParam->GetParam());
vol[1]=0;
vol[1] = copy-1; // row number
id = gMC->CurrentVolOffID(1,copy);
vol[0] = copy-1; // sector number (S-sector)
+
+ //I.Belikov's modification
+ if (vol[1]==0) {
+ gMC->TrackMomentum(pos);
+ hits[0]=pos[0];
+ hits[1]=pos[1];
+ hits[2]=pos[2];
+ hits[3]=0.; // this hit has no energy loss
+ new(lhits[fNhits++]) AliTPChit(fIshunt,gAlice->CurrentTrack(),vol,hits);
+ }
+ //end of I.Belikov's modification
gMC->TrackPosition(pos);
hits[0]=pos[0];
vol[1] = copy-1; // row number
id = gMC->CurrentVolOffID(1,copy);
vol[0] = copy+fTPCParam->GetNInnerSector()-1; // sector number (L-sector)
+
+ //I.Belikov's modification
+ if (vol[1]==0) {
+ gMC->TrackMomentum(pos);
+ hits[0]=pos[0];
+ hits[1]=pos[1];
+ hits[2]=pos[2];
+ hits[3]=0.; // this hit has no energy loss
+ new(lhits[fNhits++]) AliTPChit(fIshunt,gAlice->CurrentTrack(),vol,hits);
+ }
+ //end of I.Belikov's modification
gMC->TrackPosition(pos);
hits[0]=pos[0];
Float_t beta_gamma = ptot/gMC->TrackMass();
Int_t pid=gMC->TrackPid();
- if((pid==kElectron || pid==kPositron || pid==kGamma) && ptot > 0.002)
+ if((pid==kElectron || pid==kPositron) && ptot > 0.002)
{
pp = prim*1.58; // electrons above 20 MeV/c are on the plateau!
}
////////////////////////////////////////////////
// Version 2 for TPC //
////////////////////////////////////////////////
+
#include "AliTPC.h"
/*
$Log$
+Revision 1.11.8.2 2000/04/10 08:36:12 kowal2
+
+Updated readout chambers
+Some modifications to StepManager by M. Kowalski
+
+Revision 1.11.8.1 2000/04/10 07:56:53 kowal2
+Not used anymore - removed
+
+Revision 1.11 1999/11/04 17:28:07 fca
+Correct barrel part of HV Degrader
+
Revision 1.10 1999/10/14 16:52:08 fca
Only use PDG codes and not GEANT ones
#include <stdlib.h>
#include <TMath.h>
-
#include "AliTPCv3.h"
#include "AliRun.h"
#include "AliConst.h"
-#include "AliTPCD.h"
-#include "AliTPCParam.h"
+#include "AliTPCDigitsArray.h"
+#include"AliTPCParam.h"
#include "AliPDG.h"
ClassImp(AliTPCv3)
AliTPC(name, title)
{
//
- // Standard constructor for Time Projection Chamber version 2
+ // Standard constructor for Time Projection Chamber version 3
//
SetBufferSize(128000);
void AliTPCv3::CreateGeometry()
{
//
- // Creation of the TPC coarse geometry (version 0)
- // Origin Marek Kowalski Crakow
+ // Creation of the TPC coarse geometry (version 3)
+ // Origin Marek Kowalski Cracow
//
//Begin_Html
/*
*/
//End_Html
- AliTPCParam * fTPCParam = &(fDigParam->GetParam());
-
Int_t *idtmed = fIdtmed->GetArray();
Float_t dm[21];
Int_t nOuterSector = fTPCParam->GetNOuterSector()/2;
- Float_t InSecLowEdge = fTPCParam->GetInSecLowEdge();
- Float_t InSecUpEdge = fTPCParam->GetInSecUpEdge();
+ Float_t InSecLowEdge = fTPCParam->GetInnerRadiusLow();
+ Float_t InSecUpEdge = fTPCParam->GetInnerRadiusUp();
- Float_t OuSecLowEdge = fTPCParam->GetOuSecLowEdge();
- Float_t OuSecUpEdge = fTPCParam->GetOuSecUpEdge();
+ Float_t OuSecLowEdge = fTPCParam->GetOuterRadiusLow();
+ Float_t OuSecUpEdge = fTPCParam->GetOuterRadiusUp();
Float_t SecThick = 2.225; // Al
- Float_t edge = fTPCParam->GetEdge();
+ Float_t LowEdge = fTPCParam->GetInnerFrameSpace();
// S (Inner) sectors
- dm[0] = InSecLowEdge*TMath::Tan(0.5*InnerOpenAngle)-edge;
- dm[1] = InSecUpEdge*TMath::Tan(0.5*InnerOpenAngle)-edge;
+ dm[0] = InSecLowEdge*TMath::Tan(0.5*InnerOpenAngle)-LowEdge;
+ dm[1] = InSecUpEdge*TMath::Tan(0.5*InnerOpenAngle)-LowEdge;
dm[2] = SecThick;
dm[3] = 0.5*(InSecUpEdge-InSecLowEdge);
// L (Outer) sectors
- dm[0] = OuSecLowEdge*TMath::Tan(0.5*OuterOpenAngle)-edge;
- dm[1] = OuSecUpEdge*TMath::Tan(0.5*OuterOpenAngle)-edge;
+ Float_t UpEdge = fTPCParam->GetOuterFrameSpace();
+
+ dm[0] = OuSecLowEdge*TMath::Tan(0.5*OuterOpenAngle)-UpEdge;
+ dm[1] = OuSecUpEdge*TMath::Tan(0.5*OuterOpenAngle)-UpEdge;
dm[2] = SecThick;
dm[3] = 0.5*(OuSecUpEdge-OuSecLowEdge);
Float_t beta_gamma = ptot/gMC->TrackMass();
Int_t pid=gMC->TrackPid();
- if((pid==kElectron || pid==kPositron || pid==kGamma) && ptot > 0.002)
+ if((pid==kElectron || pid==kPositron) && ptot > 0.002)
{
pp = prim*1.58; // electrons above 20 MeV/c are on the plateau!
}
////////////////////////////////////////////////
// Version 3 for TPC //
////////////////////////////////////////////////
+
#include "AliTPC.h"
--- /dev/null
+//Begin_Html
+/*
+<img src="../../../../pic/CLFinderDemo.gif">
+*/
+//End_Html
+void CLFinderDemo()
+{
+
+ AliTPCDigitsArray *gDigitsArray= GetDigitsArray();
+ AliTPCClustersArray *gExactClusters = GetExactClustersArray();
+
+
+ AliH2F * his = gDigitsArray->LoadRow(0,0)->GenerHisto()->GetSubrange2d(440,470,60,90);
+
+ AliClusterFinder cf;
+ cf.SetThreshold(3);
+ cf.SetNoise(1);
+ Int_t index[3]={1,0,0};
+ cf.SetDetectorIndex(index);
+ cf.SetDetectorParam(gTPCParam);
+ cf.GetHisto(his);
+
+ cf.SetBFit(kFALSE);
+ cf.GetMinuit()->SetPrintLevel(-1);
+ cf.GetMinuit()->SetMaxIterations(100);
+ cf.FindPeaks1()->GetEntriesFast();
+
+
+ TCanvas *c0 = new TCanvas("signals", "Cluster finder drawing", 600,1100);
+ c0->Divide(1,3);
+ c0->cd(1);
+ cf.Draw("lego2");
+
+ c0->cd(2);
+ cf.Draw("cont1");
+ cf.DrawCluster(4,5,5);
+ c0->cd(3);
+ cf.DrawBorders("lego2");
+
+}
+
--- /dev/null
+{
+//=========Macro generated from canvas: ClassTree/
+//========= (Tue Jun 1 17:01:38 1999) by ROOT version 2.21/07
+ TCanvas *ClassTree = new TCanvas("ClassTree", "",186,135,594,449);
+ ClassTree->SetHighLightColor(2);
+ ClassTree->Range(0,5,20,20);
+ ClassTree->SetFillColor(33);
+ ClassTree->SetBorderSize(2);
+ TLine *line = new TLine(0.5,18.15,4.4,18.15);
+ line->Draw();
+ line = new TLine(4.4,17.725,4.4,18.575);
+ line->Draw();
+
+ TPaveLabel *pl = new TPaveLabel(1,17.895,4.205,18.405,"TArray","br");
+ pl->SetFillColor(30);
+ pl->SetTextSize(0.9);
+ pl->Draw();
+ line = new TLine(0.5,16.875,1,16.875);
+ line->Draw();
+
+ pl = new TPaveLabel(1,16.62,4.205,17.13,"TAttFill","br");
+ pl->SetFillColor(30);
+ pl->SetTextSize(0.9);
+ pl->Draw();
+ line = new TLine(0.5,16.025,1,16.025);
+ line->Draw();
+
+ pl = new TPaveLabel(1,15.77,4.205,16.28,"TAttLine","br");
+ pl->SetFillColor(30);
+ pl->SetTextSize(0.9);
+ pl->Draw();
+ line = new TLine(0.5,15.175,1,15.175);
+ line->Draw();
+
+ pl = new TPaveLabel(1,14.92,4.205,15.43,"TAttMarker","br");
+ pl->SetFillColor(30);
+ pl->SetTextSize(0.9);
+ pl->Draw();
+ line = new TLine(0.5,9.775,4.4,9.775);
+ line->Draw();
+ line = new TLine(4.4,7.65,4.4,12.325);
+ line->Draw();
+
+ pl = new TPaveLabel(1,9.52,4.205,10.03,"TObject","br");
+ pl->SetFillColor(5);
+ pl->SetTextSize(0.9);
+ pl->Draw();
+ line = new TLine(4.4,12.325,4.9,12.325);
+ line->Draw();
+
+ pl = new TPaveLabel(4.9,12.07,8.105,12.58,"AliArrayI","br");
+ pl->SetFillColor(18);
+ pl->SetTextSize(0.9);
+ pl->Draw();
+ line = new TLine(4.4,11.475,4.9,11.475);
+ line->Draw();
+
+ pl = new TPaveLabel(4.9,11.22,8.105,11.73,"AliArrayS","br");
+ pl->SetFillColor(18);
+ pl->SetTextSize(0.9);
+ pl->Draw();
+ line = new TLine(4.4,18.575,4.9,18.575);
+ line->Draw();
+
+ pl = new TPaveLabel(4.9,18.32,8.105,18.83,"TArrayI","br");
+ pl->SetFillColor(30);
+ pl->SetTextSize(0.9);
+ pl->Draw();
+ line = new TLine(4.4,17.725,4.9,17.725);
+ line->Draw();
+
+ pl = new TPaveLabel(4.9,17.47,8.105,17.98,"TArrayS","br");
+ pl->SetFillColor(30);
+ pl->SetTextSize(0.9);
+ pl->Draw();
+ line = new TLine(4.4,10.2,8.3,10.2);
+ line->Draw();
+
+ pl = new TPaveLabel(4.9,9.945,8.105,10.455,"TCollection","br");
+ pl->SetFillColor(18);
+ pl->SetTextSize(0.9);
+ pl->Draw();
+ line = new TLine(4.4,7.65,8.3,7.65);
+ line->Draw();
+ line = new TLine(8.3,6.8,8.3,8.075);
+ line->Draw();
+
+ pl = new TPaveLabel(4.9,7.395,8.105,7.905,"TNamed","br");
+ pl->SetFillColor(18);
+ pl->SetTextSize(0.9);
+ pl->Draw();
+ line = new TLine(8.3,8.075,12.2,8.075);
+ line->Draw();
+
+ pl = new TPaveLabel(8.8,7.82,12.005,8.33,"AliSegmentArray","br");
+ pl->SetFillColor(18);
+ pl->SetTextSize(0.9);
+ pl->Draw();
+ line = new TLine(8.3,10.2,12.2,10.2);
+ line->Draw();
+
+ pl = new TPaveLabel(8.8,9.945,12.005,10.455,"TSeqCollection","br");
+ pl->SetFillColor(18);
+ pl->SetTextSize(0.9);
+ pl->Draw();
+ line = new TLine(8.3,6.8,8.8,6.8);
+ line->Draw();
+
+ pl = new TPaveLabel(8.8,6.545,12.005,7.055,"TTree","br");
+ pl->SetFillColor(18);
+ pl->SetTextSize(0.9);
+ pl->Draw();
+ line = new TLine(12.2,8.075,12.7,8.075);
+ line->Draw();
+
+ pl = new TPaveLabel(12.7,7.82,15.905,8.33,"AliTPCClustersArray","br");
+ pl->SetFillColor(18);
+ pl->SetTextSize(0.9);
+ pl->Draw();
+ line = new TLine(12.2,10.2,16.1,10.2);
+ line->Draw();
+
+ pl = new TPaveLabel(12.7,9.945,15.905,10.455,"TObjArray","br");
+ pl->SetFillColor(18);
+ pl->SetTextSize(0.9);
+ pl->Draw();
+ line = new TLine(16.1,10.2,16.6,10.2);
+ line->Draw();
+
+ pl = new TPaveLabel(16.6,9.945,19.805,10.455,"TClonesArray","br");
+ pl->SetFillColor(18);
+ pl->SetTextSize(0.9);
+ pl->Draw();
+
+ pl = new TPaveLabel(0.1,19.1,18.2,19.9,"*AliSegmet:*AliSegmentArray:*AliArrayI:*AliArrayS:TTree:*TObjArray","br");
+ pl->SetFillColor(42);
+ pl->SetTextSize(0.7);
+ pl->Draw();
+ line = new TLine(11.4041,6.8,14.3025,10.2);
+ line->SetLineColor(6);
+ line->SetLineStyle(3);
+ line->Draw();
+ line = new TLine(11.4842,6.8,14.3025,10.2);
+ line->SetLineColor(6);
+ line->SetLineStyle(3);
+ line->Draw();
+ line = new TLine(6.5025,12.325,6.5025,18.575);
+ line->SetLineColor(4);
+ line->SetLineStyle(2);
+ line->Draw();
+ line = new TLine(6.5025,11.475,6.5025,17.725);
+ line->SetLineColor(4);
+ line->SetLineStyle(2);
+ line->Draw();
+ line = new TLine(10.4025,6.8,2.6025,16.025);
+ line->SetLineColor(4);
+ line->SetLineStyle(2);
+ line->Draw();
+ line = new TLine(10.4025,6.8,2.6025,16.875);
+ line->SetLineColor(4);
+ line->SetLineStyle(2);
+ line->Draw();
+ line = new TLine(10.4025,6.8,2.6025,15.175);
+ line->SetLineColor(4);
+ line->SetLineStyle(2);
+ line->Draw();
+ TArrow *arrow = new TArrow(5.43417,10.2,6.5025,10.2,0.008,"|>");
+ arrow->SetFillColor(2);
+ arrow->SetFillStyle(1001);
+ arrow->SetLineColor(2);
+ arrow->Draw();
+ arrow = new TArrow(6.85861,10.2,2.6025,9.775,0.008,"|>");
+ arrow->SetFillColor(2);
+ arrow->SetFillStyle(1001);
+ arrow->SetLineColor(2);
+ arrow->Draw();
+ arrow = new TArrow(9.60125,8.075,14.3025,10.2,0.008,"|>");
+ arrow->SetFillColor(2);
+ arrow->SetFillStyle(1001);
+ arrow->SetLineColor(2);
+ arrow->Draw();
+ arrow = new TArrow(10.1354,8.075,6.5025,12.325,0.008,"|>");
+ arrow->SetFillColor(2);
+ arrow->SetFillStyle(1001);
+ arrow->SetLineColor(2);
+ arrow->Draw();
+ arrow = new TArrow(11.2037,8.075,10.4025,6.8,0.008,"|>");
+ arrow->SetFillColor(2);
+ arrow->SetFillStyle(1001);
+ arrow->SetLineColor(2);
+ arrow->Draw();
+ arrow = new TArrow(13.9019,10.2,2.6025,9.775,0.008,"|>");
+ arrow->SetFillColor(2);
+ arrow->SetFillStyle(1001);
+ arrow->SetLineColor(2);
+ arrow->Draw();
+ arrow = new TArrow(19.2708,10.2,14.3025,10.2,0.008,"|>");
+ arrow->SetFillColor(2);
+ arrow->SetFillStyle(1001);
+ arrow->SetLineColor(2);
+ arrow->Draw();
+ ClassTree->Modified();
+ ClassTree->cd();
+}
# C++ sources
SRCS = AliTPC.cxx AliTPCv0.cxx AliTPCv1.cxx AliTPCv2.cxx \
- AliTPCD.cxx AliTPCPRF2D.cxx AliTPCRF1D.cxx AliTPCParam.cxx \
- AliTPCv3.cxx
+ AliTPCv3.cxx AliDetectorParam.cxx AliTPCParam.cxx \
+ AliTPCParamSR.cxx AliTPCParamCR.cxx AliTPCPRF2D.cxx \
+ AliTPCRF1D.cxx AliArrayI.cxx AliArrayS.cxx \
+ AliSegmentID.cxx AliSegmentArray.cxx AliDigits.cxx \
+ AliSimDigits.cxx AliDigitsArray.cxx AliTPCDigitsArray.cxx \
+ AliCluster.cxx AliClusters.cxx AliClustersArray.cxx \
+ AliClusterFinder.cxx AliTPCClustersRow.cxx \
+ AliTPCClustersArray.cxx AliH2F.cxx
+
# C++ Headers
-HDRS = $(SRCS:.cxx=.h) AliTPCSecGeo.h TPCLinkDef.h
+HDRS = $(SRCS:.cxx=.h) TPCLinkDef.h
# Library dictionary
# C++ compilation flags
-CXXFLAGS = $(CXXOPTS) -I$(ROOTSYS)/include -I. -I$(ALICE_ROOT)/include/
+CXXFLAGS = $(CXXOPTS) -g -I$(ROOTSYS)/include -I. -I$(ALICE_ROOT)/include
+#CXXFLAGS = $(CXXOPTS) -I$(ROOTSYS)/include -I. -I$(ALICE_ROOT)/include/
# FORTRAN compilation flags
FFLAGS = $(FOPT)
-##### TARGETS #####
+##### TARGETS #######
# Target
############################ Dependencies #####################################
--include tgt_$(ALICE_TARGET)/Make-depend
-
-### Target check creates violation reports (.viol), which depend on
-### stripped files (.ii), which in turn depend on preprocessed
-### files (.i). Dependences are in conf/GeneralDef.
-
-CHECKS = $(patsubst %.cxx,check/%.viol,$(SRCS))
-
-check: $(CHECKS)
-
-
-
-
-
+include tgt_$(ALICE_TARGET)/Make-depend
--- /dev/null
+TFile f("prf2d.root");
+AliTPCPRF2D prf1;
+AliTPCPRF2D prf2;
+AliTPCRF1D rf(kTRUE);
+rf.SetGauss(0.3,0.5,1)
+rf.Update();
+prf1.Read("prf_205035_Gati_062074_d03");
+prf2.Read("prf_205035_Gati_062074_d03");
+AliTPCParamSR param;
+param.SetInnerPRF(&prf1)
+param.SetOuterPRF(&prf2)
+param.SetTimeRF(&rf);
+Float_t x[3]={5.1,0,100}
+Int_t index[3]
+param.CalcResponse(x,index)
--- /dev/null
+/*
+#include "alles.h"
+extern AliTPCParam *gTPCParam;
+extern AliTPCClustersArray * gCalcClusters;
+extern AliTPCClustersArray * gDifClusters;
+*/
+
+
+
+TH1F * GetDX(Float_t x1=-2, Float_t x2=3, Float_t a1=-1, Float_t a2=1)
+{
+ AliTPCClustersArray *arr=gDifClusters;
+ if (arr==0) return 0;
+ TH1F * hd = new TH1F("delta x", "dx",33,x1,x2);
+ Int_t nsegment = (Int_t)arr->GetTree()->GetEntries();
+ Int_t segment;
+ for (segment = 0; segment<nsegment;segment++){
+ AliTPCClustersRow *clrow= (AliTPCClustersRow*)arr->LoadEntry(segment);
+ if (clrow==0) continue;
+ Int_t ncluster = clrow->GetArray()->GetEntriesFast();
+ for (Int_t i = 0; i<ncluster;i++){
+ AliDifCluster *cl =(AliDifCluster*)clrow->GetArray()->UncheckedAt(i);
+ // if ( (cl->fGenerTrack != cl->fTracks[0]) || (cl->fTracks[1]>0)) continue;
+ // if ( (cl->fGenerTrack != cl->fTracks[0])) continue;
+ if ( (cl->fAngleX<a2) && (cl->fAngleX>a1) ) hd->Fill(cl->fDx);
+ }
+ arr->ClearSegment(clrow->GetID());
+ }
+ return hd;
+}
+
+TH1F * GetDY(Float_t x1=-2, Float_t x2=3, Float_t a1=-1, Float_t a2=1)
+{
+ AliTPCClustersArray *arr=gDifClusters;
+ if (arr==0) return 0;
+ TH1F * hd = new TH1F("delta y", "dy",33,x1,x2);
+ Int_t nsegment = (Int_t)arr->GetTree()->GetEntries();
+ Int_t segment;
+ for (segment = 0; segment<nsegment;segment++){
+ AliTPCClustersRow *clrow= (AliTPCClustersRow*)arr->LoadEntry(segment);
+ if (clrow==0) continue;
+ Int_t ncluster = clrow->GetArray()->GetEntriesFast();
+ for (Int_t i = 0; i<ncluster;i++){
+ AliDifCluster *cl =(AliDifCluster*)clrow->GetArray()->UncheckedAt(i);
+ //if ( (cl->fGenerTrack != cl->fTracks[0]) || (cl->fTracks[1]>0)) continue;
+ //if ( (cl->fGenerTrack != cl->fTracks[0])) continue;
+ // if (cl->fNy!=2) continue;
+ if ((cl->fAngleY<a2) && (cl->fAngleY>a1) ) hd->Fill(cl->fDy);
+ }
+ arr->ClearSegment(clrow->GetID());
+ }
+ return hd;
+}
+
+
+
+TH1F * GetNX(Float_t x1=0, Float_t x2=7, Float_t a1=-1, Float_t a2=1)
+{
+ AliTPCClustersArray *arr=gDifClusters;
+ if (arr==0) return 0;
+ TH1F * hd = new TH1F("N x", "N x",33,x1,x2);
+ Int_t nsegment = (Int_t)arr->GetTree()->GetEntries();
+ Int_t segment;
+ for (segment = 0; segment<nsegment;segment++){
+ AliTPCClustersRow *clrow= (AliTPCClustersRow*)arr->LoadEntry(segment);
+ if (clrow==0) continue;
+ Int_t ncluster = clrow->GetArray()->GetEntriesFast();
+ for (Int_t i = 0; i<ncluster;i++){
+ AliDifCluster *cl =(AliDifCluster*)clrow->GetArray()->UncheckedAt(i);
+ if ((cl->fAngleX<a2) && (cl->fAngleX>a1) ) hd->Fill(cl->fNx);
+ }
+ arr->ClearSegment(clrow->GetID());
+ }
+ return hd;
+}
+
+TH1F * GetNY(Float_t x1=-0, Float_t x2=7, Float_t a1=-1, Float_t a2=1)
+{
+ AliTPCClustersArray *arr=gDifClusters;
+ if (arr==0) return 0;
+ TH1F * hd = new TH1F("N y", "N y",33,x1,x2);
+ Int_t nsegment = (Int_t)arr->GetTree()->GetEntries();
+ Int_t segment;
+ for (segment = 0; segment<nsegment;segment++){
+ AliTPCClustersRow *clrow= (AliTPCClustersRow*)arr->LoadEntry(segment);
+ if (clrow==0) continue;
+ Int_t ncluster = clrow->GetArray()->GetEntriesFast();
+ for (Int_t i = 0; i<ncluster;i++){
+ AliDifCluster *cl =(AliDifCluster*)clrow->GetArray()->UncheckedAt(i);
+ if ( (cl->fGenerTrack != cl->fTracks[0]) || (cl->fTracks[1]>0)) continue;
+ if ( (cl->fAngleY<a2) && (cl->fAngleY>a1) ) hd->Fill(cl->fNy);
+ }
+ arr->ClearSegment(clrow->GetID());
+ }
+ return hd;
+}
+
+
+
+
+TH1F * GetAngleX(Float_t x1=-2, Float_t x2=3)
+{
+ AliTPCClustersArray *arr=gDifClusters;
+ if (arr==0) return 0;
+ TH1F * hdx = new TH1F("Angle x", "Angle x",33,x1,x2);
+ Int_t nsegment = (Int_t)arr->GetTree()->GetEntries();
+ Int_t segment;
+ for (segment = 0; segment<nsegment;segment++){
+ AliTPCClustersRow *clrow= (AliTPCClustersRow*)arr->LoadEntry(segment);
+ if (clrow==0) continue;
+ Int_t ncluster = clrow->GetArray()->GetEntriesFast();
+ for (Int_t i = 0; i<ncluster;i++){
+ AliDifCluster *cl =(AliDifCluster*)clrow->GetArray()->UncheckedAt(i);
+ if ( (cl->fGenerTrack != cl->fTracks[0]) || (cl->fTracks[1]>0)) continue;
+ hdx->Fill(cl->fAngleX);
+ }
+ arr->ClearSegment(clrow->GetID());
+ }
+ return hdx;
+}
+
+TH1F * GetAngleX2(Float_t x1=-2, Float_t x2=3)
+{
+ AliTPCClustersArray *arr=gDifClusters;
+ if (arr==0) return 0;
+ TH1F * hdx = new TH1F("Angle x2", "Angle x2",33,x1,x2);
+ Int_t nsegment = (Int_t)arr->GetTree()->GetEntries();
+ Int_t segment;
+ for (segment = 0; segment<nsegment;segment++){
+ AliTPCClustersRow *clrow= (AliTPCClustersRow*)arr->LoadEntry(segment);
+ if (clrow==0) continue;
+ Int_t ncluster = clrow->GetArray()->GetEntriesFast();
+ for (Int_t i = 0; i<ncluster;i++){
+ AliDifCluster *cl =(AliDifCluster*)clrow->GetArray()->UncheckedAt(i);
+ if ( (cl->fGenerTrack != cl->fTracks[0]) || (cl->fTracks[1]>0)) continue;
+ hdx->Fill(cl->fAngleX*cl->fAngleX);
+ }
+ arr->ClearSegment(clrow->GetID());
+ }
+ return hdx;
+}
+
+TH1F * GetAngleY(Float_t x1=-2, Float_t x2=3)
+{
+ AliTPCClustersArray *arr=gDifClusters;
+ if (arr==0) return 0;
+ TH1F * hdx = new TH1F("Angle y", "Angle y",33,x1,x2);
+ Int_t nsegment = (Int_t)arr->GetTree()->GetEntries();
+ Int_t segment;
+ for (segment = 0; segment<nsegment;segment++){
+ AliTPCClustersRow *clrow= (AliTPCClustersRow*)arr->LoadEntry(segment);
+ if (clrow==0) continue;
+ Int_t ncluster = clrow->GetArray()->GetEntriesFast();
+ for (Int_t i = 0; i<ncluster;i++){
+ AliDifCluster *cl =(AliDifCluster*)clrow->GetArray()->UncheckedAt(i);
+ if ( (cl->fGenerTrack != cl->fTracks[0]) || (cl->fTracks[1]>0)) continue;
+ hdx->Fill(cl->fAngleY);
+ }
+ arr->ClearSegment(clrow->GetID());
+ }
+ return hdx;
+}
+
+TH1F * GetAngleY2(Float_t x1=-2, Float_t x2=3)
+{
+ AliTPCClustersArray *arr=gDifClusters;
+ if (arr==0) return 0;
+ TH1F * hdx = new TH1F("Angle y2", "Angle y2",33,x1,x2);
+ Int_t nsegment = (Int_t)arr->GetTree()->GetEntries();
+ Int_t segment;
+ for (segment = 0; segment<nsegment;segment++){
+ AliTPCClustersRow *clrow= (AliTPCClustersRow*)arr->LoadEntry(segment);
+ if (clrow==0) continue;
+ Int_t ncluster = clrow->GetArray()->GetEntriesFast();
+ for (Int_t i = 0; i<ncluster;i++){
+ AliDifCluster *cl =(AliDifCluster*)clrow->GetArray()->UncheckedAt(i);
+ if ( (cl->fGenerTrack != cl->fTracks[0]) || (cl->fTracks[1]>0)) continue;
+ hdx->Fill(cl->fAngleY*cl->fAngleY);
+ }
+ arr->ClearSegment(clrow->GetID());
+ }
+ return hdx;
+}
+
+
+TH1F * GetKmax(Float_t x1=0, Float_t x2=200)
+{
+ AliTPCClustersArray *arr=gDifClusters;
+ if (arr==0) return 0;
+ TH1F * hd = new TH1F("Max ADC", "Max ADC",33,x1,x2);
+ Int_t nsegment = (Int_t)arr->GetTree()->GetEntries();
+ Int_t segment;
+ for (segment = 0; segment<nsegment;segment++){
+ AliTPCClustersRow *clrow= (AliTPCClustersRow*)arr->LoadEntry(segment);
+ if (clrow==0) continue;
+ Int_t ncluster = clrow->GetArray()->GetEntriesFast();
+ for (Int_t i = 0; i<ncluster;i++){
+ AliDifCluster *cl =(AliDifCluster*)clrow->GetArray()->UncheckedAt(i);
+ if ( (cl->fGenerTrack != cl->fTracks[0]) || (cl->fTracks[1]>0)) continue;
+ hd->Fill(cl->fMax);
+ }
+ arr->ClearSegment(clrow->GetID());
+ }
+ return hd;
+}
+
+
+TH1F * GetQ(Float_t x1=0, Float_t x2=200)
+{
+ AliTPCClustersArray *arr=gDifClusters;
+ if (arr==0) return 0;
+ TH1F * hd = new TH1F("Integral Q", "Integral Q",33,x1,x2);
+ Int_t nsegment = (Int_t)arr->GetTree()->GetEntries();
+ Int_t segment;
+ for (segment = 0; segment<nsegment;segment++){
+ AliTPCClustersRow *clrow= (AliTPCClustersRow*)arr->LoadEntry(segment);
+ if (clrow==0) continue;
+ Int_t ncluster = clrow->GetArray()->GetEntriesFast();
+ for (Int_t i = 0; i<ncluster;i++){
+ AliDifCluster *cl =(AliDifCluster*)clrow->GetArray()->UncheckedAt(i);
+ if ( (cl->fGenerTrack != cl->fTracks[0]) || (cl->fTracks[1]>0)) continue;
+ hd->Fill(cl->fQ);
+ }
+ arr->ClearSegment(clrow->GetID());
+ }
+ return hd;
+}
+
+
+TH1F * GetCalcQ(Float_t x1=0, Float_t x2=1)
+{
+ AliTPCClustersArray *arr=gDifClusters;
+ if (arr==0) return 0;
+ TH1F * hd = new TH1F("kCalcQ", "kCalcQ",33,x1,x2);
+ Int_t nsegment = (Int_t)arr->GetTree()->GetEntries();
+ Int_t segment;
+ for (segment = 0; segment<nsegment;segment++){
+ AliTPCClustersRow *clrow= (AliTPCClustersRow*)arr->LoadEntry(segment);
+ if (clrow==0) continue;
+ Int_t ncluster = clrow->GetArray()->GetEntriesFast();
+ for (Int_t i = 0; i<ncluster;i++){
+ AliDifCluster *cl =(AliDifCluster*)clrow->GetArray()->UncheckedAt(i);
+ if ( (cl->fGenerTrack != cl->fTracks[0]) || (cl->fTracks[1]>0)) continue;
+ hd->Fill(cl->fOrigQ);
+ }
+ arr->ClearSegment(clrow->GetID());
+ }
+ return hd;
+}
+
+
+TH1F * GetCalcQSQR(Float_t x1=0, Float_t x2=1)
+{
+ AliTPCClustersArray *arr=gDifClusters;
+ if (arr==0) return 0;
+ TH1F * hd = new TH1F("kCalcQSQRt", "kCalcQSQRt",33,x1,x2);
+ Int_t nsegment = (Int_t)arr->GetTree()->GetEntries();
+ Int_t segment;
+ for (segment = 0; segment<nsegment;segment++){
+ AliTPCClustersRow *clrow= (AliTPCClustersRow*)arr->LoadEntry(segment);
+ if (clrow==0) continue;
+ Int_t ncluster = clrow->GetArray()->GetEntriesFast();
+ for (Int_t i = 0; i<ncluster;i++){
+ AliDifCluster *cl =(AliDifCluster*)clrow->GetArray()->UncheckedAt(i);
+ if ( (cl->fGenerTrack != cl->fTracks[0]) || (cl->fTracks[1]>0)) continue;
+ hd->Fill(TMath::Sqrt(cl->fOrigQ));
+ }
+ arr->ClearSegment(clrow->GetID());
+ }
+ return hd;
+}
+
+
+
+TH1F * GetQDivQ(Float_t x1=0, Float_t x2=1)
+{
+ AliTPCClustersArray *arr=gDifClusters;
+ if (arr==0) return 0;
+ TH1F * hd = new TH1F("kQdivCalcQ", "kQDivCalcQ",33,x1,x2);
+ Int_t nsegment = (Int_t)arr->GetTree()->GetEntries();
+ Int_t segment;
+ for (segment = 0; segment<nsegment;segment++){
+ AliTPCClustersRow *clrow= (AliTPCClustersRow*)arr->LoadEntry(segment);
+ if (clrow==0) continue;
+ Int_t ncluster = clrow->GetArray()->GetEntriesFast();
+ for (Int_t i = 0; i<ncluster;i++){
+ AliDifCluster *cl =(AliDifCluster*)clrow->GetArray()->UncheckedAt(i);
+ // if ( (cl->fGenerTrack != cl->fTracks[0]) || (cl->fTracks[1]>0)) continue;
+ hd->Fill(cl->fQ/cl->fOrigQ);
+ }
+ arr->ClearSegment(clrow->GetID());
+ }
+ return hd;
+}
+
+
+
+TH1F * GetKmaxDivQ(Float_t x1=0, Float_t x2=1)
+{
+ AliTPCClustersArray *arr=gDifClusters;
+ if (arr==0) return 0;
+ TH1F * hd = new TH1F("kMaxdivQ", "kMaxDivQ",33,x1,x2);
+ Int_t nsegment = (Int_t)arr->GetTree()->GetEntries();
+ Int_t segment;
+ for (segment = 0; segment<nsegment;segment++){
+ AliTPCClustersRow *clrow= (AliTPCClustersRow*)arr->LoadEntry(segment);
+ if (clrow==0) continue;
+ Int_t ncluster = clrow->GetArray()->GetEntriesFast();
+ for (Int_t i = 0; i<ncluster;i++){
+ AliDifCluster *cl =(AliDifCluster*)clrow->GetArray()->UncheckedAt(i);
+ if ( (cl->fGenerTrack != cl->fTracks[0]) || (cl->fTracks[1]>0)) continue;
+ hd->Fill(cl->fMax/cl->fQ);
+ }
+ arr->ClearSegment(clrow->GetID());
+ }
+ return hd;
+}
+
+
+
+
+
+
+
+
+TH2F * GetDXvRow(Float_t x1=0, Float_t x2=20, Float_t y1=0, Float_t y2=3)
+{
+ AliTPCClustersArray *arr=gDifClusters;
+ if (arr==0) return 0;
+ TH2F * hd = new TH2F("delta x versur row ", "DXvRow",33,x1,x2,33,y1,y2);
+ Int_t nsegment = (Int_t)arr->GetTree()->GetEntries();
+ Int_t segment;
+ for (segment = 0; segment<nsegment;segment++){
+ AliTPCClustersRow *clrow= (AliTPCClustersRow*)arr->LoadEntry(segment);
+ Int_t sector,row;
+ gTPCParam->AdjustSectorRow(clrow->GetID(),sector,row);
+ if (clrow==0) continue;
+ Int_t ncluster = clrow->GetArray()->GetEntriesFast();
+ for (Int_t i = 0; i<ncluster;i++){
+ AliDifCluster *cl =(AliDifCluster*)clrow->GetArray()->UncheckedAt(i);
+ if ( (cl->fGenerTrack != cl->fTracks[0]) || (cl->fTracks[1]>0)) continue;
+ hd->Fill(row,cl->fDx,1);
+ }
+ arr->ClearSegment(clrow->GetID());
+ }
+ return hd;
+}
+
+
+TH1F * GetSigmaX(Float_t x1=0, Float_t x2=2)
+{
+ AliTPCClustersArray *arr=gDifClusters;
+ if (arr==0) return 0;
+ TH1F * hd = new TH1F("SigmaX", "SigmaX",33,x1,x2);
+ Int_t nsegment = (Int_t)arr->GetTree()->GetEntries();
+ Int_t segment;
+ for (segment = 0; segment<nsegment;segment++){
+ AliTPCClustersRow *clrow= (AliTPCClustersRow*)arr->LoadEntry(segment);
+ if (clrow==0) continue;
+ Int_t ncluster = clrow->GetArray()->GetEntriesFast();
+ for (Int_t i = 0; i<ncluster;i++){
+ AliDifCluster *cl =(AliDifCluster*)clrow->GetArray()->UncheckedAt(i);
+ if ( (cl->fGenerTrack != cl->fTracks[0]) || (cl->fTracks[1]>0)) continue;
+ hd->Fill(TMath::Sqrt(cl->fSigmaX2));
+ }
+ arr->ClearSegment(clrow->GetID());
+ }
+ return hd;
+}
+
+
+TH1F * GetSigmaY(Float_t x1=0, Float_t x2=2)
+{
+ AliTPCClustersArray *arr=gDifClusters;
+ if (arr==0) return 0;
+ TH1F * hd = new TH1F("SigmaY", "SigmaY",33,x1,x2);
+ Int_t nsegment = (Int_t)arr->GetTree()->GetEntries();
+ Int_t segment;
+ for (segment = 0; segment<nsegment;segment++){
+ AliTPCClustersRow *clrow= (AliTPCClustersRow*)arr->LoadEntry(segment);
+ if (clrow==0) continue;
+ Int_t ncluster = clrow->GetArray()->GetEntriesFast();
+ for (Int_t i = 0; i<ncluster;i++){
+ AliDifCluster *cl =(AliDifCluster*)clrow->GetArray()->UncheckedAt(i);
+ if ( (cl->fGenerTrack != cl->fTracks[0]) || (cl->fTracks[1]>0)) continue;
+ hd->Fill(TMath::Sqrt(cl->fSigmaY2));
+ }
+ arr->ClearSegment(clrow->GetID());
+ }
+
+ return hd;
+}
+
+TH1F * GetArea(Float_t x1=0, Float_t x2=40)
+{
+ AliTPCClustersArray *arr=gDifClusters;
+ if (arr==0) return 0;
+ TH1F * hd = new TH1F("Cluster area", "cluster area",33,x1,x2);
+ Int_t nsegment = (Int_t)arr->GetTree()->GetEntries();
+ Int_t segment;
+ for (segment = 0; segment<nsegment;segment++){
+ AliTPCClustersRow *clrow= (AliTPCClustersRow*)arr->LoadEntry(segment);
+ if (clrow==0) continue;
+ Int_t ncluster = clrow->GetArray()->GetEntriesFast();
+ for (Int_t i = 0; i<ncluster;i++){
+ AliDifCluster *cl =(AliDifCluster*)clrow->GetArray()->UncheckedAt(i);
+ if ( (cl->fGenerTrack != cl->fTracks[0]) || (cl->fTracks[1]>0)) continue;
+ hd->Fill(cl->fArea);
+ }
+ arr->ClearSegment(clrow->GetID());
+ }
+ return hd;
+}
+
+
+TH2F * GetSigmaXvX(Float_t x1=0, Float_t x2=500,Float_t y1=0, Float_t y2=1)
+{
+ AliTPCClustersArray *arr=gDifClusters;
+ if (arr==0) return 0;
+ TH2F * hd = new TH2F("SigmaXvX", "SigmaXvX",33,x1,x2,33,y1,y2);
+ Int_t nsegment = (Int_t)arr->GetTree()->GetEntries();
+ Int_t segment;
+ for (segment = 0; segment<nsegment;segment++){
+ AliTPCClustersRow *clrow= (AliTPCClustersRow*)arr->LoadEntry(segment);
+ if (clrow==0) continue;
+ Int_t ncluster = clrow->GetArray()->GetEntriesFast();
+ for (Int_t i = 0; i<ncluster;i++){
+ AliDifCluster *cl =(AliDifCluster*)clrow->GetArray()->UncheckedAt(i);
+ if ( (cl->fGenerTrack != cl->fTracks[0]) || (cl->fTracks[1]>0)) continue;
+ hd->Fill(cl->fX,TMath::Sqrt(cl->fSigmaX2),1);
+ }
+ arr->ClearSegment(clrow->GetID());
+ }
+ return hd;
+}
+
+TH2F * GetSigmaYvX(Float_t x1=0, Float_t x2=500,Float_t y1=0, Float_t y2=1)
+{
+ AliTPCClustersArray *arr=gDifClusters;
+ if (arr==0) return 0;
+ TH2F * hd = new TH2F("SigmaYvX", "SigmaYvX",33,x1,x2,33,y1,y2);
+ Int_t nsegment = (Int_t)arr->GetTree()->GetEntries();
+ Int_t segment;
+ for (segment = 0; segment<nsegment;segment++){
+ AliTPCClustersRow *clrow= (AliTPCClustersRow*)arr->LoadEntry(segment);
+ if (clrow==0) continue;
+ Int_t ncluster = clrow->GetArray()->GetEntriesFast();
+ for (Int_t i = 0; i<ncluster;i++){
+ AliDifCluster *cl =(AliDifCluster*)clrow->GetArray()->UncheckedAt(i);
+ if ( (cl->fGenerTrack != cl->fTracks[0]) || (cl->fTracks[1]>0)) continue;
+ hd->Fill(cl->fX,TMath::Sqrt(cl->fSigmaY2),1);
+ }
+ arr->ClearSegment(clrow->GetID());
+ }
+ return hd;
+}
+
+TH2F * GetDeltaXvX(Float_t x1=0, Float_t x2=500,Float_t y1=0, Float_t y2=3)
+{
+ AliTPCClustersArray *arr=gDifClusters;
+ if (arr==0) return 0;
+ TH2F * hd = new TH2F("DeltaXvX", "DeltaXvX",33,x1,x2,33,y1,y2);
+ Int_t nsegment = (Int_t)arr->GetTree()->GetEntries();
+ Int_t segment;
+ for (segment = 0; segment<nsegment;segment++){
+ AliTPCClustersRow *clrow= (AliTPCClustersRow*)arr->LoadEntry(segment);
+ if (clrow==0) continue;
+ Int_t ncluster = clrow->GetArray()->GetEntriesFast();
+ for (Int_t i = 0; i<ncluster;i++){
+ AliDifCluster *cl =(AliDifCluster*)clrow->GetArray()->UncheckedAt(i);
+ if ( (cl->fGenerTrack != cl->fTracks[0]) || (cl->fTracks[1]>0)) continue;
+ hd->Fill(cl->fX,cl->fDy,1);
+ }
+ arr->ClearSegment(clrow->GetID());
+ }
+ return hd;
+}
+
+TH2F * GetDeltaYvX(Float_t x1=0, Float_t x2=500,Float_t y1=0, Float_t y2=0.5)
+{
+ AliTPCClustersArray *arr=gDifClusters;
+ if (arr==0) return 0;
+ TH2F * hd = new TH2F("DeltaYvX", "DeltaYvX",33,x1,x2,33,y1,y2);
+ Int_t nsegment = (Int_t)arr->GetTree()->GetEntries();
+ Int_t segment;
+ for (segment = 0; segment<nsegment;segment++){
+ AliTPCClustersRow *clrow= (AliTPCClustersRow*)arr->LoadEntry(segment);
+ if (clrow==0) continue;
+ Int_t ncluster = clrow->GetArray()->GetEntriesFast();
+ for (Int_t i = 0; i<ncluster;i++){
+ AliDifCluster *cl =(AliDifCluster*)clrow->GetArray()->UncheckedAt(i);
+ if ( (cl->fGenerTrack != cl->fTracks[0]) || (cl->fTracks[1]>0)) continue;
+ hd->Fill(cl->fX,cl->fDy,1);
+ }
+ arr->ClearSegment(clrow->GetID());
+ }
+ return hd;
+}
+
+TH2F * GetAreavX(Float_t x1=0, Float_t x2=500,Float_t y1=0, Float_t y2=20)
+{
+ AliTPCClustersArray *arr=gDifClusters;
+ if (arr==0) return 0;
+ TH2F * hd = new TH2F("AreavX", "AreavX",33,x1,x2,33,y1,y2);
+ Int_t nsegment = (Int_t)arr->GetTree()->GetEntries();
+ Int_t segment;
+ for (segment = 0; segment<nsegment;segment++){
+ AliTPCClustersRow *clrow= (AliTPCClustersRow*)arr->LoadEntry(segment);
+ if (clrow==0) continue;
+ Int_t ncluster = clrow->GetArray()->GetEntriesFast();
+ for (Int_t i = 0; i<ncluster;i++){
+ AliDifCluster *cl =(AliDifCluster*)clrow->GetArray()->UncheckedAt(i);
+ if ( (cl->fGenerTrack != cl->fTracks[0]) || (cl->fTracks[1]>0)) continue;
+ hd->Fill(cl->fX,cl->fArea,1);
+ }
+ arr->ClearSegment(clrow->GetID());
+ }
+ return hd;
+}
+
+
+TH2F * GetKvX(Float_t x1=0, Float_t x2=500,Float_t y1=0, Float_t y2=20)
+{
+ AliTPCClustersArray *arr=gDifClusters;
+ if (arr==0) return 0;
+ TH2F * hd = new TH2F("KvX", "KvX",33,x1,x2,33,y1,y2);
+ Int_t nsegment = (Int_t)arr->GetTree()->GetEntries();
+ Int_t segment;
+ for (segment = 0; segment<nsegment;segment++){
+ AliTPCClustersRow *clrow= (AliTPCClustersRow*)arr->LoadEntry(segment);
+ if (clrow==0) continue;
+ Int_t ncluster = clrow->GetArray()->GetEntriesFast();
+ for (Int_t i = 0; i<ncluster;i++){
+ AliDifCluster *cl =(AliDifCluster*)clrow->GetArray()->UncheckedAt(i);
+ if ( (cl->fGenerTrack != cl->fTracks[0]) || (cl->fTracks[1]>0)) continue;
+ hd->Fill(cl->fX,cl->fMax,1);
+ }
+ arr->ClearSegment(clrow->GetID());
+ }
+ return hd;
+}
+
--- /dev/null
+void Config()
+{
+//=======================================================================
+// Create the output file
+
+TFile *rootfile = new TFile("galice.root","recreate");
+rootfile->SetCompressionLevel(2);
+
+//=======================================================================
+// ******* GEANT STEERING parameters FOR ALICE SIMULATION *******
+geant3->SetTRIG(1); //Number of events to be processed
+geant3->SetSWIT(4,1);
+geant3->SetDEBU(0,0,1);
+//geant3->SetSWIT(2,2);
+geant3->SetDCAY(1);
+geant3->SetPAIR(1);
+geant3->SetCOMP(1);
+geant3->SetPHOT(1);
+geant3->SetPFIS(0);
+geant3->SetDRAY(0);
+geant3->SetANNI(1);
+geant3->SetBREM(1);
+geant3->SetMUNU(1);
+geant3->SetCKOV(1);
+geant3->SetHADR(1); //Select pure GEANH (HADR 1) or GEANH/NUCRIN (HADR 3)
+geant3->SetLOSS(2);
+geant3->SetMULS(1);
+geant3->SetRAYL(1);
+geant3->SetAUTO(1); //Select automatic STMIN etc... calc. (AUTO 1) or manual (AUTO 0)
+geant3->SetABAN(0); //Restore 3.16 behaviour for abandoned tracks
+geant3->SetOPTI(2); //Select optimisation level for GEANT geometry searches (0,1,2)
+Float_t cut = 1.e-3; // 1MeV cut by default
+Float_t tofmax = 1.e10;
+// GAM ELEC NHAD CHAD MUON EBREM MUHAB EDEL MUDEL MUPA TOFMAX
+geant3->SetCUTS(cut,cut, cut, cut, cut, cut, cut, cut, cut, cut, tofmax);
+//
+//=======================================================================
+// ************* STEERING parameters FOR ALICE SIMULATION **************
+// --- Specify event type to be tracked through the ALICE setup
+// --- All positions are in cm, angles in degrees, and P and E in GeV
+AliGenHIJINGpara *gener = new AliGenHIJINGpara(1000);
+gener->SetMomentumRange(0,100);
+gener->SetPhiRange(0,360);
+gener->SetThetaRange(20,160);
+gener->SetOrigin(0,0,0); //vertex position
+gener->SetSigma(0,0,0); //Sigma in (X,Y,Z) (cm) on IP position
+gener->Init();
+
+gAlice->SetField(-999,2); //Specify maximum magnetic field in Tesla (neg. ==> default field)
+
+//=================== Alice BODY parameters =============================
+AliBODY *BODY = new AliBODY("BODY","Alice envelop");
+
+
+
+//============================ TPC parameters ================================
+// --- This allows the user to specify sectors for the SLOW (TPC geometry 2)
+// --- Simulator. TPCSECL (TPSECU) <0 means that ALL lower (upper)
+// --- sectors are specified, any value other than that requires at least one
+// --- sector (lower or upper)to be specified!
+// --- Reminder: sectors 1-24 are lower sectors (1-12 -> z>0, 13-24 -> z<0)
+// --- sectors 25-72 are the upper ones (25-48 -> z>0, 49-72 -> z<0)
+// --- TPCLOWS - number of lower sectors specified (up to 6)
+// --- TPCUPS - number of upper sectors specified (up to 12)
+// --- TPCSENS - sensitive strips for the Slow Simulator !!!
+// --- This does NOT work if all S or L-sectors are specified, i.e.
+// --- if TPCSECL or TPCSECU < 0
+//-----------------------------------------------------------------------------
+
+AliTPC *TPC = new AliTPCv1("TPC","Normal TPC");
+TPC->SetSecAL(1);
+TPC->SetSecAU(1);
+TPC->SetSecLows(1, -1, -1, -1, -1, -1);
+TPC->SetSecUps(25, 26, 48, -1, -1, -1, -1, -1, -1, -1, -1, -1);
+TPC->SetSens(1);
+
+
+
+
+}
--- /dev/null
+
+/*
+#include "alles.h"
+extern AliTPCParam *gTPCParam;
+extern AliTPCClustersArray * gCalcClusters;
+extern AliTPCClustersArray * gDifClusters;
+AliTPCDigitsArray * GetDigitsArray();
+ AliTPCClustersArray * GetExactClustersArray();
+AliTPCClustersArray * GetCalcClustersArray(Bool_t newtree=kFALSE);
+AliTPCClustersArray * GetDifClustersArray(Bool_t newtree=kFALSE);
+TClonesArray * CompareClusters(TClonesArray *calcclusters,TClonesArray *exactclusters,
+ TClonesArray *diffclusters, Float_t shx, Float_t shy);
+*/
+
+void TPCDigits2Clusters(AliTPCDigitsArray * digarr, AliTPCClustersArray *calcarr,
+ AliTPCClustersArray *exarr=0, AliTPCClustersArray *difarr=0)
+{
+ //
+ //calculate clusters position from digits information
+ //
+
+
+ //initialisation of cluster finder
+ AliClusterFinder cf;
+ cf.SetThreshold(gTPCParam->GetZeroSup());
+ cf.SetDetectorParam(gTPCParam);
+ cf.SetBFit(kFALSE);
+ cf.GetMinuit()->SetPrintLevel(-1);
+ cf.GetMinuit()->SetMaxIterations(20);
+
+ if (digarr ==0) digarr = GetDigitsArray();
+ if ( (digarr == 0) || (digarr->GetTree()==0)) return;
+ if (exarr==0) exarr =GetExactClustersArray();
+ if ((exarr!=0)&&(difarr==0)) difarr= GetDifClustersArray();
+
+ if (calcarr==0) calcarr = GetCalcClustersArray(kTRUE);
+ //loop over all writen digits segments
+ Int_t nsegment = (Int_t)digarr->GetTree()->GetEntries();
+ Int_t segment;
+ for (segment = 0; segment<nsegment;segment++){
+ //load segment with index (TTree internal) number segment
+ AliSimDigits *digrow= (AliSimDigits*)digarr->LoadEntry(segment);
+ Int_t sector,row;
+ ((AliTPCParam*)digarr->GetParam())->AdjustSectorRow(digrow->GetID(),sector,row);
+
+ AliTPCClustersRow * clrow = calcarr->CreateRow(sector,row);
+ AliTPCClustersRow * difrow= difarr->CreateRow(sector,row);
+ AliTPCClustersRow * exrow = exarr->GetRow(sector,row);
+ if (exrow==0) exrow = exarr->LoadRow(sector,row);
+ TH2F *his = (TH2F*)digrow->GenerHisto();
+ digrow->ExpandTrackBuffer();
+ if (his==0) return;
+
+ //set current index for cluster finder
+ Int_t index[3]= {0,sector,row};
+ cf.GetHisto(his);
+ cf.SetDetectorIndex(index);
+ cf.FindPeaks3(clrow->GetArray());
+
+ //get cluster tracks ID
+ Int_t ncl = clrow->GetArray()->GetEntriesFast();
+ for (Int_t icl = 0 ;icl<ncl; icl++)
+ {
+ AliDigitCluster * cl =(AliDigitCluster*)clrow->GetArray()->UncheckedAt(icl);
+ Int_t i = (Int_t)cl->fMaxX;
+ Int_t j = (Int_t)cl->fMaxY;
+ cl->fTracks[0]=digrow->GetTrackIDFast(i,j,0);
+ cl->fTracks[1]=digrow->GetTrackIDFast(i,j,1);
+ cl->fTracks[2]=digrow->GetTrackIDFast(i,j,2);
+ }
+ Float_t shx = gTPCParam->GetZOffset()/gTPCParam->GetZWidth()+0.5;
+ Float_t shy= 0.5;
+ CompareClusters(clrow->GetArray(),exrow->GetArray(),difrow->GetArray(),shx,shy);
+ calcarr->StoreRow(sector,row);
+ difarr->StoreRow(sector,row);
+ digarr->ClearRow(sector,row);
+ }
+ //STORING RESULTS
+ char treeName[100];
+ sprintf(treeName,"TreeCCalc_%s",gTPCParam->GetTitle());
+ calcarr->GetTree()->Write(treeName);
+ if (difarr!=0){
+ char treeName[100];
+ sprintf(treeName,"TreeCDif_%s",gTPCParam->GetTitle());
+ difarr->GetTree()->Write(treeName);
+ }
+
+}
+
+
+AliTPCClustersArray * GetCalcClustersArray(Bool_t newtree=kFALSE, const char* name=0)
+{
+ //
+ //construct AliTPCClusters Array object
+ //
+ AliTPCClustersArray * arr=0;
+ // if ( (gAlice!=0) && (gAlice->GetDetector("TPC")!=0) ) {
+ // arr = ((AliTPC*)gAlice->GetDetector("TPC"))->GetClustersArray();
+ // if (arr!=0) arr->Update();
+ //}
+ if (arr==0) {
+ arr = new AliTPCClustersArray;
+ TFile *file = (TFile*)gROOT->GetListOfFiles()->FindObject("galice.root");
+ if (file==0) file = new TFile("galice.root","update");
+ arr->SetClusterType("AliDigitCluster");
+ arr->Setup(gTPCParam);
+ cout<<"Update status : "<<arr->Update()<<"\n";
+ char treeName[100];
+ if (name==0)
+ sprintf(treeName,"TreeCExact_%s",gTPCParam->GetTitle());
+ else
+ sprintf(treeName,"TreeCCalc_%s",gTPCParam->GetTitle());
+ if (newtree!=kTRUE){
+ cout<<"Connect tree status : "<<arr->ConnectTree(treeName)<<"\n";
+ }
+ else {
+ arr->MakeTree();
+ }
+ }
+ gCalcClusters = arr;
+ return arr;
+}
+
+
+AliTPCClustersArray * GetDifClustersArray(Bool_t newtree=kFALSE, const char* name=0)
+{
+ //
+ //construct AliTPCClusters Array object
+ //
+ AliTPCClustersArray * arr=0;
+ // if ( (gAlice!=0) && (gAlice->GetDetector("TPC")!=0) ) {
+ // arr = ((AliTPC*)gAlice->GetDetector("TPC"))->GetClustersArray();
+ // if (arr!=0) arr->Update();
+ //}
+ if (arr==0) {
+ arr = new AliTPCClustersArray;
+ TFile *file = (TFile*)gROOT->GetListOfFiles()->FindObject("galice.root");
+ if (file==0) file = new TFile("galice.root","update");
+ arr->SetClusterType("AliDifCluster");
+ arr->Setup(gTPCParam);
+ cout<<"Update status : "<<arr->Update()<<"\n";
+ char treeName[100];
+ if (name==0)
+ sprintf(treeName,"TreeCExact_%s",gTPCParam->GetTitle());
+ else
+ sprintf(treeName,"TreeCDif_%s",gTPCParam->GetTitle());
+ if (newtree!=kTRUE){
+ cout<<"Connect tree status : "<<arr->ConnectTree(treeName)<<"\n";
+ }
+ else {
+ arr->MakeTree();
+ }
+ }
+ gDifClusters = arr;
+ return arr;
+}
+
+
+
+TClonesArray * CompareClusters(TClonesArray *calcclusters,TClonesArray *exactclusters,
+ TClonesArray *diffclusters, Float_t shx, Float_t shy)
+{
+ if (calcclusters==0) return 0;
+ if (exactclusters==0) return 0;
+ if (diffclusters==0) return 0;
+ TClonesArray & diff=*diffclusters;
+
+
+ Int_t nclusters2 = calcclusters->GetEntriesFast();
+ Int_t nclusters1 = exactclusters->GetEntriesFast();
+
+ for(Int_t i=0; i<nclusters1; i++){
+ AliCluster * cl1 = (AliCluster*)exactclusters->UncheckedAt(i);
+ AliDigitCluster *cl2;
+ AliDifCluster diffc;
+ Int_t index=-1;
+ Float_t dx=10000;
+ Float_t dy=10000;
+ for (Int_t j=0; j<nclusters2;j++){
+ cl2 = (AliDigitCluster*)calcclusters->UncheckedAt(j);
+ if ( (cl2!=0)&& (cl1!=0)){
+ Float_t ddx = (cl2->fX-shx)-cl1->fX;
+ Float_t ddy = (cl2->fY-shy)-cl1->fY;
+ if ((ddx*ddx+ddy*ddy)<(dx*dx+dy*dy)){
+ dx=ddx;
+ dy=ddy;
+ index=j;
+ }
+ }
+ }
+
+ cl2 = (AliDigitCluster*)calcclusters->UncheckedAt(index);
+ if (cl2!=0){
+ diffc.fDx =dx;
+ diffc.fDy =dy;
+
+ diffc.fAngleX = cl1->fSigmaX2;
+ diffc.fAngleY = cl1->fSigmaY2;
+ diffc.fTracks[0] = cl2->fTracks[0];
+ diffc.fTracks[1] = cl2->fTracks[1];
+ diffc.fTracks[2] = cl2->fTracks[2];
+ diffc.fGenerTrack= cl1->fTracks[0];
+
+ diffc.fX = cl2->fX;
+ diffc.fY = cl2->fY;
+ diffc.fNx = cl2->fNx;
+ diffc.fNy = cl2->fNy;
+ diffc.fQ = cl2->fQ;
+ diffc.fOrigQ = cl1->fQ;
+ diffc.fSigmaX2 = cl2->fSigmaX2;
+ diffc.fSigmaY2 = cl2->fSigmaY2;
+ diffc.fArea = cl2->fArea;
+ diffc.fMax = cl2->fMax;
+ }
+ else cout<<"pici[ici/n";
+
+ new(diff[i]) AliDifCluster(diffc);
+ }
+ return diffclusters;
+}
--- /dev/null
+//#include "alles.h"
+
+void TPCHits2ExactClusters()
+{
+ if (gTPCParam==0) {
+ cout<<"TPC Param Not Initialised\n";
+ return;
+ }
+ // Dynamically link some shared libs
+ if (gClassTable->GetID("AliRun") < 0) {
+ gROOT->LoadMacro("loadlibs.C");
+ loadlibs();
+ }
+ // Connect the Root Galice file containing Geometry, Kine and Hits
+ const char * inFile = "galice.root";
+ TFile *file = (TFile*)gROOT->GetListOfFiles()->FindObject(inFile);
+ if (file) file->Close();
+ file = new TFile(inFile,"UPDATE");
+ // Get AliRun object from file or create it if not on file
+ // if (!gAlice) {
+ gAlice = (AliRun*)file->Get("gAlice");
+ if (gAlice) printf("AliRun object found on file\n");
+ if (!gAlice) gAlice = new AliRun("gAlice","Alice test program");
+ // };
+ gAlice->GetEvent(0);
+ AliTPC *TPC = (AliTPC*)gAlice->GetDetector("TPC");
+
+ //setup AliTPCClustersArray
+ AliTPCClustersArray * arr=new AliTPCClustersArray;
+ arr->SetClusterType("AliCluster");
+ arr->Setup(gTPCParam);
+ TPC->SetParam(gTPCParam);
+ arr->MakeTree();
+
+ TPC->SetClustersArray(arr);
+ TPC->Hits2ExactClustersSector(0);
+ //write results
+ char treeName[100];
+ sprintf(treeName,"TreeCExact_%s",gTPCParam->GetTitle());
+ TPC->GetClustersArray()->GetTree()->Write(treeName);
+}
+
+
+AliTPCClustersArray * GetExactClustersArray(Bool_t newtree=kFALSE, const char* name=0 )
+{
+ AliTPCClustersArray * arr;
+ if ( (gAlice!=0) && (gAlice->GetDetector("TPC")!=0) ) {
+ arr = ((AliTPC*)gAlice->GetDetector("TPC"))->GetClustersArray();
+ if (arr!=0) arr->Update();
+ }
+ if (arr==0) {
+ arr = new AliTPCClustersArray;
+ TFile *file = (TFile*)gROOT->GetListOfFiles()->FindObject("galice.root");
+ if (file==0) file = new TFile("galice.root","update");
+ arr->SetClusterType("AliCluster");
+ arr->Setup(gTPCParam);
+ cout<<"Update status : "<<arr->Update()<<"\n";
+ char treeName[100];
+ if (name==0)
+ sprintf(treeName,"TreeCExact_%s",gTPCParam->GetTitle());
+ else sprintf(treeName,"TreeCExact_%s",name);
+ if (newtree!=kTRUE){
+ cout<<"Connect tree status : "<<arr->ConnectTree(treeName)<<"\n";
+ }
+ else
+ arr->MakeTree();
+ }
+ return arr;
+}
+
+
+
+
#pragma link C++ class AliTPCtrack;
#pragma link C++ class AliTPCParam-;
-#pragma link C++ class AliTPCD-;
+#pragma link C++ class AliTPCParamSR-;
+#pragma link C++ class AliTPCParamCR-;
#pragma link C++ class AliTPCRF1D-;
#pragma link C++ class AliTPCPRF2D-;
+#pragma link C++ class AliArrayI-;
+#pragma link C++ class AliArrayS-;
+#pragma link C++ class AliDetectorParam;
+#pragma link C++ class AliSegmentID;
+#pragma link C++ class AliSegmentArray-;
+#pragma link C++ class AliCluster;
+#pragma link C++ class AliDigitCluster;
+#pragma link C++ class AliDifCluster;
+#pragma link C++ class AliClusters;
+#pragma link C++ class AliClustersArray;
+
+#pragma link C++ class AliTPCClustersRow;
+#pragma link C++ class AliTPCClustersArray;
+
+#pragma link C++ class AliDigits;
+#pragma link C++ class AliSimDigits;
+#pragma link C++ class AliDigitsArray;
+#pragma link C++ class AliTPCDigitsArray;
+
+
+#pragma link C++ class AliClusterFinder-;
+#pragma link C++ class AliCell;
+#pragma link C++ class AliH2F;
+
#endif
--- /dev/null
+void TPCtest()
+{
+// Connect the Root Galice file containing Geometry, Kine and Hits
+TFile *file = (TFile*)gROOT->GetListOfFiles()->FindObject("galice.root");
+ if (!file) file = new TFile("galice.root","UPDATE");
+
+// Get AliRun object from file or create it if not on file
+ if (!gAlice) {
+ gAlice = (AliRun*)file->Get("gAlice");
+ if (gAlice) printf("AliRun object found on file\n");
+ if (!gAlice) gAlice = new AliRun("gAlice","Alice test program");
+ }
+
+gAlice->GetEvent(0);
+AliDetector *TPC = gAlice->GetDetector("TPC");
+Int_t en;
+
+((AliTPC*)TPC)->Hits2Digits();
+
+TClonesArray *Digits = TPC->Digits();
+
+en = gAlice->TreeD()->GetEntries();
+printf("entries = %d\n",en);
+
+gAlice->TreeD()->Write();
+
+}
--- /dev/null
+TFile f("pokus.root","recreate")
+arr.MakeTree()
+TBrowser b;
+arr.AddSegment(1)
+arr[1]
+arr[1]->Dump()
+arr.AddSegment(2)
+arr[2]->Dump()
+dig.StoreSegment(1)
+arr.StoreSegment(1)
+arr.StoreSegment(2)
+arr.SetClass("AliDigits")
+arr.ConnectTree()
+TBrowser b;
+arr.SetClass("AliDigits")
+arr.MakeArray(100)
+arr.AddSegment(1)
+arr.AddSegment(2)
+arr.StoreSegment(1)
+arr.StoreSegment(2)
+arr.GetTree()->Write("pokus1")
+arr.GetTree()->Close()
+arr.SetClass("AliSimDigits")
+arr.MakeArray(1000)
+arr.ConnectTree("pokus1")
+arr.LoadSegment(1)
+arr[1]
+arr[1]->Dump()
+arr[2]
+arr.LoadSegment(2)
+arr[2]->Dump()
+.q
+.! ddd root.exe &
+.q
+.! ddd root.exe &
+AliTPCDigitsArray arr
+AliTPCDigitsArray brr
+.q
+AliTPCDigitsArray arr
+AliTPCParam par;
+arr.Setup(&par)
+arr.GetRow(1,1)
+.q
+.x mkhtml.C
+.q
+AliTPCDigitsArray arr;
+arr.CreateRow(0,4)
+.q
+AliTPCDigitsArray arr;
+AliTPCParam par;
+arr.Setup(&par)
+arr.CreateRow(0,4)
+arr.Getrow(9,4)
+arr.GetRow(0,4)
+arr.GetRow(0,4)->Dump()
+arr.GetRow(0,4)->IsA()->GetName()
+AliTPCParam par;
+par.Update()
+par.GetMaxTBin()
+.q
+AliTPCParam par;
+par.GetMaxTBin()
+AliTPCDigitsArray arr;
+arr.Setup(&par)
+arr.CreateRow(0,4)
+arr.GetRow(0,4)->Dump()
+arr.GetIndex(0,4)
+par.GetIndex(0,4)
+arr.GetParam()->GetIndex(0,4)
+(AliTPCParam* arr.GetParam())->GetIndex(0,4)
+(AliTPCParam* arr.GetParam()))->GetIndex(0,4)
+( (AliTPCParam*) arr.GetParam())->GetIndex(0,4)
+arr.GetRow(0,4)->GetSegmentID()
+arr.GetRow(0,4)->GetID()
--- /dev/null
+AliSimDigits dig;
+dig.Allocate(10,10);
+dig.AllocateTrack(3);
+
+dig.SetTrackIDFast(550,5,5,0);
+dig.SetTrackIDFast(551,5,5,1);
+dig.SetTrackIDFast(552,5,5,2);
+
+
+dig.SetTrackIDFast(550,6,5,0);
+dig.SetTrackIDFast(551,6,5,1);
+dig.SetTrackIDFast(552,6,5,2);
+
+dig.SetTrackIDFast(550,7,5,0);
+dig.SetTrackIDFast(551,7,5,1);
+dig.SetTrackIDFast(552,7,5,2);
+
+
+dig.SetTrackIDFast(440,4,4,0);
+dig.SetTrackIDFast(441,4,4,1);
+dig.SetTrackIDFast(442,4,4,2);
+
+
+
+
+dig.CompresTrackBuffer(1);
+
+dig.GetTrackID(5,5,0);
+dig.ExpandTrackBuffer() ;
+dig.GetTrackIDFast(5,5,0);
+dig.GetTrackIDFast(5,5,0);
+dig.GetTrackIDFast(5,5,1);
+dig.GetTrackIDFast(5,5,2);
+f
--- /dev/null
+TH1F * h2max = 0;
+void tpcstart(const char * param= "Param2",const char * out="out.root",
+ Int_t nevent=0, Float_t th=3)
+{
+
+
+ gtpc.SetIO("galice.root", "out.root");
+
+ AliTPCD * dig=new AliTPCD;
+ dig.SetName(param);
+ gtpc.GetIn()->cd();
+ dig.Read(param);
+ gtpc.SetDParam(dig);
+ gtpc.SetTree(nevent);
+
+ gtpc.SetbDelHisto(kTRUE);
+ gtpc.SetThreshold(3);
+}
+
+
+
+void tpccfind(Int_t threshold, Float_t thr = 2,
+ Int_t i1 = 2, Int_t i2 = 2,
+ Int_t tharea =20, Int_t thmax=100)
+{
+ ///////////////////////GRAPHICS//DECLARATION//////////////////////
+ TCanvas * c1 = new TCanvas("padcluster","Cluster finder 1",700,900);
+ c1->cd();
+ TCanvas * c2 = new TCanvas("padcluster2","Cluster finder 2",700,900);
+ c2->cd();
+ c1->cd();
+ TPad * pad11 = new TPad("pad11","",0.01,0.76,0.48,0.95,21);
+ pad11->Draw();
+ TPad * pad12 = new TPad("pad12","",0.51,0.76,0.95,0.95,21);
+ pad12->Draw();
+ TPad * pad21 = new TPad("pad21","",0.01,0.56,0.49,0.74,21);
+ pad21->Draw();
+ TPad * pad22 = new TPad("pad22","",0.51,0.56,0.95,0.74,21);
+ pad22->Draw();
+ TPad * pad31 = new TPad("pad31","",0.01,0.36,0.49,0.54,21);
+ pad31->Draw();
+ TPad * pad32 = new TPad("pad32","",0.51,0.36,0.95,0.54,21);
+ pad32->Draw();
+ TPad * pad41 = new TPad("pad41","",0.01,0.16,0.49,0.34,21);
+ pad41->Draw();
+ TPad * pad42 = new TPad("pad42","",0.51,0.16,0.95,0.34,21);
+ pad42->Draw();
+
+ c2->cd();
+ TPad * pad11_2 = new TPad("pad11_2","",0.01,0.76,0.48,0.95,21);
+ pad11_2->Draw();
+ TPad * pad12_2 = new TPad("pad12_2","",0.51,0.76,0.95,0.95,21);
+ pad12_2->Draw();
+ /////////////////////HISTOGRAMS///DECLARATION///////////////////////
+ pad11->cd();
+ TH1F * hsx = new TH1F("hsx","Sigma of distribution in time",40,0,2);
+ pad12->cd();
+ TH1F * hsy = new TH1F("hsy","Sigma of distribution in pads",40,0,2);
+
+ pad21->cd();
+ TProfile * hsx2 = new TProfile("hsx2","Sigma of distribution in time",
+ 20,100,500);
+ pad22->cd();
+ TProfile * hsy2 = new TProfile("hsy2","Sigma of distribution in pads",
+ 20,100,500);
+
+ pad31->cd();
+ TH1F * harea = new TH1F("harea","Area of the peak",26,0,52);
+ pad32->cd();
+ TH1F * hmax = new TH1F("hmax","Maximal amplitude in peak",30,0,150);
+
+
+ pad41->cd();
+ TProfile * harea2= new TProfile("harea2","Area dependence z coordinata",
+ 20,100,500);
+ pad42->cd();
+ TProfile * hmax2 = new TProfile("hmax2","Maximal amplitude dependence",
+ 20,100,500);
+ pad41->cd();
+
+ pad11_2->cd();
+ TProfile * harea2p= new TProfile("harea2p","Area dependence on pad coordinata",
+ 20,0,100);
+ pad12_2->cd();
+ TProfile * hmax2p = new TProfile("hmax2p","Maximal amplitude dependence on pad",
+ 20,0,50);
+ //////////////////CALCULATION//////////////////////////////////////////
+
+ for (Int_t k = i1;k <=i2; k++)
+ {
+ tpcanal(1,k,10,0,kFALSE);
+ TClusterFinder * cf=new TClusterFinder(0,0,threshold,1);
+ cf->GetHisto(>pc.GetHis1());
+ TClonesArray * arr = cf->FindClusters();
+ cf->Delete();
+ Int_t size = arr->GetEntries();
+
+ if ( size>0 )
+ for (Int_t i=0 ; i<size;i++)
+ {
+ Int_t index;
+ TCluster *c=(TCluster*)arr->UncheckedAt(i);
+ hsx->Fill(TMath::Sqrt(c.fSigmaX2));
+ hsy->Fill(TMath::Sqrt(c.fSigmaY2));
+ if (TMath::Sqrt(c.fSigmaX2)<thr)
+ hsx2->Fill(c.fX,TMath::Sqrt(c.fSigmaX2),1);
+ if (TMath::Sqrt(c.fSigmaY2)<thr)
+ hsy2->Fill(c.fX,TMath::Sqrt(c.fSigmaY2),1);
+ hmax->Fill(c.fMax);
+ harea->Fill(c.fArea);
+ if (c.fArea<tharea) harea2->Fill(c.fX,c.fArea,1);
+ if (c.fMax<thmax) hmax2->Fill(c.fX,c.fMax,1);
+ if (c.fArea<tharea) harea2p->Fill(c.fY,c.fArea,1);
+ if (c.fMax<thmax) hmax2p->Fill(c.fY,c.fMax,1);
+
+ }
+ }
+ gStyle->SetOptStat(1);
+ pad11->cd();
+ hsx->Draw();
+ pad12->cd();
+ hsy->Draw();
+
+ pad21->cd();
+ hsx2->Draw();
+ pad22->cd();
+ hsy2->Draw();
+
+ pad31->cd();
+ harea->Draw();
+ pad32->cd();
+ hmax->Draw();
+
+ pad41->cd();
+ harea2->Draw();
+ pad42->cd();
+ hmax2->Draw();
+
+
+ c1->cd();
+ TPaveText * comment = new TPaveText(0.05,0.02,0.95,0.14,"NDC");
+ comment->SetTextAlign(12);
+ comment->SetFillColor(42);
+ comment->ReadFile("clusters.txt");
+ comment->Draw();
+ c2->cd();
+ pad11_2->cd();
+ harea2p->Draw();
+ pad12_2->cd();
+ hmax2p->Draw();
+
+
+}
+
+
+void tpcanal(Int_t sec, Int_t row, Int_t pad, Float_t * res=0,
+ Bool_t bdraw = kTRUE,Float_t xmin=400,Float_t xmax=500)
+{
+ //calculate occupancy
+ Double_t par[3];
+ gtpc.SetSecRowTime(sec,row);
+ gtpc.SetHisto(pad);
+ //fit occupancy dependence
+
+ gStyle->SetOptStat(0);
+ g1 = new TF1("pol0_r","pol0",xmin,xmax);
+ gtpc.GetHis3()->Fit("pol0_r","R0Q");
+ char s[100];
+
+ if (bdraw == kTRUE)
+ {
+ gtpc.Draw("box");
+ gtpc.GetPad3().cd();
+ gtpc.GetPad3().SetGridx();
+ gtpc.GetPad3().SetGridy();
+ gtpc.GetPad3().SetLogy();
+ gtpc.GetPad3().Draw();
+ gtpc.GetPad2().cd();
+ gtpc.GetPad2().SetGridx();
+ gtpc.GetPad2().SetGridy();
+ fitText = new TPaveText(0.1,0.7,0.4,0.9,"NDC");
+ gtpc.GetHis3()->Draw();
+ sprintf(s,"p0 fit on interval %3.0f+- %3.0f",xmin,xmax);
+ fitText->AddText(s);
+ }
+ g1->GetParameters(&par[0]);
+ Float_t error = g1->GetParError(0);
+
+ sprintf(s,"%0.3f+- %0.3f",par[0],error);
+ if (bdraw == kTRUE)
+ {
+ gtpc.GetHis3()->Fit("pol0_r","R0Q");
+ fitText->AddText(s);
+ fitText->Draw();
+ gtpc.GetPad2().Update();
+
+ //plot histograms with specified options
+ //move pads to another position be possible add text
+ gtpc.GetPad1().SetPad(0.05,0.72,0.95,0.95);
+ gtpc.GetPad2().SetPad(0.05,0.47,0.95,0.70);
+ gtpc.GetPad3().SetPad(0.05,0.22,0.95,0.45);
+ //add comments to the histograms
+ gtpc.GetCanvas().cd();
+ TPaveText * comment = new TPaveText(0.05,0.03,0.95,0.2,"NDC");
+ comment->SetTextAlign(12);
+ comment->SetFillColor(42);
+ comment->ReadFile("comment.txt");
+ comment->Draw();
+ }
+ if (res != 0)
+ {
+ res[0] = par[0];
+ res[1] = error;
+ cout<<s<<" "<<res[0]<<" "<<res[1]<<"\n";
+ }
+}
+
+
+void tpcanalall(Int_t isec =1, Int_t lstep = 1,Float_t tmin=400)
+{
+ AliTPCParam * tpcparam = gtpc->GetParam();
+ //make window for displaying results
+ TCanvas * c_occu = new TCanvas("coccu","Occupancy dependence",700,900);
+ c_occu->Update();
+ TPad * pad1 = new TPad("occupancy","occupancy",0.05,0.25,0.95,0.95,21);
+ pad1->Draw();
+ //add comments to the histograms
+ TPaveText * comment = new TPaveText(0.05,0.03,0.95,0.2,"NDC");
+ comment->SetTextAlign(12);
+ comment->SetFillColor(42);
+ comment->ReadFile("comment.txt");
+ comment->Draw();
+ //prepare histogram
+ Int_t irow = tpcparam->GetNRow(isec);
+ Float_t xmin = tpcparam->GetPadRowRadii(isec,1);
+ Float_t xmax = tpcparam->GetPadRowRadii(isec,irow);
+ pad1->cd();
+ char s[220];
+ char sh[220];
+ sprintf(s,"occu_sector%d",isec);
+ sprintf(sh,"Occupancy in sector %d as function of pad raw",isec);
+ TH1F * occudep = new TH1F(s,sh,300,xmin,xmax);
+ Float_t res[20];
+ Float_t x;
+ for (Int_t i=2;i<irow;i+=lstep)
+ {
+ tpcanal(isec,i,10,&res[0],kFALSE,tmin);
+ x = tpcparam->GetPadRowRadii(isec,i) ;
+ Int_t index = (300*(x-xmin))/(xmax-xmin);
+ cout<<i<<" "<<index<<" "<<x<<" "<<res[0]<<" "<<res[1]<<"\n";
+ occudep->SetBinContent(index,res[0]);
+ occudep->SetBinError(index,res[1]);
+ }
+ //plot occupancy histogram
+
+ pad1->SetGridx();
+ pad1->SetGridy();
+ gStyle->SetOptFit(0);
+ occudep->Draw("error");
+ occudep->SetXTitle("pad row center position [cm]");
+ occudep->SetYTitle("occupancy");
+
+ //fit occupancy dependence
+ //linear fit
+ TF1 * g1 = new TF1("pol1_r","pol1");
+ occudep->Fit("pol1_r","+Q");
+ Double_t par[3];
+ Float_t error[3];
+ Float_t chi;
+ g1->GetParameters(&par[0]);
+ error[0]=g1->GetParError(0);
+ error[1]=g1->GetParError(1);
+ Float_t chi = g1->GetChisquare();
+ sprintf(s,"Linear fit ocupancy = (%2.3f - %2.3f) +(%2.1f+- %2.1f).r chi2 = %2.2f",
+ par[0],error[0],1000*par[1],1000*error[1],chi);
+ comment->AddText(s);
+ //(1-exp([0]1/(r*2+[1]**2) fit
+ TF1 * g1 = new TF1("polm1",occur,1,00,1);
+ occudep->Fit("polm1","+Q");
+ Double_t par[3];
+ Float_t error[3];
+ g1->GetParameters(&par[0]);
+ error[0]=g1->GetParError(0);
+ // error[1]=g1->GetParError(1);
+ chi = g1->GetChisquare();
+ sprintf(s,"(1-exp(P1/(x^2) fit P1=(%2.3f+- %2.3f) chi2=%2.2f ",
+ par[0],error[0],chi);
+ comment->AddText(s);
+ c_occu->Update();
+
+}
+
+void tpcanalspectra(Int_t isec =1, Int_t r1= 2)
+{
+ AliTPCParam * tpcparam = gtpc->GetParam();
+ //make window for displaying results
+ TCanvas * c_occu = new TCanvas("occuhis","Occupancy dependence",700,900);
+ c_occu->Update();
+ TPad * pad1 = new TPad("ocpad1","occupancy1",0.05,0.61,0.95,0.95,21);
+ pad1->Draw();
+ TPad * pad2 = new TPad("ocpad2","occupancy",0.05,0.61,0.95,0.95,21);
+ pad2->Draw();
+
+ TPad * pad3 = new TPad("ocpad3","occupancy1",0.05,0.25,0.95,0.60,21);
+ pad3->Draw();
+ TPad * pad4 = new TPad("ocpad4","occupancy",0.05,0.25,0.95,0.60,21);
+ pad4->Draw();
+
+ //add comments to the histograms
+ TPaveText * comment = new TPaveText(0.05,0.03,0.95,0.2,"NDC");
+ comment->SetTextAlign(12);
+ comment->SetFillColor(42);
+ comment->ReadFile("comment.txt");
+ comment->Draw();
+ TH2F his
+ //prepare histogram
+ for (Int_t i=1;i<irow;i+=lstep)
+ {
+ tpcanal(isec,i,10,&res[0],kFALSE,tmin);
+ }
+ //plot occupancy histogram
+
+ pad1->SetGridx();
+ pad1->SetGridy();
+}
+
+
+
+
+void tpcdraw(Int_t sec, Int_t row, Int_t pad)
+{
+ gStyle->SetOptStat(0);
+ //calculate occupancy for selected sector and pad row
+ //for selected pad is obtained signal shape
+ Double_t par[3];
+ gtpc.SetSecRowTime(sec,row);
+ gtpc.SetHisto(pad);
+ gtpc.Draw("box");
+ //plot histograms with specified options
+ //move pads to another position be possible add text
+ gtpc.GetPad1().SetPad(0.05,0.72,0.95,0.95);
+ gtpc.GetPad2().SetPad(0.05,0.47,0.95,0.70);
+ gtpc.GetPad3().SetPad(0.05,0.22,0.95,0.45);
+ //fit histogram of occupancy on specified range <150,500>
+ gtpc.GetPad2().cd();
+ g1 = new TF1("pol0_r","pol0",150,500);
+ gtpc.GetHis3()->Fit("pol0_r","R0Q");
+ g1->GetParameters(&par[0]);
+ Float_t error = g1->GetParError(0);
+ fitText = new TPaveText(0.15,0.7,0.3,0.9,"NDC");
+ fitText->AddText("p0 fit on interval <150-500>");
+ char s[100];
+ sprintf(s,"%0.3f+- %0.3f",par[0],error);
+ fitText->AddText(s);
+ fitText->Draw();
+ gtpc.GetPad2().Update();
+ //set logarithmic
+ gtpc.GetPad3().cd();
+ gtpc.GetPad3().SetLogy();
+ gtpc.GetPad3().Draw();
+ //add comments to the histograms
+ gtpc.GetCanvas().cd();
+ TPaveText * comment = new TPaveText(0.05,0.03,0.95,0.2,"NDC");
+ comment->SetTextAlign(12);
+ comment->SetFillColor(42);
+ comment->ReadFile("comment.txt");
+ comment->Draw();
+ gtpc.GetCanvas().Update();
+
+
+}
+
+
+void oDependence()
+{
+ //set plot options
+ gStyle->SetOptFit(1);
+ gStyle->SetOptStat(1);
+ TCanvas * c1 = new TCanvas("canPRF","Pad response function",700,900);
+ TPad * pad1 = new TPad("pad1THR","",0.05,0.55,0.45,0.95,21);
+ pad1->Draw();
+ TPad * pad2 = new TPad("pad2PRF","",0.55,0.55,0.95,0.95,21);
+ pad2->Draw();
+ TPad * pad3 = new TPad("pad3PRF","",0.55,0.05,0.95,0.45,21);
+ pad3->Draw();
+
+ pad1->cd();
+ pad1->SetGridx();
+ pad1->SetGridy();
+ pad2->SetGridx();
+ pad2->SetGridy();
+ pad3->SetGridx();
+ pad3->SetGridy();
+
+ //make histogram of threshold dependence
+ TH1F * hotd =new TH1F("Occupancy dependence on threshold",
+ "Ocupancy at first pad row as function of threshold",
+ 25,0.,25.);
+
+ hotd->SetBinContent(5,0.625);
+ hotd->SetBinError(5,0.02);
+ hotd->SetBinContent(10,0.559);
+ hotd->SetBinError(10,0.02);
+ hotd->SetBinContent(20,0.478);
+ hotd->SetBinError(20,0.02);
+ hotd->SetXTitle("Threshold [channels]");
+ hotd->SetYTitle("occupancy");
+ hotd->Fit("pol1","+");
+ hotd->Draw("error");
+ //make histogram of PRF dependence
+ TH1F * hoprfd =new TH1F("Occupancy dependence on PRF width",
+ "Occupancy at first pad row as function of generic PRF sigma for 2.05x0.35 cm pad size ",
+ 65, 0.,6.5);
+ hoprfd->SetBinContent(10,0.492);
+ hoprfd->SetBinError(10,0.02);
+
+ hoprfd->SetBinContent(20,0.524);
+ hoprfd->SetBinError(20,0.02);
+
+ hoprfd->SetBinContent(30,0.559);
+ hoprfd->SetBinError(30,0.02);
+ hoprfd->SetXTitle("Sigma of PRF [mm]");
+ hoprfd->SetYTitle("occupancy");
+ pad2->cd();
+ hoprfd->Fit("pol1","+");
+ hoprfd->Draw("error");
+ pad2->Draw();
+ //pad 3 histogram
+ pad3->cd();
+ TH1F * hoprfd88 =new TH1F("Occupancy dependence on PRF width 08x08",
+ "Occupancy at first pad row as function of generic PRF sigma for 0.8x0.8 cm pad size ",
+ 65, 0.,6.5);
+
+ hoprfd88->SetBinContent(20,0.322);
+ hoprfd88->SetBinError(20,0.02);
+
+ hoprfd88->SetBinContent(30,0.344);
+ hoprfd88->SetBinError(30,0.02);
+
+ hoprfd88->SetBinContent(40,0.369);
+ hoprfd88->SetBinError(40,0.02);
+
+ hoprfd88->SetBinContent(60,0.416);
+ hoprfd88->SetBinError(60,0.02);
+ hoprfd88->SetXTitle("Sigma of PRF [mm]");
+ hoprfd88->SetYTitle("occupancy");
+ hoprfd88->Fit("pol1","+");
+ hoprfd88->Draw("error");
+ c1->cd();
+ TPaveText * comment = new TPaveText(0.05,0.15,0.45,0.35,"NDC");
+ comment->SetTextAlign(12);
+ comment->SetFillColor(42);
+ comment->ReadFile("commentdep.txt");
+ comment->Draw();
+
+}
+
+void produceHisto()
+{
+ TH1F * hmostimp =new TH1F("number most important",
+ "Mean value number of over threshold digits produced by \
+most important particle",
+ 20,0.,23.);
+ gStyle->SetOptStat(0);
+ hmostimp->Fill(1.,33.51);
+ hmostimp->Fill(5.,34.32);
+ hmostimp->Fill(10.,35.78);
+ hmostimp->Fill(15.,36.85);
+ hmostimp->Fill(20.,37.61);
+ hmostimp->Write();
+ hmostimp->SetMinimum(32.);
+ delete hmostimp;
+
+ TH1F * hall =new TH1F("number all3",
+ "Mean value Number of over threshold digits produced by \
+alll three stored particles",
+ 20,0.,23.);
+ gStyle->SetOptStat(0);
+ hall->Fill(1.,77.05);
+ hall->Fill(5.,76.905);
+ hall->Fill(10.,71.9);
+ hall->Fill(15.,69.7);
+ hall->Fill(20.,65.15);
+ hall->Write();
+ hall->SetMinimum(32.);
+}
+
+void create6()
+{
+ TCanvas *cnumber =new TCanvas("Number","Number",600,900);
+ TPad *pad1 =new TPad("pad1","pad1",0.05,0.7,0.45,0.95);
+ pad1->cd();
+ pad1->Draw();
+ gtpc.fout->Get("His_1_1").Draw();
+ pad1->Update();
+ TPad *pad2 =new TPad("pad2","pad2",0.55,0.7,0.95,0.95);
+ TPad *pad3 =new TPad("pad3","pad3",0.05,0.35,0.45,0.66);
+ TPad *pad4 =new TPad("pad4","pad4",0.55,0.35,0.95,0.66);
+ TPad *pad5 =new TPad("pad5","pad5",0.05,0.05,0.45,0.32);
+ TPad *pad6 =new TPad("pad5","pad6",0.55,0.05,0.95,0.32);
+}
+
+Double_t xtom1(Double_t *x, Double_t *par)
+{
+ Double_t xm=x[0]/100.;
+ return (par[0]/(xm*xm));
+}
+
+Double_t xtomo(Double_t *x, Double_t *par)
+{
+ Double_t xm=x[0]/100.;
+ return (par[0]/(xm**par[1]));
+}
+
+Double_t occur(Double_t *x, Double_t *par)
+{
+ Double_t xm=x[0]/100.;
+ return (1-exp(-par[0]/(xm**2)));
+}
+
+void probability(Float_t param = 1, Float_t x1 = 0.9, Float_t x2 = 1.3,
+ Float_t over = 2,const char * com ="", Int_t N=20)
+{
+
+ //create canvas for drawing
+ TCanvas * c1 = new TCanvas("canprob","Pad response function",700,900);
+ TPad * pad1 = new TPad("Theoretical probability","",0.05,0.22,0.95,0.95,21);
+ pad1->Draw();
+
+ //create histogram with estimated occupancy
+ //normalised to obtained occupancy at first pad
+ Float_t y1=0;
+ Float_t y2;
+ char s[120];
+ sprintf(s,"1-exp(-[1]/x**%f)",over);
+ cout<<s<<"\n";
+ TF1 *funr1 = new TF1("funr1",s,x1,x2);
+ funr1->SetParameters(1,param);
+ sprintf(s,"Probability according 1-exp(-%1.3f/x**%1.1f distribution)",
+ param,over);
+ pad1->cd();
+ TH1F * hOccuT = new TH1F("hOccuT",s,5*N,x1,x2);
+ Float_t x=x1;
+ Float_t y;
+
+ for (Float_t i = 0;i<N+1;i++)
+ {
+ y = funr1->Eval(x);
+ hOccuT->Fill(x,y);
+ x+=(x2-x1)/Float_t(N);
+ };
+ //fitting calculated dependence with linear fit and with
+ //generic function
+ pad1->cd();
+ sprintf(s,"[1]/(x**%1.1f)",over);
+ TF1 *lin1 = new TF1("lin1","pol1",x1,x2);
+ lin1->SetLineColor(2);
+ lin1->SetLineWidth(5);
+ lin1->SetLineStyle(1);
+ hOccuT->Draw();
+ hOccuT->Fit("lin1","S+");
+
+ sprintf(s,"[1]/(x**%1.1f)",over);
+ TF1 *funorig = new TF1("funorig",s,x1,x2);
+ funorig->SetLineColor(3);
+ funorig->SetLineWidth(5);
+ funorig->SetLineStyle(2);
+ hOccuT->Fit("funorig","S+");
+
+ //find minimum and maximum and scale histo
+ if (y1 == 0)
+ {
+ Float_t ymin,ymax;
+ y1=lin1->Eval(x2);
+ y2=lin1->Eval(x1);
+ ymin= funorig->Eval(x2);
+ ymax= funorig->Eval(x1);
+ if (ymin<y1) y1=ymin;
+ if (ymax>y2) y2=ymax;
+ }
+ gStyle->SetOptFit(0);
+ gStyle->SetOptStat(0);
+ hOccuT->SetMaximum(y2);
+ hOccuT->SetMinimum(y1);
+ hOccuT->SetXTitle("r position [m]");
+ hOccuT->SetYTitle("probability");
+ //add comments to the histograms
+ c1->cd();
+ TPaveText * comment = new TPaveText(0.05,0.03,0.95,0.20,"NDC");
+ comment->SetTextAlign(12);
+ comment->SetFillColor(42);
+ TText *title = comment->AddText("Estimation of occupancy dependence on R position");
+ title->SetTextSize(0.04);
+ comment->AddText("Observed efect of probability saturation");
+ sprintf(s,"Supposed generic flux dependence : %1.3f/(x**%1.1f)",param,over);
+ comment->AddText(s);
+ comment->AddText("Probility : 1-exp(-flux*mean particle \"pad x time\" area)");
+ comment->AddText("Full line linear fit ");
+ comment->AddText("Dashed line : fit by generic flux function ");
+
+ comment->AddText(com);
+ comment->Draw();
+}
+
+
+
+void digamp(Float_t t1, Float_t t2, Float_t p1, Float_t p2, Float_t th)
+{
+ gStyle->SetOptStat(1);
+ TH1F * h2max = new TH1F("all amplitudes","all amplitude", 20, 1,600);
+ for (Int_t itime = t1;itime<t2;itime++)
+ for (Int_t ipad = p1;ipad<p2;ipad++)
+ {
+ Int_t index = gtpc.GetHis1().GetBin(itime,ipad);
+ Float_t weight = gtpc.GetHis1().GetBinContent(index);
+ // cout<<itime<<"\t"<<ipad<<"\t"<<weight<<"\n";
+ if (weight > th) h2max->Fill(weight);
+ };
+ h2max->Draw();
+}
+
+void digampM(Float_t t1, Float_t t2, Float_t p1, Float_t p2, Float_t th)
+{
+ gStyle->SetOptStat(1);
+
+ //create canvas for drawing
+ // TCanvas * c1 = new TCanvas("dh","Amplitude",700,900);
+ //TPad * pad1 = new TPad("amplitude","",0.05,0.22,0.95,0.95,21);
+ //pad1->Draw();
+
+ if (h2max == 0) h2max = new TH1F("max amplitudes","max amplitude", 25, 1,250);
+ for (Int_t itime = t1;itime<t2;itime++)
+ for (Int_t ipad = p1;ipad<p2;ipad++)
+ {
+ Bool_t bmax = kTRUE;
+ Int_t index = gtpc.GetHis1().GetBin(itime,ipad);
+ Float_t weight = gtpc.GetHis1().GetBinContent(index);
+ if (weight>th)
+ {
+ for (Int_t i = -1;i<2;i++)
+ for (Int_t j = -1;j<2;j++)
+ if (!((0==i)&&(0==j)))
+ {
+ index = gtpc.GetHis1().GetBin(itime+i,ipad+j);
+ Float_t weightl = gtpc.GetHis1().GetBinContent(index);
+ if (!(weightl<weight)) bmax = kFALSE;
+ }
+ if (kTRUE==bmax) h2max->Fill(weight);
+ }
+ };
+ h2max->Draw("error");
+
+}
+
+
+
+void digampMALL(Float_t t1, Float_t t2, Float_t p1, Float_t p2, Float_t th )
+{
+ for (Int_t i=1;i<20;i++)
+ {
+ tpcanal(1,i,10);
+ digampM(t1,t2,p1,p2,th);
+ }
+}
--- /dev/null
+void MakeClusterTree(Int_t n)
+{
+ TFile * f = new TFile("pokus.root","recreate");
+ AliTPCClustersArray arr;
+ arr.MakeArray(10000);
+ arr.MakeTree();
+ for (Int_t i=0;i<n;i++) {
+ AliTPCClustersRow * row =new AliTPCClustersRow;
+ row->SetIndex(i);
+ arr.AddSegment(row);
+ }
+ for (Int_t i=0;i<n;i++) arr.StoreSegment(n-i);
+ arr.GetTree()->Write("pokus1");
+
+
+}
+
+
+void MakeTree(Int_t n)
+{
+ AliSegmentArray arr;
+
+ TFile * f= new TFile("pokus.root","recreate");
+ arr.MakeArray(10000);
+ arr.MakeTree();
+ // for (Int_t i=0;i<n;i++) arr.AddSegment(new AliSegment(Int_t((gRandom->Rndm())*n)));
+
+ //for (Int_t i=0;i<n;i++) arr.StoreSegment(Int_t((gRandom->Rndm())*n));
+ for (Int_t i=0;i<n;i++) arr.AddSegment(new AliSegment(i));
+ for (Int_t i=0;i<n;i++) arr.StoreSegment(n-i);
+ arr.GetTree()->Write("pokus1");
+}
+
+void ConnectTree(Int_t n,AliSegmentArray *a)
+{
+ AliSegmentArray &arr= *a;
+ // TFile * f = new TFile("pokus.root","update");
+ TFile * f = new TFile("pokus.root","update");
+ arr.MakeArray(10000);
+ arr.ConnectTree("pokus1");
+ for (Int_t i=0;i<n;i++) arr.LoadSegment(i);
+ for (Int_t i=0;i<n;i++)
+ {
+ if (arr[i]==0) continue;
+ if (arr[i]->GetID()!=i) cout<<i<<"\n";
+ }
+}
+
--- /dev/null
+/**************************************************************************
+ * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
+ * *
+ * Author: The ALICE Off-line Project. *
+ * Contributors are mentioned in the code where appropriate. *
+ * *
+ * Permission to use, copy, modify and distribute this software and its *
+ * documentation strictly for non-commercial purposes is hereby granted *
+ * without fee, provided that the above copyright notice appears in all *
+ * copies and that both the copyright notice and this permission notice *
+ * appear in the supporting documentation. The authors make no claims *
+ * about the suitability of this software for any purpose. It is *
+ * provided "as is" without express or implied warranty. *
+ **************************************************************************/
+
+/*
+$Log$
+Revision 1.1.2.2 2000/04/10 11:40:46 kowal2
+
+Needed for tracking
+
+*/
+
+static int PropagateTo(TVector &x, Double_t fX, Double_t xk) {
+ if (TMath::Abs(x(2)*xk - x(3)) >= 0.999) {
+ cerr<<"Propagation failed !\n";
+ return 0;
+ }
+
+ Double_t x1=fX, x2=x1+(xk-x1), dx=x2-x1;//, y1=x(0), z1=x(1);
+ Double_t c1=x(2)*x1 - x(3), r1=sqrt(1.- c1*c1);
+ Double_t c2=x(2)*x2 - x(3), r2=sqrt(1.- c2*c2);
+
+ x(0) += dx*(c1+c2)/(r1+r2);
+ x(1) += dx*(c1+c2)/(c1*r2 + c2*r1)*x(4);
+
+ return 1;
+}
+
+static int Rotate(TVector &x, Double_t fX, Double_t alpha) {
+ Double_t x1=fX, y1=x(0);
+ Double_t ca=cos(alpha), sa=sin(alpha);
+ Double_t r1=x(2)*fX - x(3);
+
+ fX = x1*ca + y1*sa;
+ x(0)=-x1*sa + y1*ca;
+ x(3)=x(3)*ca + (x(2)*y1 + sqrt(1.- r1*r1))*sa;
+
+ Double_t r2=x(2)*fX - x(3);
+ if (TMath::Abs(r2) >= 0.999) {
+ //cerr<<"Rotation failed !\n";
+ return 0;
+ }
+
+ Double_t y0=x(0) + sqrt(1.- r2*r2)/x(2);
+ if ((x(0)-y0)*x(2) >= 0.) {
+ //cerr<<"Rotation failed !!!\n";
+ return 0;
+ }
+
+ return 1;
+}
+
+//_____________________________________________________________________________
+static int templ(TVector par, Double_t x, Double_t dy, Double_t dz,
+ const AliTPCSector *sec, int s, int rf=0)
+{
+ //-----------------------------------------------------------------
+ // This function tries to find a track prolongation.
+ //
+ // Origin: Iouri Belikov, CERN, Jouri.Belikov@cern.ch
+ //-----------------------------------------------------------------
+ int accepted=0;
+ const int ROWS_TO_SKIP=100;
+ int try_again=ROWS_TO_SKIP;
+ Double_t alpha=sec->GetAlpha();
+ int ns=int(2*TMath::Pi()/alpha+0.5);
+
+ Double_t xold=x;
+ for (int nr=sec->GetRowNumber(x)-1; nr>=rf; nr--,xold=x) {
+ //cerr<<nr<<endl;
+ Double_t x=sec->GetX(nr), ymax=sec->GetMaxY(nr);
+ if (!PropagateTo(par,xold,x)) return 0;
+
+ AliTPCcluster *cl=0;
+ const AliTPCRow& row=sec[s][nr];
+ Double_t road=dy, y=par(0), z=par(1);
+
+ if (road>30) {
+ return 0;
+ }
+
+ if (row) {
+ for (int i=row.Find(y-road); i<row; i++) {
+ AliTPCcluster* c=(AliTPCcluster*)(row[i]);
+ if (c->fY > y+road) break;
+ if (TMath::Abs(c->fZ - z) > dz) continue;
+ cl=c;
+ }
+ }
+ if (cl) {
+ par(0)=cl->fY; par(1)=cl->fZ;
+ //dy=TMath::Sqrt(cl->fSigmaY2); dz=TMath::Sqrt(cl->fSigmaZ2);
+ //cerr<<nr<<' '<<cl->fTracks[0]<<' '<<cl->fTracks[1]<<' '<<cl->fTracks[2]<<endl;
+ accepted++;
+ try_again=ROWS_TO_SKIP;
+ } else {
+ if (try_again==0) break;
+ if (y > ymax) {
+ s = (s+1) % ns;
+ if (!Rotate(par,x,alpha)) return 0;
+ dy*=2;
+ } else if (y <-ymax) {
+ s = (s-1+ns) % ns;
+ if (!Rotate(par,x,-alpha)) return 0;
+ dy*=2;
+ }
+ try_again--;
+ }
+ }
+
+ //cerr<<endl;
+ return accepted;
+}
+
+