]>
Commit | Line | Data |
---|---|---|
7c673cae FG |
1 | /*! |
2 | @file | |
3 | Forward declares `boost::hana::maximum`. | |
4 | ||
5 | @copyright Louis Dionne 2013-2016 | |
6 | Distributed under the Boost Software License, Version 1.0. | |
7 | (See accompanying file LICENSE.md or copy at http://boost.org/LICENSE_1_0.txt) | |
8 | */ | |
9 | ||
10 | #ifndef BOOST_HANA_FWD_MAXIMUM_HPP | |
11 | #define BOOST_HANA_FWD_MAXIMUM_HPP | |
12 | ||
13 | #include <boost/hana/config.hpp> | |
14 | #include <boost/hana/core/when.hpp> | |
15 | #include <boost/hana/detail/nested_by_fwd.hpp> | |
16 | ||
17 | ||
18 | BOOST_HANA_NAMESPACE_BEGIN | |
19 | //! Return the greatest element of a non-empty structure with respect to | |
20 | //! a `predicate`, by default `less`. | |
21 | //! @ingroup group-Foldable | |
22 | //! | |
23 | //! Given a non-empty structure and an optional binary predicate | |
24 | //! (`less` by default), `maximum` returns the greatest element of | |
25 | //! the structure, i.e. an element which is greater than or equal to | |
26 | //! every other element in the structure, according to the predicate. | |
27 | //! | |
28 | //! If the structure contains heterogeneous objects, then the predicate | |
29 | //! must return a compile-time `Logical`. If no predicate is provided, | |
30 | //! the elements in the structure must be Orderable, or compile-time | |
31 | //! Orderable if the structure is heterogeneous. | |
32 | //! | |
33 | //! | |
34 | //! Signature | |
35 | //! --------- | |
36 | //! Given a Foldable `F`, a Logical `Bool` and a predicate | |
37 | //! \f$ \mathtt{pred} : T \times T \to Bool \f$, `maximum` has the | |
38 | //! following signatures. For the variant with a provided predicate, | |
39 | //! \f[ | |
40 | //! \mathtt{maximum} : F(T) \times (T \times T \to Bool) \to T | |
41 | //! \f] | |
42 | //! | |
43 | //! for the variant without a custom predicate, `T` is required to be | |
44 | //! Orderable. The signature is then | |
45 | //! \f[ | |
46 | //! \mathtt{maximum} : F(T) \to T | |
47 | //! \f] | |
48 | //! | |
49 | //! @param xs | |
50 | //! The structure to find the greatest element of. | |
51 | //! | |
52 | //! @param predicate | |
53 | //! A function called as `predicate(x, y)`, where `x` and `y` are elements | |
54 | //! of the structure. `predicate` should be a strict weak ordering on the | |
55 | //! elements of the structure and its return value should be a Logical, | |
56 | //! or a compile-time Logical if the structure is heterogeneous. | |
57 | //! | |
58 | //! ### Example | |
59 | //! @include example/maximum.cpp | |
60 | //! | |
61 | //! | |
62 | //! Syntactic sugar (`maximum.by`) | |
63 | //! ------------------------------ | |
64 | //! `maximum` can be called in a third way, which provides a nice syntax | |
65 | //! especially when working with the `ordering` combinator: | |
66 | //! @code | |
67 | //! maximum.by(predicate, xs) == maximum(xs, predicate) | |
68 | //! maximum.by(predicate) == maximum(-, predicate) | |
69 | //! @endcode | |
70 | //! | |
71 | //! where `maximum(-, predicate)` denotes the partial application of | |
72 | //! `maximum` to `predicate`. | |
73 | //! | |
74 | //! ### Example | |
75 | //! @include example/maximum_by.cpp | |
76 | //! | |
77 | //! | |
78 | //! Tag dispatching | |
79 | //! --------------- | |
80 | //! Both the non-predicated version and the predicated versions of | |
81 | //! `maximum` are tag-dispatched methods, and hence they can be | |
82 | //! customized independently. One reason for this is that some | |
83 | //! structures are able to provide a much more efficient implementation | |
84 | //! of `maximum` when the `less` predicate is used. Here is how the | |
85 | //! different versions of `maximum` are dispatched: | |
86 | //! @code | |
87 | //! maximum(xs) -> maximum_impl<tag of xs>::apply(xs) | |
88 | //! maximum(xs, pred) -> maximum_pred_impl<tag of xs>::apply(xs, pred) | |
89 | //! @endcode | |
90 | //! | |
91 | //! Also note that `maximum.by` is not tag-dispatched on its own, since it | |
92 | //! is just syntactic sugar for calling the corresponding `maximum`. | |
93 | #ifdef BOOST_HANA_DOXYGEN_INVOKED | |
94 | constexpr auto maximum = [](auto&& xs[, auto&& predicate]) -> decltype(auto) { | |
95 | return tag-dispatched; | |
96 | }; | |
97 | #else | |
98 | template <typename T, typename = void> | |
99 | struct maximum_impl : maximum_impl<T, when<true>> { }; | |
100 | ||
101 | template <typename T, typename = void> | |
102 | struct maximum_pred_impl : maximum_pred_impl<T, when<true>> { }; | |
103 | ||
104 | struct maximum_t : detail::nested_by<maximum_t> { | |
105 | template <typename Xs> | |
106 | constexpr decltype(auto) operator()(Xs&& xs) const; | |
107 | ||
108 | template <typename Xs, typename Predicate> | |
109 | constexpr decltype(auto) operator()(Xs&& xs, Predicate&& pred) const; | |
110 | }; | |
111 | ||
112 | constexpr maximum_t maximum{}; | |
113 | #endif | |
114 | BOOST_HANA_NAMESPACE_END | |
115 | ||
116 | #endif // !BOOST_HANA_FWD_MAXIMUM_HPP |