2019-09-26 Jonathan Wakely <jwakely@redhat.com>
+ * include/bits/stl_pair.h (pair): Add _GLIBCXX20_CONSTEXPR to
+ piecewise construction constructor, assignment operators, and swap.
+ * include/std/tuple (pair::pair(piecewise_construct_t, tuple, tuple)):
+ Add _GLIBCXX20_CONSTEXPR.
+ (pair::pair(tuple, tuple, _Index_tuple, _Index_tuple)): Likewise.
+ * testsuite/20_util/pair/constexpr_assign.cc: New test.
+ * testsuite/20_util/pair/constexpr_swap.cc: New test.
+
* include/experimental/internet (operator==, operator<): Fix loop
condition to avoid reading past the end of the array.
second(std::forward<_U2>(__p.second)) { }
template<typename... _Args1, typename... _Args2>
+ _GLIBCXX20_CONSTEXPR
pair(piecewise_construct_t, tuple<_Args1...>, tuple<_Args2...>);
- pair&
+ _GLIBCXX20_CONSTEXPR pair&
operator=(typename conditional<
__and_<is_copy_assignable<_T1>,
is_copy_assignable<_T2>>::value,
return *this;
}
- pair&
+ _GLIBCXX20_CONSTEXPR pair&
operator=(typename conditional<
__and_<is_move_assignable<_T1>,
is_move_assignable<_T2>>::value,
}
template<typename _U1, typename _U2>
- typename enable_if<__and_<is_assignable<_T1&, const _U1&>,
- is_assignable<_T2&, const _U2&>>::value,
- pair&>::type
+ _GLIBCXX20_CONSTEXPR
+ typename enable_if<__and_<is_assignable<_T1&, const _U1&>,
+ is_assignable<_T2&, const _U2&>>::value,
+ pair&>::type
operator=(const pair<_U1, _U2>& __p)
{
first = __p.first;
}
template<typename _U1, typename _U2>
- typename enable_if<__and_<is_assignable<_T1&, _U1&&>,
- is_assignable<_T2&, _U2&&>>::value,
- pair&>::type
+ _GLIBCXX20_CONSTEXPR
+ typename enable_if<__and_<is_assignable<_T1&, _U1&&>,
+ is_assignable<_T2&, _U2&&>>::value,
+ pair&>::type
operator=(pair<_U1, _U2>&& __p)
{
first = std::forward<_U1>(__p.first);
}
/// Swap the first members and then the second members.
- void
+ _GLIBCXX20_CONSTEXPR void
swap(pair& __p)
noexcept(__and_<__is_nothrow_swappable<_T1>,
__is_nothrow_swappable<_T2>>::value)
private:
template<typename... _Args1, std::size_t... _Indexes1,
typename... _Args2, std::size_t... _Indexes2>
+ _GLIBCXX20_CONSTEXPR
pair(tuple<_Args1...>&, tuple<_Args2...>&,
_Index_tuple<_Indexes1...>, _Index_tuple<_Indexes2...>);
#endif
* which has performance implications, e.g. see https://gcc.gnu.org/PR38466
*/
template<typename _T1, typename _T2>
- inline
+ _GLIBCXX20_CONSTEXPR inline
#if __cplusplus > 201402L || !defined(__STRICT_ANSI__) // c++1z or gnu++11
// Constrained free swap overload, see p0185r1
typename enable_if<__and_<__is_swappable<_T1>,
*/
template<class _T1, class _T2>
template<typename... _Args1, typename... _Args2>
- inline
+ _GLIBCXX20_CONSTEXPR inline
pair<_T1, _T2>::
pair(piecewise_construct_t,
tuple<_Args1...> __first, tuple<_Args2...> __second)
template<class _T1, class _T2>
template<typename... _Args1, std::size_t... _Indexes1,
typename... _Args2, std::size_t... _Indexes2>
- inline
+ _GLIBCXX20_CONSTEXPR inline
pair<_T1, _T2>::
pair(tuple<_Args1...>& __tuple1, tuple<_Args2...>& __tuple2,
_Index_tuple<_Indexes1...>, _Index_tuple<_Indexes2...>)
--- /dev/null
+// Copyright (C) 2019 Free Software Foundation, Inc.
+//
+// This file is part of the GNU ISO C++ Library. This library is free
+// software; you can redistribute it and/or modify it under the
+// terms of the GNU General Public License as published by the
+// Free Software Foundation; either version 3, or (at your option)
+// any later version.
+
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+// GNU General Public License for more details.
+
+// You should have received a copy of the GNU General Public License along
+// with this library; see the file COPYING3. If not see
+// <http://www.gnu.org/licenses/>.
+
+// { dg-options "-std=gnu++2a" }
+// { dg-do compile { target c++2a } }
+
+#include <utility>
+#include <tuple>
+
+constexpr int
+test01(int i, int j)
+{
+ using T = std::tuple<int>;
+ std::pair<int, int> p0, p1, p2, p3;
+ std::pair<int, int> pij(std::piecewise_construct, T(i), T(j));
+ p0 = pij;
+ p1 = std::move(pij);
+ std::pair<long, long> pijl(i, j);
+ p2 = pijl;
+ p3 = std::move(pijl);
+ return p0.first + p0.second + p1.first + p1.second
+ + p2.first + p2.second + p3.first + p3.second;
+}
+
+static_assert( test01(3, 100) == 412 );
--- /dev/null
+// Copyright (C) 2019 Free Software Foundation, Inc.
+//
+// This file is part of the GNU ISO C++ Library. This library is free
+// software; you can redistribute it and/or modify it under the
+// terms of the GNU General Public License as published by the
+// Free Software Foundation; either version 3, or (at your option)
+// any later version.
+
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+// GNU General Public License for more details.
+
+// You should have received a copy of the GNU General Public License along
+// with this library; see the file COPYING3. If not see
+// <http://www.gnu.org/licenses/>.
+
+// { dg-options "-std=gnu++2a" }
+// { dg-do compile { target c++2a } }
+
+#include <utility>
+#include <tuple>
+
+constexpr int
+test01(int i, int j)
+{
+ using T = std::tuple<int>;
+ std::pair<int, int> p0, p1;
+ std::pair<int, int> pij(std::piecewise_construct, T(i), T(j));
+ std::pair<int, int> pji(std::piecewise_construct, T(j), T(i));
+ p0.swap(pij);
+ swap(p1, pji);
+ return p0.first - p0.second - p1.first + p1.second;
+}
+
+static_assert( test01(5, 100) == -190 );