Go to the documentation of this file.00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017 #ifndef __itkBSplineDerivativeKernelFunction2_h
00018 #define __itkBSplineDerivativeKernelFunction2_h
00019
00020 #include "itkKernelFunction.h"
00021 #include "vnl/vnl_math.h"
00022
00023
00024 namespace itk
00025 {
00026
00042 template <unsigned int VSplineOrder = 3>
00043 class ITK_EXPORT BSplineDerivativeKernelFunction2 : public KernelFunction
00044 {
00045 public:
00047 typedef BSplineDerivativeKernelFunction2 Self;
00048 typedef KernelFunction Superclass;
00049 typedef SmartPointer<Self> Pointer;
00050
00052 itkNewMacro(Self);
00053
00055 itkTypeMacro(BSplineDerivativeKernelFunction2, KernelFunction);
00056
00058 itkStaticConstMacro(SplineOrder, unsigned int, VSplineOrder);
00059
00061
00062
00063
00064
00065
00067 inline double Evaluate( const double & u ) const
00068 {
00069 return this->Evaluate( Dispatch<VSplineOrder>(), u );
00070 }
00071
00072 protected:
00073 BSplineDerivativeKernelFunction2(){};
00074 ~BSplineDerivativeKernelFunction2(){};
00075
00076 void PrintSelf(std::ostream& os, Indent indent) const
00077 {
00078 Superclass::PrintSelf( os, indent );
00079 os << indent << "Spline Order: " << SplineOrder << std::endl;
00080 }
00081
00082 private:
00083 BSplineDerivativeKernelFunction2(const Self&);
00084 void operator=(const Self&);
00085
00087 struct DispatchBase {};
00088 template<unsigned int>
00089 struct Dispatch : DispatchBase {};
00090
00113 inline double Evaluate ( const Dispatch<1>&, const double& u) const
00114 {
00115
00116 double absValue = vnl_math_abs( u );
00117
00118 if ( absValue < 1.0 )
00119 {
00120 return -vnl_math_sgn( u );
00121 }
00122 else if ( absValue == 1.0 )
00123 {
00124 return -vnl_math_sgn( u ) / 2.0;
00125 }
00126 else
00127 {
00128 return 0.0;
00129 }
00130
00131 }
00132
00134 inline double Evaluate ( const Dispatch<2>&, const double& u) const
00135 {
00136 double absValue = vnl_math_abs( u );
00137
00138 if ( absValue < 0.5 )
00139 {
00140 return -2.0 * u;
00141 }
00142 else if ( absValue < 1.5 )
00143 {
00144 return u - 1.5 * vnl_math_sgn( u );
00145 }
00146 else
00147 {
00148 return 0.0;
00149 }
00150
00151 }
00152
00154 inline double Evaluate ( const Dispatch<3>&, const double& u) const
00155 {
00156 const double absValue = vnl_math_abs( u );
00157 const double sqrValue = vnl_math_sqr( u );
00158
00159 if ( absValue < 1.0 )
00160 {
00161 if ( u > 0.0)
00162 {
00163 const double dummy = vnl_math_abs( u + 0.5 );
00164 return ( 6.0 * sqrValue - 2.0 * u - 6.0 * dummy + 3.0 ) / 4.0;
00165 }
00166 else
00167 {
00168 const double dummy = vnl_math_abs( u - 0.5 );
00169 return -( 6.0 * sqrValue + 2.0 * u - 6.0 * dummy + 3.0 ) / 4.0;
00170 }
00171 }
00172 else if ( absValue < 2.0 )
00173 {
00174 if ( u > 0.0 )
00175 {
00176 const double dummy = vnl_math_abs( u - 0.5 );
00177 return ( u - sqrValue + 3.0 * dummy - 2.5 ) / 2.0;
00178 }
00179 else
00180 {
00181 const double dummy = vnl_math_abs( u + 0.5 );
00182 return ( u + sqrValue - 3.0 * dummy + 2.5 ) / 2.0;
00183 }
00184 }
00185 else
00186 {
00187 return 0.0;
00188 }
00189
00190 }
00191
00193 inline double Evaluate ( const DispatchBase&, const double&) const
00194 {
00195 itkExceptionMacro("Evaluate not implemented for spline\
00196 order " << SplineOrder);
00197 return 0.0;
00198
00199 }
00200
00201 };
00202
00203
00204 }
00205
00206 #endif