group.hpp 2.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293
  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. #ifndef BOOST_HANA_TEST_LAWS_GROUP_HPP
  5. #define BOOST_HANA_TEST_LAWS_GROUP_HPP
  6. #include <boost/hana/assert.hpp>
  7. #include <boost/hana/bool.hpp>
  8. #include <boost/hana/concept/comparable.hpp>
  9. #include <boost/hana/core/when.hpp>
  10. #include <boost/hana/concept/group.hpp>
  11. #include <boost/hana/lazy.hpp>
  12. #include <laws/base.hpp>
  13. namespace boost { namespace hana { namespace test {
  14. template <typename G, typename = when<true>>
  15. struct TestGroup : TestGroup<G, laws> {
  16. using TestGroup<G, laws>::TestGroup;
  17. };
  18. template <typename G>
  19. struct TestGroup<G, laws> {
  20. template <typename Xs>
  21. TestGroup(Xs xs) {
  22. hana::for_each(xs, [](auto x) {
  23. static_assert(Group<decltype(x)>{}, "");
  24. });
  25. #ifdef BOOST_HANA_WORKAROUND_MSVC_DECLTYPEAUTO_RETURNTYPE_662735
  26. zero<G>(); // force adding zero<G>'s member function to pending temploid list
  27. #endif
  28. foreach2(xs, [](auto x, auto y) {
  29. // left inverse
  30. BOOST_HANA_CHECK(hana::equal(
  31. hana::plus(x, hana::negate(x)),
  32. zero<G>()
  33. ));
  34. // right inverse
  35. BOOST_HANA_CHECK(hana::equal(
  36. hana::plus(hana::negate(x), x),
  37. zero<G>()
  38. ));
  39. // default definition of minus
  40. BOOST_HANA_CHECK(hana::equal(
  41. hana::minus(x, y),
  42. hana::plus(x, hana::negate(y))
  43. ));
  44. BOOST_HANA_CHECK(hana::equal(
  45. hana::minus(y, x),
  46. hana::plus(y, hana::negate(x))
  47. ));
  48. // default definition of negate
  49. BOOST_HANA_CHECK(hana::equal(
  50. hana::negate(hana::negate(x)),
  51. x
  52. ));
  53. });
  54. }
  55. };
  56. template <typename C>
  57. struct TestGroup<C, when<Constant<C>::value>>
  58. : TestGroup<C, laws>
  59. {
  60. template <typename Xs>
  61. TestGroup(Xs xs) : TestGroup<C, laws>{xs} {
  62. foreach2(xs, [](auto x, auto y) {
  63. BOOST_HANA_CHECK(hana::equal(
  64. hana::negate(hana::value(x)),
  65. hana::value(hana::negate(x))
  66. ));
  67. BOOST_HANA_CHECK(hana::equal(
  68. hana::minus(hana::value(x), hana::value(y)),
  69. hana::value(hana::minus(x, y))
  70. ));
  71. });
  72. }
  73. };
  74. }}} // end namespace boost::hana::test
  75. #endif // !BOOST_HANA_TEST_LAWS_GROUP_HPP