17b20e05cSzoecarver //===----------------------------------------------------------------------===//
27b20e05cSzoecarver //
37b20e05cSzoecarver // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
47b20e05cSzoecarver // See https://llvm.org/LICENSE.txt for license information.
57b20e05cSzoecarver // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
67b20e05cSzoecarver //
77b20e05cSzoecarver //===----------------------------------------------------------------------===//
87b20e05cSzoecarver
97b20e05cSzoecarver // UNSUPPORTED: c++03, c++11, c++14, c++17
107b20e05cSzoecarver
114e00a192SCasey Carter #include "test_macros.h"
124e00a192SCasey Carter
1314324fa4SNikolas Klauser TEST_CLANG_DIAGNOSTIC_IGNORED("-Wsign-compare")
1414324fa4SNikolas Klauser TEST_GCC_DIAGNOSTIC_IGNORED("-Wsign-compare")
1514324fa4SNikolas Klauser TEST_MSVC_DIAGNOSTIC_IGNORED(4018 4389) // various "signed/unsigned mismatch"
167b20e05cSzoecarver
17*40aaa272SHristo Hristov // constexpr iota_view(type_identity_t<W> value, type_identity_t<Bound> bound); // explicit since C++23
187b20e05cSzoecarver
197b20e05cSzoecarver #include <ranges>
207b20e05cSzoecarver #include <cassert>
217b20e05cSzoecarver
22*40aaa272SHristo Hristov #include "test_convertible.h"
237b20e05cSzoecarver #include "types.h"
247b20e05cSzoecarver
25*40aaa272SHristo Hristov // SFINAE tests.
26*40aaa272SHristo Hristov
27*40aaa272SHristo Hristov #if TEST_STD_VER >= 23
28*40aaa272SHristo Hristov
29*40aaa272SHristo Hristov static_assert(!test_convertible<std::ranges::iota_view<SomeInt, SomeInt>,
30*40aaa272SHristo Hristov decltype(std::ranges::iota_view<SomeInt, SomeInt>{}.begin()),
31*40aaa272SHristo Hristov decltype(std::ranges::iota_view<SomeInt, SomeInt>{}.end())>(),
32*40aaa272SHristo Hristov "This constructor must be explicit");
33*40aaa272SHristo Hristov
34*40aaa272SHristo Hristov static_assert(!test_convertible<std::ranges::iota_view<SomeInt>,
35*40aaa272SHristo Hristov decltype(std::ranges::iota_view<SomeInt>{}.begin()),
36*40aaa272SHristo Hristov decltype(std::unreachable_sentinel)>(),
37*40aaa272SHristo Hristov "This constructor must be explicit");
38*40aaa272SHristo Hristov
39*40aaa272SHristo Hristov static_assert(!test_convertible<std::ranges::iota_view<SomeInt, IntComparableWith<SomeInt>>,
40*40aaa272SHristo Hristov decltype(std::ranges::iota_view{SomeInt(0), IntComparableWith(SomeInt(10))}.begin()),
41*40aaa272SHristo Hristov decltype(std::ranges::iota_view{SomeInt(0), IntComparableWith(SomeInt(10))}.end())>(),
42*40aaa272SHristo Hristov "This constructor must be explicit");
43*40aaa272SHristo Hristov
44*40aaa272SHristo Hristov #else
45*40aaa272SHristo Hristov
46*40aaa272SHristo Hristov static_assert( test_convertible<std::ranges::iota_view<SomeInt, SomeInt>,
47*40aaa272SHristo Hristov decltype(std::ranges::iota_view<SomeInt, SomeInt>{}.begin()),
48*40aaa272SHristo Hristov decltype(std::ranges::iota_view<SomeInt, SomeInt>{}.end())>(),
49*40aaa272SHristo Hristov "This constructor must not be explicit");
50*40aaa272SHristo Hristov
51*40aaa272SHristo Hristov static_assert( test_convertible<std::ranges::iota_view<SomeInt>,
52*40aaa272SHristo Hristov decltype(std::ranges::iota_view<SomeInt>{}.begin()),
53*40aaa272SHristo Hristov decltype(std::unreachable_sentinel)>(),
54*40aaa272SHristo Hristov "This constructor must not be explicit");
55*40aaa272SHristo Hristov
56*40aaa272SHristo Hristov static_assert( test_convertible<std::ranges::iota_view<SomeInt, IntComparableWith<SomeInt>>,
57*40aaa272SHristo Hristov decltype(std::ranges::iota_view{SomeInt(0), IntComparableWith(SomeInt(10))}.begin()),
58*40aaa272SHristo Hristov decltype(std::ranges::iota_view{SomeInt(0), IntComparableWith(SomeInt(10))}.end())>(),
59*40aaa272SHristo Hristov "This constructor must not be explicit");
60*40aaa272SHristo Hristov
61*40aaa272SHristo Hristov #endif // TEST_STD_VER >= 23
62*40aaa272SHristo Hristov
test()637b20e05cSzoecarver constexpr bool test() {
647b20e05cSzoecarver {
657b20e05cSzoecarver std::ranges::iota_view<SomeInt, SomeInt> io(SomeInt(0), SomeInt(10));
667b20e05cSzoecarver assert(std::ranges::next(io.begin(), 10) == io.end());
677b20e05cSzoecarver }
687b20e05cSzoecarver
697b20e05cSzoecarver {
707b20e05cSzoecarver std::ranges::iota_view<SomeInt> io(SomeInt(0), std::unreachable_sentinel);
717b20e05cSzoecarver assert(std::ranges::next(io.begin(), 10) != io.end());
727b20e05cSzoecarver }
737b20e05cSzoecarver
747b20e05cSzoecarver {
757b20e05cSzoecarver std::ranges::iota_view<SomeInt, IntComparableWith<SomeInt>> io(SomeInt(0), IntComparableWith(SomeInt(10)));
767b20e05cSzoecarver assert(std::ranges::next(io.begin(), 10) == io.end());
777b20e05cSzoecarver }
787b20e05cSzoecarver
797b20e05cSzoecarver {
807b20e05cSzoecarver // This is allowed only when using the constructor (not the deduction guide).
817b20e05cSzoecarver std::ranges::iota_view<int, unsigned> signedUnsigned(0, 10);
827b20e05cSzoecarver assert(std::ranges::next(signedUnsigned.begin(), 10) == signedUnsigned.end());
837b20e05cSzoecarver }
847b20e05cSzoecarver
857b20e05cSzoecarver {
867b20e05cSzoecarver // This is allowed only when using the constructor (not the deduction guide).
877b20e05cSzoecarver std::ranges::iota_view<unsigned, int> signedUnsigned(0, 10);
887b20e05cSzoecarver assert(std::ranges::next(signedUnsigned.begin(), 10) == signedUnsigned.end());
897b20e05cSzoecarver }
907b20e05cSzoecarver
917b20e05cSzoecarver return true;
927b20e05cSzoecarver }
937b20e05cSzoecarver
main(int,char **)947b20e05cSzoecarver int main(int, char**) {
957b20e05cSzoecarver test();
967b20e05cSzoecarver static_assert(test());
977b20e05cSzoecarver
987b20e05cSzoecarver return 0;
997b20e05cSzoecarver }
100