contrib/mul/vil3d/algo/vil3d_exp_filter.h
Go to the documentation of this file.
00001 #ifndef vil3d_exp_filter_h_
00002 #define vil3d_exp_filter_h_
00003 //:
00004 // \file
00005 // \brief Apply exponential filter to 3D images
00006 // \author Tim Cootes
00007 
00008 #include <vil/algo/vil_exp_filter_1d.h>
00009 #include <vil3d/vil3d_image_view.h>
00010 #include <vil3d/vil3d_switch_axes.h>
00011 
00012 //: Apply exponential filter along i to src_im to produce dest_im
00013 //  Symmetric exponential filter of the form exp(c*|i|) applied. c=log(kf)
00014 //  Uses fast recursive implementation.
00015 // \relatesalso vil_image_view
00016 template <class srcT, class destT, class accumT>
00017 inline void vil3d_exp_filter_i(const vil3d_image_view<srcT>& src_im,
00018                                vil3d_image_view<destT>& dest_im,
00019                                accumT kf)
00020 {
00021   unsigned ni = src_im.ni();
00022   unsigned nj = src_im.nj();
00023   unsigned nk = src_im.nk();
00024   dest_im.set_size(ni,nj,nk,src_im.nplanes());
00025   vcl_ptrdiff_t s_istep = src_im.istep(), s_jstep = src_im.jstep();
00026   vcl_ptrdiff_t s_kstep = src_im.kstep();
00027   vcl_ptrdiff_t d_istep = dest_im.istep(),d_jstep = dest_im.jstep();
00028   vcl_ptrdiff_t d_kstep = dest_im.kstep();
00029 
00030   for (unsigned p=0;p<src_im.nplanes();++p)
00031   {
00032     const srcT*  src_slice  = src_im.origin_ptr()+p*src_im.planestep();
00033     destT* dest_slice = dest_im.origin_ptr()+p*dest_im.planestep();
00034     // Filter slice
00035     for (unsigned k=0;k<nk;++k,src_slice+=s_kstep,dest_slice+=d_kstep)
00036     {
00037       const srcT* src_row = src_slice;
00038       destT* dest_row = dest_slice;
00039       // Filter each row
00040       for (unsigned j=0;j<nj;++j,src_row+=s_jstep,dest_row+=d_jstep)
00041         vil_exp_filter_1d(src_row,s_istep, dest_row,d_istep,   ni, kf);
00042     }
00043   }
00044 }
00045 
00046 //: Apply exponential filter along each axis of src_im in turn
00047 //  Symmetric exponential filter of the form exp(c*|i|) applied. 
00048 //  c=log(ki) along i, log(kj) along j, log(kk) along k.
00049 //  Uses fast recursive implementation.
00050 // \relatesalso vil_image_view
00051 template <class srcT, class destT, class accumT>
00052 inline void vil3d_exp_filter(const vil3d_image_view<srcT>& src_im,
00053                              vil3d_image_view<destT>& dest_im,
00054                              accumT ki, accumT kj, accumT kk)
00055 {
00056   // Smooth along i axis
00057   vil3d_image_view<destT> smooth_i;
00058   vil3d_exp_filter_i(src_im,smooth_i,ki);
00059 
00060   // Smooth along j axis
00061   vil3d_image_view<destT> smooth_j;
00062   vil3d_exp_filter_i(vil3d_switch_axes_jik(smooth_i),
00063                      smooth_j,kj);
00064     // Note that smooth_j is nj * ni * nk
00065 
00066   // Smooth along k axis
00067   dest_im.set_size(src_im.ni(),src_im.nj(),src_im.nk(),src_im.nplanes());
00068   vil3d_image_view<destT> dest_kij = vil3d_switch_axes_kij(dest_im);
00069 
00070   // Use of vil3d_switch_axes_kji ensures axes are nk*ni*nj to match dest_kij
00071   vil3d_exp_filter_i(vil3d_switch_axes_kji(smooth_j), dest_kij,kk);
00072 }
00073 
00074 //: Apply exponential filter along each axis of src_im in turn
00075 //  Symmetric exponential filter of the form exp(c*|i|) applied. c=log(kf)
00076 //  Uses fast recursive implementation.
00077 // \relatesalso vil_image_view
00078 template <class srcT, class destT, class accumT>
00079 inline void vil3d_exp_filter(const vil3d_image_view<srcT>& src_im,
00080                              vil3d_image_view<destT>& dest_im,
00081                              accumT kf)
00082 {
00083   vil3d_exp_filter(src_im,dest_im,kf,kf,kf);
00084 }
00085 
00086 #endif // vil3d_exp_filter_h_