2 * (C) Copyright Nick Thompson 2018.
3 * Use, modification and distribution are subject to the
4 * Boost Software License, Version 1.0. (See accompanying file
5 * LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
10 #include <forward_list>
14 #include <boost/core/lightweight_test.hpp>
15 #include <boost/numeric/ublas/vector.hpp>
16 #include <boost/math/constants/constants.hpp>
17 #include <boost/math/tools/norms.hpp>
18 #include <boost/multiprecision/cpp_bin_float.hpp>
19 #include <boost/multiprecision/cpp_complex.hpp>
24 using boost::multiprecision::cpp_bin_float_50;
25 using boost::multiprecision::cpp_complex_50;
26 using boost::math::tools::lp_norm;
27 using boost::math::tools::l1_norm;
28 using boost::math::tools::l2_norm;
29 using boost::math::tools::sup_norm;
30 using boost::math::tools::lp_distance;
31 using boost::math::tools::l1_distance;
32 using boost::math::tools::l2_distance;
33 using boost::math::tools::sup_distance;
34 using boost::math::tools::total_variation;
38 * 1) Does it work with multiprecision?
39 * 2) Does it work with .cbegin()/.cend() if the data is not altered?
40 * 3) Does it work with ublas and std::array? (Checking Eigen and Armadillo will make the CI system really unhappy.)
41 * 4) Does it work with std::forward_list if a forward iterator is all that is required?
42 * 5) Does it work with complex data if complex data is sensible?
45 // To stress test, set global_seed = 0, global_size = huge.
46 static const constexpr size_t global_seed = 834;
47 static const constexpr size_t global_size = 64;
50 std::vector<T> generate_random_vector(size_t size, size_t seed)
54 std::random_device rd;
57 std::vector<T> v(size);
59 std::mt19937 gen(seed);
61 if constexpr (std::is_floating_point<T>::value)
63 std::normal_distribution<T> dis(0, 1);
64 for (size_t i = 0; i < v.size(); ++i)
70 else if constexpr (std::is_integral<T>::value)
72 // Rescaling by larger than 2 is UB!
73 std::uniform_int_distribution<T> dis(std::numeric_limits<T>::lowest()/2, (std::numeric_limits<T>::max)()/2);
74 for (size_t i = 0; i < v.size(); ++i)
80 else if constexpr (boost::is_complex<T>::value)
82 std::normal_distribution<typename T::value_type> dis(0, 1);
83 for (size_t i = 0; i < v.size(); ++i)
85 v[i] = {dis(gen), dis(gen)};
89 else if constexpr (boost::multiprecision::number_category<T>::value == boost::multiprecision::number_kind_complex)
91 std::normal_distribution<long double> dis(0, 1);
92 for (size_t i = 0; i < v.size(); ++i)
94 v[i] = {dis(gen), dis(gen)};
98 else if constexpr (boost::multiprecision::number_category<T>::value == boost::multiprecision::number_kind_floating_point)
100 std::normal_distribution<long double> dis(0, 1);
101 for (size_t i = 0; i < v.size(); ++i)
109 BOOST_ASSERT_MSG(false, "Could not identify type for random vector generation.");
118 Real tol = 50*std::numeric_limits<Real>::epsilon();
120 std::array<Real, 3> u{1,0,0};
121 Real l3 = lp_norm(u.begin(), u.end(), 3);
122 BOOST_TEST(abs(l3 - 1) < tol);
125 l3 = lp_norm(u.cbegin(), u.cend(), 3);
126 BOOST_TEST(abs(l3 - 8) < tol);
128 std::vector<Real> v(500);
129 for (size_t i = 0; i < v.size(); ++i) {
132 Real l8 = lp_norm(v, 8);
133 Real expected = 7*pow(v.size(), static_cast<Real>(1)/static_cast<Real>(8));
134 BOOST_TEST(abs(l8 - expected) < tol*abs(expected));
136 // Does it work with ublas vectors?
137 // Does it handle the overflow of intermediates?
138 boost::numeric::ublas::vector<Real> w(4);
139 Real bignum = sqrt((std::numeric_limits<Real>::max)())/256;
140 for (size_t i = 0; i < w.size(); ++i)
144 Real l20 = lp_norm(w.cbegin(), w.cend(), 4);
145 expected = bignum*pow(w.size(), static_cast<Real>(1)/static_cast<Real>(4));
146 BOOST_TEST(abs(l20 - expected) < tol*expected);
148 v = generate_random_vector<Real>(global_size, global_seed);
150 Real l7 = scale*lp_norm(v, 7);
155 Real l7_ = lp_norm(v, 7);
156 BOOST_TEST(abs(l7_ - l7) < tol*l7);
160 template<class Complex>
161 void test_complex_lp()
163 typedef typename Complex::value_type Real;
164 Real tol = 50*std::numeric_limits<Real>::epsilon();
165 std::vector<Complex> v{{1,0}, {0,0}, {0,0}};
166 Real l3 = lp_norm(v.cbegin(), v.cend(), 3);
167 BOOST_TEST(abs(l3 - 1) < tol);
170 BOOST_TEST(abs(l3 - 1) < tol);
172 v = generate_random_vector<Complex>(global_size, global_seed);
174 Real l7 = scale*lp_norm(v, 7);
179 Real l7_ = lp_norm(v, 7);
180 BOOST_TEST(abs(l7_ - l7) < tol*l7);
184 void test_integer_lp()
186 double tol = 100*std::numeric_limits<double>::epsilon();
188 std::array<Z, 3> u{1,0,0};
189 double l3 = lp_norm(u.begin(), u.end(), 3);
190 BOOST_TEST(abs(l3 - 1) < tol);
192 auto v = generate_random_vector<Z>(global_size, global_seed);
194 double l7 = scale*lp_norm(v, 7);
199 double l7_ = lp_norm(v, 7);
200 BOOST_TEST(abs(l7_ - l7) < tol*l7);
204 void test_lp_distance()
206 Real tol = 100*std::numeric_limits<Real>::epsilon();
208 std::vector<Real> u{1,0,0};
209 std::vector<Real> v{0,0,0};
211 Real dist = lp_distance(u,u, 3);
212 BOOST_TEST(abs(dist) < tol);
214 dist = lp_distance(u,v, 3);
215 BOOST_TEST(abs(dist - 1) < tol);
217 v = generate_random_vector<Real>(global_size, global_seed);
218 u = generate_random_vector<Real>(global_size, global_seed+1);
219 Real dist1 = lp_distance(u, v, 7);
220 Real dist2 = lp_distance(v, u, 7);
222 BOOST_TEST(abs(dist1 - dist2) < tol*dist1);
225 template<class Complex>
226 void test_complex_lp_distance()
228 using Real = typename Complex::value_type;
229 Real tol = 100*std::numeric_limits<Real>::epsilon();
231 std::vector<Complex> u{{1,0},{0,0},{0,0}};
232 std::vector<Complex> v{{0,0},{0,0},{0,0}};
234 Real dist = boost::math::tools::lp_distance(u,u, 3);
235 BOOST_TEST(abs(dist) < tol);
237 dist = boost::math::tools::lp_distance(u,v, 3);
238 BOOST_TEST(abs(dist - 1) < tol);
240 v = generate_random_vector<Complex>(global_size, global_seed);
241 u = generate_random_vector<Complex>(global_size, global_seed + 1);
242 Real dist1 = lp_distance(u, v, 7);
243 Real dist2 = lp_distance(v, u, 7);
245 BOOST_TEST(abs(dist1 - dist2) < tol*dist1);
249 void test_integer_lp_distance()
251 double tol = 100*std::numeric_limits<double>::epsilon();
253 std::array<Z, 3> u{1,0,0};
254 std::array<Z, 3> w{0,0,0};
255 double l3 = lp_distance(u, w, 3);
256 BOOST_TEST(abs(l3 - 1) < tol);
258 auto v = generate_random_vector<Z>(global_size, global_seed);
264 auto s = generate_random_vector<Z>(global_size, global_seed + 1);
265 double dist1 = lp_distance(v, s, 7);
266 double dist2 = lp_distance(s, v, 7);
267 BOOST_TEST(abs(dist1 - dist2) < tol*dist2);
272 void test_integer_total_variation()
274 double eps = std::numeric_limits<double>::epsilon();
275 std::vector<Z> v{1,1};
276 double tv = boost::math::tools::total_variation(v);
277 BOOST_TEST_EQ(tv, 0);
280 tv = boost::math::tools::total_variation(v.begin(), v.end());
281 BOOST_TEST_EQ(tv, 1);
284 for (size_t i = 0; i < v.size(); ++i) {
288 tv = boost::math::tools::total_variation(v);
289 BOOST_TEST_EQ(tv, v.size() -1);
291 for (size_t i = 0; i < v.size(); ++i)
296 tv = boost::math::tools::total_variation(v);
297 BOOST_TEST_EQ(tv, (v.size() - 1)*(v.size() - 1));
299 // Work with std::array?
300 std::array<Z, 2> w{1,1};
301 tv = boost::math::tools::total_variation(w);
304 std::array<Z, 4> u{1, 2, 1, 2};
305 tv = boost::math::tools::total_variation(u);
306 BOOST_TEST_EQ(tv, 3);
308 v = generate_random_vector<Z>(global_size, global_seed);
309 double tv1 = 2*total_variation(v);
315 double tv2 = total_variation(v);
316 BOOST_TEST(abs(tv1 - tv2) < tv1*eps);
320 void test_total_variation()
322 Real tol = std::numeric_limits<Real>::epsilon();
323 std::vector<Real> v{1,1};
324 Real tv = total_variation(v.begin(), v.end());
325 BOOST_TEST(tv >= 0 && abs(tv) < tol);
327 tv = total_variation(v);
328 BOOST_TEST(tv >= 0 && abs(tv) < tol);
331 tv = total_variation(v.begin(), v.end());
332 BOOST_TEST(abs(tv - 1) < tol);
335 for (size_t i = 0; i < v.size(); ++i) {
339 tv = total_variation(v.begin(), v.end());
340 BOOST_TEST(abs(tv - (v.size() -1)) < tol);
342 for (size_t i = 0; i < v.size(); ++i) {
346 tv = total_variation(v.begin(), v.end());
347 BOOST_TEST(abs(tv - (v.size() - 1)*(v.size() - 1)) < tol);
350 v = generate_random_vector<Real>(global_size, global_seed);
352 Real tv1 = scale*total_variation(v);
357 Real tv2 = total_variation(v);
358 BOOST_TEST(abs(tv1 - tv2) < tol*tv1);
364 Real tol = std::numeric_limits<Real>::epsilon();
365 std::vector<Real> v{-2,1,0};
366 Real s = boost::math::tools::sup_norm(v.begin(), v.end());
367 BOOST_TEST(abs(s - 2) < tol);
369 s = boost::math::tools::sup_norm(v);
370 BOOST_TEST(abs(s - 2) < tol);
372 // Work with std::array?
373 std::array<Real, 3> w{-2,1,0};
374 s = boost::math::tools::sup_norm(w);
375 BOOST_TEST(abs(s - 2) < tol);
377 v = generate_random_vector<Real>(global_size, global_seed);
379 Real sup1 = scale*sup_norm(v);
384 Real sup2 = sup_norm(v);
385 BOOST_TEST(abs(sup1 - sup2) < tol*sup1);
389 void test_integer_sup_norm()
391 double eps = std::numeric_limits<double>::epsilon();
392 std::vector<Z> v{2,1,0};
393 Z s = sup_norm(v.begin(), v.end());
399 v = generate_random_vector<Z>(global_size, global_seed);
400 double sup1 = 2*sup_norm(v);
406 double sup2 = sup_norm(v);
407 BOOST_TEST(abs(sup1 - sup2) < sup1*eps);
410 template<class Complex>
411 void test_complex_sup_norm()
413 typedef typename Complex::value_type Real;
414 Real tol = std::numeric_limits<Real>::epsilon();
415 std::vector<Complex> w{{0,-8}, {1,1}, {3,2}};
416 Real s = sup_norm(w.cbegin(), w.cend());
417 BOOST_TEST(abs(s-8) < tol);
420 BOOST_TEST(abs(s-8) < tol);
422 auto v = generate_random_vector<Complex>(global_size, global_seed);
424 Real sup1 = scale*sup_norm(v);
429 Real sup2 = sup_norm(v);
430 BOOST_TEST(abs(sup1 - sup2) < tol*sup1);
434 void test_l0_pseudo_norm()
436 std::vector<Real> v{0,0,1};
437 size_t count = boost::math::tools::l0_pseudo_norm(v.begin(), v.end());
438 BOOST_TEST_EQ(count, 1);
440 // Compiles with cbegin()/cend()?
441 count = boost::math::tools::l0_pseudo_norm(v.cbegin(), v.cend());
442 BOOST_TEST_EQ(count, 1);
444 count = boost::math::tools::l0_pseudo_norm(v);
445 BOOST_TEST_EQ(count, 1);
447 std::array<Real, 3> w{0,0,1};
448 count = boost::math::tools::l0_pseudo_norm(w);
449 BOOST_TEST_EQ(count, 1);
452 template<class Complex>
453 void test_complex_l0_pseudo_norm()
455 std::vector<Complex> v{{0,0}, {0,0}, {1,0}};
456 size_t count = boost::math::tools::l0_pseudo_norm(v.begin(), v.end());
457 BOOST_TEST_EQ(count, 1);
459 count = boost::math::tools::l0_pseudo_norm(v);
460 BOOST_TEST_EQ(count, 1);
464 void test_hamming_distance()
466 std::vector<Z> v{1,2,3};
467 std::vector<Z> w{1,2,4};
468 size_t count = boost::math::tools::hamming_distance(v, w);
469 BOOST_TEST_EQ(count, 1);
471 count = boost::math::tools::hamming_distance(v, v);
472 BOOST_TEST_EQ(count, 0);
478 Real tol = std::numeric_limits<Real>::epsilon();
479 std::vector<Real> v{1,1,1};
480 Real l1 = l1_norm(v.begin(), v.end());
481 BOOST_TEST(abs(l1 - 3) < tol);
484 BOOST_TEST(abs(l1 - 3) < tol);
486 std::array<Real, 3> w{1,1,1};
488 BOOST_TEST(abs(l1 - 3) < tol);
490 v = generate_random_vector<Real>(global_size, global_seed);
492 Real l1_1 = scale*l1_norm(v);
497 Real l1_2 = l1_norm(v);
498 BOOST_TEST(abs(l1_1 - l1_2) < tol*l1_1);
502 void test_integer_l1_norm()
504 double eps = std::numeric_limits<double>::epsilon();
505 std::vector<Z> v{1,1,1};
506 Z l1 = boost::math::tools::l1_norm(v.begin(), v.end());
507 BOOST_TEST_EQ(l1, 3);
509 v = generate_random_vector<Z>(global_size, global_seed);
510 double l1_1 = 2*l1_norm(v);
516 double l1_2 = l1_norm(v);
517 BOOST_TEST(l1_1 > 0);
518 BOOST_TEST(l1_2 > 0);
519 if (abs(l1_1 - l1_2) > 2*l1_1*eps)
521 std::cout << std::setprecision(std::numeric_limits<double>::digits10);
522 std::cout << "L1_1 = " << l1_1 << "\n";
523 std::cout << "L1_2 = " << l1_2 << "\n";
524 BOOST_TEST(abs(l1_1 - l1_2) < 2*l1_1*eps);
528 template<class Complex>
529 void test_complex_l1_norm()
531 typedef typename Complex::value_type Real;
532 Real tol = std::numeric_limits<Real>::epsilon();
533 std::vector<Complex> v{{1,0}, {0,1},{0,-1}};
534 Real l1 = l1_norm(v.begin(), v.end());
535 BOOST_TEST(abs(l1 - 3) < tol);
538 BOOST_TEST(abs(l1 - 3) < tol);
540 v = generate_random_vector<Complex>(global_size, global_seed);
542 Real l1_1 = scale*l1_norm(v);
547 Real l1_2 = l1_norm(v);
548 BOOST_TEST(abs(l1_1 - l1_2) < tol*l1_1);
552 void test_l1_distance()
554 Real tol = std::numeric_limits<Real>::epsilon();
555 std::vector<Real> v{1,2,3};
556 std::vector<Real> w{1,1,1};
557 Real l1 = boost::math::tools::l1_distance(v, v);
558 BOOST_TEST(abs(l1) < tol);
560 l1 = boost::math::tools::l1_distance(w, v);
561 BOOST_TEST(abs(l1 - 3) < tol);
563 l1 = boost::math::tools::l1_distance(v, w);
564 BOOST_TEST(abs(l1 - 3) < tol);
566 v = generate_random_vector<Real>(global_size, global_seed);
567 w = generate_random_vector<Real>(global_size, global_seed+1);
568 Real dist1 = l1_distance(v, w);
569 Real dist2 = l1_distance(w, v);
570 BOOST_TEST(abs(dist1 - dist2) < tol*dist1);
574 void test_integer_l1_distance()
576 double tol = std::numeric_limits<double>::epsilon();
577 std::vector<Z> v{1,2,3};
578 std::vector<Z> w{1,1,1};
579 double l1 = boost::math::tools::l1_distance(v, v);
580 BOOST_TEST(abs(l1) < tol);
582 l1 = boost::math::tools::l1_distance(w, v);
583 BOOST_TEST(abs(l1 - 3) < tol);
585 l1 = boost::math::tools::l1_distance(v, w);
586 BOOST_TEST(abs(l1 - 3) < tol);
588 v = generate_random_vector<Z>(global_size, global_seed);
589 w = generate_random_vector<Z>(global_size, global_seed + 1);
590 double dist1 = l1_distance(v, w);
591 double dist2 = l1_distance(w, v);
592 BOOST_TEST(abs(dist1 - dist2) < tol*dist1);
595 template<class Complex>
596 void test_complex_l1_distance()
598 typedef typename Complex::value_type Real;
599 Real tol = std::numeric_limits<Real>::epsilon();
600 std::vector<Complex> v{{1,0}, {0,1},{0,-1}};
601 Real l1 = boost::math::tools::l1_distance(v, v);
602 BOOST_TEST(abs(l1) < tol);
604 std::vector<Complex> w{{2,0}, {0,1},{0,-1}};
605 l1 = boost::math::tools::l1_distance(v.cbegin(), v.cend(), w.cbegin());
606 BOOST_TEST(abs(l1 - 1) < tol);
608 v = generate_random_vector<Complex>(global_size, global_seed);
609 w = generate_random_vector<Complex>(global_size, global_seed + 1);
610 Real dist1 = l1_distance(v, w);
611 Real dist2 = l1_distance(w, v);
612 BOOST_TEST(abs(dist1 - dist2) < tol*dist1);
620 Real tol = std::numeric_limits<Real>::epsilon();
621 std::vector<Real> v{1,1,1,1};
622 Real l2 = boost::math::tools::l2_norm(v.begin(), v.end());
623 BOOST_TEST(abs(l2 - 2) < tol);
625 l2 = boost::math::tools::l2_norm(v);
626 BOOST_TEST(abs(l2 - 2) < tol);
628 std::array<Real, 4> w{1,1,1,1};
629 l2 = boost::math::tools::l2_norm(w);
630 BOOST_TEST(abs(l2 - 2) < tol);
632 Real bignum = 4*sqrt((std::numeric_limits<Real>::max)());
637 l2 = boost::math::tools::l2_norm(v.begin(), v.end());
638 BOOST_TEST(abs(l2 - bignum) < tol*l2);
640 v = generate_random_vector<Real>(global_size, global_seed);
642 Real l2_1 = scale*l2_norm(v);
647 Real l2_2 = l2_norm(v);
648 BOOST_TEST(l2_1 > 0);
649 BOOST_TEST(l2_2 > 0);
650 BOOST_TEST(abs(l2_1 - l2_2) < tol*l2_1);
654 void test_integer_l2_norm()
656 double tol = 100*std::numeric_limits<double>::epsilon();
657 std::vector<Z> v{1,1,1,1};
658 double l2 = boost::math::tools::l2_norm(v.begin(), v.end());
659 BOOST_TEST(abs(l2 - 2) < tol);
661 v = generate_random_vector<Z>(global_size, global_seed);
663 double l2_1 = scale*l2_norm(v);
668 double l2_2 = l2_norm(v);
669 BOOST_TEST(l2_1 > 0);
670 BOOST_TEST(l2_2 > 0);
671 BOOST_TEST(abs(l2_1 - l2_2) < tol*l2_1);
674 template<class Complex>
675 void test_complex_l2_norm()
677 typedef typename Complex::value_type Real;
678 Real tol = 100*std::numeric_limits<Real>::epsilon();
679 std::vector<Complex> v{{1,0}, {0,1},{0,-1}, {1,0}};
680 Real l2 = boost::math::tools::l2_norm(v.begin(), v.end());
681 BOOST_TEST(abs(l2 - 2) < tol);
683 l2 = boost::math::tools::l2_norm(v);
684 BOOST_TEST(abs(l2 - 2) < tol);
686 v = generate_random_vector<Complex>(global_size, global_seed);
688 Real l2_1 = scale*l2_norm(v);
693 Real l2_2 = l2_norm(v);
694 BOOST_TEST(abs(l2_1 - l2_2) < tol*l2_1);
698 void test_l2_distance()
700 Real tol = std::numeric_limits<Real>::epsilon();
701 std::vector<Real> v{1,1,1,1};
702 Real l2 = boost::math::tools::l2_distance(v, v);
703 BOOST_TEST(abs(l2) < tol);
705 v = generate_random_vector<Real>(global_size, global_seed);
706 auto w = generate_random_vector<Real>(global_size, global_seed + 1);
707 Real dist1 = l2_distance(v, w);
708 Real dist2 = l2_distance(w, v);
709 BOOST_TEST(abs(dist1 - dist2) < tol*dist1);
714 void test_integer_l2_distance()
716 double tol = std::numeric_limits<double>::epsilon();
717 std::vector<Z> v{1,1,1,1};
718 double l2 = boost::math::tools::l2_distance(v, v);
719 BOOST_TEST(abs(l2) < tol);
721 v = generate_random_vector<Z>(global_size, global_seed);
722 auto w = generate_random_vector<Z>(global_size, global_seed + 1);
723 double dist1 = l2_distance(v, w);
724 double dist2 = l2_distance(w, v);
725 BOOST_TEST(abs(dist1 - dist2) < tol*dist1);
728 template<class Complex>
729 void test_complex_l2_distance()
731 typedef typename Complex::value_type Real;
732 Real tol = 100*std::numeric_limits<Real>::epsilon();
733 std::vector<Complex> v{{1,0}, {0,1},{0,-1}, {1,0}};
734 Real l2 = boost::math::tools::l2_distance(v, v);
735 BOOST_TEST(abs(l2) < tol);
737 v = generate_random_vector<Complex>(global_size, global_seed);
738 auto w = generate_random_vector<Complex>(global_size, global_seed + 1);
739 Real dist1 = l2_distance(v, w);
740 Real dist2 = l2_distance(w, v);
741 BOOST_TEST(abs(dist1 - dist2) < tol*dist1);
745 void test_sup_distance()
747 Real tol = std::numeric_limits<Real>::epsilon();
748 std::vector<Real> v{1,1,1,1};
749 std::vector<Real> w{0,0,0,0};
750 Real sup = boost::math::tools::sup_distance(v, v);
751 BOOST_TEST(abs(sup) < tol);
752 sup = boost::math::tools::sup_distance(v, w);
753 BOOST_TEST(abs(sup -1) < tol);
755 v = generate_random_vector<Real>(global_size, global_seed);
756 w = generate_random_vector<Real>(global_size, global_seed + 1);
757 Real dist1 = sup_distance(v, w);
758 Real dist2 = sup_distance(w, v);
759 BOOST_TEST(abs(dist1 - dist2) < tol*dist1);
764 void test_integer_sup_distance()
766 double tol = std::numeric_limits<double>::epsilon();
767 std::vector<Z> v{1,1,1,1};
768 std::vector<Z> w{0,0,0,0};
769 double sup = boost::math::tools::sup_distance(v, v);
770 BOOST_TEST(abs(sup) < tol);
772 sup = boost::math::tools::sup_distance(v, w);
773 BOOST_TEST(abs(sup -1) < tol);
775 v = generate_random_vector<Z>(global_size, global_seed);
776 w = generate_random_vector<Z>(global_size, global_seed + 1);
777 double dist1 = sup_distance(v, w);
778 double dist2 = sup_distance(w, v);
779 BOOST_TEST(abs(dist1 - dist2) < tol*dist1);
782 template<class Complex>
783 void test_complex_sup_distance()
785 typedef typename Complex::value_type Real;
786 Real tol = 100*std::numeric_limits<Real>::epsilon();
787 std::vector<Complex> v{{1,0}, {0,1},{0,-1}, {1,0}};
788 Real sup = boost::math::tools::sup_distance(v, v);
789 BOOST_TEST(abs(sup) < tol);
791 v = generate_random_vector<Complex>(global_size, global_seed);
792 auto w = generate_random_vector<Complex>(global_size, global_seed + 1);
793 Real dist1 = sup_distance(v, w);
794 Real dist2 = sup_distance(w, v);
795 BOOST_TEST(abs(dist1 - dist2) < tol*dist1);
800 test_l0_pseudo_norm<unsigned>();
801 test_l0_pseudo_norm<int>();
802 test_l0_pseudo_norm<float>();
803 test_l0_pseudo_norm<double>();
804 test_l0_pseudo_norm<long double>();
805 test_l0_pseudo_norm<cpp_bin_float_50>();
807 test_complex_l0_pseudo_norm<std::complex<float>>();
808 test_complex_l0_pseudo_norm<std::complex<double>>();
809 test_complex_l0_pseudo_norm<std::complex<long double>>();
810 test_complex_l0_pseudo_norm<cpp_complex_50>();
812 test_hamming_distance<int>();
813 test_hamming_distance<unsigned>();
815 test_l1_norm<float>();
816 test_l1_norm<double>();
817 test_l1_norm<long double>();
818 test_l1_norm<cpp_bin_float_50>();
820 test_integer_l1_norm<int>();
821 test_integer_l1_norm<unsigned>();
823 test_complex_l1_norm<std::complex<float>>();
824 test_complex_l1_norm<std::complex<double>>();
825 test_complex_l1_norm<std::complex<long double>>();
826 test_complex_l1_norm<cpp_complex_50>();
828 test_l1_distance<float>();
829 test_l1_distance<cpp_bin_float_50>();
831 test_integer_l1_distance<int>();
832 test_integer_l1_distance<unsigned>();
834 test_complex_l1_distance<std::complex<float>>();
835 test_complex_l1_distance<cpp_complex_50>();
837 test_complex_l2_norm<std::complex<float>>();
838 test_complex_l2_norm<std::complex<double>>();
839 test_complex_l2_norm<std::complex<long double>>();
840 test_complex_l2_norm<cpp_complex_50>();
842 test_l2_norm<float>();
843 test_l2_norm<double>();
844 test_l2_norm<long double>();
845 test_l2_norm<cpp_bin_float_50>();
847 test_integer_l2_norm<int>();
848 test_integer_l2_norm<unsigned>();
850 test_l2_distance<double>();
851 test_l2_distance<cpp_bin_float_50>();
853 test_integer_l2_distance<int>();
854 test_integer_l2_distance<unsigned>();
856 test_complex_l2_distance<std::complex<double>>();
857 test_complex_l2_distance<cpp_complex_50>();
861 test_lp<long double>();
862 test_lp<cpp_bin_float_50>();
864 test_complex_lp<std::complex<float>>();
865 test_complex_lp<std::complex<double>>();
866 test_complex_lp<std::complex<long double>>();
867 test_complex_lp<cpp_complex_50>();
869 test_integer_lp<int>();
870 test_integer_lp<unsigned>();
872 test_lp_distance<double>();
873 test_lp_distance<cpp_bin_float_50>();
875 test_complex_lp_distance<std::complex<double>>();
876 test_complex_lp_distance<cpp_complex_50>();
878 test_integer_lp_distance<int>();
879 test_integer_lp_distance<unsigned>();
881 test_sup_norm<float>();
882 test_sup_norm<double>();
883 test_sup_norm<long double>();
884 test_sup_norm<cpp_bin_float_50>();
886 test_integer_sup_norm<int>();
887 test_integer_sup_norm<unsigned>();
889 test_complex_sup_norm<std::complex<float>>();
890 test_complex_sup_norm<std::complex<double>>();
891 test_complex_sup_norm<std::complex<long double>>();
892 test_complex_sup_norm<cpp_complex_50>();
894 test_sup_distance<double>();
895 test_sup_distance<cpp_bin_float_50>();
897 test_integer_sup_distance<int>();
898 test_integer_sup_distance<unsigned>();
900 test_complex_sup_distance<std::complex<double>>();
901 test_complex_sup_distance<cpp_complex_50>();
903 test_total_variation<float>();
904 test_total_variation<double>();
905 test_total_variation<long double>();
906 test_total_variation<cpp_bin_float_50>();
908 test_integer_total_variation<uint32_t>();
909 test_integer_total_variation<int>();
911 return boost::report_errors();