This source file includes following definitions.
- BOOST_AUTO_TEST_SUITE
- BOOST_AUTO_TEST_CASE
- BOOST_AUTO_TEST_CASE
- BOOST_AUTO_TEST_CASE
- BOOST_AUTO_TEST_CASE
- BOOST_AUTO_TEST_CASE
- BOOST_AUTO_TEST_CASE
- BOOST_AUTO_TEST_CASE
- BOOST_AUTO_TEST_CASE
- BOOST_AUTO_TEST_CASE
- BOOST_AUTO_TEST_CASE
- BOOST_AUTO_TEST_CASE
- BOOST_AUTO_TEST_CASE
- BOOST_AUTO_TEST_CASE
- BOOST_AUTO_TEST_CASE
- BOOST_AUTO_TEST_CASE
- BOOST_AUTO_TEST_CASE
- BOOST_AUTO_TEST_CASE
- BOOST_AUTO_TEST_CASE
- BOOST_AUTO_TEST_CASE
- BOOST_AUTO_TEST_CASE
- BOOST_AUTO_TEST_CASE
- BOOST_AUTO_TEST_CASE_TEMPLATE
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21 #include "stdafx.h"
22
23 #define BOOST_TEST_MODULE libjmmcg_tests
24 #include <boost/test/included/unit_test.hpp>
25 #include <boost/test/test_case_template.hpp>
26 #include <boost/mpl/list.hpp>
27
28 #include "core/ave_deviation_meter.hpp"
29 #include "core/fma.hpp"
30
31 #include <chrono>
32
33 BOOST_AUTO_TEST_SUITE(fam)
34
35 BOOST_AUTO_TEST_CASE(all_zero)
36 {
37 using namespace jmmcg::fma;
38
39 const double m=0;
40 const double x=0;
41 const double c=0;
42 const double y=dbl(x)*m+c;
43 BOOST_CHECK_EQUAL(y, 0.0);
44 }
45
46 BOOST_AUTO_TEST_CASE(all_zero_commute_multiply)
47 {
48 using namespace jmmcg::fma;
49
50 const double m=3;
51 const double x=4;
52 const double c=5;
53 const double y=m*dbl(x)+c;
54 BOOST_CHECK_EQUAL(y, 17.0);
55 }
56
57 BOOST_AUTO_TEST_CASE(all_zero_commute_add)
58 {
59 using namespace jmmcg::fma;
60
61 const double m=3;
62 const double x=4;
63 const double c=5;
64 const double y=c+dbl(x)*m;
65 BOOST_CHECK_EQUAL(y, 17.0);
66 }
67
68 BOOST_AUTO_TEST_CASE(all_zero_commute_multipy_and_add)
69 {
70 using namespace jmmcg::fma;
71
72 const double m=3;
73 const double x=4;
74 const double c=5;
75 const double y=c+m*dbl(x);
76 BOOST_CHECK_EQUAL(y, 17.0);
77 }
78
79 BOOST_AUTO_TEST_CASE(all_zero_nest)
80 {
81 using namespace jmmcg::fma;
82
83 const double m=3;
84 const double x=4;
85 const double c=5;
86 const double y=dbl(dbl(x)*m+c)*m+c;
87 BOOST_CHECK_EQUAL(y, 56.0);
88 }
89
90 BOOST_AUTO_TEST_CASE(m_one_others_zero)
91 {
92 using namespace jmmcg::fma;
93
94 const double m=1;
95 const double x=0;
96 const double c=0;
97 const double y=dbl(x)*m+c;
98 BOOST_CHECK_EQUAL(y, 0.0);
99 }
100
101 BOOST_AUTO_TEST_CASE(all_ones)
102 {
103 using namespace jmmcg::fma;
104
105 const double m=1;
106 const double x=1;
107 const double c=1;
108 const double y=dbl(x)*m+c;
109 BOOST_CHECK_EQUAL(y, 2.0);
110 }
111
112 BOOST_AUTO_TEST_CASE(one_two)
113 {
114 using namespace jmmcg::fma;
115
116 const double m=1;
117 const double x=2;
118 const double c=1;
119 const double y=dbl(x)*m+c;
120 BOOST_CHECK_EQUAL(y, 3.0);
121 }
122
123 BOOST_AUTO_TEST_CASE(all_twos)
124 {
125 using namespace jmmcg::fma;
126
127 const double m=2;
128 const double x=2;
129 const double c=2;
130 const double y=dbl(x)*m+c;
131 BOOST_CHECK_EQUAL(y, 6.0);
132 }
133
134 BOOST_AUTO_TEST_CASE(subtract_twos)
135 {
136 using namespace jmmcg::fma;
137
138 const double m=2;
139 const double x=2;
140 const double c=2;
141 const double y=dbl(x)*m-c;
142 BOOST_CHECK_EQUAL(y, 2.0);
143 }
144
145 BOOST_AUTO_TEST_CASE(associative_subtract_twos)
146 {
147 using namespace jmmcg::fma;
148
149 const double m=2;
150 const double x=2;
151 const double c=2;
152 const double y=c-dbl(x)*m;
153 BOOST_CHECK_EQUAL(y, -2.0);
154 }
155
156 BOOST_AUTO_TEST_CASE(all_zero_two_surrounding_multiplies)
157 {
158 using namespace jmmcg::fma;
159
160 const double m=3;
161 const double x=4;
162 const double c=5;
163 const double y=m*dbl(x)*m+c;
164 BOOST_CHECK_EQUAL(y, 41.0);
165 }
166
167 BOOST_AUTO_TEST_CASE(all_zero_two_post_multiplies)
168 {
169 using namespace jmmcg::fma;
170
171 const double m=3;
172 const double x=4;
173 const double c=5;
174 const double y=dbl(x)*m*m+c;
175 BOOST_CHECK_EQUAL(y, 41.0);
176 }
177
178 BOOST_AUTO_TEST_CASE(all_zero_two_preceeding_multiplies)
179 {
180 using namespace jmmcg::fma;
181
182 const double m=3;
183 const double x=4;
184 const double c=5;
185 const double y=m*m*dbl(x)+c;
186 BOOST_CHECK_EQUAL(y, 41.0);
187 }
188
189 BOOST_AUTO_TEST_CASE(all_zero_two_dbls_add)
190 {
191 using namespace jmmcg::fma;
192
193 const dbl m=3;
194 const double x=4;
195 const dbl c=5;
196 const dbl y=m*m*dbl(x)+c;
197 BOOST_CHECK_EQUAL(y, 41.0);
198 }
199
200 BOOST_AUTO_TEST_CASE(all_zero_two_dbls_subtract)
201 {
202 using namespace jmmcg::fma;
203
204 const dbl m=3;
205 const double x=4;
206 const dbl c=5;
207 const dbl y=m*m*dbl(x)-c;
208 BOOST_CHECK_EQUAL(y, 31.0);
209 }
210
211 BOOST_AUTO_TEST_CASE(all_zero_two_dbls_associative_add)
212 {
213 using namespace jmmcg::fma;
214
215 const dbl m=2;
216 const double x=3;
217 const dbl c=4;
218 const dbl y=c+m*m*dbl(x);
219 BOOST_CHECK_EQUAL(y, 16.0);
220 }
221
222 BOOST_AUTO_TEST_CASE(all_zero_two_dbls_associative_subtract)
223 {
224 using namespace jmmcg::fma;
225
226 const dbl m=3;
227 const double x=4;
228 const dbl c=5;
229 const dbl y=c-m*m*dbl(x);
230 BOOST_CHECK_EQUAL(y, -31.0);
231 }
232
233 BOOST_AUTO_TEST_CASE(multiply_equals_add)
234 {
235 using namespace jmmcg::fma;
236
237 const double m=3;
238 const double c=5;
239 double y=4;
240 y*=dbl(m)+c;
241 BOOST_CHECK_EQUAL(y, 17.0);
242 }
243
244 BOOST_AUTO_TEST_CASE(multiply_equals_subtract)
245 {
246 using namespace jmmcg::fma;
247
248 const double m=3;
249 const double c=5;
250 double y=4;
251 y*=dbl(m)-c;
252 BOOST_CHECK_EQUAL(y, 7.0);
253 }
254
255 BOOST_AUTO_TEST_CASE(add_equals)
256 {
257 using namespace jmmcg::fma;
258
259 const double m=3;
260 const double x=4;
261 double y=5;
262 y+=x*dbl(m);
263 BOOST_CHECK_EQUAL(y, 17.0);
264 }
265
266 BOOST_AUTO_TEST_CASE(subtract_equals)
267 {
268 using namespace jmmcg::fma;
269
270 const double m=3;
271 const double x=4;
272 double y=5;
273 y-=x*dbl(m);
274 BOOST_CHECK_EQUAL(y, 7.0);
275 }
276
277 typedef boost::mpl::list<
278 double,
279 jmmcg::fma::dbl
280 > check_fma_tests;
281
282 BOOST_AUTO_TEST_CASE_TEMPLATE(performance_all_zero_commute_multiply, T, check_fma_tests)
283 {
284 using timed_results_t=jmmcg::ave_deviation_meter<double>;
285
286 #ifdef JMMCG_PERFORMANCE_TESTS
287 const unsigned long test_size=2<<19;
288 const unsigned long num_reps=10000;
289 #else
290 const unsigned long test_size=2<<2;
291 const unsigned long num_reps=2;
292 #endif
293
294 const std::pair<timed_results_t, bool> timed_results(jmmcg::compute_average_deviation<timed_results_t::value_type>(
295 0.1,
296 num_reps,
297 [test_size]() {
298 const double m=3;
299 const double x=4;
300 const double c=5;
301 double y=0;
302 const auto t1=std::chrono::high_resolution_clock::now();
303 for (unsigned long num_loops=0;num_loops<test_size;++num_loops) {
304 y+=m*T(x)+c;
305 }
306 const auto t2=std::chrono::high_resolution_clock::now();
307 BOOST_CHECK_EQUAL(y, test_size*17.0);
308 return timed_results_t::value_type(std::chrono::duration_cast<std::chrono::nanoseconds>(t2 - t1).count())/test_size;
309 }
310 ));
311 std::cout<<"Time per "<<typeid(T).name()<<" operation: "<<timed_results.first<<" nanosec."<<std::endl;
312 #ifdef JMMCG_PERFORMANCE_TESTS
313 BOOST_CHECK(!timed_results.second);
314 #endif
315 }
316
317 BOOST_AUTO_TEST_SUITE_END()