Skip to content

Commit 7b50536

Browse files
committed
Constrained CPO
1 parent e66aca5 commit 7b50536

File tree

3 files changed

+21
-3
lines changed

3 files changed

+21
-3
lines changed

libcxx/include/__ranges/iota_view.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -375,6 +375,7 @@ namespace views {
375375
namespace __iota {
376376
struct __fn {
377377
template <class _Start>
378+
requires(requires(_Start __s) { ranges::iota_view<decay_t<_Start>>(std::forward<_Start>(__s)); })
378379
_LIBCPP_HIDE_FROM_ABI constexpr auto operator()(_Start&& __start) const
379380
noexcept(noexcept(ranges::iota_view(std::forward<_Start>(__start))))
380381
-> decltype(ranges::iota_view(std::forward<_Start>(__start))) {

libcxx/test/std/ranges/range.factories/range.iota.view/views_iota.pass.cpp

Lines changed: 18 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -46,7 +46,14 @@ constexpr void testType(U u) {
4646

4747
struct X {};
4848

49-
constexpr bool test() {
49+
template <typename IntT>
50+
concept CanDoubleWrap = requires(IntT i) { std::views::iota(std::views::iota(i)); };
51+
52+
template <typename T>
53+
concept HasIota = requires(T t) { std::views::iota(t); };
54+
55+
constexpr bool
56+
test() {
5057
testType<SomeInt>(SomeInt(10));
5158
testType<SomeInt>(IntComparableWith(SomeInt(10)));
5259
testType<signed long>(IntComparableWith<signed long>(10));
@@ -68,6 +75,16 @@ constexpr bool test() {
6875
{
6976
static_assert(std::same_as<decltype(std::views::iota), decltype(std::ranges::views::iota)>);
7077
}
78+
{ // LWG4096
79+
// [[maybe_unused]] auto i1 = std::views::iota(std::views::iota(82));
80+
// [[maybe_unused]] auto i2 = std::views::iota(std::views::iota(SomeInt(94)));
81+
82+
static_assert(!CanDoubleWrap<int>);
83+
static_assert(!CanDoubleWrap<SomeInt>);
84+
static_assert(!HasIota<decltype(std::views::iota(82))>);
85+
static_assert(!HasIota<decltype(std::views::iota(SomeInt(94)))>);
86+
static_assert(!std::is_invocable_v<decltype(std::views::iota), decltype(std::views::iota(82))>);
87+
}
7188

7289
return true;
7390
}

libcxx/test/std/ranges/range.factories/range.iota.view/views_iota.verify.cpp

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -19,11 +19,11 @@ void test() {
1919
{
2020
[[maybe_unused]] auto i1 = std::views::iota(0); // OK
2121
[[maybe_unused]] auto i2 = std::views::iota(std::views::iota(0));
22-
// expected-error-re@*:* {{constraints not satisfied for class template 'iota_view'{{.*}}}}
22+
// expected-error@*:* {{no matching function for call to object of type 'const __iota::__fn'}}
2323
}
2424
{
2525
[[maybe_unused]] auto i1 = std::views::iota(SomeInt(0)); // OK
2626
[[maybe_unused]] auto i2 = std::views::iota(std::views::iota(SomeInt(0)));
27-
//expected-error-re@*:* {{constraints not satisfied for class template 'iota_view'{{.*}}}}
27+
//expected-error@*:* {{no matching function for call to object of type 'const __iota::__fn'}}
2828
}
2929
}

0 commit comments

Comments
 (0)