29 plumed_assert( fmin.size()==dd.size() && fmax.size()==dd.size() );
31 np.resize( dd.size() );
stride.resize( dd.size() );
unsigned totalp=1;
32 for(
unsigned i=0;i<dd.size();++i){
np[i]=dd[i];
stride[dd.size()-1-i]=totalp; totalp*=
np[i]; }
36 std::vector<double> delr(
np.size() );
37 for(
unsigned j=0;j<
np.size();++j) delr[j] = ( fmax[j] - fmin[j] )/
static_cast<double>(
np[j]-1);
39 for(
unsigned i=0;i<totalp;++i){
41 for(
unsigned j=0;j<
np.size();++j){
42 kk=std::floor(
double(ii) /
double(
stride[j]) );
48 lb.resize(
np.size() );
ub.resize(
np.size() );
56 nspline.resize(
np.size() );
57 for(
unsigned i=0;i<
np.size();++i) nspline[i]=
np[i];
61 plumed_dbg_massert( pos.size()==
np.size(),
"position size does not match the size of the grid");
63 unsigned jold, ccf_box, bnew=0;
64 for(
unsigned i=0;i<
np.size();++i){
65 jold=
static_cast<int>( std::floor(
double(
bold)/
double(
stride[i]) ) );
67 ccf_box=
search1( i, pos[i], jold );
70 plumed_dbg_assert(
bold==0 );
bold=bnew;
76 int inc=
stride[kk], jl=jold*
stride[kk], ju=(jold+1)*stride[kk], jm;
83 else if( ju>=(
np[kk]-1)*inc ){ju=(
np[kk]-1)*inc;
break; }
92 else if( jl<=0 ){ jl=0;
break; }
98 jm = (ju+jl) / (2*inc) ;
99 if ( x>
splinepoints(jm*inc,kk) ) jl=jm*inc;
else ju=jm*inc;
101 plumed_dbg_assert( jl%stride[kk]==0 && ju==jl+stride[kk] );
108 plumed_massert(
np.size()==1,
"should be one dimensional data");
114 plumed_assert( ff[0].getNumberOfDerivatives()==1 );
116 double d1,
norm;
unsigned pij;
117 for(
unsigned i=0;i<
np[0]-1;++i){
119 norm=(d1*d1)/6.0; pij=i*4;
120 clist[pij]=ff[i].get(); pij++;
121 clist[pij]=ff[i+1].get(); pij++;
122 clist[pij]=ff[i].getDerivative(0)*
norm; pij++;
123 clist[pij]=ff[i+1].getDerivative(0)*
norm;
128 plumed_dbg_assert( pos.size()==1 );
131 double d1=
ub[0] -
lb[0];
132 double b=( pos[0] - lb[0] ) / d1,
a=(
ub[0] - pos[0] ) / d1;
134 double *cbase=&
clist[(mybox*4)+3], *c3=cbase-1, *c2=c3-1, *c1=c2-1;
135 double f=
a*(*c1) + b*(*c2) + (
a*
a*
a-
a)*(*c3) + (b*b*b-b)*(*cbase);
142 plumed_massert(
np.size()==2,
"should be two dimensional data");
143 static int wt_d[16*16]=
144 {1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
145 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0,
146 -3, 0, 0, 3, 0, 0, 0, 0,-2, 0, 0,-1, 0, 0, 0, 0,
147 2, 0, 0,-2, 0, 0, 0, 0, 1, 0, 0, 1, 0, 0, 0, 0,
148 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
149 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0,
150 0, 0, 0, 0,-3, 0, 0, 3, 0, 0, 0, 0,-2, 0, 0,-1,
151 0, 0, 0, 0, 2, 0, 0,-2, 0, 0, 0, 0, 1, 0, 0, 1,
152 -3, 3, 0, 0,-2,-1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
153 0, 0, 0, 0, 0, 0, 0, 0,-3, 3, 0, 0,-2,-1, 0, 0,
154 9,-9, 9,-9, 6, 3,-3,-6, 6,-6,-3, 3, 4, 2, 1, 2,
155 -6, 6,-6, 6,-4,-2, 2, 4,-3, 3, 3,-3,-2,-1,-1,-2,
156 2,-2, 0, 0, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
157 0, 0, 0, 0, 0, 0, 0, 0, 2,-2, 0, 0, 1, 1, 0, 0,
158 -6, 6,-6, 6,-3,-3, 3, 3,-4, 4, 2,-2,-2,-2,-1,-1,
159 4,-4, 4,-4, 2, 2,-2,-2, 2,-2,-2, 2, 1, 1, 1, 1};
162 unsigned l=0;
wt.
resize(16,16);
t1.resize(16);
t2.resize(16);
163 for (
unsigned i=0;i<16;i++)
for (
unsigned j=0;j<16;j++){
wt(i,j)=wt_d[l++]; }
170 plumed_assert( ff[0].getNumberOfDerivatives()==2 );
172 dcross=0.0;
unsigned iplus, iminus;
173 for(
unsigned i=1;i<
np[0]-1;++i){
175 for(
unsigned j=1;j<np[1]-1;++j){
176 dcross(i,j) = ( ff[iplus+j+1].get() + ff[iminus+j-1].get() - ff[iplus+j-1].get() - ff[iminus+j+1].get() ) /
182 std::vector<double> y(4), dy1(4), dy2(4), d2y12(4);
184 unsigned pij=0;
unsigned ipos;
185 for (
unsigned i=0;i<np[0]-1;++i){
187 for (
unsigned j=0; j<np[1]-1;++j){
189 y[0] = ff[ipos+j].get(); y[1] = ff[ipos+stride[0]+j].get(); y[2] = ff[ipos+stride[0]+j+1].get(); y[3] = ff[ipos+j+1].get();
190 dy1[0] = ff[ipos+j].getDerivative(0); dy1[1] = ff[ipos+stride[0]+j].getDerivative(0);
191 dy1[2] = ff[ipos+stride[0]+j+1].getDerivative(0); dy1[3] = ff[ipos+j+1].getDerivative(0);
192 dy2[0] = ff[ipos+j].getDerivative(1); dy2[1] = ff[ipos+stride[0]+j].getDerivative(1);
193 dy2[2] = ff[ipos+stride[0]+j+1].getDerivative(1); dy2[3] = ff[ipos+j+1].getDerivative(1);
195 IBicCoeff( y, dy1, dy2, d2y12, d1, d2, tc);
198 for(
unsigned k=0; k<4; ++k){
for(
unsigned n=0;
n<4; ++
n){
clist[pij++]=tc(k,
n); } }
204 const std::vector<double>& d2y12,
const double& d1,
const double& d2,
Matrix<double>& c ){
205 double xx, d1d2=d1*d2;
206 for(
unsigned i=0;i<4;i++){
t1[i] = y[i];
t1[i+4] = dy1[i]*d1;
t1[i+8] = dy2[i]*d2;
t1[i+12] = d2y12[i]*d1d2; }
207 for(
unsigned i=0;i<16;i++){ xx=0.0;
for(
unsigned k=0;k<16;k++){ xx +=
wt(i,k)*
t1[k]; }
t2[i]=xx; }
208 unsigned l=0;
for(
unsigned i=0;i<4;i++){
for(
unsigned j=0;j<4;j++){ c(i,j)=
t2[l++]; } }
213 plumed_dbg_assert( pos.size()==2 );
215 double d1 =
ub[0] -
lb[0], d2 =
ub[1] - lb[1];
216 double t = (pos[0] - lb[0]) / d1, u = (pos[1] - lb[1]) / d2;
219 double *cbase=&
clist[(mybox+1)*16-1], *c3, *c2, *c1, *c0;
222 for (
int i=3; i>=0; i--) {
223 c3=cbase; c2=c3-1; c1=c2-1; c0=c1-1; cbase=c0-1;
224 f= t*f + ( ( (*c3)*u + (*c2) )*u + (*c1) )*u + (*c0);
226 delete cbase;
delete c3;
delete c2;
delete c1;
delete c0;
double getPointSpacing(const unsigned dir, const unsigned k) const
virtual ~CInterpolation()
Matrix< double > splinepoints
double getCrossTermDenominator(const unsigned i, const unsigned j) const
InterpolateBicubic(const std::vector< unsigned > &dd, const std::vector< double > &fmin, const std::vector< double > &fmax)
double get_fdf(const std::vector< double > &pos)
std::vector< double > clist
void set_table(const std::vector< Value > &ff)
void getNumbersOfPoints(std::vector< unsigned > &nspline) const
std::vector< unsigned > np
unsigned findBox(const std::vector< double > &pos)
unsigned search1(const unsigned &kk, const double &x, const unsigned &jold) const
std::vector< unsigned > stride
double get_fdf(const std::vector< double > &pos)
unsigned getNumberOfSplinePoints() const
std::vector< double > clist
void resize(const unsigned nr, const unsigned nc)
Resize the matrix.
void set_table(const std::vector< Value > &ff)
CInterpolation(const std::vector< unsigned > &dd, const std::vector< double > &fmin, const std::vector< double > &fmax)
void IBicCoeff(const std::vector< double > &y, const std::vector< double > &dy1, const std::vector< double > &dy2, const std::vector< double > &d2y12, const double &d1, const double &d2, Matrix< double > &c)
InterpolateCubic(const std::vector< unsigned > &dd, const std::vector< double > &fmin, const std::vector< double > &fmax)
T norm(const std::vector< T > &A)
Calculate the dot product between a vector and itself.