Go to the documentation of this file.00001 #ifndef OPENTISSUE_CORE_MATH_INTERPOLATION_INTERPOLATION_POLYNOMIAL_INTERPOLATOR_H
00002 #define OPENTISSUE_CORE_MATH_INTERPOLATION_INTERPOLATION_POLYNOMIAL_INTERPOLATOR_H
00003
00004
00005
00006
00007
00008
00009
00010 #include <OpenTissue/configuration.h>
00011
00012 #include <OpenTissue/core/math/interpolation/interpolation_base_interpolator.h>
00013
00014
00015 namespace OpenTissue
00016 {
00017
00018 namespace interpolation
00019 {
00020
00032 template<typename real_type_>
00033 class PolynomialInterpolator : public BaseInterpolator< PolynomialInterpolator<real_type_>, real_type_ >
00034 {
00035 public:
00036
00037 typedef real_type_ real_type;
00038
00039 private:
00040
00041 real_type m_error;
00042 int m_n;
00043 real_type * m_xa;
00044 real_type * m_ya;
00045 real_type * m_C;
00046 real_type * m_D;
00047
00048 public:
00049
00050 PolynomialInterpolator()
00051 : m_error(0.0)
00052 , m_n(-1)
00053 , m_xa(0)
00054 , m_ya(0)
00055 , m_C(0)
00056 , m_D(0)
00057 {}
00058
00059 ~PolynomialInterpolator()
00060 {
00061 if(m_C)
00062 delete [] m_C;
00063 if(m_D)
00064 delete [] m_D;
00065 }
00066
00074 void set_tableau(real_type * x,real_type * y,int cnt)
00075 {
00076
00077 this->m_xa = x;
00078 this->m_ya = y;
00079
00080
00081 if(m_C==0)
00082 {
00083 m_C = new real_type[cnt];
00084 m_D = new real_type[cnt];
00085 }
00086 else if(cnt<m_n)
00087 {
00088 delete [] m_C;
00089 m_C = new real_type[cnt];
00090 delete [] m_D;
00091 m_D = new real_type[cnt];
00092 }
00093 this->m_n = cnt;
00094 }
00095
00105 real_type get_value(real_type const & x)
00106 {
00107
00108
00109
00110 real_type diff = static_cast<real_type>( std::fabs(x-m_xa[0]) );
00111 int ns = 0;
00112 m_D[0] = m_C[0] = m_ya[0];
00113 for(int i=1;i<m_n;++i)
00114 {
00115 real_type test = static_cast<real_type>( std::fabs(x-m_xa[i]) );
00116 if(test<diff)
00117 {
00118 ns = i;
00119 diff = test;
00120 }
00121 m_C[i] = m_D[i] = m_ya[i];
00122 }
00123
00124
00125 real_type y = m_ya[ns];
00126
00127 for(int m=1;m<m_n;++m)
00128 {
00129 for(int i=0;i<(m_n-m);++i)
00130 {
00131 real_type ho = m_xa[i] - x;
00132
00133
00134
00135
00136 real_type hp = m_xa[i+m] - x;
00137 real_type w = m_C[i+1]-m_D[i];
00138 real_type denominator= ho-hp;
00139
00140 if(denominator==0)
00141 {
00142
00143 std::cerr << "PolynomialInterpolator::get_value(): Unexpected internal error, unable to compute!" << std::endl;
00144 return static_cast<real_type>(0.0);
00145 }
00146 denominator = w / denominator;
00147
00148
00149
00150
00151
00152 m_D[i] = hp*denominator;
00153
00154
00155
00156
00157
00158 m_C[i] = ho*denominator;
00159 }
00160
00161
00162
00163
00164 if((2*ns)<(m_n-m))
00165 {
00166 m_error = m_C[ns];
00167 }
00168 else
00169 {
00170 ns = ns - 1;
00171 m_error = m_D[ns];
00172 }
00173 y += m_error;
00174 }
00175
00176 return y;
00177 }
00178
00184 real_type get_error_estimate()const { return m_error;}
00185
00186 };
00187
00188 }
00189
00190 }
00191
00192
00193 #endif