diff --git a/example/map.cpp b/example/map.cpp index 05bb1ea1b..a3c39bd9c 100644 --- a/example/map.cpp +++ b/example/map.cpp @@ -14,21 +14,49 @@ Distributed under the Boost Software License, Version 1.0. #include using namespace boost::hana; -using namespace std::literals; int main() { { -//! [comparable] +//! [make] +using namespace std::literals; +auto m = make( + make(int_<1>, "foobar"s), + make(type, 1234) +); +//! [make] +(void)m; + +}{ + +//! [make_map] +using namespace std::literals; BOOST_HANA_RUNTIME_CHECK( - map( + make_map( + make(int_<1>, "foobar"s), + make(type, 1234) + ) + == + make( + make(int_<1>, "foobar"s), + make(type, 1234) + ) +); +//! [make_map] + +}{ + +//! [comparable] +using namespace std::literals; +BOOST_HANA_RUNTIME_CHECK( + make_map( pair(char_<'a'>, "foobar"s), pair(type, nullptr) ) == - map( + make_map( pair(type, (void*)0), pair(char_<'a'>, "foobar"s) ) @@ -38,7 +66,7 @@ BOOST_HANA_RUNTIME_CHECK( }{ //! [searchable] -BOOST_HANA_CONSTEXPR_LAMBDA auto m = map( +BOOST_HANA_CONSTEXPR_LAMBDA auto m = make_map( pair(type, 'i'), pair(type, 'f') ); diff --git a/example/record.cpp b/example/record.cpp index ed61095c5..c081cd508 100644 --- a/example/record.cpp +++ b/example/record.cpp @@ -32,10 +32,10 @@ namespace boost { namespace hana { struct members_impl { static BOOST_HANA_CONSTEXPR_LAMBDA auto apply() { return make( - pair(name, [](auto&& p) -> decltype(auto) { + make(name, [](auto&& p) -> decltype(auto) { return id(std::forward(p).name); }), - pair(age, [](auto&& p) -> decltype(auto) { + make(age, [](auto&& p) -> decltype(auto) { return id(std::forward(p).age); }) ); @@ -53,8 +53,8 @@ int main() { BOOST_HANA_CONSTANT_CHECK(lookup(john, "clearly not a member") == nothing); BOOST_HANA_RUNTIME_CHECK(to(john) == make("John", 30)); - BOOST_HANA_RUNTIME_CHECK(to(john) == map( - pair(name, "John"), - pair(age, 30) + BOOST_HANA_RUNTIME_CHECK(to(john) == make( + make(name, "John"), + make(age, 30) )); } diff --git a/example/searchable.cpp b/example/searchable.cpp index ecc640e89..589b3f9c7 100644 --- a/example/searchable.cpp +++ b/example/searchable.cpp @@ -115,10 +115,10 @@ BOOST_HANA_CONSTANT_CHECK( BOOST_HANA_CONSTANT_CHECK(lookup(make(int_<1>, type, '3'), type) == just(type)); BOOST_HANA_CONSTANT_CHECK(lookup(make(int_<1>, type, '3'), type) == nothing); -BOOST_HANA_CONSTEXPR_LAMBDA auto m = map( - pair(1, 'x'), - pair(type, 3.3), - pair(type, type) +BOOST_HANA_CONSTEXPR_LAMBDA auto m = make( + make(1, 'x'), + make(type, 3.3), + make(type, type) ); BOOST_HANA_CONSTEXPR_CHECK(lookup(m, type) == just(3.3)); //! [lookup] diff --git a/include/boost/hana/fwd/map.hpp b/include/boost/hana/fwd/map.hpp index 5be8d0497..033b9b135 100644 --- a/include/boost/hana/fwd/map.hpp +++ b/include/boost/hana/fwd/map.hpp @@ -11,6 +11,7 @@ Distributed under the Boost Software License, Version 1.0. #define BOOST_HANA_FWD_MAP_HPP #include +#include namespace boost { namespace hana { @@ -53,31 +54,40 @@ namespace boost { namespace hana { //! A `Map` can be converted to a Sequence of Products. struct Map { }; - //! Creates a `Map` with the given key/value associations. - //! @relates Map - //! - //! @note - //! The keys must all be unique. -#ifdef BOOST_HANA_DOXYGEN_INVOKED - constexpr auto map = [](auto&& ...pairs) { - return unspecified-type; - }; -#else template struct _map { Storage storage; struct hana { using datatype = Map; }; }; - struct _make_map { - template - constexpr decltype(auto) operator()(Pairs&& ...pairs) const; +#ifdef BOOST_HANA_DOXYGEN_INVOKED + //! Create a `Map` with the given key/value associations. + //! @relates Map + //! + //! Given zero `Product`s or more representing key/value associations, + //! `make` returns a Map associating these keys to these values. + //! All the keys must be unique. + //! + //! + //! Example + //! ------- + //! @snippet example/map.cpp make + template <> + constexpr auto make = [](auto&& ...pairs) { + return unspecified-type{forwarded(pairs)...}; }; - - constexpr _make_map map{}; #endif - //! Returns a list of the keys of the map, in unspecified order. + //! Alias to `make`; provided for convenience. + //! @relates Map + //! + //! + //! Example + //! ------- + //! @snippet example/map.cpp make_map + constexpr auto make_map = make; + + //! Returns a Sequence of the keys of the map, in unspecified order. //! @relates Map #ifdef BOOST_HANA_DOXYGEN_INVOKED constexpr auto keys = [](auto&& map) -> decltype(auto) { @@ -92,7 +102,7 @@ namespace boost { namespace hana { constexpr _keys keys{}; #endif - //! Returns a list of the values of the map, in unspecified order. + //! Returns a Sequence of the values of the map, in unspecified order. //! @relates Map #ifdef BOOST_HANA_DOXYGEN_INVOKED constexpr auto values = [](auto&& map) -> decltype(auto) { diff --git a/include/boost/hana/map.hpp b/include/boost/hana/map.hpp index 3bcf45da5..d0b00f49f 100644 --- a/include/boost/hana/map.hpp +++ b/include/boost/hana/map.hpp @@ -15,6 +15,7 @@ Distributed under the Boost Software License, Version 1.0. #include #include #include +#include #include #include #include @@ -38,13 +39,16 @@ namespace boost { namespace hana { //! @cond ////////////////////////////////////////////////////////////////////////// - // map + // make ////////////////////////////////////////////////////////////////////////// - template - constexpr decltype(auto) _make_map::operator()(Pairs&& ...pairs) const { - return detail::create<_map>{}( + template <> + struct make_impl { + template + static constexpr auto apply(Pairs&& ...pairs) { + return detail::create<_map>{}( hana::make(detail::std::forward(pairs)...)); - } + } + }; ////////////////////////////////////////////////////////////////////////// // keys @@ -134,7 +138,7 @@ namespace boost { namespace hana { struct to_impl{} && !models{}>> { template static constexpr decltype(auto) apply(Xs&& xs) - { return hana::unpack(detail::std::forward(xs), map); } + { return hana::unpack(detail::std::forward(xs), make); } }; template diff --git a/test/include/test/auto/iterable.hpp b/test/include/test/auto/iterable.hpp index e28cc9190..c6270e646 100644 --- a/test/include/test/auto/iterable.hpp +++ b/test/include/test/auto/iterable.hpp @@ -97,7 +97,7 @@ namespace boost { namespace hana { namespace test { auto state = test::injection([]{})(); auto f = test::injection([]{}); - auto check = map( + auto check = make( // when length == 0 pair(size_t<0>, [=](auto xs) { BOOST_HANA_CONSTANT_CHECK(equal( diff --git a/test/map.cpp b/test/map.cpp index f343eafe5..d3162a767 100644 --- a/test/map.cpp +++ b/test/map.cpp @@ -40,10 +40,10 @@ namespace boost { namespace hana { namespace test { template <> auto objects = make( - map(), - map(p<1, 1>), - map(p<1, 2>), - map(p<1, 1>, p<2, 2>) + make(), + make(p<1, 1>), + make(p<1, 2>), + make(p<1, 1>, p<2, 2>) ); }}} @@ -62,19 +62,19 @@ int main() { // keys { BOOST_HANA_CONSTANT_CHECK(equal( - keys(map()), + keys(make()), list() )); BOOST_HANA_CONSTANT_CHECK(equal( - keys(map(p<1, 1>)), + keys(make(p<1, 1>)), list(key<1>) )); BOOST_HANA_CONSTANT_CHECK(equal( - keys(map(p<1, 1>, p<2, 2>)), + keys(make(p<1, 1>, p<2, 2>)), list(key<1>, key<2>) )); BOOST_HANA_CONSTANT_CHECK(equal( - keys(map(p<1, 1>, p<2, 2>, p<3, 3>)), + keys(make(p<1, 1>, p<2, 2>, p<3, 3>)), list(key<1>, key<2>, key<3>) )); } @@ -82,19 +82,19 @@ int main() { // values { BOOST_HANA_CONSTANT_CHECK(equal( - values(map()), + values(make()), list() )); BOOST_HANA_CONSTANT_CHECK(equal( - values(map(p<1, 1>)), + values(make(p<1, 1>)), list(val<1>) )); BOOST_HANA_CONSTANT_CHECK(equal( - values(map(p<1, 1>, p<2, 2>)), + values(make(p<1, 1>, p<2, 2>)), list(val<1>, val<2>) )); BOOST_HANA_CONSTANT_CHECK(equal( - values(map(p<1, 1>, p<2, 2>, p<3, 3>)), + values(make(p<1, 1>, p<2, 2>, p<3, 3>)), list(val<1>, val<2>, val<3>) )); } @@ -105,7 +105,7 @@ int main() { { BOOST_HANA_CONSTANT_CHECK(equal( to(record(test::x<1>, test::x<2>)), - map(pair(test::member1, test::x<1>), + make(pair(test::member1, test::x<1>), pair(test::member2, test::x<2>)) )); } @@ -114,19 +114,19 @@ int main() { { BOOST_HANA_CONSTANT_CHECK(equal( to(foldable()), - map() + make() )); BOOST_HANA_CONSTANT_CHECK(equal( to(foldable(p<1, 1>)), - map(p<1, 1>) + make(p<1, 1>) )); BOOST_HANA_CONSTANT_CHECK(equal( to(foldable(p<1, 1>, p<2, 2>)), - map(p<1, 1>, p<2, 2>) + make(p<1, 1>, p<2, 2>) )); BOOST_HANA_CONSTANT_CHECK(equal( to(foldable(p<1, 1>, p<2, 2>, p<3, 3>)), - map(p<1, 1>, p<2, 2>, p<3, 3>) + make(p<1, 1>, p<2, 2>, p<3, 3>) )); } @@ -134,7 +134,7 @@ int main() { { BOOST_HANA_CONSTEXPR_LAMBDA auto check = [=](auto ...xs) { BOOST_HANA_CONSTANT_CHECK( - elem(permutations(list(xs...)), to(map(xs...))) + elem(permutations(list(xs...)), to(make(xs...))) ); }; check(); @@ -150,54 +150,63 @@ int main() { { // equal { - BOOST_HANA_CONSTANT_CHECK(equal(map(), map())); - BOOST_HANA_CONSTANT_CHECK(not_(equal(map(p<1, 1>), map()))); - BOOST_HANA_CONSTANT_CHECK(not_(equal(map(), map(p<1, 1>)))); + BOOST_HANA_CONSTANT_CHECK(equal( + make(), + make() + )); + BOOST_HANA_CONSTANT_CHECK(not_(equal( + make(p<1, 1>), + make()) + )); + BOOST_HANA_CONSTANT_CHECK(not_(equal( + make(), + make(p<1, 1>) + ))); BOOST_HANA_CONSTANT_CHECK(equal( - map(p<1, 1>), - map(p<1, 1>) + make(p<1, 1>), + make(p<1, 1>) )); BOOST_HANA_CONSTANT_CHECK(not_(equal( - map(p<1, 1>), - map(p<1, 2>)) + make(p<1, 1>), + make(p<1, 2>)) )); BOOST_HANA_CONSTANT_CHECK(not_(equal( - map(p<1, 1>), - map(p<2, 1>)) + make(p<1, 1>), + make(p<2, 1>)) )); BOOST_HANA_CONSTANT_CHECK(not_(equal( - map(p<1, 1>), - map(p<1, 1>, p<2, 2>)) + make(p<1, 1>), + make(p<1, 1>, p<2, 2>)) )); BOOST_HANA_CONSTANT_CHECK(equal( - map(p<1, 1>, p<2, 2>), - map(p<1, 1>, p<2, 2>) + make(p<1, 1>, p<2, 2>), + make(p<1, 1>, p<2, 2>) )); BOOST_HANA_CONSTANT_CHECK(equal( - map(p<1, 1>, p<2, 2>), - map(p<2, 2>, p<1, 1>) + make(p<1, 1>, p<2, 2>), + make(p<2, 2>, p<1, 1>) )); BOOST_HANA_CONSTANT_CHECK(not_(equal( - map(p<1, 1>, p<2, 2>), - map(p<9, 1>, p<2, 2>)) + make(p<1, 1>, p<2, 2>), + make(p<9, 1>, p<2, 2>)) )); BOOST_HANA_CONSTANT_CHECK(not_(equal( - map(p<1, 1>, p<2, 2>), - map(p<1, 9>, p<2, 2>)) + make(p<1, 1>, p<2, 2>), + make(p<1, 9>, p<2, 2>)) )); BOOST_HANA_CONSTANT_CHECK(not_(equal( - map(p<1, 1>, p<2, 2>), - map(p<1, 1>, p<9, 2>)) + make(p<1, 1>, p<2, 2>), + make(p<1, 1>, p<9, 2>)) )); BOOST_HANA_CONSTANT_CHECK(not_(equal( - map(p<1, 1>, p<2, 2>), - map(p<1, 1>, p<2, 9>)) + make(p<1, 1>, p<2, 2>), + make(p<1, 1>, p<2, 9>)) )); BOOST_HANA_CONSTANT_CHECK(not_(equal( - map(p<1, 1>, p<2, 2>), - map(p<1, 1>, p<2, 2>, p<3, 3>)) + make(p<1, 1>, p<2, 2>), + make(p<1, 1>, p<2, 2>, p<3, 3>)) )); } } @@ -206,42 +215,54 @@ int main() { { // any_of { - BOOST_HANA_CONSTANT_CHECK(not_(any_of(map(), equal.to(key<1>)))); + BOOST_HANA_CONSTANT_CHECK( + not_(any_of(make(), equal.to(key<1>))) + ); - BOOST_HANA_CONSTANT_CHECK(any_of(map(p<1, 1>), equal.to(key<1>))); - BOOST_HANA_CONSTANT_CHECK(not_(any_of(map(p<1, 1>), equal.to(key<2>)))); + BOOST_HANA_CONSTANT_CHECK( + any_of(make(p<1, 1>), equal.to(key<1>)) + ); + BOOST_HANA_CONSTANT_CHECK( + not_(any_of(make(p<1, 1>), equal.to(key<2>))) + ); - BOOST_HANA_CONSTANT_CHECK(any_of(map(p<1, 1>, p<2, 2>), equal.to(key<1>))); - BOOST_HANA_CONSTANT_CHECK(any_of(map(p<1, 1>, p<2, 2>), equal.to(key<2>))); - BOOST_HANA_CONSTANT_CHECK(not_(any_of(map(p<1, 1>, p<2, 2>), equal.to(key<3>)))); + BOOST_HANA_CONSTANT_CHECK( + any_of(make(p<1, 1>, p<2, 2>), equal.to(key<1>)) + ); + BOOST_HANA_CONSTANT_CHECK( + any_of(make(p<1, 1>, p<2, 2>), equal.to(key<2>)) + ); + BOOST_HANA_CONSTANT_CHECK( + not_(any_of(make(p<1, 1>, p<2, 2>), equal.to(key<3>))) + ); } // find { BOOST_HANA_CONSTANT_CHECK(equal( - find(map(), equal.to(key<1>)), + find(make(), equal.to(key<1>)), nothing )); BOOST_HANA_CONSTANT_CHECK(equal( - find(map(p<1, 1>), equal.to(key<1>)), + find(make(p<1, 1>), equal.to(key<1>)), just(val<1>) )); BOOST_HANA_CONSTANT_CHECK(equal( - find(map(p<1, 1>), equal.to(key<2>)), + find(make(p<1, 1>), equal.to(key<2>)), nothing )); BOOST_HANA_CONSTANT_CHECK(equal( - find(map(p<1, 1>, p<2, 2>), equal.to(key<1>)), + find(make(p<1, 1>, p<2, 2>), equal.to(key<1>)), just(val<1>) )); BOOST_HANA_CONSTANT_CHECK(equal( - find(map(p<1, 1>, p<2, 2>), equal.to(key<2>)), + find(make(p<1, 1>, p<2, 2>), equal.to(key<2>)), just(val<2>) )); BOOST_HANA_CONSTANT_CHECK(equal( - find(map(p<1, 1>, p<2, 2>), equal.to(key<3>)), + find(make(p<1, 1>, p<2, 2>), equal.to(key<3>)), nothing )); }