[PATCH v2] libstdc++: improve documentation for bits/stl_function.h [PR51539]

Jonathan Wakely jwakely@redhat.com
Wed Aug 18 12:49:56 GMT 2021


On Tue, 17 Aug 2021 at 21:39, Krzysztof Żelechowski
<giecrilj@stegny.2a.pl> wrote:
>
> PR  libstdc++/PR51539
>
> ChangeLog
>         * libstdc++-v3/include/bits/stl_function.h: Improve documentation.
>
> diff --git a/libstdc++-v3/include/bits/stl_function.h b/libstdc++-v3/include/
> bits/stl_function.h
> index 073018d522d..a0b84f93d18 100644
> --- a/libstdc++-v3/include/bits/stl_function.h
> +++ b/libstdc++-v3/include/bits/stl_function.h
> @@ -112,7 +112,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>      };
>
>    /**
> -   *  This is one of the @link functors functor base classes@endlink.
> +   *  a base class for @link functors functors@endlink taking 2 parameters
>     */
>    template<typename _Arg1, typename _Arg2, typename _Result>
>      struct binary_function
> @@ -162,60 +162,66 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>      struct negate;
>  #endif
>
> -  /// One of the @link arithmetic_functors math functors@endlink.
> +  /// An @link arithmetic_functors arithmetic functor@endlink representing
> addition

I think it would be better to remove all the @link commands. They are
already defined in a @{ group so they are grouped with the arithmetic
functors, and the @link just makes the comment hard to read in the
source. I like to optimize for reading the source, not just reading
the Doxygen docs (which almost nobody actually looks at). i.e. just:

/// A function object representing addition



>    template<typename _Tp>
>      struct plus : public binary_function<_Tp, _Tp, _Tp>
>      {
> +        /// Returns the sum (`operator+`) of two parameters.
>        _GLIBCXX14_CONSTEXPR
>        _Tp
>        operator()(const _Tp& __x, const _Tp& __y) const
>        { return __x + __y; }
>      };
>
> -  /// One of the @link arithmetic_functors math functors@endlink.
> +  /// An @link arithmetic_functors arithmetic functor@endlink representing
> subtraction
>    template<typename _Tp>
>      struct minus : public binary_function<_Tp, _Tp, _Tp>
>      {
> +        /// Returns the difference (`operator-`) between parameter 2 and
> parameter 1.

I think this is conventionally called the difference _of_ x and y, not
the difference between y and x.

And we can use the parameter names:

/// Returns the difference (`operator-`) of `x` and `y`


>        _GLIBCXX14_CONSTEXPR
>        _Tp
>        operator()(const _Tp& __x, const _Tp& __y) const
>        { return __x - __y; }
>      };
>
> -  /// One of the @link arithmetic_functors math functors@endlink.
> +  /// An @link arithmetic_functors arithmetic functor@endlink representing
> multiplication
>    template<typename _Tp>
>      struct multiplies : public binary_function<_Tp, _Tp, _Tp>
>      {
> +        /// Returns the product (`operator*`) of two parameters.
>        _GLIBCXX14_CONSTEXPR
>        _Tp
>        operator()(const _Tp& __x, const _Tp& __y) const
>        { return __x * __y; }
>      };
>
> -  /// One of the @link arithmetic_functors math functors@endlink.
> +  /// An @link arithmetic_functors arithmetic functor@endlink representing
> division
>    template<typename _Tp>
>      struct divides : public binary_function<_Tp, _Tp, _Tp>
>      {
> +        /// Returns the quotient (`operator/`) of filling parameter 2 with
> parameter 1.

Nobody uses this terminology.

/// Returns the quotient (`operator/`) of `x` and `y`

>        _GLIBCXX14_CONSTEXPR
>        _Tp
>        operator()(const _Tp& __x, const _Tp& __y) const
>        { return __x / __y; }
>      };
>
> -  /// One of the @link arithmetic_functors math functors@endlink.
> +  /// An @link arithmetic_functors arithmetic functor@endlink representing
> remainder

This doesn't work grammatically. All the other cases describe an
operation, but "remainder" is not an operation, it's the result of an
operation.

You could say "yielding the remainder" instead of "representing remainder".


>    template<typename _Tp>
>      struct modulus : public binary_function<_Tp, _Tp, _Tp>
>      {
> +        /// Returns the remainder (`operator%`) after filling parameter 2
> with parameter 1.

Nobody uses this terminology. I suggest:

/// Returns the remainder (`operator%`) from the division of `x` by `y`


>        _GLIBCXX14_CONSTEXPR
>        _Tp
>        operator()(const _Tp& __x, const _Tp& __y) const
>        { return __x % __y; }
>      };
>
> -  /// One of the @link arithmetic_functors math functors@endlink.
> +  /// An @link arithmetic_functors arithmetic functor@endlink representing
> reflexion

Bad terminology again. This one's harder to state briefly, but I
suggest "yielding the negative"

>    template<typename _Tp>
>      struct negate : public unary_function<_Tp, _Tp>
>      {
> +        /// Returns the opposite value (`operator-`) to the parameter.

"the negative (`operator-`) of the parameter"

This is the terminology used in the C and C++ standards for the unary
minus operator.

>        _GLIBCXX14_CONSTEXPR
>        _Tp
>        operator()(const _Tp& __x) const
> @@ -225,10 +231,12 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>  #if __cplusplus > 201103L
>
>  #define __cpp_lib_transparent_operators 201510
> -
> +  /// An @link arithmetic_functors arithmetic functor@endlink representing
> generic addition

I'm not sure "generic addition" really helps here. What is generic
addition? How is it different from normal addition?

Maybe we want to add a "@defgroup heteregeneous_comparisons" for the
<void> specializations which explains that they do not require (and
convert) their arguments to the same type. That can also explain the
is_transparent member, and give an example of using them with an
associative container to avoid expensive conversions during lookup.

> +  /// @since C++11

No, @since C++14 (and similarly for all the other <void> specializations).

>    template<>
>      struct plus<void>
>      {
> +        /// Returns the sum (`operator+`) of two parameters.
>        template <typename _Tp, typename _Up>
>         _GLIBCXX14_CONSTEXPR
>         auto
> @@ -240,10 +248,12 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>        typedef __is_transparent is_transparent;
>      };
>
> -  /// One of the @link arithmetic_functors math functors@endlink.
> +  /// An @link arithmetic_functors arithmetic functor@endlink representing
> generic subtraction
> +  /// @since C++11
>    template<>
>      struct minus<void>
>      {
> +       /// Returns the difference (`operator-`) between parameter 2 and
> parameter 1.
>        template <typename _Tp, typename _Up>
>         _GLIBCXX14_CONSTEXPR
>         auto
> @@ -255,10 +265,12 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>        typedef __is_transparent is_transparent;
>      };
>
> -  /// One of the @link arithmetic_functors math functors@endlink.
> +  /// An @link arithmetic_functors arithmetic functor@endlink representing
> generic multiplication
> +  /// @since C++11
>    template<>
>      struct multiplies<void>
>      {
> +        /// Returns the product (`operator*`) of two parameters.
>        template <typename _Tp, typename _Up>
>         _GLIBCXX14_CONSTEXPR
>         auto
> @@ -270,10 +282,12 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>        typedef __is_transparent is_transparent;
>      };
>
> -  /// One of the @link arithmetic_functors math functors@endlink.
> +  /// An @link arithmetic_functors arithmetic functor@endlink representing
> generic division
> +  /// @since C++11
>    template<>
>      struct divides<void>
>      {
> +        /// Returns the quotient (`operator/`) of filling parameter 2 with
> parameter 1.
>        template <typename _Tp, typename _Up>
>         _GLIBCXX14_CONSTEXPR
>         auto
> @@ -285,10 +299,12 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>        typedef __is_transparent is_transparent;
>      };
>
> -  /// One of the @link arithmetic_functors math functors@endlink.
> +  /// An @link arithmetic_functors arithmetic functor@endlink representing
> generic remainder
> +  /// @since C++11
>    template<>
>      struct modulus<void>
>      {
> +        /// Returns the remainder (`operator%`) after filling parameter 2
> with parameter 1.
>        template <typename _Tp, typename _Up>
>         _GLIBCXX14_CONSTEXPR
>         auto
> @@ -300,10 +316,12 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>        typedef __is_transparent is_transparent;
>      };
>
> -  /// One of the @link arithmetic_functors math functors@endlink.
> +  /// An @link arithmetic_functors arithmetic functor@endlink representing
> generic reflexion
> +  /// @since C++11
>    template<>
>      struct negate<void>
>      {
> +        /// Returns the opposite value (`operator-`) to the parameter.
>        template <typename _Tp>
>         _GLIBCXX14_CONSTEXPR
>         auto
> @@ -346,60 +364,66 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>      struct less_equal;
>  #endif
>
> -  /// One of the @link comparison_functors comparison functors@endlink.
> +  /// a @link comparison_functors comparison functor@endlink representing
> equality

The sentence should start with a capital letter.

>    template<typename _Tp>
>      struct equal_to : public binary_function<_Tp, _Tp, bool>
>      {
> +       /// Tests whether two parameters are equal (`operator==`).
>        _GLIBCXX14_CONSTEXPR
>        bool
>        operator()(const _Tp& __x, const _Tp& __y) const
>        { return __x == __y; }
>      };
>
> -  /// One of the @link comparison_functors comparison functors@endlink.
> +  /// a @link comparison_functors comparison functor@endlink representing
> inequality
>    template<typename _Tp>
>      struct not_equal_to : public binary_function<_Tp, _Tp, bool>
>      {
> +       /// Tests whether two parameters are different (`operator!=`).

I think I prefer "not equal" to "different". It's more precise, and
implies the correspondence with operator== (rather than with operator-
which you've described as difference earlier in the file).


>        _GLIBCXX14_CONSTEXPR
>        bool
>        operator()(const _Tp& __x, const _Tp& __y) const
>        { return __x != __y; }
>      };
>
> -  /// One of the @link comparison_functors comparison functors@endlink.
> +  /// a @link comparison_functors comparison functor@endlink representing
> superiority ("greater than")

I don't like "superiority" and "inferiority". In general, if neither
Wikipedia nor Wolfram Mathworld uses the term this way, it's clearly
not the right choice.

I think it would be better to just say: representing 'greater than'

That is shorter, and clearer.


>    template<typename _Tp>
>      struct greater : public binary_function<_Tp, _Tp, bool>
>      {
> +       /// Tests whether parameter 1 is greater (`operator>`) than parameter
> 2.

I don't like the use of "parameter 1" and "parameter 2" here. They
have names, we can just say `x` and `y`.

And if we're doing that, I wonder why we don't just say "@returns `x >
y`" which is precise and correct. It's not accurate to say `operator>`
because there is no such function for fundamental types, e.g.
std::greater<int>()(1, 2) does not use a function called `operator>`
it uses the built-in > operator. There is a distinction, and the way
you're documenting it is not strictly correct.

We could do that for every operator() that you're documenting.
Personally I think that would be much better (and it's also how
cppreference.com describes these).


>        _GLIBCXX14_CONSTEXPR
>        bool
>        operator()(const _Tp& __x, const _Tp& __y) const
>        { return __x > __y; }
>      };
>
> -  /// One of the @link comparison_functors comparison functors@endlink.
> +  /// a @link comparison_functors comparison functor@endlink representing
> inferiority ("less than")
>    template<typename _Tp>
>      struct less : public binary_function<_Tp, _Tp, bool>
>      {
> +       /// Tests whether parameter 1 is smaller (`operator<`) than parameter
> 2.
>        _GLIBCXX14_CONSTEXPR
>        bool
>        operator()(const _Tp& __x, const _Tp& __y) const
>        { return __x < __y; }
>      };
>
> -  /// One of the @link comparison_functors comparison functors@endlink.
> +  /// a @link comparison_functors comparison functor@endlink representing
> weak superiority ("at least")

If I search Google for "weak superiority" all the hits are for a
completely unrelated term:
https://portal.research.lu.se/ws/files/85707643/Value_Superiority_Oxford_Handbook_of_Value_Theory.pdf

The class template is called "greater_equal" and uses the >= operator,
why are you going out of your way to use different terms?

>    template<typename _Tp>
>      struct greater_equal : public binary_function<_Tp, _Tp, bool>
>      {
> +       /// Tests whether parameter 1 is at least as big (`operator>=`) as
> parameter 2.

Again, I don't think there's a better way to say it than:

/// @returns `x >= y`



>        _GLIBCXX14_CONSTEXPR
>        bool
>        operator()(const _Tp& __x, const _Tp& __y) const
>        { return __x >= __y; }
>      };
>
> -  /// One of the @link comparison_functors comparison functors@endlink.
> +  /// a @link comparison_functors comparison functor@endlink representing
> weak inferiority ("at most")
>    template<typename _Tp>
>      struct less_equal : public binary_function<_Tp, _Tp, bool>
>      {
> +       /// Tests whether parameter 1 is at most as big (`operator<=`) as
> parameter 2.
>        _GLIBCXX14_CONSTEXPR
>        bool
>        operator()(const _Tp& __x, const _Tp& __y) const
> @@ -483,10 +507,12 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>      };
>
>  #if __cplusplus >= 201402L
> -  /// One of the @link comparison_functors comparison functors@endlink.
> +  /// a @link comparison_functors comparison functor@endlink representing
> generic equality
> +  /// @since C++14
>    template<>
>      struct equal_to<void>
>      {
> +       /// Tests whether two parameters are equal (`operator==`).
>        template <typename _Tp, typename _Up>
>         constexpr auto
>         operator()(_Tp&& __t, _Up&& __u) const
> @@ -497,10 +523,12 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>        typedef __is_transparent is_transparent;
>      };
>
> -  /// One of the @link comparison_functors comparison functors@endlink.
> +  /// a @link comparison_functors comparison functor@endlink representing
> generic inequality
> +  /// @since C++14
>    template<>
>      struct not_equal_to<void>
>      {
> +       /// Tests whether two parameters are different (`operator!=`).
>        template <typename _Tp, typename _Up>
>         constexpr auto
>         operator()(_Tp&& __t, _Up&& __u) const
> @@ -511,10 +539,15 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>        typedef __is_transparent is_transparent;
>      };
>
> -  /// One of the @link comparison_functors comparison functors@endlink.
> +  /// a @link comparison_functors comparison functor@endlink representing
> generic superiority ("greater than")
> +  /// @since C++14
>    template<>
>      struct greater<void>
>      {
> +       /** Tests whether parameter 1 is greater (`operator>`) than parameter
> 2.
> +        * If both parameters can be converted to pointers and cannot be
> compared using (`operator>`),
> +        * compare the pointers instead, without considering their common base
> types, if any.
> +        */
>        template <typename _Tp, typename _Up>
>         constexpr auto
>         operator()(_Tp&& __t, _Up&& __u) const
> @@ -525,6 +558,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>                         __ptr_cmp<_Tp, _Up>{});
>         }
>
> +       /// If both parameters are pointers, compare the pointers to their
> common base type instead.
>        template<typename _Tp, typename _Up>
>         constexpr bool
>         operator()(_Tp* __t, _Up* __u) const noexcept
> @@ -573,10 +607,15 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>               is_convertible<_Up, const volatile void*>>;
>      };
>
> -  /// One of the @link comparison_functors comparison functors@endlink.
> +  /// a @link comparison_functors comparison functor@endlink representing
> generic inferiority ("less than")
> +  /// @since C++14
>    template<>
>      struct less<void>
>      {
> +       /** Tests whether parameter 1 is smaller (`operator<`) than parameter
> 2.
> +        * If both parameters can be converted to pointers and cannot be
> compared using (`operator<`),
> +        * compare the pointers instead, without considering their common base
> types, if any.
> +        */
>        template <typename _Tp, typename _Up>
>         constexpr auto
>         operator()(_Tp&& __t, _Up&& __u) const
> @@ -587,7 +626,8 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>                         __ptr_cmp<_Tp, _Up>{});
>         }
>
> -      template<typename _Tp, typename _Up>
> +        /// If both parameters are pointers, compare the pointers to their
> common base type instead.
> +     template<typename _Tp, typename _Up>
>         constexpr bool
>         operator()(_Tp* __t, _Up* __u) const noexcept
>         { return less<common_type_t<_Tp*, _Up*>>{}(__t, __u); }
> @@ -635,10 +675,15 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>               is_convertible<_Up, const volatile void*>>;
>      };
>
> -  /// One of the @link comparison_functors comparison functors@endlink.
> +  /// a @link comparison_functors comparison functor@endlink representing
> generic weak superiority ("at least")
> +  /// @since C++14
>    template<>
>      struct greater_equal<void>
>      {
> +       /** Tests whether parameter 1 is at least as big (`operator>=`) as
> parameter 2.
> +        * If both parameters can be converted to pointers and cannot be
> compared using (`operator>=`),
> +        * compare the pointers instead, without considering their common base
> types, if any.
> +        */
>        template <typename _Tp, typename _Up>
>         constexpr auto
>         operator()(_Tp&& __t, _Up&& __u) const
> @@ -649,6 +694,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>                         __ptr_cmp<_Tp, _Up>{});
>         }
>
> +        /// If both parameters are pointers, compare the pointers to their
> common base type instead.
>        template<typename _Tp, typename _Up>
>         constexpr bool
>         operator()(_Tp* __t, _Up* __u) const noexcept
> @@ -697,10 +743,15 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>               is_convertible<_Up, const volatile void*>>;
>      };
>
> -  /// One of the @link comparison_functors comparison functors@endlink.
> +  /// a @link comparison_functors comparison functor@endlink representing
> generic weak inferiority ("at most")
> +  /// @since C++14
>    template<>
>      struct less_equal<void>
>      {
> +       /** Tests whether parameter 1 is at most as big (`operator<=`) as
> parameter 2.
> +        * If both parameters can be converted to pointers and cannot be
> compared using (`operator<=`),
> +        * compare the pointers instead, without considering their common base
> types, if any.
> +        */
>        template <typename _Tp, typename _Up>
>         constexpr auto
>         operator()(_Tp&& __t, _Up&& __u) const
> @@ -711,6 +762,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>                         __ptr_cmp<_Tp, _Up>{});
>         }
>
> +        /// If both parameters are pointers, compare the pointers to their
> common base type instead.
>        template<typename _Tp, typename _Up>
>         constexpr bool
>         operator()(_Tp* __t, _Up* __u) const noexcept
> @@ -781,30 +833,33 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>      struct logical_not;
>  #endif
>
> -  /// One of the @link logical_functors Boolean operations functors@endlink.
> +  /// a @link logical_functors logical functor@endlink representing
> conjunction
>    template<typename _Tp>
>      struct logical_and : public binary_function<_Tp, _Tp, bool>
>      {
> +        /// Tests whether both predicates are fulfilled (`operator&&`).
>        _GLIBCXX14_CONSTEXPR
>        bool
>        operator()(const _Tp& __x, const _Tp& __y) const
>        { return __x && __y; }
>      };
>
> -  /// One of the @link logical_functors Boolean operations functors@endlink.
> +  /// a @link logical_functors logical functor@endlink representing
> alternative

"disjunction" not alternative.

>    template<typename _Tp>
>      struct logical_or : public binary_function<_Tp, _Tp, bool>
>      {
> +        /// Tests whether either predicate is fulfilled (`operator||`).
>        _GLIBCXX14_CONSTEXPR
>        bool
>        operator()(const _Tp& __x, const _Tp& __y) const
>        { return __x || __y; }
>      };
>
> -  /// One of the @link logical_functors Boolean operations functors@endlink.
> +  /// a @link logical_functors logical functor@endlink representing negation
>    template<typename _Tp>
>      struct logical_not : public unary_function<_Tp, bool>
>      {
> +        /// Tests whether the predicate is not fulfilled (`operator!`).
>        _GLIBCXX14_CONSTEXPR
>        bool
>        operator()(const _Tp& __x) const
> @@ -812,10 +867,12 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>      };
>
>  #if __cplusplus > 201103L
> -  /// One of the @link logical_functors Boolean operations functors@endlink.
> +  /// a @link logical_functors logical functor@endlink representing generic
> conjunction
> +    /// @since C++11
>    template<>
>      struct logical_and<void>
>      {
> +        /// Tests whether both predicates are fulfilled (`operator&&`).
>        template <typename _Tp, typename _Up>
>         _GLIBCXX14_CONSTEXPR
>         auto
> @@ -827,10 +884,12 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>        typedef __is_transparent is_transparent;
>      };
>
> -  /// One of the @link logical_functors Boolean operations functors@endlink.
> +  /// a @link logical_functors logical functor@endlink representing generic
> alternative
> +    /// @since C++11
>    template<>
>      struct logical_or<void>
>      {
> +        /// Tests whether either predicate is fulfilled (`operator||`).
>        template <typename _Tp, typename _Up>
>         _GLIBCXX14_CONSTEXPR
>         auto
> @@ -842,10 +901,12 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>        typedef __is_transparent is_transparent;
>      };
>
> -  /// One of the @link logical_functors Boolean operations functors@endlink.
> +  /// a @link logical_functors logical functor@endlink representing generic
> negation
> +    /// @since C++11
>    template<>
>      struct logical_not<void>
>      {
> +        /// Tests whether the predicate is not fulfilled (`operator!`).
>        template <typename _Tp>
>         _GLIBCXX14_CONSTEXPR
>         auto
> @@ -859,7 +920,17 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>  #endif
>    /** @} */
>
> -#if __cplusplus > 201103L
> +  // 20.14.11 bitwise operations
> +  /** @defgroup bitwise_functors Bitwise Operations Classes
> +   * @ingroup functors
> +   *
> +   *  Here are wrapper functors for bitwise operations: `&`, `|`, `^`
> +   *  and `~`.

"The library provides function objects for the bitwise operations ..."


> +   *
> +   *  @{
> +   */
> +
> +  #if __cplusplus > 201103L
>    template<typename _Tp = void>
>      struct bit_and;
>
> @@ -875,36 +946,44 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>
>    // _GLIBCXX_RESOLVE_LIB_DEFECTS
>    // DR 660. Missing Bitwise Operations.
> +  /// a @link bitwise_functors bitwise functor@endlink representing
> intersection

This seems far too general. I think "bitwise AND" is better.

>    template<typename _Tp>
>      struct bit_and : public binary_function<_Tp, _Tp, _Tp>
>      {
> +        /// Returns the intersection (`operator&`) of two bit sets.

Again, too general. These are not bit sets.

/// Returns the bitwise AND (`operator&`) of the parameters

Or simply:

/// @returns `x & y`


>        _GLIBCXX14_CONSTEXPR
>        _Tp
>        operator()(const _Tp& __x, const _Tp& __y) const
>        { return __x & __y; }
>      };
>
> +  /// a @link bitwise_functors bitwise functor@endlink representing union

"bitwise OR" or "bitwise inclusive OR"

>    template<typename _Tp>
>      struct bit_or : public binary_function<_Tp, _Tp, _Tp>
>      {
> +        /// Returns the union (`operator|`) of two bit sets.
>        _GLIBCXX14_CONSTEXPR
>        _Tp
>        operator()(const _Tp& __x, const _Tp& __y) const
>        { return __x | __y; }
>      };
>
> +  /// a @link bitwise_functors bitwise functor@endlink representing symmetric
> difference

"bitwise XOR" or "bitwise exclusive OR"

>    template<typename _Tp>
>      struct bit_xor : public binary_function<_Tp, _Tp, _Tp>
>      {
> +        /// Returns the symmetric difference (`operator^`) of two bit sets.
>        _GLIBCXX14_CONSTEXPR
>        _Tp
>        operator()(const _Tp& __x, const _Tp& __y) const
>        { return __x ^ __y; }
>      };
>
> +  /// a @link bitwise_functors bitwise functor@endlink representing
> complement
>    template<typename _Tp>
>      struct bit_not : public unary_function<_Tp, _Tp>
>      {
> +        /// Returns the complement (`operator~`) of a bit set.

"of a value"

Or simply:

/// @returns `~x`

>      _GLIBCXX14_CONSTEXPR
>        _Tp
>        operator()(const _Tp& __x) const
> @@ -912,9 +991,12 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>      };
>
>  #if __cplusplus > 201103L
> +  /// a @link bitwise_functors bitwise functor@endlink representing generic
> intersection
> +    /// @since C++11
>    template <>
>      struct bit_and<void>
>      {
> +        /// Returns the intersection (`operator&`) of two bit sets.
>        template <typename _Tp, typename _Up>
>         _GLIBCXX14_CONSTEXPR
>         auto
> @@ -926,9 +1008,12 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>        typedef __is_transparent is_transparent;
>      };
>
> +  /// a @link bitwise_functors bitwise functor@endlink representing generic
> union
> +    /// @since C++11
>    template <>
>      struct bit_or<void>
>      {
> +        /// Returns the union (`operator|`) of two bit sets.
>        template <typename _Tp, typename _Up>
>         _GLIBCXX14_CONSTEXPR
>         auto
> @@ -940,9 +1025,12 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>        typedef __is_transparent is_transparent;
>      };
>
> +  /// a @link bitwise_functors bitwise functor@endlink representing generic
> symmetric difference
> +    /// @since C++11
>    template <>
>      struct bit_xor<void>
>      {
> +        /// Returns the symmetric difference (`operator^`) of two bit sets.
>        template <typename _Tp, typename _Up>
>         _GLIBCXX14_CONSTEXPR
>         auto
> @@ -954,9 +1042,12 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>        typedef __is_transparent is_transparent;
>      };
>
> +  /// a @link bitwise_functors bitwise functor@endlink representing generic
> complement
> +    /// @since C++11
>    template <>
>      struct bit_not<void>
>      {
> +        /// Returns the complement (`operator~`) of a bit set.
>        template <typename _Tp>
>         _GLIBCXX14_CONSTEXPR
>         auto
> @@ -998,7 +1089,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>     *
>     *  @{
>     */
> -  /// One of the @link negators negation functors@endlink.
> +  /// the unary @link negators negation functor@endlink

Capitalization.

>    template<typename _Predicate>
>      class unary_negate
>      : public unary_function<typename _Predicate::argument_type, bool>
> @@ -1007,24 +1098,26 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>        _Predicate _M_pred;
>
>      public:
> +        /// This negation functor will negate the given predicate.

I don't think this is a good description of the constructor.

"Wraps the given predicate"

>        _GLIBCXX14_CONSTEXPR
>        explicit
>        unary_negate(const _Predicate& __x) : _M_pred(__x) { }
>
> +        /// Returns the logical negation (`operator!`) of the observed
> predicate.

I don't know what "observed" is telling me, which isn't useful documentation.

I'd prefer something like:

/// Calls the wrapped predicate with the argument and negates the result
/// @returns `!f(x)` where `f` is the wrapped predicate


>        _GLIBCXX14_CONSTEXPR
>        bool
>        operator()(const typename _Predicate::argument_type& __x) const
>        { return !_M_pred(__x); }
>      };
>
> -  /// One of the @link negators negation functors@endlink.
> +  /// Returns a composite predicate that negates the given predicate.

/// A function object adaptor that negates the given predicate

>    template<typename _Predicate>
>      _GLIBCXX14_CONSTEXPR
>      inline unary_negate<_Predicate>
>      not1(const _Predicate& __pred)
>      { return unary_negate<_Predicate>(__pred); }
>
> -  /// One of the @link negators negation functors@endlink.
> +  /// the binary @link negators negation functor@endlink
>    template<typename _Predicate>
>      class binary_negate
>      : public binary_function<typename _Predicate::first_argument_type,
> @@ -1034,10 +1127,12 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>        _Predicate _M_pred;
>
>      public:
> +        /// This negation functor will negate the given predicate.
>        _GLIBCXX14_CONSTEXPR
>        explicit
>        binary_negate(const _Predicate& __x) : _M_pred(__x) { }
>
> +        /// Returns the logical negation (`operator!`) of the observed
> predicate.
>        _GLIBCXX14_CONSTEXPR
>        bool
>        operator()(const typename _Predicate::first_argument_type& __x,
> @@ -1045,7 +1140,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>        { return !_M_pred(__x, __y); }
>      };
>
> -  /// One of the @link negators negation functors@endlink.
> +  /// Returns a composite predicate that negates the given predicate.
>    template<typename _Predicate>
>      _GLIBCXX14_CONSTEXPR
>      inline binary_negate<_Predicate>
> @@ -1075,7 +1170,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>     *
>     *  @{
>     */
> -  /// One of the @link pointer_adaptors adaptors for function
> pointers@endlink.
> +  /// An @link pointer_adaptors adaptor@endlink for a pointer to a unary
> function
>    template<typename _Arg, typename _Result>
>      class pointer_to_unary_function : public unary_function<_Arg, _Result>
>      {
> @@ -1083,24 +1178,27 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>        _Result (*_M_ptr)(_Arg);
>
>      public:
> +        /// Constructs an invalid adaptor.
>        pointer_to_unary_function() { }
>
> +        /// Constructs an adaptor for the given function.
>        explicit
>        pointer_to_unary_function(_Result (*__x)(_Arg))
>        : _M_ptr(__x) { }
>
> +        /// Calls the observed function and returns the result.
>        _Result
>        operator()(_Arg __x) const
>        { return _M_ptr(__x); }
>      };
>
> -  /// One of the @link pointer_adaptors adaptors for function
> pointers@endlink.
> +  /// Returns an adaptor for the given unary function.
>    template<typename _Arg, typename _Result>
>      inline pointer_to_unary_function<_Arg, _Result>
>      ptr_fun(_Result (*__x)(_Arg))
>      { return pointer_to_unary_function<_Arg, _Result>(__x); }
>
> -  /// One of the @link pointer_adaptors adaptors for function
> pointers@endlink.
> +  /// An @link pointer_adaptors adaptor@endlink for a pointer to a binary
> function
>    template<typename _Arg1, typename _Arg2, typename _Result>
>      class pointer_to_binary_function
>      : public binary_function<_Arg1, _Arg2, _Result>
> @@ -1109,18 +1207,21 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>        _Result (*_M_ptr)(_Arg1, _Arg2);
>
>      public:
> +        /// Constructs an invalid adaptor.
>        pointer_to_binary_function() { }
>
> +        /// Constructs an adaptor for the given function.
>        explicit
>        pointer_to_binary_function(_Result (*__x)(_Arg1, _Arg2))
>        : _M_ptr(__x) { }
>
> -      _Result
> +         /// Calls the observed function and returns the result.
> +     _Result
>        operator()(_Arg1 __x, _Arg2 __y) const
>        { return _M_ptr(__x, __y); }
>      };
>
> -  /// One of the @link pointer_adaptors adaptors for function
> pointers@endlink.
> +  /// Returns an adaptor for the given binary function.
>    template<typename _Arg1, typename _Arg2, typename _Result>
>      inline pointer_to_binary_function<_Arg1, _Arg2, _Result>
>      ptr_fun(_Result (*__x)(_Arg1, _Arg2))
> @@ -1197,16 +1298,17 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>     *
>     *  @{
>     */
> -  /// One of the @link memory_adaptors adaptors for member

"memory_adaptors" here is a bad name (see
<https://gcc.gnu.org/r144290> which introduced it) but we can just
change it to ptrmem_adaptors, rather than change it to
pointer_adaptors. If we did want to change it, we'd want to get rid of
the @defgroup for memory_adaptors, not just leave it hanging around
doing nothing.

> -  /// pointers@endlink.
> +  /// a @link pointer_adaptors pointer adaptor@endlink for a pointer to a
> nullary modifying member function

You're just making up novel terminology again. Nobody talks about
"modifying" and "preserving" member functions, please use non-const
and const.

Adding doxygen comments that use novel or confusing terminology is
worse than not having any comments at all.

>    template<typename _Ret, typename _Tp>
>      class mem_fun_t : public unary_function<_Tp*, _Ret>
>      {
>      public:
> +        /// Constructs an adaptor for the given member function.
>        explicit
>        mem_fun_t(_Ret (_Tp::*__pf)())
>        : _M_f(__pf) { }
>
> +        /// Calls the observed member function on the given object and
> returns the result.
>        _Ret
>        operator()(_Tp* __p) const
>        { return (__p->*_M_f)(); }
> @@ -1215,16 +1317,17 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>        _Ret (_Tp::*_M_f)();
>      };
>
> -  /// One of the @link memory_adaptors adaptors for member
> -  /// pointers@endlink.
> +  /// a @link pointer_adaptors pointer adaptor@endlink for a pointer to a
> nullary preserving member function
>    template<typename _Ret, typename _Tp>
>      class const_mem_fun_t : public unary_function<const _Tp*, _Ret>
>      {
>      public:
> +        /// Constructs an adaptor for the given member function.
>        explicit
>        const_mem_fun_t(_Ret (_Tp::*__pf)() const)
>        : _M_f(__pf) { }
>
> +        /// Calls the observed member function on the given constant object
> and returns the result.
>        _Ret
>        operator()(const _Tp* __p) const
>        { return (__p->*_M_f)(); }
> @@ -1233,16 +1336,17 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>        _Ret (_Tp::*_M_f)() const;
>      };
>
> -  /// One of the @link memory_adaptors adaptors for member
> -  /// pointers@endlink.
> +  /// a @link pointer_adaptors reference adaptor@endlink for a pointer to a
> nullary modifying member function
>    template<typename _Ret, typename _Tp>
>      class mem_fun_ref_t : public unary_function<_Tp, _Ret>
>      {
>      public:
> +        /// Constructs an adaptor for the given member function.
>        explicit
>        mem_fun_ref_t(_Ret (_Tp::*__pf)())
>        : _M_f(__pf) { }
>
> +        /// Calls the observed member function on the given object and
> returns the result.
>        _Ret
>        operator()(_Tp& __r) const
>        { return (__r.*_M_f)(); }
> @@ -1251,16 +1355,17 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>        _Ret (_Tp::*_M_f)();
>    };
>
> -  /// One of the @link memory_adaptors adaptors for member
> -  /// pointers@endlink.
> +  /// a @link pointer_adaptors reference adaptor@endlink for a pointer to a
> nullary preserving member function
>    template<typename _Ret, typename _Tp>
>      class const_mem_fun_ref_t : public unary_function<_Tp, _Ret>
>      {
>      public:
> +       /// Constructs an adaptor for the given member function.
>        explicit
>        const_mem_fun_ref_t(_Ret (_Tp::*__pf)() const)
>        : _M_f(__pf) { }
>
> +        /// Calls the observed member function on the given constant object
> and returns the result.
>        _Ret
>        operator()(const _Tp& __r) const
>        { return (__r.*_M_f)(); }
> @@ -1269,17 +1374,18 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>        _Ret (_Tp::*_M_f)() const;
>      };
>
> -  /// One of the @link memory_adaptors adaptors for member
> -  /// pointers@endlink.
> +  /// a @link pointer_adaptors pointer adaptor@endlink for a pointer to a
> unary modifying member function
>    template<typename _Ret, typename _Tp, typename _Arg>
>      class mem_fun1_t : public binary_function<_Tp*, _Arg, _Ret>
>      {
>      public:
> +        /// Constructs an adaptor for the given member function.
>        explicit
>        mem_fun1_t(_Ret (_Tp::*__pf)(_Arg))
>        : _M_f(__pf) { }
>
> -      _Ret
> +         /// Calls the observed member function on the given object and
> returns the result.
> +     _Ret
>        operator()(_Tp* __p, _Arg __x) const
>        { return (__p->*_M_f)(__x); }
>
> @@ -1287,16 +1393,17 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>        _Ret (_Tp::*_M_f)(_Arg);
>      };
>
> -  /// One of the @link memory_adaptors adaptors for member
> -  /// pointers@endlink.
> +  /// a @link pointer_adaptors pointer adaptor@endlink for a pointer to a
> unary preserving member function
>    template<typename _Ret, typename _Tp, typename _Arg>
>      class const_mem_fun1_t : public binary_function<const _Tp*, _Arg, _Ret>
>      {
>      public:
> +        /// Constructs an adaptor for the given member function.
>        explicit
>        const_mem_fun1_t(_Ret (_Tp::*__pf)(_Arg) const)
>        : _M_f(__pf) { }
>
> +        /// Calls the observed member function on the given constant object
> and returns the result.
>        _Ret
>        operator()(const _Tp* __p, _Arg __x) const
>        { return (__p->*_M_f)(__x); }
> @@ -1305,16 +1412,17 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>        _Ret (_Tp::*_M_f)(_Arg) const;
>      };
>
> -  /// One of the @link memory_adaptors adaptors for member
> -  /// pointers@endlink.
> +  /// a @link pointer_adaptors reference adaptor@endlink for a pointer to a
> unary modifying member function
>    template<typename _Ret, typename _Tp, typename _Arg>
>      class mem_fun1_ref_t : public binary_function<_Tp, _Arg, _Ret>
>      {
>      public:
> +        /// Constructs an adaptor for the given member function.
>        explicit
>        mem_fun1_ref_t(_Ret (_Tp::*__pf)(_Arg))
>        : _M_f(__pf) { }
>
> +       /// Calls the observed member function on the given object and returns
> the result.
>        _Ret
>        operator()(_Tp& __r, _Arg __x) const
>        { return (__r.*_M_f)(__x); }
> @@ -1323,16 +1431,17 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>        _Ret (_Tp::*_M_f)(_Arg);
>      };
>
> -  /// One of the @link memory_adaptors adaptors for member
> -  /// pointers@endlink.
> +  /// a @link pointer_adaptors reference adaptor@endlink for a pointer to a
> unary preserving member function
>    template<typename _Ret, typename _Tp, typename _Arg>
>      class const_mem_fun1_ref_t : public binary_function<_Tp, _Arg, _Ret>
>      {
>      public:
> +        /// Constructs an adaptor for the given member function.
>        explicit
>        const_mem_fun1_ref_t(_Ret (_Tp::*__pf)(_Arg) const)
>        : _M_f(__pf) { }
>
> +        /// Calls the observed member function on the given constant object
> and returns the result.
>        _Ret
>        operator()(const _Tp& __r, _Arg __x) const
>        { return (__r.*_M_f)(__x); }
> @@ -1343,41 +1452,49 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
>
>    // Mem_fun adaptor helper functions.  There are only two:
>    // mem_fun and mem_fun_ref.
> +    /// Returns a pointer adaptor corresponding to the given nullary

What is a "pointer adaptor"? It's nothing to do with the @defgroup
pointer_adaptors documentation group, which relates to adaptors for
function pointers.



> modifying member function
>    template<typename _Ret, typename _Tp>
>      inline mem_fun_t<_Ret, _Tp>
>      mem_fun(_Ret (_Tp::*__f)())
>      { return mem_fun_t<_Ret, _Tp>(__f); }
> -
> +
> + /// Returns a pointer adaptor corresponding to the given nullary preserving
> member function
>    template<typename _Ret, typename _Tp>
>      inline const_mem_fun_t<_Ret, _Tp>
>      mem_fun(_Ret (_Tp::*__f)() const)
>      { return const_mem_fun_t<_Ret, _Tp>(__f); }
>
> + /// Returns a reference adaptor corresponding to the given nullary modifying

What is a "reference adaptor"?

In the terminology of the STL, this function itself is the adaptor,
not the thing it returns. The thing it returns is an adaptable
function object, not an adaptor.


> member function
>    template<typename _Ret, typename _Tp>
>      inline mem_fun_ref_t<_Ret, _Tp>
>      mem_fun_ref(_Ret (_Tp::*__f)())
>      { return mem_fun_ref_t<_Ret, _Tp>(__f); }
>
> + /// Returns a reference adaptor corresponding to the given nullary
> preserving member function
>    template<typename _Ret, typename _Tp>
>      inline const_mem_fun_ref_t<_Ret, _Tp>
>      mem_fun_ref(_Ret (_Tp::*__f)() const)
>      { return const_mem_fun_ref_t<_Ret, _Tp>(__f); }
>
> + /// Returns a pointer adaptor corresponding to the given unary modifying
> member function
>    template<typename _Ret, typename _Tp, typename _Arg>
>      inline mem_fun1_t<_Ret, _Tp, _Arg>
>      mem_fun(_Ret (_Tp::*__f)(_Arg))
>      { return mem_fun1_t<_Ret, _Tp, _Arg>(__f); }
>
> +/// Returns a pointer adaptor corresponding to the given unary preserving
> member function
>    template<typename _Ret, typename _Tp, typename _Arg>
>      inline const_mem_fun1_t<_Ret, _Tp, _Arg>
>      mem_fun(_Ret (_Tp::*__f)(_Arg) const)
>      { return const_mem_fun1_t<_Ret, _Tp, _Arg>(__f); }
>
> +/// Returns a reference adaptor corresponding to the given unary modifying
> member function
>    template<typename _Ret, typename _Tp, typename _Arg>
>      inline mem_fun1_ref_t<_Ret, _Tp, _Arg>
>      mem_fun_ref(_Ret (_Tp::*__f)(_Arg))
>      { return mem_fun1_ref_t<_Ret, _Tp, _Arg>(__f); }
>
> +/// Returns a reference adaptor corresponding to the given unary preserving
> member function
>    template<typename _Ret, typename _Tp, typename _Arg>
>      inline const_mem_fun1_ref_t<_Ret, _Tp, _Arg>
>      mem_fun_ref(_Ret (_Tp::*__f)(_Arg) const)



More information about the Gcc-patches mailing list