Skip to content

Commit

Permalink
[SetTheoretic] Add SetTheoretic concept
Browse files Browse the repository at this point in the history
It adds SetTheoretic concept for functions-
union, intersection, difference, symmetric_difference.

Closes #357
  • Loading branch information
shreyans800755 committed Aug 20, 2017
1 parent 59393ca commit 584a8e0
Show file tree
Hide file tree
Showing 10 changed files with 150 additions and 12 deletions.
6 changes: 6 additions & 0 deletions example/misc/infinite_set.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@

#include <boost/hana/and.hpp>
#include <boost/hana/any_of.hpp>
#include <boost/hana/concept/set_theoretic.hpp>
#include <boost/hana/flatten.hpp>
#include <boost/hana/functional/compose.hpp>
#include <boost/hana/functional/partial.hpp>
Expand Down Expand Up @@ -48,6 +49,11 @@ constexpr auto doubleton(X x, Y y) {
}

namespace boost { namespace hana {
template <>
struct SetTheoretic<infinite_set_tag> {
static constexpr bool value = true;
};

template <>
struct union_impl<infinite_set_tag> {
template <typename Xs, typename Ys>
Expand Down
1 change: 1 addition & 0 deletions include/boost/hana/concept.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,7 @@ Distributed under the Boost Software License, Version 1.0.
#include <boost/hana/concept/ring.hpp>
#include <boost/hana/concept/searchable.hpp>
#include <boost/hana/concept/sequence.hpp>
#include <boost/hana/concept/set_theoretic.hpp>
#include <boost/hana/concept/struct.hpp>

#endif // !BOOST_HANA_CONCEPT_HPP
37 changes: 37 additions & 0 deletions include/boost/hana/concept/set_theoretic.hpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,37 @@
/*!
@file
Defines `boost::hana::SetTheoretic`.
@copyright Shreyans Doshi 2017
Distributed under the Boost Software License, Version 1.0.
(See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt)
*/

#ifndef BOOST_HANA_CONCEPT_SET_THEORETIC_HPP
#define BOOST_HANA_CONCEPT_SET_THEORETIC_HPP

#include <boost/hana/fwd/concept/set_theoretic.hpp>

#include <boost/hana/config.hpp>
#include <boost/hana/core/default.hpp>
#include <boost/hana/core/tag_of.hpp>
#include <boost/hana/detail/integral_constant.hpp>
#include <boost/hana/difference.hpp>
#include <boost/hana/intersection.hpp>
#include <boost/hana/symmetric_difference.hpp>
#include <boost/hana/union.hpp>


BOOST_HANA_NAMESPACE_BEGIN
template <typename STh>
struct SetTheoretic
: hana::integral_constant<bool,
!is_default<difference_impl<typename tag_of<STh>::type>>::value &&
!is_default<intersection_impl<typename tag_of<STh>::type>>::value &&
!is_default<symmetric_difference_impl<typename tag_of<STh>::type>>::value &&
!is_default<union_impl<typename tag_of<STh>::type>>::value
>
{ };
BOOST_HANA_NAMESPACE_END

#endif // !BOOST_HANA_CONCEPT_SET_THEORETIC_HPP
17 changes: 14 additions & 3 deletions include/boost/hana/difference.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ Distributed under the Boost Software License, Version 1.0.

#include <boost/hana/fwd/difference.hpp>

#include <boost/hana/concept/set_theoretic.hpp>
#include <boost/hana/config.hpp>
#include <boost/hana/core/dispatch.hpp>
#include <boost/hana/erase_key.hpp>
Expand All @@ -21,11 +22,21 @@ BOOST_HANA_NAMESPACE_BEGIN
//! @cond
template <typename Xs, typename Ys>
constexpr auto difference_t::operator()(Xs&& xs, Ys&& ys) const {
using S = typename hana::tag_of<Xs>::type;
using Difference = BOOST_HANA_DISPATCH_IF(difference_impl<S>,
true
using TX = typename hana::tag_of<Xs>::type;
using TY = typename hana::tag_of<Ys>::type;
using Difference = BOOST_HANA_DISPATCH_IF(difference_impl<TX>,
hana::SetTheoretic<TX>::value &&
std::is_same<TX, TY>::value
);

#ifndef BOOST_HANA_CONFIG_DISABLE_CONCEPT_CHECKS
static_assert(hana::SetTheoretic<TX>::value,
"hana::difference(xs, ys) requires 'xs' to be SetTheoretic");

static_assert(std::is_same<TX, TY>::value,
"hana::difference(xs, ys) requires 'xs' and 'ys' to be SetTheoretic");
#endif

return Difference::apply(static_cast<Xs&&>(xs), static_cast<Ys&&>(ys));
}
//! @endcond
Expand Down
37 changes: 37 additions & 0 deletions include/boost/hana/fwd/concept/set_theoretic.hpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,37 @@
/*!
@file
Forward declares `boost::hana::SetTheoretic`.
@copyright Shreyans Doshi 2017
Distributed under the Boost Software License, Version 1.0.
(See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt)
*/

#ifndef BOOST_HANA_FWD_CONCEPT_SET_THEORETIC_HPP
#define BOOST_HANA_FWD_CONCEPT_SET_THEORETIC_HPP

#include <boost/hana/config.hpp>


BOOST_HANA_NAMESPACE_BEGIN
//! @ingroup group-concepts
//! @defgroup group-SetTheoretic SetTheoretic
//! The `SetTheoretic` concept represents data structures supporting
//! set-theoretic functions like union, instersection, difference,
//! and symmetric_difference.
//!
//! Minimal complete definition
//! ---------------------------
//! `union_`, `intersection`, `difference` and `symmetric_difference`
//!
//! Concrete models
//! ---------------
//! `hana::set`, `hana::map`
//!
//!
//! [1]: https://github.com/boostorg/hana/issues/357
template <typename STh>
struct SetTheoretic;
BOOST_HANA_NAMESPACE_END

#endif // !BOOST_HANA_FWD_CONCEPT_SET_THEORETIC_HPP
17 changes: 14 additions & 3 deletions include/boost/hana/intersection.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ Distributed under the Boost Software License, Version 1.0.

#include <boost/hana/fwd/intersection.hpp>

#include <boost/hana/concept/set_theoretic.hpp>
#include <boost/hana/config.hpp>
#include <boost/hana/core/dispatch.hpp>

Expand All @@ -20,10 +21,20 @@ BOOST_HANA_NAMESPACE_BEGIN
//! @cond
template <typename Xs, typename Ys>
constexpr auto intersection_t::operator()(Xs&& xs, Ys&& ys) const {
using S = typename hana::tag_of<Xs>::type;
using Intersection = BOOST_HANA_DISPATCH_IF(intersection_impl<S>,
true
using TX = typename hana::tag_of<Xs>::type;
using TY = typename hana::tag_of<Ys>::type;
using Intersection = BOOST_HANA_DISPATCH_IF(intersection_impl<TX>,
hana::SetTheoretic<TX>::value &&
std::is_same<TX, TY>::value
);

#ifndef BOOST_HANA_CONFIG_DISABLE_CONCEPT_CHECKS
static_assert(hana::SetTheoretic<TX>::value,
"hana::intersection(xs, ys) requires 'xs' to be SetTheoretic");

static_assert(std::is_same<TX, TY>::value,
"hana::intersection(xs, ys) requires 'xs' and 'ys' to be SetTheoretic");
#endif

return Intersection::apply(static_cast<Xs&&>(xs), static_cast<Ys&&>(ys));
}
Expand Down
7 changes: 7 additions & 0 deletions include/boost/hana/map.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@ Distributed under the Boost Software License, Version 1.0.
#include <boost/hana/concept/comparable.hpp>
#include <boost/hana/concept/constant.hpp>
#include <boost/hana/concept/product.hpp>
#include <boost/hana/concept/set_theoretic.hpp>
#include <boost/hana/config.hpp>
#include <boost/hana/contains.hpp>
#include <boost/hana/core/is_a.hpp>
Expand Down Expand Up @@ -207,6 +208,12 @@ BOOST_HANA_NAMESPACE_BEGIN
using type = detail::map_impl<HashTable, Storage>;
};
}

template <>
struct SetTheoretic<map_tag> {
static constexpr bool value = true;
};


//////////////////////////////////////////////////////////////////////////
// make<map_tag>
Expand Down
6 changes: 6 additions & 0 deletions include/boost/hana/set.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ Distributed under the Boost Software License, Version 1.0.
#include <boost/hana/concept/comparable.hpp>
#include <boost/hana/concept/constant.hpp>
#include <boost/hana/concept/hashable.hpp>
#include <boost/hana/concept/set_theoretic.hpp>
#include <boost/hana/config.hpp>
#include <boost/hana/contains.hpp>
#include <boost/hana/core/make.hpp>
Expand Down Expand Up @@ -77,6 +78,11 @@ BOOST_HANA_NAMESPACE_BEGIN
constexpr set(set&& other) = default;
};
//! @endcond

template <>
struct SetTheoretic<set_tag> {
static constexpr bool value = true;
};

//////////////////////////////////////////////////////////////////////////
// Operators
Expand Down
17 changes: 14 additions & 3 deletions include/boost/hana/symmetric_difference.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ Distributed under the Boost Software License, Version 1.0.

#include <boost/hana/fwd/symmetric_difference.hpp>

#include <boost/hana/concept/set_theoretic.hpp>
#include <boost/hana/config.hpp>
#include <boost/hana/core/dispatch.hpp>
#include <boost/hana/difference.hpp>
Expand All @@ -22,10 +23,20 @@ BOOST_HANA_NAMESPACE_BEGIN
//! @cond
template <typename Xs, typename Ys>
constexpr auto symmetric_difference_t::operator()(Xs&& xs, Ys&& ys) const {
using S = typename hana::tag_of<Xs>::type;
using SymmetricDifference = BOOST_HANA_DISPATCH_IF(symmetric_difference_impl<S>,
true
using TX = typename hana::tag_of<Xs>::type;
using TY = typename hana::tag_of<Ys>::type;
using SymmetricDifference = BOOST_HANA_DISPATCH_IF(symmetric_difference_impl<TX>,
hana::SetTheoretic<TX>::value &&
std::is_same<TX, TY>::value
);

#ifndef BOOST_HANA_CONFIG_DISABLE_CONCEPT_CHECKS
static_assert(hana::SetTheoretic<TX>::value,
"hana::symmetric_difference(xs, ys) requires 'xs' to be SetTheoretic");

static_assert(std::is_same<TX, TY>::value,
"hana::symmetric_difference(xs, ys) requires 'xs' and 'ys' to be SetTheoretic");
#endif

return SymmetricDifference::apply(static_cast<Xs&&>(xs), static_cast<Ys&&>(ys));
}
Expand Down
17 changes: 14 additions & 3 deletions include/boost/hana/union.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ Distributed under the Boost Software License, Version 1.0.

#include <boost/hana/fwd/union.hpp>

#include <boost/hana/concept/set_theoretic.hpp>
#include <boost/hana/config.hpp>
#include <boost/hana/core/dispatch.hpp>

Expand All @@ -20,11 +21,21 @@ BOOST_HANA_NAMESPACE_BEGIN
//! @cond
template <typename Xs, typename Ys>
constexpr auto union_t::operator()(Xs&& xs, Ys&& ys) const {
using S = typename hana::tag_of<Xs>::type;
using Union = BOOST_HANA_DISPATCH_IF(union_impl<S>,
true
using TX = typename hana::tag_of<Xs>::type;
using TY = typename hana::tag_of<Ys>::type;
using Union = BOOST_HANA_DISPATCH_IF(union_impl<TX>,
hana::SetTheoretic<TX>::value &&
std::is_same<TX, TY>::value
);

#ifndef BOOST_HANA_CONFIG_DISABLE_CONCEPT_CHECKS
static_assert(hana::SetTheoretic<TX>::value,
"hana::union_(xs, ys) requires 'xs' to be SetTheoretic");

static_assert(std::is_same<TX, TY>::value,
"hana::union_(xs, ys) requires 'xs' and 'ys' to be SetTheoretic");
#endif

return Union::apply(static_cast<Xs&&>(xs), static_cast<Ys&&>(ys));
}
//! @endcond
Expand Down

0 comments on commit 584a8e0

Please sign in to comment.