$extrastylesheet
Olena  User documentation 2.1
An Image Processing Platform
 All Classes Namespaces Functions Variables Typedefs Enumerations Enumerator Friends Groups Pages
influence_zone_geodesic.hh
1 // Copyright (C) 2008, 2009, 2011, 2012 EPITA Research and Development
2 // Laboratory (LRDE)
3 //
4 // This file is part of Olena.
5 //
6 // Olena is free software: you can redistribute it and/or modify it under
7 // the terms of the GNU General Public License as published by the Free
8 // Software Foundation, version 2 of the License.
9 //
10 // Olena is distributed in the hope that it will be useful,
11 // but WITHOUT ANY WARRANTY; without even the implied warranty of
12 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 // General Public License for more details.
14 //
15 // You should have received a copy of the GNU General Public License
16 // along with Olena. If not, see <http://www.gnu.org/licenses/>.
17 //
18 // As a special exception, you may use this file as part of a free
19 // software project without restriction. Specifically, if other files
20 // instantiate templates or use macros or inline functions from this
21 // file, or you compile this file and link it with other files to produce
22 // an executable, this file does not by itself cause the resulting
23 // executable to be covered by the GNU General Public License. This
24 // exception does not however invalidate any other reasons why the
25 // executable file might be covered by the GNU General Public License.
26 
27 #ifndef MLN_TRANSFORM_INFLUENCE_ZONE_GEODESIC_HH
28 # define MLN_TRANSFORM_INFLUENCE_ZONE_GEODESIC_HH
29 
33 
34 # include <mln/extension/adjust.hh>
35 # include <mln/canvas/distance_geodesic.hh>
36 # include <mln/transform/internal/influence_zone_functor.hh>
37 
38 
39 namespace mln
40 {
41 
42  namespace transform
43  {
44 
54  template <typename I, typename N>
55  mln_concrete(I)
56  influence_zone_geodesic(const Image<I>& input, const Neighborhood<N>& nbh);
57 
58 
59 
60 # ifndef MLN_INCLUDE_ONLY
61 
62 
63  namespace internal
64  {
65 
66  template <typename I, typename N>
67  void
68  influence_zone_geodesic_tests(const Image<I>& input,
69  const Neighborhood<N>& nbh)
70  {
71  mln_precondition(exact(input).is_valid());
72  mln_precondition(exact(nbh).is_valid());
73 
74  (void) input;
75  (void) nbh;
76  }
77 
78  } // end of namespace mln::transform::internal
79 
80 
81  namespace impl
82  {
83 
84  namespace generic
85  {
86 
87  template <typename I, typename N>
88  mln_concrete(I)
89  influence_zone_geodesic(const Image<I>& input,
90  const Neighborhood<N>& nbh)
91  {
92  (void) input;
93  (void) nbh;
94 
95  // FIXME: To be written...
96  mlc_abort(I)::check();
97  }
98 
99  } // end of namespace mln::transform::impl::generic
100 
101 
102  template <typename I, typename N>
103  mln_concrete(I)
104  influence_zone_geodesic_fastest(const Image<I>& input_,
105  const Neighborhood<N>& nbh_)
106  {
107  mln_trace("transform::impl::influence_zone_geodesic_fastest");
108 
109  const I& input = exact(input_);
110  const N& nbh = exact(nbh_);
111 
112  internal::influence_zone_geodesic_tests(input, nbh);
113 
114  std::queue<mln_value(I)*> q;
115  mln_concrete(I) output;
116 
117  util::array<int> dp = offsets_wrt(input, nbh);
118  const unsigned n_nbhs = dp.nelements();
119 
120  // Initialization.
121  {
122  extension::adjust(input, nbh);
123  output = duplicate(input);
124  // For the extension to be ignored:
125  extension::fill(input, 0); // in initialization
126  extension::fill(output, 1); // in propagation
127 
128  const unsigned nelts = input.nelements();
129  const mln_value(I)* p_i = input.buffer();
130  mln_value(I)* p_o = output.buffer();
131  for (unsigned i = 0; i < nelts; ++i, ++p_i, ++p_o)
132  {
133  if (*p_i == 0)
134  continue;
135  for (unsigned j = 0; j < n_nbhs; ++j)
136  {
137  const mln_value(I)* n_i = p_i + dp[j];
138  if (*n_i == 0)
139  {
140  q.push(p_o);
141  break;
142  }
143  }
144  }
145 
146  }
147 
148  // Propagation.
149  {
150  mln_value(I)* ptr;
151 
152  while (! q.empty())
153  {
154  ptr = q.front();
155  q.pop();
156  mln_invariant(*ptr != 0);
157  for (unsigned j = 0; j < n_nbhs; ++j)
158  {
159  mln_value(I)* ntr = ptr + dp[j];
160  if (*ntr == 0)
161  {
162  *ntr = *ptr;
163  q.push(ntr);
164  }
165  }
166  }
167  }
168 
169  return output;
170  }
171 
172 
173  } // end of namespace mln::transform::impl
174 
175 
176  namespace internal
177  {
178 
179  template <typename I, typename N>
180  mln_concrete(I)
181  influence_zone_geodesic_dispatch(trait::image::value_alignment::any,
182  trait::image::value_storage::any,
183  trait::image::value_access::any,
184  const I& input,
185  const N& nbh)
186  {
187  return impl::generic::influence_zone_geodesic(input, nbh);
188  }
189 
190 
191  template <typename I, typename N>
192  mln_concrete(I)
193  influence_zone_geodesic_dispatch(trait::image::value_alignment::with_grid,
194  trait::image::value_storage::one_block,
195  trait::image::value_access::direct,
196  const I& input,
197  const N& nbh)
198  {
199  return impl::influence_zone_geodesic_fastest(input, nbh);
200  }
201 
202 
203  template <typename I, typename N>
204  mln_concrete(I)
205  influence_zone_geodesic_dispatch(const Image<I>& input,
206  const Neighborhood<N>& nbh)
207  {
208  return
209  influence_zone_geodesic_dispatch(mln_trait_image_value_alignment(I)(),
210  mln_trait_image_value_storage(I)(),
211  mln_trait_image_value_access(I)(),
212  exact(input), exact(nbh));
213  }
214 
215  } // end of namespace mln::transform::internal
216 
217 
218  template <typename I, typename N>
219  mln_concrete(I)
220  influence_zone_geodesic(const Image<I>& input, const Neighborhood<N>& nbh)
221  {
222  mln_trace("transform::influence_zone_geodesic");
223 
224  internal::influence_zone_geodesic_tests(input, nbh);
225 
226  mln_concrete(I)
227  output = internal::influence_zone_geodesic_dispatch(input, nbh);
228 
229  return output;
230  }
231 
232 # endif // ! MLN_INCLUDE_ONLY
233 
234  } // end of namespace mln::transform
235 
236 } // end of namespace mln
237 
238 
239 #endif // ! MLN_TRANSFORM_INFLUENCE_ZONE_GEODESIC_HH