]>
Commit | Line | Data |
---|---|---|
7c673cae FG |
1 | /* Boost test/test_float.cpp |
2 | * test arithmetic operations on a range of intervals | |
3 | * | |
4 | * Copyright 2003 Guillaume Melquiond | |
5 | * | |
6 | * Distributed under the Boost Software License, Version 1.0. | |
7 | * (See accompanying file LICENSE_1_0.txt or | |
8 | * copy at http://www.boost.org/LICENSE_1_0.txt) | |
9 | */ | |
10 | ||
11 | #include <boost/numeric/interval.hpp> | |
1e59de90 | 12 | #include <boost/core/lightweight_test.hpp> |
7c673cae FG |
13 | #include <boost/config.hpp> |
14 | #include "bugs.hpp" | |
15 | ||
16 | /* All the following tests should be BOOST_CHECK; however, if a test fails, | |
17 | the probability is high that hundreds of other tests will fail, so it is | |
18 | replaced by BOOST_REQUIRE to avoid flooding the logs. */ | |
19 | ||
20 | template<class T, class F> | |
21 | void test_unary() { | |
22 | typedef typename F::I I; | |
23 | for(I a(-10., -9.91); a.lower() <= 10.; a += 0.3) { | |
24 | if (!F::validate(a)) continue; | |
25 | I rI = F::f_I(a); | |
26 | T rT1 = F::f_T(a.lower()), rT2 = F::f_T(a.upper()), | |
27 | rT3 = F::f_T(median(a)); | |
1e59de90 TL |
28 | if (!BOOST_TEST(in(rT1, rI)) || |
29 | !BOOST_TEST(in(rT2, rI)) || | |
30 | !BOOST_TEST(in(rT3, rI))) { | |
31 | return; | |
32 | } | |
7c673cae FG |
33 | } |
34 | } | |
35 | ||
36 | template<class T, class F> | |
37 | void test_binary() { | |
38 | typedef typename F::I I; | |
39 | for(I a(-10., -9.91); a.lower() <= 10.; a += 0.3) { | |
40 | for(I b(-10., -9.91); b.lower() <= 10.; b += 0.3) { | |
41 | if (!F::validate(a, b)) continue; | |
42 | T al = a.lower(), au = a.upper(), bl = b.lower(), bu = b.upper(); | |
43 | I rII = F::f_II(a, b); | |
44 | I rIT1 = F::f_IT(a, bl), rIT2 = F::f_IT(a, bu); | |
45 | I rTI1 = F::f_TI(al, b), rTI2 = F::f_TI(au, b); | |
46 | I rTT1 = F::f_TT(al, bl), rTT2 = F::f_TT(al, bu); | |
47 | I rTT3 = F::f_TT(au, bl), rTT4 = F::f_TT(au, bu); | |
1e59de90 TL |
48 | if (!BOOST_TEST(subset(rTT1, rIT1)) || |
49 | !BOOST_TEST(subset(rTT3, rIT1)) || | |
50 | !BOOST_TEST(subset(rTT2, rIT2)) || | |
51 | !BOOST_TEST(subset(rTT4, rIT2)) || | |
52 | !BOOST_TEST(subset(rTT1, rTI1)) || | |
53 | !BOOST_TEST(subset(rTT2, rTI1)) || | |
54 | !BOOST_TEST(subset(rTT3, rTI2)) || | |
55 | !BOOST_TEST(subset(rTT4, rTI2)) || | |
56 | !BOOST_TEST(subset(rIT1, rII)) || | |
57 | !BOOST_TEST(subset(rIT2, rII)) || | |
58 | !BOOST_TEST(subset(rTI1, rII)) || | |
59 | !BOOST_TEST(subset(rTI2, rII))) { | |
60 | return; | |
61 | } | |
7c673cae FG |
62 | } |
63 | } | |
64 | } | |
65 | ||
66 | #define new_unary_bunch(name, op, val) \ | |
67 | template<class T> \ | |
68 | struct name { \ | |
69 | typedef boost::numeric::interval<T> I; \ | |
70 | static I f_I(const I& a) { return op(a); } \ | |
71 | static T f_T(const T& a) { return op(a); } \ | |
72 | static bool validate(const I& a) { return val; } \ | |
73 | } | |
74 | ||
75 | //#ifndef BOOST_NO_STDC_NAMESPACE | |
76 | using std::abs; | |
77 | using std::sqrt; | |
78 | //#endif | |
79 | ||
80 | new_unary_bunch(bunch_pos, +, true); | |
81 | new_unary_bunch(bunch_neg, -, true); | |
82 | new_unary_bunch(bunch_sqrt, sqrt, a.lower() >= 0.); | |
83 | new_unary_bunch(bunch_abs, abs, true); | |
84 | ||
85 | template<class T> | |
86 | void test_all_unaries() { | |
1e59de90 TL |
87 | test_unary<T, bunch_pos<T> >(); |
88 | test_unary<T, bunch_neg<T> >(); | |
89 | test_unary<T, bunch_sqrt<T> >(); | |
90 | test_unary<T, bunch_abs<T> >(); | |
7c673cae FG |
91 | } |
92 | ||
93 | #define new_binary_bunch(name, op, val) \ | |
94 | template<class T> \ | |
95 | struct bunch_##name { \ | |
96 | typedef boost::numeric::interval<T> I; \ | |
97 | static I f_II(const I& a, const I& b) { return a op b; } \ | |
98 | static I f_IT(const I& a, const T& b) { return a op b; } \ | |
99 | static I f_TI(const T& a, const I& b) { return a op b; } \ | |
100 | static I f_TT(const T& a, const T& b) \ | |
101 | { return boost::numeric::interval_lib::name<I>(a,b); } \ | |
102 | static bool validate(const I& a, const I& b) { return val; } \ | |
103 | } | |
104 | ||
105 | new_binary_bunch(add, +, true); | |
106 | new_binary_bunch(sub, -, true); | |
107 | new_binary_bunch(mul, *, true); | |
108 | new_binary_bunch(div, /, !zero_in(b)); | |
109 | ||
110 | template<class T> | |
111 | void test_all_binaries() { | |
1e59de90 TL |
112 | test_binary<T, bunch_add<T> >(); |
113 | test_binary<T, bunch_sub<T> >(); | |
114 | test_binary<T, bunch_mul<T> >(); | |
115 | test_binary<T, bunch_div<T> >(); | |
7c673cae FG |
116 | } |
117 | ||
1e59de90 | 118 | int main() { |
7c673cae FG |
119 | test_all_unaries<float> (); |
120 | test_all_binaries<float> (); | |
7c673cae FG |
121 | test_all_unaries<double>(); |
122 | test_all_binaries<double>(); | |
7c673cae FG |
123 | //test_all_unaries<long double>(); |
124 | //test_all_binaries<long double>(); | |
20effc67 | 125 | # ifdef BOOST_BORLANDC |
7c673cae FG |
126 | ::detail::ignore_warnings(); |
127 | # endif | |
1e59de90 | 128 | return boost::report_errors(); |
7c673cae | 129 | } |