ChangeLog | 10 ++++++
oln/level/arith.hh | 34 ++++++++++++++++++++
tests/level/tests/arith_and_conversion | 55 +++++++++++++++++++++++++++++++++
3 files changed, 99 insertions(+)
Index: olena/ChangeLog
from Roland Levillain <roland(a)lrde.epita.fr>
Add level::minus taking a conversion function.
* oln/level/arith.hh
(minus (const convert::abstract::conversion<C, B>&,
const abstract::image<I1>&, const abstract::image<I2>& input2)):
New.
* tests/level/tests/arith_and_conversion: New test.
2005-06-23 Roland Levillain <roland(a)lrde.epita.fr>
Index: olena/oln/level/arith.hh
--- olena/oln/level/arith.hh (révision 216)
+++ olena/oln/level/arith.hh (copie de travail)
@@ -35,6 +35,7 @@
# include <oln/core/apply.hh>
# include <oln/ops/arith.hh>
+# include <oln/convert/conversion.hh>
# include <oln/utils/clone.hh>
@@ -169,6 +170,39 @@
return output;
}
+ // Variant taking a conversion function in parameter.
+ template <typename C, typename B, typename I1, typename I2>
+ typename ch_value_type<I1, typename convoutput<C, B, typename
arith_output<f_::minus_, I1, I2>::T>::ret>::ret
+ minus (const convert::abstract::conversion<C, B>& conv,
+ const abstract::image<I1>& input1,
+ const abstract::image<I2>& input2)
+ {
+ mlc::eq<oln_type_of(I1, grid), oln_type_of(I2, grid)>::ensure();
+
+ entering("level::minus");
+ registering(input1, "input1");
+ registering(input2, "input2");
+
+ precondition(input1.size() == input2.size());
+
+ typedef oln_type_of(I1, value) T1;
+ typedef oln_type_of(I2, value) T2;
+
+ // The return type, if there were no conversion.
+ typedef typename arith_output<f_::minus_, I1, I2>::T oper_output_type;
+ // The actual return type.
+ typedef typename
+ ch_value_type<I1,
+ typename convoutput<C, B, oper_output_type>::ret>::ret
+ output_type;
+ output_type output("output");
+ output = apply2(convert::compconv2(conv, f_::minus_<T1, T2>()),
+ input1, input2);
+
+ exiting("level::minus");
+ return output;
+ }
+
// times
Index: olena/tests/level/tests/arith_and_conversion
--- olena/tests/level/tests/arith_and_conversion (révision 0)
+++ olena/tests/level/tests/arith_and_conversion (révision 0)
@@ -0,0 +1,55 @@
+ // -*- C++ -*-
+#include <ntg/int.hh>
+#include <oln/basics2d.hh>
+#include <oln/convert/force.hh>
+#include <oln/level/arith.hh>
+#include <oln/level/fill.hh>
+#include <oln/level/compare.hh>
+
+using namespace oln;
+
+
+// FIXME: Not safe, nor generic. Re-introduce static initialization
+// in Olena and use it instead.
+template<typename T>
+image2d<T>
+image_from_array(coord_t nrows, coord_t ncols, T values[])
+{
+ image2d<T> output(nrows, ncols);
+ unsigned i = 0;
+ oln_type_of(image2d<T>, fwd_piter) p(output.size());
+ for_all_p (p)
+ {
+ output[p] = values[i];
+ ++i;
+ }
+ return output;
+}
+
+
+bool check()
+{
+ typedef ntg::int_u8 value_type;
+
+ value_type ima1_values[] = { 2, 8, 2,
+ 3, 4, 5,
+ 6, 7, 8 };
+ image2d<value_type> ima1 = image_from_array<value_type>(3, 3,
ima1_values);
+
+ image2d<value_type> ima2(3, 3);
+ level::fill(ima2, 2);
+
+ // Checking level::minus, with convert::force conversion.
+ {
+ image2d<value_type> diff =
+ level::minus(convert::force<value_type>(), ima1, ima2);
+ value_type diff_ref[] = { 0, 6, 0,
+ 1, 2, 3,
+ 4, 5, 6 };
+ if (not level::is_equal(diff,
+ image_from_array<value_type>(3, 3, diff_ref)))
+ return true;
+ }
+
+ return false;
+}