[committed] libstdc++: Remove constraints from std::optional monadic ops [PR102863]
Commit Message
The constraints on transform and and_then can cause errors when checking
satisfaction. The constraints that were present in R6 of the paper were
moved for he final F8 revision, and so should have been included in the
implementation.
libstdc++-v3/ChangeLog:
PR libstdc++/102863
* include/std/optional (optional::and_then, optional::transform):
Remove requires-clause.
* testsuite/20_util/optional/monadic/and_then.cc: Check
overload resolution doesn't cause errors.
* testsuite/20_util/optional/monadic/transform.cc: Likewise.
Tested x86_64-linux. Committed to trunk.
commit 0fac85a24f40ef6098b756e8e8655205f4bfbf3e
Author: Jonathan Wakely <jwakely@redhat.com>
Date: Thu Oct 21 01:19:45 2021
libstdc++: Remove constraints from std::optional monadic ops [PR102863]
The constraints on transform and and_then can cause errors when checking
satisfaction. The constraints that were present in R6 of the paper were
moved for he final F8 revision, and so should have been included in the
implementation.
libstdc++-v3/ChangeLog:
PR libstdc++/102863
* include/std/optional (optional::and_then, optional::transform):
Remove requires-clause.
* testsuite/20_util/optional/monadic/and_then.cc: Check
overload resolution doesn't cause errors.
* testsuite/20_util/optional/monadic/transform.cc: Likewise.
Comments
On 21/10/21 01:23 +0100, Jonathan Wakely wrote:
>The constraints on transform and and_then can cause errors when checking
>satisfaction. The constraints that were present in R6 of the paper were
>moved for he final F8 revision, and so should have been included in the
Bah, I meant "removed for the final R8 revision, and so should not
have been included ..."
>implementation.
@@ -1048,7 +1048,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
// [optional.monadic]
- template<typename _Fn> requires invocable<_Fn, _Tp&>
+ template<typename _Fn>
constexpr auto
and_then(_Fn&& __f) &
{
@@ -1060,7 +1060,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
return _Up();
}
- template<typename _Fn> requires invocable<_Fn, const _Tp&>
+ template<typename _Fn>
constexpr auto
and_then(_Fn&& __f) const &
{
@@ -1072,7 +1072,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
return _Up();
}
- template<typename _Fn> requires invocable<_Fn, _Tp>
+ template<typename _Fn>
constexpr auto
and_then(_Fn&& __f) &&
{
@@ -1084,7 +1084,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
return _Up();
}
- template<typename _Fn> requires invocable<_Fn, const _Tp>
+ template<typename _Fn>
constexpr auto
and_then(_Fn&& __f) const &&
{
@@ -1096,7 +1096,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
return _Up();
}
- template<typename _Fn> requires invocable<_Fn, _Tp&>
+ template<typename _Fn>
constexpr auto
transform(_Fn&& __f) &
{
@@ -1107,7 +1107,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
return optional<_Up>();
}
- template<typename _Fn> requires invocable<_Fn, const _Tp&>
+ template<typename _Fn>
constexpr auto
transform(_Fn&& __f) const &
{
@@ -1118,7 +1118,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
return optional<_Up>();
}
- template<typename _Fn> requires invocable<_Fn, _Tp>
+ template<typename _Fn>
constexpr auto
transform(_Fn&& __f) &&
{
@@ -1129,7 +1129,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
return optional<_Up>();
}
- template<typename _Fn> requires invocable<_Fn, const _Tp>
+ template<typename _Fn>
constexpr auto
transform(_Fn&& __f) const &&
{
@@ -113,8 +113,20 @@ test_forwarding()
static_assert( test_forwarding() );
+void f(int&) { }
+
+void
+test_unconstrained()
+{
+ // PR libstc++/102863 - Optional monadic ops should not be constrained
+ std::optional<int> x;
+ auto answer = x.and_then([](auto& y) { f(y); return std::optional<int>{42}; });
+ VERIFY( !answer );
+}
+
int main()
{
test_and_then();
test_forwarding();
+ test_unconstrained();
}
@@ -132,9 +132,21 @@ test_copy_elision()
static_assert( test_copy_elision() );
+void f(int&) { }
+
+void
+test_unconstrained()
+{
+ // PR libstc++/102863 - Optional monadic ops should not be constrained
+ std::optional<int> x;
+ auto answer = x.transform([](auto& y) { f(y); return 42; });
+ VERIFY( !answer );
+}
+
int main()
{
test_transform();
test_forwarding();
test_copy_elision();
+ test_unconstrained();
}