https://gcc.gnu.org/bugzilla/show_bug.cgi?id=90700

--- Comment #2 from Jonathan Wakely <redi at gcc dot gnu.org> ---
Author: redi
Date: Thu Jun  6 12:13:36 2019
New Revision: 271998

URL: https://gcc.gnu.org/viewcvs?rev=271998&root=gcc&view=rev
Log:
Refactor SFINAE constraints on std::tuple constructors

Replace the _TC class template with the better-named _TupleConstraints
one, which provides a different set of member functions. The new members
do not distinguish construction from lvalues and rvalues, but expects
the caller to do that by providing different template arguments. Within
the std::tuple primary template and std::tuple<T1, T2> partial
specialization the _TupleConstraints members are used via new alias
templates like _ImplicitCtor and _ExplicitCtor which makes the
constructor constraints less verbose and repetitive. For example, where
we previously had:

     template<typename... _UElements, typename
             enable_if<
                _TMC<_UElements...>::template
                   _MoveConstructibleTuple<_UElements...>()
                 && _TMC<_UElements...>::template
                   _ImplicitlyMoveConvertibleTuple<_UElements...>()
                 && (sizeof...(_Elements) >= 1),
       bool>::type=true>
       constexpr tuple(_UElements&&... __elements)

We now have:

     template<typename... _UElements,
             bool _Valid = __valid_args<_UElements...>(),
             _ImplicitCtor<_Valid, _UElements...> = true>
      constexpr
      tuple(_UElements&&... __elements)

There are two semantic changes as a result of the refactoring:

- The allocator-extended default constructor is now constrained.
- The rewritten constraints fix PR 90700.

        * include/std/tuple (_TC): Replace with _TupleConstraints.
        (_TupleConstraints): New helper for SFINAE constraints, with more
        expressive member functions to reduce duplication when used.
        (tuple::_TC2, tuple::_TMC, tuple::_TNTC): Remove.
        (tuple::_TCC): Replace dummy type parameter with bool non-type
        parameter that can be used to check the pack size.
        (tuple::_ImplicitDefaultCtor, tuple::_ExplicitDefaultCtor)
        (tuple::_ImplicitCtor, tuple::_ExplicitCtor): New alias templates for
        checking constraints in constructors.
        (tuple::__valid_args, tuple::_UseOtherCtor, tuple::__use_other_ctor):
        New SFINAE helpers.
        (tuple::tuple): Use new helpers to reduce repitition in constraints.
        (tuple::tuple(allocator_arg_t, const Alloc&)): Constrain.
        (tuple<T1, T2>::_TCC, tuple<T1, T2>::_ImplicitDefaultCtor)
        (tuple<T1, T2>::_ExplicitDefaultCtor, tuple<T1, T2>::_ImplicitCtor)
        (tuple<T1, T2>::_ExplicitCtor): New alias templates for checking
        constraints in constructors.
        (tuple::__is_alloc_arg()): New SFINAE helpers.
        (tuple<T1, T2>::tuple): Use new helpers to reduce repitition in
        constraints.
        (tuple<T1, T2>::tuple(allocator_arg_t, const Alloc&)): Constrain.
        * testsuite/20_util/tuple/cons/90700.cc: New test.
        * testsuite/20_util/tuple/cons/allocators.cc: Add default constructor
        to meet new constraint on allocator-extended default constructor.

Added:
    trunk/libstdc++-v3/testsuite/20_util/tuple/cons/90700.cc
Modified:
    trunk/libstdc++-v3/ChangeLog
    trunk/libstdc++-v3/include/std/tuple
    trunk/libstdc++-v3/testsuite/20_util/tuple/cons/allocators.cc

Reply via email to