1 // Copyright Louis Dionne 2013-2017 2 // Distributed under the Boost Software License, Version 1.0. 3 // (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) 4 5 #ifndef BOOST_HANA_TEST_LAWS_HASHABLE_HPP 6 #define BOOST_HANA_TEST_LAWS_HASHABLE_HPP 7 8 #include <boost/hana/assert.hpp> 9 #include <boost/hana/bool.hpp> 10 #include <boost/hana/concept/hashable.hpp> 11 #include <boost/hana/core/default.hpp> 12 #include <boost/hana/core/tag_of.hpp> 13 #include <boost/hana/core/when.hpp> 14 #include <boost/hana/equal.hpp> 15 #include <boost/hana/for_each.hpp> 16 #include <boost/hana/hash.hpp> 17 #include <boost/hana/if.hpp> 18 19 #include <laws/base.hpp> 20 21 22 namespace boost { namespace hana { namespace test { 23 template <typename G, typename = when<true>> 24 struct TestHashable : TestHashable<G, laws> { 25 using TestHashable<G, laws>::TestHashable; 26 }; 27 28 template <typename H> 29 struct TestHashable<H, laws> { 30 template <typename Xs> TestHashableboost::hana::test::TestHashable31 TestHashable(Xs xs) { 32 hana::for_each(xs, [](auto x) { 33 static_assert(Hashable<decltype(x)>{}, ""); 34 }); 35 36 hana::for_each(xs, [&](auto const& x) { 37 hana::for_each(xs, [&](auto const& y) { 38 using X = hana::tag_of_t<decltype(x)>; 39 using Y = hana::tag_of_t<decltype(y)>; 40 constexpr bool comparable = !hana::is_default< 41 hana::equal_impl<X, Y> 42 >::value; 43 44 hana::if_(hana::bool_c<comparable>, 45 [](auto const& x, auto const& y) { 46 BOOST_HANA_CHECK( 47 hana::equal(x, y) 48 ^implies^ 49 hana::equal(hana::hash(x), hana::hash(y)) 50 ); 51 }, 52 [](auto...) { } 53 )(x, y); 54 }); 55 }); 56 } 57 }; 58 }}} // end namespace boost::hana::test 59 60 #endif // !BOOST_HANA_TEST_LAWS_HASHABLE_HPP 61