From a5e74b29517ae8b9cc38bbfb2d8b9efc93c63bfa Mon Sep 17 00:00:00 2001 From: Peter Dimov Date: Sun, 15 Oct 2017 15:52:32 +0300 Subject: [PATCH] Add mp_less, mp_min, mp_max --- doc/mp11/function.adoc | 22 ++++++++++++ include/boost/mp11/function.hpp | 10 ++++++ test/Jamfile | 3 ++ test/mp_less.cpp | 63 +++++++++++++++++++++++++++++++++ test/mp_max.cpp | 26 ++++++++++++++ test/mp_min.cpp | 26 ++++++++++++++ 6 files changed, 150 insertions(+) create mode 100644 test/mp_less.cpp create mode 100644 test/mp_max.cpp create mode 100644 test/mp_min.cpp diff --git a/doc/mp11/function.adoc b/doc/mp11/function.adoc index 2fe7cda..75c004a 100644 --- a/doc/mp11/function.adoc +++ b/doc/mp11/function.adoc @@ -106,3 +106,25 @@ using R4 = mp_any; // compile-time error `mp_plus` is an integral constant type with a value that is the sum of `U::value` for all types `U` in `T...`. `mp_plus<>` is `mp_int<0>`. + +## mp_less + + template using mp_less = /*...*/; + +`mp_less` is `mp_true` when the numeric value of `T1::value` is less than the numeric value of `T2::value`, +`mp_false` otherwise. + +(Note that this is not necessarily the same as `T1::value < T2::value` when comparing between signed and unsigned types; +`-1 < 1u` is `false`, but `mp_less, mp_size_t<1>>` is `mp_true`.) + +## mp_min + + template using mp_min = mp_min_element, mp_less>; + +`mp_min` returns the type `U` in `T...` with the lowest `U::value`. + +## mp_max + + template using mp_max = mp_max_element, mp_less>; + +`mp_max` returns the type `U` in `T...` with the highest `U::value`. diff --git a/include/boost/mp11/function.hpp b/include/boost/mp11/function.hpp index df2f92e..ddcd45d 100644 --- a/include/boost/mp11/function.hpp +++ b/include/boost/mp11/function.hpp @@ -13,6 +13,7 @@ #include #include #include +#include #include namespace boost @@ -162,6 +163,15 @@ template struct mp_same_impl template using mp_same = typename detail::mp_same_impl::type; +// mp_less +template using mp_less = mp_bool<(T1::value < 0 && T2::value >= 0) || ((T1::value < T2::value) && !(T1::value >= 0 && T2::value < 0))>; + +// mp_min +template using mp_min = mp_min_element, mp_less>; + +// mp_max +template using mp_max = mp_max_element, mp_less>; + } // namespace mp11 } // namespace boost diff --git a/test/Jamfile b/test/Jamfile index a3dffcd..86d4f0c 100644 --- a/test/Jamfile +++ b/test/Jamfile @@ -124,6 +124,9 @@ run mp_any.cpp ; run mp_or.cpp ; run mp_same.cpp ; run mp_plus.cpp ; +run mp_less.cpp ; +run mp_min.cpp ; +run mp_max.cpp ; # map run mp_map_find.cpp ; diff --git a/test/mp_less.cpp b/test/mp_less.cpp new file mode 100644 index 0000000..932c285 --- /dev/null +++ b/test/mp_less.cpp @@ -0,0 +1,63 @@ + +// Copyright 2017 Peter Dimov. +// +// Distributed under the Boost Software License, Version 1.0. +// +// See accompanying file LICENSE_1_0.txt or copy at +// http://www.boost.org/LICENSE_1_0.txt + + +#include +#include +#include +#include + +int main() +{ + using boost::mp11::mp_less; + using boost::mp11::mp_true; + using boost::mp11::mp_false; + using boost::mp11::mp_int; + using boost::mp11::mp_size_t; + + BOOST_TEST_TRAIT_TRUE((std::is_same, mp_int<-1>>, mp_false>)); + BOOST_TEST_TRAIT_TRUE((std::is_same, mp_int<0>>, mp_false>)); + BOOST_TEST_TRAIT_TRUE((std::is_same, mp_int<1>>, mp_true>)); + BOOST_TEST_TRAIT_TRUE((std::is_same, mp_int<2>>, mp_true>)); + + BOOST_TEST_TRAIT_TRUE((std::is_same, mp_int<-2>>, mp_false>)); + BOOST_TEST_TRAIT_TRUE((std::is_same, mp_int<-1>>, mp_false>)); + BOOST_TEST_TRAIT_TRUE((std::is_same, mp_int<0>>, mp_true>)); + BOOST_TEST_TRAIT_TRUE((std::is_same, mp_int<1>>, mp_true>)); + + BOOST_TEST_TRAIT_TRUE((std::is_same, mp_int<-1>>, mp_false>)); + BOOST_TEST_TRAIT_TRUE((std::is_same, mp_int<0>>, mp_false>)); + BOOST_TEST_TRAIT_TRUE((std::is_same, mp_int<1>>, mp_false>)); + BOOST_TEST_TRAIT_TRUE((std::is_same, mp_int<2>>, mp_true>)); + + BOOST_TEST_TRAIT_TRUE((std::is_same, mp_size_t<0>>, mp_false>)); + BOOST_TEST_TRAIT_TRUE((std::is_same, mp_size_t<1>>, mp_true>)); + BOOST_TEST_TRAIT_TRUE((std::is_same, mp_size_t<2>>, mp_true>)); + BOOST_TEST_TRAIT_TRUE((std::is_same, mp_size_t<3>>, mp_true>)); + + BOOST_TEST_TRAIT_TRUE((std::is_same, mp_size_t<0>>, mp_false>)); + BOOST_TEST_TRAIT_TRUE((std::is_same, mp_size_t<1>>, mp_false>)); + BOOST_TEST_TRAIT_TRUE((std::is_same, mp_size_t<2>>, mp_true>)); + BOOST_TEST_TRAIT_TRUE((std::is_same, mp_size_t<3>>, mp_true>)); + + BOOST_TEST_TRAIT_TRUE((std::is_same, mp_size_t<0>>, mp_false>)); + BOOST_TEST_TRAIT_TRUE((std::is_same, mp_size_t<1>>, mp_false>)); + BOOST_TEST_TRAIT_TRUE((std::is_same, mp_size_t<2>>, mp_false>)); + BOOST_TEST_TRAIT_TRUE((std::is_same, mp_size_t<3>>, mp_true>)); + + BOOST_TEST_TRAIT_TRUE((std::is_same, mp_int<-1>>, mp_false>)); + BOOST_TEST_TRAIT_TRUE((std::is_same, mp_int<0>>, mp_false>)); + BOOST_TEST_TRAIT_TRUE((std::is_same, mp_int<1>>, mp_true>)); + + BOOST_TEST_TRAIT_TRUE((std::is_same, mp_size_t<1>>, mp_true>)); + BOOST_TEST_TRAIT_TRUE((std::is_same, mp_size_t<1>>, mp_true>)); + BOOST_TEST_TRAIT_TRUE((std::is_same, mp_size_t<1>>, mp_false>)); + BOOST_TEST_TRAIT_TRUE((std::is_same, mp_size_t<1>>, mp_false>)); + + return boost::report_errors(); +} diff --git a/test/mp_max.cpp b/test/mp_max.cpp new file mode 100644 index 0000000..6ea6e73 --- /dev/null +++ b/test/mp_max.cpp @@ -0,0 +1,26 @@ + +// Copyright 2017 Peter Dimov. +// +// Distributed under the Boost Software License, Version 1.0. +// +// See accompanying file LICENSE_1_0.txt or copy at +// http://www.boost.org/LICENSE_1_0.txt + + +#include +#include +#include +#include + +int main() +{ + using boost::mp11::mp_max; + using boost::mp11::mp_int; + using boost::mp11::mp_size_t; + + BOOST_TEST_TRAIT_TRUE((std::is_same>, mp_int<1>>)); + BOOST_TEST_TRAIT_TRUE((std::is_same, mp_int<1>, mp_int<2>, mp_int<3>>, mp_int<3>>)); + BOOST_TEST_TRAIT_TRUE((std::is_same, mp_size_t<1>, mp_int<-2>, mp_size_t<2>>, mp_size_t<2>>)); + + return boost::report_errors(); +} diff --git a/test/mp_min.cpp b/test/mp_min.cpp new file mode 100644 index 0000000..1c2cd6f --- /dev/null +++ b/test/mp_min.cpp @@ -0,0 +1,26 @@ + +// Copyright 2017 Peter Dimov. +// +// Distributed under the Boost Software License, Version 1.0. +// +// See accompanying file LICENSE_1_0.txt or copy at +// http://www.boost.org/LICENSE_1_0.txt + + +#include +#include +#include +#include + +int main() +{ + using boost::mp11::mp_min; + using boost::mp11::mp_int; + using boost::mp11::mp_size_t; + + BOOST_TEST_TRAIT_TRUE((std::is_same>, mp_int<1>>)); + BOOST_TEST_TRAIT_TRUE((std::is_same, mp_int<1>, mp_int<2>, mp_int<3>>, mp_int<1>>)); + BOOST_TEST_TRAIT_TRUE((std::is_same, mp_size_t<1>, mp_int<-2>, mp_size_t<2>>, mp_int<-2>>)); + + return boost::report_errors(); +}