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

volume.hh

00001 // Copyright (C) 2007, 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_ACCU_SHAPE_VOLUME_HH
00027 # define MLN_ACCU_SHAPE_VOLUME_HH
00028 
00032 
00043 # include <mln/accu/internal/base.hh>
00044 # include <mln/core/concept/meta_accumulator.hh>
00045 # include <mln/math/diff_abs.hh>
00046 
00047 # include <mln/util/pix.hh>
00048 # include <mln/literal/zero.hh>
00049 
00050 namespace mln
00051 {
00052 
00053   namespace accu
00054   {
00055 
00056     namespace shape
00057     {
00058 
00065       template <typename I>
00066       struct volume
00067         : public mln::accu::internal::base< unsigned , volume<I> >
00068       {
00076         typedef util::pix<I> argument;
00078         typedef typename argument::value value;
00079 
00080         volume();
00081 
00084         void init();
00085         void take(const argument& pixel);
00086         void take(const volume<I>& other);
00087 
00089         void set_value(unsigned v);
00091 
00093         unsigned to_result() const;
00094 
00097         bool is_valid() const;
00098 
00099       protected:
00101         value ref_level__;
00103         unsigned area__;
00105         unsigned volume_;
00106       };
00107 
00108 
00109     } // end of mln::accu::shape
00110 
00111 
00112     namespace meta
00113     {
00114 
00115       namespace shape
00116       {
00117 
00119 
00120         struct volume : public Meta_Accumulator< volume >
00121         {
00122           template <typename I>
00123           struct with
00124           {
00125             typedef accu::shape::volume<I> ret;
00126           };
00127         };
00128 
00129       } // end of namespace mln::accu::meta::shape
00130 
00131     } // end of namespace mln::accu::meta
00132 
00133 # ifndef MLN_INCLUDE_ONLY
00134 
00135     namespace shape
00136     {
00137 
00138       template <typename I>
00139       inline
00140       volume<I>::volume()
00141       {
00142         init();
00143       }
00144 
00145       template <typename I>
00146       inline
00147       void
00148       volume<I>::init()
00149       {
00150         ref_level__ = literal::zero;
00151         volume_ = 0;
00152         area__ = 0;
00153       }
00154 
00155       template <typename I>
00156       inline
00157       void
00158       volume<I>::take(const argument& pixel)
00159       {
00160         /* FIXME: Growing a component using this particular `take'
00161         routine won't work, since the update does not take care of
00162         the reference level to compute the new volume.  Maybe we
00163         could distinguish two cases:
00164 
00165         1. the empty accumulator case (which corresponds to the
00166         following code);
00167         2. the non-empty accumulator case (which sohuld act as in
00168         `take(const volume<I>& other)').
00169 
00170         Currently, the implementation is only valid if the
00171         accumulator was initialy empty before the call to
00172         `take(const argument&)'.  */
00173         ref_level__ = pixel.v();
00174         ++area__;
00175         ++volume_;
00176       }
00177 
00178       template <typename I>
00179       inline
00180       void
00181       volume<I>::take(const volume<I>& other)
00182       {
00183         area__ += other.area__;
00184         /* FIXME: Is it `t.area__' or `area__' ? Théo said it was
00185         the latter, but both the ISMM 2005 paper and Olena 0.11 use
00186         the former.  */
00187         volume_ +=
00188           other.volume_  +
00189           other.area__ * mln::math::diff_abs(other.ref_level__, ref_level__);
00190         // Member ref_level__ is not touched.
00191       }
00192 
00193       template <typename I>
00194       inline
00195       unsigned
00196       volume<I>::to_result() const
00197       {
00198         return volume_;
00199       }
00200 
00201       template <typename I>
00202       inline
00203       void
00204       volume<I>::set_value(unsigned v)
00205       {
00206         volume_ = v;
00207         // Reset the other members.
00208         ref_level__ = literal::zero;
00209         area__ = 0;
00210       }
00211 
00212       template <typename I>
00213       inline
00214       bool
00215       volume<I>::is_valid() const
00216       {
00217         return true;
00218       }
00219 
00220     } // end of namespace mln::accu::shape
00221 
00222 # endif // ! MLN_INCLUDE_ONLY
00223 
00224   } // end of namespace mln::accu
00225 
00226 } // end of namespace mln
00227 
00228 
00229 #endif // ! MLN_ACCU_SHAPE_VOLUME_HH

Generated on Tue Oct 4 2011 15:25:08 for Milena (Olena) by  doxygen 1.7.1