[libcxx-commits] [libcxx] 7bdf416 - [libc++] Remove conditional noexcepts from view_interface.
Arthur O'Dwyer via libcxx-commits
libcxx-commits at lists.llvm.org
Tue Feb 15 08:13:41 PST 2022
Author: Arthur O'Dwyer
Date: 2022-02-15T11:12:42-05:00
New Revision: 7bdf41653c90a6f1802e79b12b52d2d55cb9bd8d
URL: https://github.com/llvm/llvm-project/commit/7bdf41653c90a6f1802e79b12b52d2d55cb9bd8d
DIFF: https://github.com/llvm/llvm-project/commit/7bdf41653c90a6f1802e79b12b52d2d55cb9bd8d.diff
LOG: [libc++] Remove conditional noexcepts from view_interface.
As suggested in D117966.
These conditional noexcepts are *permitted* by the Standard (as long
as there were no mistakes in them, I guess); but not *mandated*.
The Standard doesn't put any noexcept-specifications on these member functions.
The same logic would apply to `transform_view::iterator::operator*`
and `transform_view::iterator::operator[]`, but the Standard mandates
conditional noexcept on `iter_move(transform_view::iterator)`, and
I think it doesn't make much sense to say "moving from this iterator
is conditionally noexcept but not-moving from it is noexcept(false),"
so I'm leaving transform_view alone for now.
Differential Revision: https://reviews.llvm.org/D119374
Added:
Modified:
libcxx/include/__ranges/view_interface.h
libcxx/test/std/ranges/range.utility/view.interface/view.interface.pass.cpp
Removed:
################################################################################
diff --git a/libcxx/include/__ranges/view_interface.h b/libcxx/include/__ranges/view_interface.h
index 190bb8ad9cfdd..b0794b02b963b 100644
--- a/libcxx/include/__ranges/view_interface.h
+++ b/libcxx/include/__ranges/view_interface.h
@@ -9,6 +9,8 @@
#ifndef _LIBCPP___RANGES_VIEW_INTERFACE_H
#define _LIBCPP___RANGES_VIEW_INTERFACE_H
+#include <__concepts/derived_from.h>
+#include <__concepts/same_as.h>
#include <__config>
#include <__debug>
#include <__iterator/concepts.h>
@@ -18,7 +20,6 @@
#include <__ranges/access.h>
#include <__ranges/concepts.h>
#include <__ranges/empty.h>
-#include <concepts>
#include <type_traits>
#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
@@ -31,12 +32,6 @@ _LIBCPP_BEGIN_NAMESPACE_STD
namespace ranges {
-template<class _Tp>
-concept __can_empty = requires(_Tp __t) { ranges::empty(__t); };
-
-template<class _Tp>
-void __implicitly_convert_to(type_identity_t<_Tp>) noexcept;
-
template<class _Derived>
requires is_class_v<_Derived> && same_as<_Derived, remove_cv_t<_Derived>>
class view_interface {
@@ -55,7 +50,6 @@ class view_interface {
public:
template<class _D2 = _Derived>
[[nodiscard]] _LIBCPP_HIDE_FROM_ABI constexpr bool empty()
- noexcept(noexcept(__implicitly_convert_to<bool>(ranges::begin(__derived()) == ranges::end(__derived()))))
requires forward_range<_D2>
{
return ranges::begin(__derived()) == ranges::end(__derived());
@@ -63,7 +57,6 @@ class view_interface {
template<class _D2 = _Derived>
[[nodiscard]] _LIBCPP_HIDE_FROM_ABI constexpr bool empty() const
- noexcept(noexcept(__implicitly_convert_to<bool>(ranges::begin(__derived()) == ranges::end(__derived()))))
requires forward_range<const _D2>
{
return ranges::begin(__derived()) == ranges::end(__derived());
@@ -72,8 +65,7 @@ class view_interface {
template<class _D2 = _Derived>
_LIBCPP_HIDE_FROM_ABI
constexpr explicit operator bool()
- noexcept(noexcept(ranges::empty(declval<_D2>())))
- requires __can_empty<_D2>
+ requires requires (_D2& __t) { ranges::empty(__t); }
{
return !ranges::empty(__derived());
}
@@ -81,8 +73,7 @@ class view_interface {
template<class _D2 = _Derived>
_LIBCPP_HIDE_FROM_ABI
constexpr explicit operator bool() const
- noexcept(noexcept(ranges::empty(declval<const _D2>())))
- requires __can_empty<const _D2>
+ requires requires (const _D2& __t) { ranges::empty(__t); }
{
return !ranges::empty(__derived());
}
@@ -90,7 +81,6 @@ class view_interface {
template<class _D2 = _Derived>
_LIBCPP_HIDE_FROM_ABI
constexpr auto data()
- noexcept(noexcept(std::to_address(ranges::begin(__derived()))))
requires contiguous_iterator<iterator_t<_D2>>
{
return std::to_address(ranges::begin(__derived()));
@@ -99,7 +89,6 @@ class view_interface {
template<class _D2 = _Derived>
_LIBCPP_HIDE_FROM_ABI
constexpr auto data() const
- noexcept(noexcept(std::to_address(ranges::begin(__derived()))))
requires range<const _D2> && contiguous_iterator<iterator_t<const _D2>>
{
return std::to_address(ranges::begin(__derived()));
@@ -108,9 +97,7 @@ class view_interface {
template<class _D2 = _Derived>
_LIBCPP_HIDE_FROM_ABI
constexpr auto size()
- noexcept(noexcept(ranges::end(__derived()) - ranges::begin(__derived())))
- requires forward_range<_D2>
- && sized_sentinel_for<sentinel_t<_D2>, iterator_t<_D2>>
+ requires forward_range<_D2> && sized_sentinel_for<sentinel_t<_D2>, iterator_t<_D2>>
{
return ranges::end(__derived()) - ranges::begin(__derived());
}
@@ -118,9 +105,7 @@ class view_interface {
template<class _D2 = _Derived>
_LIBCPP_HIDE_FROM_ABI
constexpr auto size() const
- noexcept(noexcept(ranges::end(__derived()) - ranges::begin(__derived())))
- requires forward_range<const _D2>
- && sized_sentinel_for<sentinel_t<const _D2>, iterator_t<const _D2>>
+ requires forward_range<const _D2> && sized_sentinel_for<sentinel_t<const _D2>, iterator_t<const _D2>>
{
return ranges::end(__derived()) - ranges::begin(__derived());
}
@@ -128,7 +113,6 @@ class view_interface {
template<class _D2 = _Derived>
_LIBCPP_HIDE_FROM_ABI
constexpr decltype(auto) front()
- noexcept(noexcept(*ranges::begin(__derived())))
requires forward_range<_D2>
{
_LIBCPP_ASSERT(!empty(),
@@ -139,7 +123,6 @@ class view_interface {
template<class _D2 = _Derived>
_LIBCPP_HIDE_FROM_ABI
constexpr decltype(auto) front() const
- noexcept(noexcept(*ranges::begin(__derived())))
requires forward_range<const _D2>
{
_LIBCPP_ASSERT(!empty(),
@@ -150,7 +133,6 @@ class view_interface {
template<class _D2 = _Derived>
_LIBCPP_HIDE_FROM_ABI
constexpr decltype(auto) back()
- noexcept(noexcept(*ranges::prev(ranges::end(__derived()))))
requires bidirectional_range<_D2> && common_range<_D2>
{
_LIBCPP_ASSERT(!empty(),
@@ -161,7 +143,6 @@ class view_interface {
template<class _D2 = _Derived>
_LIBCPP_HIDE_FROM_ABI
constexpr decltype(auto) back() const
- noexcept(noexcept(*ranges::prev(ranges::end(__derived()))))
requires bidirectional_range<const _D2> && common_range<const _D2>
{
_LIBCPP_ASSERT(!empty(),
@@ -172,7 +153,6 @@ class view_interface {
template<random_access_range _RARange = _Derived>
_LIBCPP_HIDE_FROM_ABI
constexpr decltype(auto) operator[](range_
diff erence_t<_RARange> __index)
- noexcept(noexcept(ranges::begin(__derived())[__index]))
{
return ranges::begin(__derived())[__index];
}
@@ -180,7 +160,6 @@ class view_interface {
template<random_access_range _RARange = const _Derived>
_LIBCPP_HIDE_FROM_ABI
constexpr decltype(auto) operator[](range_
diff erence_t<_RARange> __index) const
- noexcept(noexcept(ranges::begin(__derived())[__index]))
{
return ranges::begin(__derived())[__index];
}
diff --git a/libcxx/test/std/ranges/range.utility/view.interface/view.interface.pass.cpp b/libcxx/test/std/ranges/range.utility/view.interface/view.interface.pass.cpp
index 2720a75e7b8da..9faa3f564f5b6 100644
--- a/libcxx/test/std/ranges/range.utility/view.interface/view.interface.pass.cpp
+++ b/libcxx/test/std/ranges/range.utility/view.interface/view.interface.pass.cpp
@@ -126,17 +126,16 @@ struct DataIsNull : std::ranges::view_interface<DataIsNull> {
};
static_assert(std::ranges::view<DataIsNull>);
-template<bool IsNoexcept>
-struct BoolConvertibleComparison : std::ranges::view_interface<BoolConvertibleComparison<IsNoexcept>> {
+struct BoolConvertibleComparison : std::ranges::view_interface<BoolConvertibleComparison> {
struct ResultType {
bool value;
- constexpr operator bool() const noexcept(IsNoexcept) { return value; }
+ constexpr operator bool() const { return value; }
};
struct SentinelType {
int *base_;
- SentinelType() = default;
- explicit constexpr SentinelType(int *base) : base_(base) {}
+ explicit SentinelType() = default;
+ constexpr explicit SentinelType(int *base) : base_(base) {}
friend constexpr ResultType operator==(ForwardIter const& iter, SentinelType const& sent) noexcept { return {iter.base() == sent.base_}; }
friend constexpr ResultType operator==(SentinelType const& sent, ForwardIter const& iter) noexcept { return {iter.base() == sent.base_}; }
friend constexpr ResultType operator!=(ForwardIter const& iter, SentinelType const& sent) noexcept { return {iter.base() != sent.base_}; }
@@ -144,11 +143,10 @@ struct BoolConvertibleComparison : std::ranges::view_interface<BoolConvertibleCo
};
int buff[8] = {0, 1, 2, 3, 4, 5, 6, 7};
- constexpr ForwardIter begin() const noexcept { return ForwardIter(const_cast<int*>(buff)); }
- constexpr SentinelType end() const noexcept { return SentinelType(const_cast<int*>(buff) + 8); }
+ constexpr ForwardIter begin() const { return ForwardIter(const_cast<int*>(buff)); }
+ constexpr SentinelType end() const { return SentinelType(const_cast<int*>(buff) + 8); }
};
-static_assert(std::ranges::view<BoolConvertibleComparison<true>>);
-static_assert(std::ranges::view<BoolConvertibleComparison<false>>);
+static_assert(std::ranges::view<BoolConvertibleComparison>);
template<class T>
concept EmptyInvocable = requires (T const& obj) { obj.empty(); };
@@ -189,19 +187,17 @@ constexpr bool testEmpty() {
MoveOnlyForwardRange moveOnly;
assert(!std::move(moveOnly).empty());
- BoolConvertibleComparison<true> boolConv;
- BoolConvertibleComparison<false> boolConv2;
- LIBCPP_ASSERT_NOEXCEPT(boolConv.empty());
- ASSERT_NOT_NOEXCEPT(boolConv2.empty());
+ BoolConvertibleComparison boolConv;
+ ASSERT_NOT_NOEXCEPT(boolConv.empty());
assert(!boolConv.empty());
- assert(!static_cast<BoolConvertibleComparison<true> const&>(boolConv).empty());
+ assert(!static_cast<const BoolConvertibleComparison&>(boolConv).empty());
assert(boolConv);
- assert(static_cast<BoolConvertibleComparison<true> const&>(boolConv));
+ assert(static_cast<const BoolConvertibleComparison&>(boolConv));
assert(!std::ranges::empty(boolConv));
- assert(!std::ranges::empty(static_cast<BoolConvertibleComparison<true> const&>(boolConv)));
+ assert(!std::ranges::empty(static_cast<const BoolConvertibleComparison&>(boolConv)));
return true;
}
More information about the libcxx-commits
mailing list