Milena (Olena)
User documentation 2.0a Id
|
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_DATA_TRANSFORM_INPLACE_HH 00027 # define MLN_DATA_TRANSFORM_INPLACE_HH 00028 00034 00035 # include <mln/core/concept/image.hh> 00036 # include <mln/core/concept/function.hh> 00037 # include <mln/value/set.hh> 00038 # include <mln/value/lut_vec.hh> 00039 # include <mln/opt/value.hh> 00040 00041 00042 namespace mln 00043 { 00044 00045 namespace data 00046 { 00047 00057 template <typename I, typename F> 00058 void 00059 transform_inplace(Image<I>& ima, const Function_v2v<F>& f); 00060 00061 00072 template <typename I1, typename I2, typename F> 00073 void 00074 transform_inplace(Image<I1>& ima, const Image<I2>& aux, 00075 const Function_vv2v<F>& f); 00076 00077 00078 00079 # ifndef MLN_INCLUDE_ONLY 00080 00081 00082 // Tests. 00083 00084 namespace internal 00085 { 00086 00087 template <typename I, typename F> 00088 inline 00089 void transform_inplace_tests(const Image<I>& ima, 00090 const Function_v2v<F>& f) 00091 { 00092 // Properties checks. 00093 mlc_or(mlc_is(mln_trait_image_pw_io(I), 00094 trait::image::pw_io::read_write), 00095 mlc_is(mln_trait_image_vw_io(I), 00096 trait::image::vw_io::read_write))::check(); 00097 mlc_converts_to(mln_result(F), mln_value(I))::check(); 00098 00099 // Dynamic test. 00100 mln_precondition(exact(ima).is_valid()); 00101 00102 // Avoid a warning. 00103 (void) ima; 00104 (void) f; 00105 } 00106 00107 template <typename I1, typename I2, typename F> 00108 inline 00109 void transform_inplace_tests(Image<I1>& ima, 00110 const Image<I2>& aux, 00111 const Function_vv2v<F>& f) 00112 { 00113 // Properties checks. 00114 mlc_or(mlc_is(mln_trait_image_pw_io(I1), 00115 trait::image::pw_io::read_write), 00116 mlc_is(mln_trait_image_vw_io(I1), 00117 trait::image::vw_io::read_write))::check(); 00118 mlc_converts_to(mln_result(F), mln_value(I1))::check(); 00119 00120 // Dynamic test. 00121 mln_precondition(exact(ima).is_valid()); 00122 mln_precondition(exact(aux).is_valid()); 00123 mln_precondition(exact(aux).domain() == exact(ima).domain()); 00124 00125 // Avoid warnings. 00126 (void) ima; 00127 (void) aux; 00128 (void) f; 00129 } 00130 00131 } // end of namespace mln::data::internal 00132 00133 00134 namespace impl 00135 { 00136 00137 // Generic implementations. 00138 00139 namespace generic 00140 { 00141 00146 // 00147 template <typename I, typename F> 00148 void 00149 transform_inplace(Image<I>& ima_, const Function_v2v<F>& f_) 00150 { 00151 trace::entering("data::impl::generic::transform_inplace"); 00152 00153 mlc_is(mln_trait_image_pw_io(I), 00154 trait::image::pw_io::read_write)::check(); 00155 00156 I& ima = exact(ima_); 00157 const F& f = exact(f_); 00158 00159 internal::transform_inplace_tests(ima, f); 00160 00161 mln_piter(I) p(ima.domain()); 00162 for_all(p) 00163 ima(p) = f(ima(p)); 00164 00165 trace::exiting("data::impl::generic::transform_inplace"); 00166 } 00167 00173 // 00174 template <typename I1, typename I2, typename F> 00175 void 00176 transform_inplace(Image<I1>& ima_, const Image<I2>& aux_, 00177 const Function_vv2v<F>& f_) 00178 { 00179 trace::entering("data::impl::generic::transform_inplace"); 00180 00181 mlc_is(mln_trait_image_pw_io(I1), 00182 trait::image::pw_io::read_write)::check(); 00183 00184 I1& ima = exact(ima_); 00185 const I2& aux = exact(aux_); 00186 const F& f = exact(f_); 00187 00188 internal::transform_inplace_tests(ima, aux, f); 00189 00190 mln_piter(I1) p(ima.domain()); 00191 for_all(p) 00192 ima(p) = f(ima(p), aux(p)); 00193 00194 trace::exiting("data::impl::generic::transform_inplace"); 00195 } 00196 00197 } // end of namespace mln::data::impl::generic 00198 00200 00201 template <typename I, typename F> 00202 void 00203 transform_inplace_lowq(Image<I>& input_, 00204 const Function_v2v<F>& f_) 00205 { 00206 trace::entering("data::impl::transform_inplace_lowq"); 00207 00208 mlc_is(mln_trait_image_pw_io(I), 00209 trait::image::pw_io::read_write)::check(); 00210 00211 I& input = exact(input_); 00212 const F& f = exact(f_); 00213 00214 internal::transform_inplace_tests(input, f); 00215 00216 value::lut_vec<mln_vset(I), mln_result(F)> 00217 lut(input.values_eligible(), f); 00218 00219 mln_piter(I) p(input.domain()); 00220 for_all(p) 00221 input(p) = lut(input(p)); 00222 00223 trace::exiting("data::impl::transform_inplace_lowq"); 00224 } 00225 00226 template <typename I, typename F> 00227 void 00228 transform_inplace_taken(Image<I>& input_, 00229 const Function_v2v<F>& f_) 00230 { 00231 trace::entering("data::impl::transform_inplace_taken"); 00232 00233 mlc_is(mln_trait_image_pw_io(I), 00234 trait::image::pw_io::read_write)::check(); 00235 00236 I& input = exact(input_); 00237 const F& f = exact(f_); 00238 00239 internal::transform_inplace_tests(input, f); 00240 00241 value::lut_vec<mln_vset(I), mln_result(F)> 00242 lut(input.taken_values(), f); 00243 00244 mln_piter(I) p(input.domain()); 00245 for_all(p) 00246 input(p) = lut(input(p)); 00247 00248 trace::exiting("data::impl::transform_inplace_taken"); 00249 } 00250 00251 00252 template <typename I, typename F> 00253 void 00254 transform_inplace_singleton(Image<I>& input_, 00255 const Function_v2v<F>& f_) 00256 { 00257 trace::entering("data::impl::transform_inplace_singleton"); 00258 00259 I& input = exact(input_); 00260 const F& f = exact(f_); 00261 00262 internal::transform_inplace_tests(input, f); 00263 00264 opt::value(input) = f(opt::value(input)); 00265 00266 trace::exiting("data::impl::transform_inplace_singleton"); 00267 } 00268 00269 template <typename I, typename F> 00270 void 00271 transform_inplace_fastest(Image<I>& ima_, const Function_v2v<F>& f_) 00272 { 00273 trace::entering("data::impl::transform_inplace_fastest"); 00274 00275 I& ima = exact(ima_); 00276 const F& f = exact(f_); 00277 00278 internal::transform_inplace_tests(ima, f); 00279 00280 mln_pixter(I) p(ima); 00281 for_all(p) 00282 p.val() = f(p.val()); 00283 00284 trace::exiting("data::impl::transform_inplace_fastest"); 00285 } 00286 00287 00288 template <typename I, typename F> 00289 void 00290 transform_inplace_fastest_lowq(Image<I>& input_, 00291 const Function_v2v<F>& f_) 00292 { 00293 trace::entering("data::impl::transform_inplace_fastest_lowq"); 00294 00295 I& input = exact(input_); 00296 const F& f = exact(f_); 00297 00298 internal::transform_inplace_tests(input, f); 00299 00300 value::lut_vec<mln_vset(I), mln_result(F)> 00301 lut(input.values_eligible(), f); 00302 00303 mln_pixter(I) pi(input); 00304 for_all(pi) 00305 pi.val() = lut(pi.val()); 00306 00307 trace::exiting("data::impl::transform_inplace_fastest_lowq"); 00308 } 00309 00310 00311 template <typename I1, typename I2, typename F> 00312 void 00313 transform_inplace_fastest(Image<I1>& ima_, const Image<I2>& aux_, 00314 const Function_vv2v<F>& f_) 00315 { 00316 trace::entering("data::impl::transform_inplace_fastest"); 00317 00318 mlc_is(mln_trait_image_pw_io(I1), 00319 trait::image::pw_io::read_write)::check(); 00320 00321 I1& ima = exact(ima_); 00322 const I2& aux = exact(aux_); 00323 const F& f = exact(f_); 00324 00325 internal::transform_inplace_tests(ima, aux, f); 00326 00327 mln_pixter(I1) pi(ima); 00328 mln_pixter(const I2) pa(aux); 00329 for_all_2(pi, pa) 00330 pi.val() = f(pi.val(), pa.val()); 00331 00332 trace::exiting("data::impl::transform_inplace_fastest"); 00333 } 00334 00335 00336 } // end of namespace mln::data::impl 00337 00338 00339 00340 // Dispatch. 00341 00342 namespace internal 00343 { 00344 00345 // (ima, f) version. 00346 00348 template <typename I, typename F> 00349 void 00350 transform_inplace_dispatch(trait::image::vw_set::any, 00351 trait::image::quant::any, 00352 Image<I>& ima, const Function_v2v<F>& f) 00353 { 00354 data::impl::generic::transform_inplace(ima, f); 00355 } 00356 00357 template <typename I, typename F> 00358 void 00359 transform_inplace_dispatch(trait::image::vw_set::uni, 00360 trait::image::quant::any, 00361 Image<I>& ima, const Function_v2v<F>& f) 00362 { 00363 data::impl::transform_inplace_taken(ima, f); 00364 } 00365 00366 template <typename I, typename F> 00367 void 00368 transform_inplace_dispatch(trait::image::vw_set::any, 00369 trait::image::quant::low, 00370 Image<I>& ima, const Function_v2v<F>& f) 00371 { 00372 data::impl::transform_inplace_lowq(ima, f); 00373 } 00374 00375 00376 00378 template <typename I, typename F> 00379 void 00380 transform_inplace_dispatch_fast(trait::image::quant::any, 00381 Image<I>& ima, const Function_v2v<F>& f) 00382 { 00383 data::impl::transform_inplace_fastest(ima, f); 00384 } 00385 00386 template <typename I, typename F> 00387 void 00388 transform_inplace_dispatch_fast(trait::image::quant::low, 00389 Image<I>& ima, const Function_v2v<F>& f) 00390 { 00391 data::impl::transform_inplace_fastest_lowq(ima, f); 00392 } 00393 00394 00395 00396 00398 template <typename I, typename F> 00399 void 00400 transform_inplace_dispatch(trait::image::value_storage::any, 00401 trait::image::value_access::any, 00402 Image<I>& ima, const Function_v2v<F>& f) 00403 { 00404 transform_inplace_dispatch(mln_trait_image_vw_set(I)(), 00405 mln_trait_image_quant(I)(), 00406 ima, f); 00407 } 00408 00409 template <typename I, typename F> 00410 void 00411 transform_inplace_dispatch(trait::image::value_storage::singleton, 00412 trait::image::value_access::any, 00413 Image<I>& ima, const Function_v2v<F>& f) 00414 { 00415 data::impl::transform_inplace_singleton(ima, f); 00416 } 00417 00418 00419 template <typename I, typename F> 00420 void 00421 transform_inplace_dispatch(trait::image::value_storage::one_block, 00422 trait::image::value_access::direct, 00423 Image<I>& ima, const Function_v2v<F>& f) 00424 { 00425 transform_inplace_dispatch_fast(mln_trait_image_quant(I)(), 00426 ima, f); 00427 } 00428 00429 00430 00431 00433 template <typename I, typename F> 00434 void 00435 transform_inplace_dispatch(Image<I>& ima, const Function_v2v<F>& f) 00436 { 00437 transform_inplace_dispatch(mln_trait_image_value_storage(I)(), 00438 mln_trait_image_value_access(I)(), 00439 ima, f); 00440 } 00441 00442 00443 00444 // (ima, aux, f) version. 00445 00446 template <typename I1, typename I2, typename F> 00447 void 00448 transform_inplace_dispatch(trait::image::value_alignment::any, 00449 trait::image::value_alignment::any, 00450 trait::image::speed::any, 00451 trait::image::speed::any, 00452 Image<I1>& ima, const Image<I2>& aux, 00453 const Function_vv2v<F>& f) 00454 { 00455 data::impl::generic::transform_inplace(ima, aux, f); 00456 } 00457 00458 template <typename I1, typename I2, typename F> 00459 void 00460 transform_inplace_dispatch(trait::image::value_alignment::with_grid, 00461 trait::image::value_alignment::with_grid, 00462 trait::image::speed::fastest, 00463 trait::image::speed::fastest, 00464 Image<I1>& ima, const Image<I2>& aux, 00465 const Function_vv2v<F>& f) 00466 { 00467 data::impl::transform_inplace_fastest(ima, aux, f); 00468 } 00469 00470 template <typename I1, typename I2, typename F> 00471 void 00472 transform_inplace_dispatch(Image<I1>& ima, const Image<I2>& aux, 00473 const Function_vv2v<F>& f) 00474 { 00475 transform_inplace_dispatch(mln_trait_image_value_alignment(I1)(), 00476 mln_trait_image_value_alignment(I2)(), 00477 mln_trait_image_speed(I1)(), 00478 mln_trait_image_speed(I2)(), 00479 ima, aux, f); 00480 } 00481 00482 } // end of namespace mln::data::internal 00483 00484 00485 00486 // Facades. 00487 00488 template <typename I, typename F> 00489 void 00490 transform_inplace(Image<I>& ima, const Function_v2v<F>& f) 00491 { 00492 trace::entering("data::transform_inplace"); 00493 00494 internal::transform_inplace_tests(ima, f); 00495 internal::transform_inplace_dispatch(ima, f); 00496 00497 trace::exiting("data::transform_inplace"); 00498 } 00499 00500 template <typename I1, typename I2, typename F> 00501 void 00502 transform_inplace(Image<I1>& ima, const Image<I2>& aux, 00503 const Function_vv2v<F>& f) 00504 { 00505 trace::entering("data::transform_inplace"); 00506 00507 internal::transform_inplace_tests(ima, aux, f); 00508 internal::transform_inplace_dispatch(ima, aux, f); 00509 00510 trace::exiting("data::transform_inplace"); 00511 } 00512 00513 00514 # endif // ! MLN_INCLUDE_ONLY 00515 00516 } // end of namespace mln::data 00517 00518 } // end of namespace mln 00519 00520 00521 #endif // ! MLN_DATA_TRANSFORM_INPLACE_HH