1//===----------------------------------------------------------------------===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8// UNSUPPORTED: c++03, c++11, c++14, c++17
9
10// <span>
11
12// template<size_t Count>
13// constexpr span<element_type, Count> last() const;
14//
15// constexpr span<element_type, dynamic_extent> last(size_type count) const;
16//
17// Mandates: Count <= Extent is true.
18
19#include <span>
20#include <cassert>
21#include <algorithm>
22#include <string>
23
24#include "test_macros.h"
25
26template <typename Span, std::size_t Count>
27constexpr bool testConstexprSpan(Span sp) {
28 LIBCPP_ASSERT((noexcept(sp.template last<Count>())));
29 LIBCPP_ASSERT((noexcept(sp.last(Count))));
30 auto s1 = sp.template last<Count>();
31 auto s2 = sp.last(Count);
32 using S1 = decltype(s1);
33 using S2 = decltype(s2);
34 ASSERT_SAME_TYPE(typename Span::value_type, typename S1::value_type);
35 ASSERT_SAME_TYPE(typename Span::value_type, typename S2::value_type);
36 static_assert(S1::extent == Count, "");
37 static_assert(S2::extent == std::dynamic_extent, "");
38 return s1.data() == s2.data() && s1.size() == s2.size() && std::equal(s1.begin(), s1.end(), sp.end() - Count);
39}
40
41template <typename Span, std::size_t Count>
42void testRuntimeSpan(Span sp) {
43 LIBCPP_ASSERT((noexcept(sp.template last<Count>())));
44 LIBCPP_ASSERT((noexcept(sp.last(Count))));
45 auto s1 = sp.template last<Count>();
46 auto s2 = sp.last(Count);
47 using S1 = decltype(s1);
48 using S2 = decltype(s2);
49 ASSERT_SAME_TYPE(typename Span::value_type, typename S1::value_type);
50 ASSERT_SAME_TYPE(typename Span::value_type, typename S2::value_type);
51 static_assert(S1::extent == Count, "");
52 static_assert(S2::extent == std::dynamic_extent, "");
53 assert(s1.data() == s2.data());
54 assert(s1.size() == s2.size());
55 assert(std::equal(s1.begin(), s1.end(), sp.end() - Count));
56}
57
58constexpr int carr1[] = {1, 2, 3, 4};
59int arr[] = {5, 6, 7};
60std::string sarr[] = {"ABC", "DEF", "GHI", "JKL", "MNO"};
61
62int main(int, char**) {
63 {
64 using Sp = std::span<const int>;
65 static_assert(testConstexprSpan<Sp, 0>(Sp{}), "");
66
67 static_assert(testConstexprSpan<Sp, 0>(Sp{carr1}), "");
68 static_assert(testConstexprSpan<Sp, 1>(Sp{carr1}), "");
69 static_assert(testConstexprSpan<Sp, 2>(Sp{carr1}), "");
70 static_assert(testConstexprSpan<Sp, 3>(Sp{carr1}), "");
71 static_assert(testConstexprSpan<Sp, 4>(Sp{carr1}), "");
72 }
73
74 {
75 using Sp = std::span<const int, 4>;
76
77 static_assert(testConstexprSpan<Sp, 0>(Sp{carr1}), "");
78 static_assert(testConstexprSpan<Sp, 1>(Sp{carr1}), "");
79 static_assert(testConstexprSpan<Sp, 2>(Sp{carr1}), "");
80 static_assert(testConstexprSpan<Sp, 3>(Sp{carr1}), "");
81 static_assert(testConstexprSpan<Sp, 4>(Sp{carr1}), "");
82 }
83
84 {
85 using Sp = std::span<int>;
86 testRuntimeSpan<Sp, 0>(Sp{});
87
88 testRuntimeSpan<Sp, 0>(Sp{arr});
89 testRuntimeSpan<Sp, 1>(Sp{arr});
90 testRuntimeSpan<Sp, 2>(Sp{arr});
91 testRuntimeSpan<Sp, 3>(Sp{arr});
92 }
93
94 {
95 using Sp = std::span<int, 3>;
96
97 testRuntimeSpan<Sp, 0>(Sp{arr});
98 testRuntimeSpan<Sp, 1>(Sp{arr});
99 testRuntimeSpan<Sp, 2>(Sp{arr});
100 testRuntimeSpan<Sp, 3>(Sp{arr});
101 }
102
103 {
104 using Sp = std::span<std::string>;
105 testConstexprSpan<Sp, 0>(Sp{});
106
107 testRuntimeSpan<Sp, 0>(Sp{sarr});
108 testRuntimeSpan<Sp, 1>(Sp{sarr});
109 testRuntimeSpan<Sp, 2>(Sp{sarr});
110 testRuntimeSpan<Sp, 3>(Sp{sarr});
111 testRuntimeSpan<Sp, 4>(Sp{sarr});
112 testRuntimeSpan<Sp, 5>(Sp{sarr});
113 }
114
115 {
116 using Sp = std::span<std::string, 5>;
117
118 testRuntimeSpan<Sp, 0>(Sp{sarr});
119 testRuntimeSpan<Sp, 1>(Sp{sarr});
120 testRuntimeSpan<Sp, 2>(Sp{sarr});
121 testRuntimeSpan<Sp, 3>(Sp{sarr});
122 testRuntimeSpan<Sp, 4>(Sp{sarr});
123 testRuntimeSpan<Sp, 5>(Sp{sarr});
124 }
125
126 return 0;
127}
128

source code of libcxx/test/std/containers/views/views.span/span.sub/last.pass.cpp