Milena (Olena)  User documentation 2.0a Id
 All Classes Namespaces Functions Variables Typedefs Enumerator Groups Pages
vertical_symmetry.hh
1 // Copyright (C) 2010 EPITA Research and Development Laboratory (LRDE)
2 //
3 // This file is part of Olena.
4 //
5 // Olena is free software: you can redistribute it and/or modify it under
6 // the terms of the GNU General Public License as published by the Free
7 // Software Foundation, version 2 of the License.
8 //
9 // Olena is distributed in the hope that it will be useful,
10 // but WITHOUT ANY WARRANTY; without even the implied warranty of
11 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 // General Public License for more details.
13 //
14 // You should have received a copy of the GNU General Public License
15 // along with Olena. If not, see <http://www.gnu.org/licenses/>.
16 //
17 // As a special exception, you may use this file as part of a free
18 // software project without restriction. Specifically, if other files
19 // instantiate templates or use macros or inline functions from this
20 // file, or you compile this file and link it with other files to produce
21 // an executable, this file does not by itself cause the resulting
22 // executable to be covered by the GNU General Public License. This
23 // exception does not however invalidate any other reasons why the
24 // executable file might be covered by the GNU General Public License.
25 
29 
30 #ifndef MLN_GEOM_VERTICAL_SYMMETRY_HH
31 # define MLN_GEOM_VERTICAL_SYMMETRY_HH
32 
33 # include <mln/core/concept/image.hh>
34 # include <mln/core/box_runend_piter.hh>
35 # include <mln/core/box_runstart_piter.hh>
36 
37 namespace mln
38 {
39 
40  namespace geom
41  {
42 
44  //
45  template <typename I>
46  mln_concrete(I)
47  vertical_symmetry(const Image<I>& input);
48 
49 
50 # ifndef MLN_INCLUDE_ONLY
51 
52 
53  // Implementations
54 
55  namespace impl
56  {
57 
58  namespace generic
59  {
60 
61  template <typename I>
62  mln_concrete(I)
63  vertical_symmetry(const Image<I>& input_)
64  {
65  const I& input = exact(input_);
66  mln_precondition(input.is_valid());
67 
68  mln_concrete(I) output(input.domain());
69 
70  typedef mln_site(I) P;
71  box_runstart_piter<P>
72  pi(input.domain()),
73  po(output.domain());
74 
75  unsigned ncols = input.ncols();
76 
77  for_all_2(pi, po)
78  {
79  mln_site(I) idi = pi, ido = po;
80  ido[1] = ncols - 1;
81  for (unsigned n = 0; n < ncols; ++n, ++idi[1], --ido[1])
82  output(ido) = input(idi);
83  }
84 
85  return output;
86  }
87 
88  } // end of namespace mln::geom::impl::generic
89 
90 
91  template <typename I>
92  mln_concrete(I)
93  vertical_symmetry_fastest(const Image<I>& input_)
94  {
95  const I& input = exact(input_);
96  mln_precondition(input.is_valid());
97 
98  mln_concrete(I) output(input.domain());
99 
100  typedef mln_site(I) P;
101  box_runstart_piter<P>
102  pi(input.domain()),
103  po(output.domain());
104 
105  unsigned ncols = input.ncols();
106 
107  typedef mln_value(I)* ptr_t;
108 
109  for_all_2(pi, po)
110  {
111  const mln_value(I)* ptr_in = & input(pi);
112  ptr_t ptr_out = (& output(po)) + ncols - 1;
113 
114  for (unsigned n = 0; n < ncols; ++n)
115  *ptr_out-- = *ptr_in++;
116  }
117 
118  return output;
119  }
120 
121 
122  } // end of namespace mln::geom::impl
123 
124 
125 
126  // Dispatch
127 
128  namespace internal
129  {
130 
131  template <typename I>
132  mln_concrete(I)
133  vertical_symmetry_dispatch(
134  trait::image::value_alignment::any,
135  trait::image::value_storage::any,
136  trait::image::value_access::any,
137  const Image<I>& input)
138  {
139  return impl::generic::vertical_symmetry(input);
140  }
141 
142 
143  template <typename I>
144  mln_concrete(I)
145  vertical_symmetry_dispatch(
146  trait::image::value_alignment::with_grid,
147  trait::image::value_storage::one_block,
148  trait::image::value_access::direct,
149  const Image<I>& input)
150  {
151  return impl::vertical_symmetry_fastest(input);
152  }
153 
154 
155  template <typename I>
156  mln_concrete(I)
157  vertical_symmetry_dispatch(const Image<I>& input)
158  {
159  return vertical_symmetry_dispatch(
160  mln_trait_image_value_alignment(I)(),
161  mln_trait_image_value_storage(I)(),
162  mln_trait_image_value_access(I)(),
163  input);
164  }
165 
166  } // end of namespace mln::geom::internal
167 
168 
169 
170  // Facade
171 
172  template <typename I>
173  mln_concrete(I)
174  vertical_symmetry(const Image<I>& input_)
175  {
176  trace::entering("geom::vertical_symmetry");
177 
178  const I& input = exact(input_);
179  mln_precondition(input.is_valid());
180 
181  mln_concrete(I) output = internal::vertical_symmetry_dispatch(input);
182 
183  trace::exiting("geom::vertical_symmetry");
184  return output;
185  }
186 
187 
188 # endif // ! MLN_INCLUDE_ONLY
189 
190 
191  } // end of namespace mln::geom
192 
193 } // end of namespace mln
194 
195 
196 #endif // ! MLN_GEOM_VERTICAL_SYMMETRY_HH