99adacae |
1 | #ifndef ALICHEB3DCALC_H |
2 | #define ALICHEB3DCALC_H |
3 | /* Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. * |
4 | * See cxx source for full Copyright notice */ |
40389866 |
5 | #include <TNamed.h> |
5406439e |
6 | class TSystem; |
99adacae |
7 | // |
8 | // Author: Ruben Shahoyan |
9 | // ruben.shahoyan@cern.ch 09/09/2006 |
10 | // See Comments in AliCheb3D.h |
11 | // |
40389866 |
12 | |
13 | |
14 | // to decrease the compilable code size comment this define. This will exclude the routines |
15 | // used for the calculation and saving of the coefficients. |
1d18ebe0 |
16 | //#define _INC_CREATION_ALICHEB3D_ |
40389866 |
17 | |
18 | // when _BRING_TO_BOUNDARY_ is defined, the point outside of the fitted folume is assumed |
19 | // to be on the surface |
5de97576 |
20 | // #define _BRING_TO_BOUNDARY_ |
40389866 |
21 | // |
22 | |
99adacae |
23 | |
24 | class AliCheb3DCalc: public TNamed |
25 | { |
26 | public: |
27 | AliCheb3DCalc(); |
40389866 |
28 | AliCheb3DCalc(const AliCheb3DCalc& src); |
29 | AliCheb3DCalc(FILE* stream); |
30 | ~AliCheb3DCalc() {Clear();} |
99adacae |
31 | // |
40389866 |
32 | AliCheb3DCalc& operator=(const AliCheb3DCalc& rhs); |
5406439e |
33 | void Print(const Option_t* opt="") const; |
99adacae |
34 | void LoadData(FILE* stream); |
5406439e |
35 | Float_t EvalDeriv(int dim, const Float_t *par) const; |
36 | Float_t EvalDeriv2(int dim1,int dim2, const Float_t *par) const; |
99adacae |
37 | // |
38 | #ifdef _INC_CREATION_ALICHEB3D_ |
5406439e |
39 | void SaveData(const char* outfile,Bool_t append=kFALSE) const; |
40 | void SaveData(FILE* stream=stdout) const; |
99adacae |
41 | #endif |
42 | // |
99adacae |
43 | void InitRows(int nr); |
44 | void InitCols(int nc); |
2572efdf |
45 | Int_t GetNCoefs() const {return fNCoefs;} |
1d18ebe0 |
46 | Int_t GetNCols() const {return (Int_t)fNCols;} |
47 | Int_t GetNRows() const {return (Int_t)fNRows;} |
48 | Int_t GetNElemBound2D() const {return (Int_t)fNElemBound2D;} |
2572efdf |
49 | Int_t GetMaxColsAtRow() const; |
1d18ebe0 |
50 | UShort_t* GetNColsAtRow() const {return fNColsAtRow;} |
51 | UShort_t* GetColAtRowBg() const {return fColAtRowBg;} |
40389866 |
52 | void InitElemBound2D(int ne); |
1d18ebe0 |
53 | UShort_t* GetCoefBound2D0() const {return fCoefBound2D0;} |
54 | UShort_t* GetCoefBound2D1() const {return fCoefBound2D1;} |
5406439e |
55 | void Clear(const Option_t* option = ""); |
1cf34ee8 |
56 | static Float_t ChebEval1D(Float_t x, const Float_t * array, int ncf); |
57 | static Float_t ChebEval1Deriv(Float_t x, const Float_t * array, int ncf); |
58 | static Float_t ChebEval1Deriv2(Float_t x, const Float_t * array, int ncf); |
40389866 |
59 | void InitCoefs(int nc); |
99adacae |
60 | Float_t * GetCoefs() const {return fCoefs;} |
61 | // |
40389866 |
62 | static void ReadLine(TString& str,FILE* stream); |
63 | // |
1d18ebe0 |
64 | Float_t Eval(const Float_t *par) const; |
65 | Double_t Eval(const Double_t *par) const; |
ff66b122 |
66 | // |
99adacae |
67 | protected: |
68 | Int_t fNCoefs; // total number of coeeficients |
69 | Int_t fNRows; // number of significant rows in the 3D coeffs matrix |
70 | Int_t fNCols; // max number of significant cols in the 3D coeffs matrix |
71 | Int_t fNElemBound2D; // number of elements (fNRows*fNCols) to store for the 2D boundary of significant coeffs |
1d18ebe0 |
72 | UShort_t* fNColsAtRow; //[fNRows] number of sighificant columns (2nd dim) at each row of 3D coefs matrix |
73 | UShort_t* fColAtRowBg; //[fNRows] beginnig of significant columns (2nd dim) for row in the 2D boundary matrix |
74 | UShort_t* fCoefBound2D0; //[fNElemBound2D] 2D matrix defining the boundary of significance for 3D coeffs.matrix (Ncoefs for col/row) |
75 | UShort_t* fCoefBound2D1; //[fNElemBound2D] 2D matrix defining the start beginnig of significant coeffs for col/row |
99adacae |
76 | Float_t * fCoefs; //[fNCoefs] array of Chebyshev coefficients |
77 | // |
78 | Float_t * fTmpCf1; //[fNCols] temp. coeffs for 2d summation |
79 | Float_t * fTmpCf0; //[fNRows] temp. coeffs for 1d summation |
80 | // |
1d18ebe0 |
81 | ClassDef(AliCheb3DCalc,3) // Class for interpolation of 3D->1 function by Chebyshev parametrization |
99adacae |
82 | }; |
83 | |
40389866 |
84 | //__________________________________________________________________________________________ |
85 | inline Float_t AliCheb3DCalc::ChebEval1D(Float_t x, const Float_t * array, int ncf ) |
99adacae |
86 | { |
87 | // evaluate 1D Chebyshev parameterization. x is the argument mapped to [-1:1] interval |
db83d72f |
88 | if (ncf<=0) return 0; |
40389866 |
89 | Float_t b0, b1, b2, x2 = x+x; |
99adacae |
90 | b0 = array[--ncf]; |
91 | b1 = b2 = 0; |
92 | for (int i=ncf;i--;) { |
93 | b2 = b1; |
94 | b1 = b0; |
95 | b0 = array[i] + x2*b1 -b2; |
96 | } |
97 | return b0 - x*b1; |
40389866 |
98 | // |
99adacae |
99 | } |
100 | |
1d18ebe0 |
101 | //__________________________________________________________________________________________ |
102 | inline Float_t AliCheb3DCalc::Eval(const Float_t *par) const |
103 | { |
104 | // evaluate Chebyshev parameterization for 3D function. |
105 | // VERY IMPORTANT: par must contain the function arguments ALREADY MAPPED to [-1:1] interval |
106 | if (!fNRows) return 0.; |
107 | int ncfRC; |
108 | for (int id0=fNRows;id0--;) { |
109 | int nCLoc = fNColsAtRow[id0]; // number of significant coefs on this row |
110 | int col0 = fColAtRowBg[id0]; // beginning of local column in the 2D boundary matrix |
111 | for (int id1=nCLoc;id1--;) { |
112 | int id = id1+col0; |
113 | fTmpCf1[id1] = (ncfRC=fCoefBound2D0[id]) ? ChebEval1D(par[2],fCoefs + fCoefBound2D1[id], ncfRC) : 0.0; |
114 | } |
115 | fTmpCf0[id0] = nCLoc>0 ? ChebEval1D(par[1],fTmpCf1,nCLoc):0.0; |
116 | } |
117 | return ChebEval1D(par[0],fTmpCf0,fNRows); |
118 | } |
119 | |
120 | //__________________________________________________________________________________________ |
121 | inline Double_t AliCheb3DCalc::Eval(const Double_t *par) const |
122 | { |
123 | // evaluate Chebyshev parameterization for 3D function. |
124 | // VERY IMPORTANT: par must contain the function arguments ALREADY MAPPED to [-1:1] interval |
125 | if (!fNRows) return 0.; |
126 | int ncfRC; |
127 | for (int id0=fNRows;id0--;) { |
128 | int nCLoc = fNColsAtRow[id0]; // number of significant coefs on this row |
129 | int col0 = fColAtRowBg[id0]; // beginning of local column in the 2D boundary matrix |
130 | for (int id1=nCLoc;id1--;) { |
131 | int id = id1+col0; |
132 | fTmpCf1[id1] = (ncfRC=fCoefBound2D0[id]) ? ChebEval1D(par[2],fCoefs + fCoefBound2D1[id], ncfRC) : 0.0; |
133 | } |
134 | fTmpCf0[id0] = nCLoc>0 ? ChebEval1D(par[1],fTmpCf1,nCLoc):0.0; |
135 | } |
136 | return ChebEval1D(par[0],fTmpCf0,fNRows); |
137 | } |
138 | |
99adacae |
139 | #endif |