1414#include " Chebyshev3DCalc.h"
1515#include " FairLogger.h"
1616
17- using namespace AliceO2 ::Field ;
17+ using namespace AliceO2 ::MathUtils ;
1818
1919ClassImp (Chebyshev3D)
2020
21+ const Float_t Chebyshev3D::sMinimumPrecision = 1.e-12f;
22+
2123Chebyshev3D::Chebyshev3D ()
2224 : mOutputArrayDimension(0 ),
23- mPrecision(0 ),
25+ mPrecision(sMinimumPrecision ),
2426 mChebyshevParameter(1 ),
2527 mMaxCoefficients(0 ),
2628 mTemporaryUserResults(0 ),
@@ -111,11 +113,11 @@ Chebyshev3D::Chebyshev3D(FILE* stream)
111113}
112114
113115#ifdef _INC_CREATION_Chebyshev3D_
114- Chebyshev3D::Chebyshev3D (const char * funName, int DimOut , const Float_t* bmin, const Float_t* bmax, Int_t* npoints,
115- Float_t prec )
116+ Chebyshev3D::Chebyshev3D (const char * funName, int dimOut , const Float_t* bmin, const Float_t* bmax,
117+ const Int_t* npoints, Float_t prec, const Float_t* precD )
116118 : TNamed(funName, funName),
117119 mOutputArrayDimension(0 ),
118- mPrecision(TMath::Max(1 .E- 12f , prec)),
120+ mPrecision(TMath::Max(sMinimumPrecision , prec)),
119121 mChebyshevParameter(1 ),
120122 mMaxCoefficients(0 ),
121123 mTemporaryUserResults(0 ),
@@ -124,7 +126,7 @@ Chebyshev3D::Chebyshev3D(const char* funName, int DimOut, const Float_t* bmin, c
124126 mUserMacro(0 ),
125127 mLogger(FairLogger::GetLogger())
126128{
127- if (DimOut < 1 ) {
129+ if (dimOut < 1 ) {
128130 Error (" Chebyshev3D" , " Requested output dimension is %d\n Stop\n " , mOutputArrayDimension );
129131 exit (1 );
130132 }
@@ -134,7 +136,7 @@ Chebyshev3D::Chebyshev3D(const char* funName, int DimOut, const Float_t* bmin, c
134136 mTemporaryChebyshevGridOffs [i] = 0 .;
135137 mTemporaryCoefficient [i] = 0 ;
136138 }
137- setDimOut (DimOut );
139+ setDimOut (dimOut,precD );
138140 prepareBoundaries (bmin, bmax);
139141 defineGrid (npoints);
140142 setuserFunction (funName);
@@ -143,10 +145,10 @@ Chebyshev3D::Chebyshev3D(const char* funName, int DimOut, const Float_t* bmin, c
143145#endif
144146
145147#ifdef _INC_CREATION_Chebyshev3D_
146- Chebyshev3D::Chebyshev3D (void (*ptr)(float *, float *), int DimOut, Float_t* bmin, Float_t* bmax, Int_t* npoints,
147- Float_t prec )
148+ Chebyshev3D::Chebyshev3D (void (*ptr)(float *, float *), int dimOut, const Float_t* bmin, const Float_t* bmax,
149+ const Int_t* npoints, Float_t prec, const Float_t* precD )
148150 : mOutputArrayDimension(0 ),
149- mPrecision(TMath::Max(1 .E- 12f , prec)),
151+ mPrecision(TMath::Max(sMinimumPrecision , prec)),
150152 mChebyshevParameter(1 ),
151153 mMaxCoefficients(0 ),
152154 mTemporaryUserResults(0 ),
@@ -155,11 +157,7 @@ Chebyshev3D::Chebyshev3D(void (*ptr)(float*, float*), int DimOut, Float_t* bmin,
155157 mUserMacro(0 ),
156158 mLogger(FairLogger::GetLogger())
157159{
158- if (DimOut < 1 ) {
159- Error (" Chebyshev3D" , " Requested output dimension is %d\n Stop\n " , mOutputArrayDimension );
160- exit (1 );
161- }
162- if (DimOut < 1 ) {
160+ if (dimOut < 1 ) {
163161 Error (" Chebyshev3D" , " Requested output dimension is %d\n Stop\n " , mOutputArrayDimension );
164162 exit (1 );
165163 }
@@ -169,7 +167,7 @@ Chebyshev3D::Chebyshev3D(void (*ptr)(float*, float*), int DimOut, Float_t* bmin,
169167 mTemporaryChebyshevGridOffs [i] = 0 .;
170168 mTemporaryCoefficient [i] = 0 ;
171169 }
172- setDimOut (DimOut );
170+ setDimOut (dimOut,precD );
173171 prepareBoundaries (bmin, bmax);
174172 defineGrid (npoints);
175173 setuserFunction (ptr);
@@ -178,10 +176,10 @@ Chebyshev3D::Chebyshev3D(void (*ptr)(float*, float*), int DimOut, Float_t* bmin,
178176#endif
179177
180178#ifdef _INC_CREATION_Chebyshev3D_
181- Chebyshev3D::Chebyshev3D (void (*ptr)(float *, float *), int DimOut, Float_t* bmin, Float_t* bmax, Int_t* npX, Int_t* npY,
182- Int_t* npZ, Float_t prec)
179+ Chebyshev3D::Chebyshev3D (void (*ptr)(float *, float *), int dimOut, const Float_t* bmin, const Float_t* bmax,
180+ const Int_t* npX, const Int_t* npY, const Int_t* npZ, Float_t prec, const Float_t* precD )
183181 : mOutputArrayDimension(0 ),
184- mPrecision(TMath::Max(1 .E- 12f , prec)),
182+ mPrecision(TMath::Max(sMinimumPrecision , prec)),
185183 mChebyshevParameter(1 ),
186184 mMaxCoefficients(0 ),
187185 mTemporaryUserResults(0 ),
@@ -190,11 +188,7 @@ Chebyshev3D::Chebyshev3D(void (*ptr)(float*, float*), int DimOut, Float_t* bmin,
190188 mUserMacro(0 ),
191189 mLogger(FairLogger::GetLogger())
192190{
193- if (DimOut < 1 ) {
194- Error (" Chebyshev3D" , " Requested output dimension is %d\n Stop\n " , mOutputArrayDimension );
195- exit (1 );
196- }
197- if (DimOut < 1 ) {
191+ if (dimOut < 1 ) {
198192 Error (" Chebyshev3D" , " Requested output dimension is %d\n Stop\n " , mOutputArrayDimension );
199193 exit (1 );
200194 }
@@ -204,7 +198,7 @@ Chebyshev3D::Chebyshev3D(void (*ptr)(float*, float*), int DimOut, Float_t* bmin,
204198 mTemporaryChebyshevGridOffs [i] = 0 .;
205199 mTemporaryCoefficient [i] = 0 ;
206200 }
207- setDimOut (DimOut );
201+ setDimOut (dimOut,precD );
208202 prepareBoundaries (bmin, bmax);
209203 setuserFunction (ptr);
210204
@@ -218,10 +212,10 @@ Chebyshev3D::Chebyshev3D(void (*ptr)(float*, float*), int DimOut, Float_t* bmin,
218212#endif
219213
220214#ifdef _INC_CREATION_Chebyshev3D_
221- Chebyshev3D::Chebyshev3D (void (*ptr)(float *, float *), int DimOut, Float_t* bmin, Float_t* bmax, Float_t prec,
222- Bool_t run )
215+ Chebyshev3D::Chebyshev3D (void (*ptr)(float *, float *), int dimOut, const Float_t* bmin, const Float_t* bmax,
216+ Float_t prec, Bool_t run, const Float_t* precD )
223217 : mOutputArrayDimension(0 ),
224- mPrecision(TMath::Max(1 .E- 12f , prec)),
218+ mPrecision(TMath::Max(sMinimumPrecision , prec)),
225219 mChebyshevParameter(1 ),
226220 mMaxCoefficients(0 ),
227221 mTemporaryUserResults(0 ),
@@ -230,11 +224,11 @@ Chebyshev3D::Chebyshev3D(void (*ptr)(float*, float*), int DimOut, Float_t* bmin,
230224 mUserMacro(0 ),
231225 mLogger(FairLogger::GetLogger())
232226{
233- if (DimOut != 3 ) {
227+ if (dimOut != 3 ) {
234228 Error (" Chebyshev3D" , " This constructor works only for 3D fits, %dD fit was requested\n " , mOutputArrayDimension );
235229 exit (1 );
236230 }
237- if (DimOut < 1 ) {
231+ if (dimOut < 1 ) {
238232 Error (" Chebyshev3D" , " Requested output dimension is %d\n Stop\n " , mOutputArrayDimension );
239233 exit (1 );
240234 }
@@ -244,7 +238,7 @@ Chebyshev3D::Chebyshev3D(void (*ptr)(float*, float*), int DimOut, Float_t* bmin,
244238 mTemporaryChebyshevGridOffs [i] = 0 .;
245239 mTemporaryCoefficient [i] = 0 ;
246240 }
247- setDimOut (DimOut );
241+ setDimOut (dimOut, precD );
248242 prepareBoundaries (bmin, bmax);
249243 setuserFunction (ptr);
250244
@@ -458,7 +452,7 @@ Int_t Chebyshev3D::calculateChebyshevCoefficients(const Float_t* funval, int np,
458452#endif
459453
460454#ifdef _INC_CREATION_Chebyshev3D_
461- void Chebyshev3D::defineGrid (Int_t* npoints)
455+ void Chebyshev3D::defineGrid (const Int_t* npoints)
462456{
463457 // prepare the grid of Chebyshev roots in each dimension
464458 const int kMinPoints = 1 ;
@@ -519,15 +513,17 @@ Int_t Chebyshev3D::chebyshevFit(int dmOut)
519513 Float_t* tmpCoef2D = new Float_t[mNumberOfPoints [0 ] * mNumberOfPoints [1 ]];
520514 Float_t* tmpCoef1D = new Float_t[maxDim];
521515
522- Float_t rTiny = 0.1 * mPrecision / Float_t (maxDim); // neglect coefficient below this threshold
523-
524516 // 1D Cheb.fit for 0-th dimension at current steps of remaining dimensions
525517 int ncmax = 0 ;
526518
527519 printf (" Dim%d : 00.00%% Done" , dmOut);
528520 fflush (stdout);
529521 Chebyshev3DCalc* cheb = getChebyshevCalc (dmOut);
530522
523+ Float_t prec = cheb->getPrecision ();
524+ if (prec<sMinimumPrecision ) prec = mPrecision ; // no specific precision for this dim.
525+ Float_t rTiny = 0.1 * prec / Float_t (maxDim); // neglect coefficient below this threshold
526+
531527 float ncals2count = mNumberOfPoints [2 ] * mNumberOfPoints [1 ] * mNumberOfPoints [0 ];
532528 float ncals = 0 ;
533529 float frac = 0 ;
@@ -551,7 +547,7 @@ Int_t Chebyshev3D::chebyshevFit(int dmOut)
551547 fflush (stdout);
552548 }
553549 }
554- int nc = calculateChebyshevCoefficients (fvals, mNumberOfPoints [0 ], tmpCoef1D, mPrecision );
550+ int nc = calculateChebyshevCoefficients (fvals, mNumberOfPoints [0 ], tmpCoef1D, prec );
555551 for (int id0 = mNumberOfPoints [0 ]; id0--;) {
556552 tmpCoef2D[id1 + id0 * mNumberOfPoints [1 ]] = tmpCoef1D[id0];
557553 }
@@ -579,7 +575,7 @@ Int_t Chebyshev3D::chebyshevFit(int dmOut)
579575 }
580576
581577 // now find 2D surface which separates significant coefficients of 3D matrix from nonsignificant ones (up to
582- // mPrecision )
578+ // prec )
583579 UShort_t* tmpCoefSurf = new UShort_t[mNumberOfPoints [0 ] * mNumberOfPoints [1 ]];
584580 for (int id0 = mNumberOfPoints [0 ]; id0--;) {
585581 for (int id1 = mNumberOfPoints [1 ]; id1--;) {
@@ -597,7 +593,7 @@ Int_t Chebyshev3D::chebyshevFit(int dmOut)
597593 continue ;
598594 } // neglect coefs below the threshold
599595 resid += cfa;
600- if (resid < mPrecision ) {
596+ if (resid < prec ) {
601597 continue ; // this coeff is negligible
602598 }
603599 // otherwise go back 1 step
@@ -638,9 +634,9 @@ Int_t Chebyshev3D::chebyshevFit(int dmOut)
638634 nRows--;
639635 }
640636 // find max significant column and fill the permanent storage for the max sigificant column of each row
641- cheb->initRows (nRows); // create needed arrays;
637+ cheb->initializeRows (nRows); // create needed arrays;
642638 UShort_t* nColsAtRow = cheb->getNumberOfColumnsAtRow ();
643- UShort_t* colAtRowBg = cheb->GetColAtRowBg ();
639+ UShort_t* colAtRowBg = cheb->getColAtRowBg ();
644640 int nCols = 0 ;
645641 int nElemBound2D = 0 ;
646642 for (int id0 = 0 ; id0 < nRows; id0++) {
@@ -651,12 +647,12 @@ Int_t Chebyshev3D::chebyshevFit(int dmOut)
651647 nCols = nColsAtRow[id0];
652648 }
653649 }
654- cheb->initCols (nCols);
650+ cheb->initializeColumns (nCols);
655651 delete[] tmpCols;
656652
657653 // create the 2D matrix defining the boundary of significance for 3D coeffs.matrix
658654 // and count the number of siginifacnt coefficients
659- cheb->InitElemBound2D (nElemBound2D);
655+ cheb->initializeElementBound2D (nElemBound2D);
660656 UShort_t* coefBound2D0 = cheb->getCoefficientBound2D0 ();
661657 UShort_t* coefBound2D1 = cheb->getCoefficientBound2D1 ();
662658 mMaxCoefficients = 0 ; // redefine number of coeffs
@@ -821,7 +817,7 @@ void Chebyshev3D::loadData(FILE* stream)
821817 }
822818}
823819
824- void Chebyshev3D::setDimOut (const int d)
820+ void Chebyshev3D::setDimOut (const int d, const float * prec )
825821{
826822 // init output dimensions
827823 mOutputArrayDimension = d;
@@ -831,6 +827,8 @@ void Chebyshev3D::setDimOut(const int d)
831827 mTemporaryUserResults = new Float_t[mOutputArrayDimension ];
832828 mChebyshevParameter .Delete ();
833829 for (int i = 0 ; i < d; i++) {
830+ Chebyshev3DCalc* clc = new Chebyshev3DCalc ();
831+ clc->setPrecision (prec && prec[i]>sMinimumPrecision ? prec[i] : mPrecision );
834832 mChebyshevParameter .AddAtAndExpand (new Chebyshev3DCalc (), i);
835833 }
836834}
@@ -860,6 +858,10 @@ TH1* Chebyshev3D::TestRMS(int idim, int npoints, TH1* histo)
860858 if (!histo) {
861859 histo = new TH1D (GetName (), " Control: Function - Parametrization" , 100 , -2 * mPrecision , 2 * mPrecision );
862860 }
861+
862+ float prc = getChebyshevCalc (idim)->getPrecision ();
863+ if (prc<sMinimumPrecision ) prc = mPrecision ; // no dimension specific precision
864+
863865 for (int ip = npoints; ip--;) {
864866 gRandom ->RndmArray (3 , (Float_t*)mTemporaryCoefficient );
865867 for (int i = 3 ; i--;) {
@@ -877,7 +879,7 @@ TH1* Chebyshev3D::TestRMS(int idim, int npoints, TH1* histo)
877879
878880#ifdef _INC_CREATION_Chebyshev3D_
879881
880- void Chebyshev3D::estimateNumberOfPoints (float Prec , int gridBC[3 ][3 ], Int_t npd1, Int_t npd2, Int_t npd3)
882+ void Chebyshev3D::estimateNumberOfPoints (float prec , int gridBC[3 ][3 ], Int_t npd1, Int_t npd2, Int_t npd3)
881883{
882884 // Estimate number of points to generate a training data
883885 const int kScp = 9 ;
@@ -904,7 +906,7 @@ void Chebyshev3D::estimateNumberOfPoints(float Prec, int gridBC[3][3], Int_t npd
904906 xyz[id1] = mMinBoundaries [id1] + kScl [i1] * (mMaxBoundaries [id1] - mMinBoundaries [id1]);
905907 for (int i2 = 0 ; i2 < kScp ; i2++) {
906908 xyz[id2] = mMinBoundaries [id2] + kScl [i2] * (mMaxBoundaries [id2] - mMinBoundaries [id2]);
907- int * npt = getNcNeeded (xyz, idim, dimMN, dimMX, Prec , npdTst[idim]); // npoints for Bx,By,Bz
909+ int * npt = getNcNeeded (xyz, idim, dimMN, dimMX, prec , npdTst[idim]); // npoints for Bx,By,Bz
908910 for (int ib = 0 ; ib < 3 ; ib++) {
909911 if (npt[ib] > gridBC[ib][idim]) {
910912 gridBC[ib][idim] = npt[ib];
0 commit comments