• Main Page
  • Related Pages
  • Modules
  • Namespaces
  • Classes
  • Files
  • File List

multiple_size.hh

00001 // Copyright (C) 2008, 2009 EPITA Research and Development Laboratory (LRDE)
00002 //
00003 // This file is part of Olena.
00004 //
00005 // Olena is free software: you can redistribute it and/or modify it under
00006 // the terms of the GNU General Public License as published by the Free
00007 // Software Foundation, version 2 of the License.
00008 //
00009 // Olena is distributed in the hope that it will be useful,
00010 // but WITHOUT ANY WARRANTY; without even the implied warranty of
00011 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
00012 // General Public License for more details.
00013 //
00014 // You should have received a copy of the GNU General Public License
00015 // along with Olena.  If not, see <http://www.gnu.org/licenses/>.
00016 //
00017 // As a special exception, you may use this file as part of a free
00018 // software project without restriction.  Specifically, if other files
00019 // instantiate templates or use macros or inline functions from this
00020 // file, or you compile this file and link it with other files to produce
00021 // an executable, this file does not by itself cause the resulting
00022 // executable to be covered by the GNU General Public License.  This
00023 // exception does not however invalidate any other reasons why the
00024 // executable file might be covered by the GNU General Public License.
00025 
00026 #ifndef MLN_WIN_MULTIPLE_SIZE_HH
00027 # define MLN_WIN_MULTIPLE_SIZE_HH
00028 
00034 
00035 # include <mln/core/internal/window_base.hh>
00036 # include <mln/core/internal/site_relative_iterator_base.hh>
00037 # include <mln/util/array.hh>
00038 # include <mln/metal/ands.hh>
00039 
00040 
00041 
00042 namespace mln
00043 {
00044 
00045   // Forward declarations.
00046   namespace win
00047   {
00048     template <unsigned n, typename W, typename F> class multiple_size;
00049     template <unsigned n, typename W, typename F> class multiple_size_qiter;
00050   }
00051 
00052 
00053 
00054   namespace trait
00055   {
00056 
00057     template <unsigned n, typename W, typename F>
00058     struct window_< win::multiple_size<n,W,F> >
00059     {
00060       typedef trait::window::size::unknown     size;
00061       typedef trait::window::support::regular  support;
00062       typedef trait::window::definition::n_ary definition;
00063     };
00064 
00065   } // end of namespace trait
00066 
00067 
00068 
00069   namespace win
00070   {
00071 
00075     //
00076     template <unsigned n, typename W, typename F>
00077     class multiple_size
00078 
00079       : public internal::window_base< mln_dpsite(W), multiple_size<n,W,F> >,
00080 
00081         private metal::ands< mlc_bool(n > 1),
00082                              mlc_is(mln_trait_window_size(W),
00083                                     trait::window::size::fixed),
00084                              mlc_is(mln_trait_window_support(W),
00085                                     trait::window::support::regular) >::check_t
00086     {
00087     public:
00088 
00089       typedef mln_dpsite(W) dpsite;
00090       typedef  mln_psite(W)  psite;
00091       typedef   mln_site(W)   site;
00092 
00093       typedef multiple_size< n, window<dpsite>, F > regular;
00094 
00095       typedef multiple_size_qiter<n,W,F> fwd_qiter;
00096       typedef multiple_size_qiter<n,W,F> bkd_qiter;
00097       typedef multiple_size_qiter<n,W,F> qiter;
00098 
00099       typedef W element;
00100 
00101       multiple_size();
00102 
00103       multiple_size(const F& f);
00104 
00105       bool is_empty() const;
00106 
00107       void set_window(unsigned i, const W& win);
00108 
00109       const W& window_(unsigned i) const;
00110 
00111       unsigned nwindows() const;
00112 
00113       const F& function() const;
00114 
00115       unsigned size_around(const mln_psite(W)& p) const;
00116 
00117       const mln_dpsite(W)& ith_dp_around(unsigned i, const mln_psite(W)& p) const;
00118 
00119       bool is_centered() const;
00120 
00121       bool is_symmetric() const;
00122 
00123       void sym();
00124 
00125       unsigned delta() const;
00126 
00127     private:
00128 
00129       util::array<W> win_;
00130       F f_;
00131     };
00132 
00133 
00134     template <unsigned n, typename W, typename F>
00135     class multiple_size_qiter
00136       : public internal::site_relative_iterator_base< multiple_size<n,W,F>,
00137                                                       multiple_size_qiter<n,W,F> >
00138     {
00139       typedef multiple_size_qiter<n,W,F> self_;
00140       typedef internal::site_relative_iterator_base< multiple_size<n,W,F>, self_ > super_;
00141     public:
00142 
00143       multiple_size_qiter();
00144 
00145       template <typename P>
00146       multiple_size_qiter(const multiple_size<n,W,F>& w, const P& c);
00147 
00149       bool is_valid_() const;
00150 
00152       void invalidate_();
00153 
00155       void do_start_();
00156 
00158       void do_next_();
00159 
00161       mln_psite(W) compute_p_() const;
00162 
00163     private:
00164       int i_;
00165       int size_() const;
00166     };
00167 
00168 
00169 
00170 # ifndef MLN_INCLUDE_ONLY
00171 
00172     // win::multiple_size<n,W,F>
00173 
00174     template <unsigned n, typename W, typename F>
00175     inline
00176     multiple_size<n,W,F>::multiple_size()
00177       : f_()
00178     {
00179     }
00180 
00181     template <unsigned n, typename W, typename F>
00182     inline
00183     multiple_size<n,W,F>::multiple_size(const F& f)
00184       : f_(f)
00185     {
00186     }
00187 
00188     template <unsigned n, typename W, typename F>
00189     inline
00190     bool
00191     multiple_size<n,W,F>::is_empty() const
00192     {
00193       return win_.is_empty();
00194     }
00195 
00196     template <unsigned n, typename W, typename F>
00197     inline
00198     void
00199     multiple_size<n,W,F>::set_window(unsigned i, const W& win)
00200     {
00201       mln_precondition(i == win_.nelements());
00202       win_.append(win);
00203     }
00204 
00205     template <unsigned n, typename W, typename F>
00206     inline
00207     const W&
00208     multiple_size<n,W,F>::window_(unsigned i) const
00209     {
00210       mln_precondition(i < win_.nelements());
00211       return win_[i];
00212     }
00213 
00214     template <unsigned n, typename W, typename F>
00215     inline
00216     unsigned
00217     multiple_size<n,W,F>::nwindows() const
00218     {
00219       return win_.nelements();
00220     }
00221 
00222     template <unsigned n, typename W, typename F>
00223     inline
00224     const F&
00225     multiple_size<n,W,F>::function() const
00226     {
00227       return f_;
00228     }
00229 
00230     template <unsigned n, typename W, typename F>
00231     inline
00232     bool
00233     multiple_size<n,W,F>::is_centered() const
00234     {
00235       mln_precondition(win_.nelements() >= 1);
00236       for (unsigned i = 0; i < win_.nelements(); ++i)
00237         if (! win_[i].is_centered())
00238           return false;
00239       return true;
00240     }
00241 
00242     template <unsigned n, typename W, typename F>
00243     inline
00244     bool
00245     multiple_size<n,W,F>::is_symmetric() const
00246     {
00247       mln_precondition(win_.nelements() >= 1);
00248       for (unsigned i = 0; i < win_.nelements(); ++i)
00249         if (! win_[i].is_symmetric())
00250           return false;
00251       return true;
00252     }
00253 
00254     template <unsigned n, typename W, typename F>
00255     inline
00256     void
00257     multiple_size<n,W,F>::sym()
00258     {
00259       mln_precondition(win_.nelements() >= 1);
00260       for (unsigned i = 0; i < win_.nelements(); ++i)
00261         win_[i].sym();
00262     }
00263 
00264     template <unsigned n, typename W, typename F>
00265     inline
00266     unsigned
00267     multiple_size<n,W,F>::delta() const
00268     {
00269       mln_precondition(win_.nelements() >= 1);
00270       unsigned d = win_[0].delta();
00271       for (unsigned i = 1; i < win_.nelements(); ++i)
00272         {
00273           unsigned d_i = win_[i].delta();
00274           if (d_i > d)
00275             d = d_i;
00276         }
00277       return d;
00278     }
00279 
00280     template <unsigned n, typename W, typename F>
00281     inline
00282     unsigned
00283     multiple_size<n,W,F>::size_around(const mln_psite(W)& p) const
00284     {
00285       mln_precondition(win_.nelements() >= 2);
00286       mln_precondition(f_(p) < win_.nelements());
00287       return win_[f_(p)].size();
00288     }
00289 
00290     template <unsigned n, typename W, typename F>
00291     inline
00292     const mln_dpsite(W)&
00293     multiple_size<n,W,F>::ith_dp_around(unsigned i, const mln_psite(W)& p) const
00294     {
00295       mln_precondition(win_.nelements() >= 2);
00296       mln_precondition(f_(p) < win_.nelements());
00297       mln_precondition(i < win_[f_(p)].size());
00298       return win_[f_(p)].dp(i);
00299     }
00300 
00301 
00302     // win::multiple_size_qiter<n,W,F>
00303 
00304     template <unsigned n, typename W, typename F>
00305     inline
00306     multiple_size_qiter<n,W,F>::multiple_size_qiter()
00307     {
00308     }
00309 
00310     template <unsigned n, typename W, typename F>
00311     template <typename P>
00312     inline
00313     multiple_size_qiter<n,W,F>::multiple_size_qiter(const multiple_size<n,W,F>& w, const P& c)
00314     {
00315       this->center_at(c);
00316       // We have to first change the center so that 'invalidate' can
00317       // work when changing the target.
00318       this->change_target(w);
00319     }
00320 
00321     template <unsigned n, typename W, typename F>
00322     inline
00323     bool
00324     multiple_size_qiter<n,W,F>::is_valid_() const
00325     {
00326       return i_ != -1 && i_ < size_();
00327     }
00328 
00329     template <unsigned n, typename W, typename F>
00330     inline
00331     void
00332     multiple_size_qiter<n,W,F>::invalidate_()
00333     {
00334       i_ = -1;
00335     }
00336 
00337     template <unsigned n, typename W, typename F>
00338     inline
00339     void
00340     multiple_size_qiter<n,W,F>::do_start_()
00341     {
00342       i_ = 0;
00343     }
00344 
00345     template <unsigned n, typename W, typename F>
00346     inline
00347     void
00348     multiple_size_qiter<n,W,F>::do_next_()
00349     {
00350       ++i_;
00351     }
00352 
00353     template <unsigned n, typename W, typename F>
00354     inline
00355     mln_psite(W)
00356     multiple_size_qiter<n,W,F>::compute_p_() const
00357     {
00358       return *this->c_ + this->s_->ith_dp_around(i_, *this->c_);
00359     }
00360 
00361     template <unsigned n, typename W, typename F>
00362     inline
00363     int
00364     multiple_size_qiter<n,W,F>::size_() const
00365     {
00366       return int(this->s_->size_around(*this->c_));
00367     }
00368 
00369 # endif // ! MLN_INCLUDE_ONLY
00370 
00371 
00372   } // end of namespace mln::win
00373 
00374 } // end of namespace mln
00375 
00376 
00377 #endif // ! MLN_WIN_MULTIPLE_SIZE_HH

Generated on Thu Sep 8 2011 18:32:09 for Milena (Olena) by  doxygen 1.7.1