[libcxx][span] Remove const_iterator from std::span

This implements the resolution to LWG-3320.

Differential Revision: https://reviews.llvm.org/D75642
This commit is contained in:
Michael Schellenberger Costa 2020-05-14 08:27:13 -04:00 committed by Louis Dionne
parent cb1eeb42c0
commit c5ff4031c6
7 changed files with 35 additions and 115 deletions

View File

@ -46,9 +46,7 @@ public:
using reference = element_type&;
using const_reference = const element_type&;
using iterator = implementation-defined;
using const_iterator = implementation-defined;
using reverse_iterator = std::reverse_iterator<iterator>;
using const_reverse_iterator = std::reverse_iterator<const_iterator>;
static constexpr size_type extent = Extent;
// [span.cons], span constructors, copy, assignment, and destructor
@ -97,12 +95,8 @@ public:
// [span.iterators], span iterator support
constexpr iterator begin() const noexcept;
constexpr iterator end() const noexcept;
constexpr const_iterator cbegin() const noexcept;
constexpr const_iterator cend() const noexcept;
constexpr reverse_iterator rbegin() const noexcept;
constexpr reverse_iterator rend() const noexcept;
constexpr const_reverse_iterator crbegin() const noexcept;
constexpr const_reverse_iterator crend() const noexcept;
private:
pointer data_; // exposition only
@ -201,9 +195,7 @@ public:
using reference = _Tp &;
using const_reference = const _Tp &;
using iterator = __wrap_iter<pointer>;
using const_iterator = __wrap_iter<const_pointer>;
using reverse_iterator = _VSTD::reverse_iterator<iterator>;
using const_reverse_iterator = _VSTD::reverse_iterator<const_iterator>;
static constexpr size_type extent = _Extent;
@ -340,12 +332,8 @@ public:
// [span.iter], span iterator support
_LIBCPP_INLINE_VISIBILITY constexpr iterator begin() const noexcept { return iterator(data()); }
_LIBCPP_INLINE_VISIBILITY constexpr iterator end() const noexcept { return iterator(data() + size()); }
_LIBCPP_INLINE_VISIBILITY constexpr const_iterator cbegin() const noexcept { return const_iterator(data()); }
_LIBCPP_INLINE_VISIBILITY constexpr const_iterator cend() const noexcept { return const_iterator(data() + size()); }
_LIBCPP_INLINE_VISIBILITY constexpr reverse_iterator rbegin() const noexcept { return reverse_iterator(end()); }
_LIBCPP_INLINE_VISIBILITY constexpr reverse_iterator rend() const noexcept { return reverse_iterator(begin()); }
_LIBCPP_INLINE_VISIBILITY constexpr const_reverse_iterator crbegin() const noexcept { return const_reverse_iterator(cend()); }
_LIBCPP_INLINE_VISIBILITY constexpr const_reverse_iterator crend() const noexcept { return const_reverse_iterator(cbegin()); }
_LIBCPP_INLINE_VISIBILITY constexpr void swap(span &__other) noexcept
{
@ -381,9 +369,7 @@ public:
using reference = _Tp &;
using const_reference = const _Tp &;
using iterator = __wrap_iter<pointer>;
using const_iterator = __wrap_iter<const_pointer>;
using reverse_iterator = _VSTD::reverse_iterator<iterator>;
using const_reverse_iterator = _VSTD::reverse_iterator<const_iterator>;
static constexpr size_type extent = dynamic_extent;
@ -510,12 +496,8 @@ public:
// [span.iter], span iterator support
_LIBCPP_INLINE_VISIBILITY constexpr iterator begin() const noexcept { return iterator(data()); }
_LIBCPP_INLINE_VISIBILITY constexpr iterator end() const noexcept { return iterator(data() + size()); }
_LIBCPP_INLINE_VISIBILITY constexpr const_iterator cbegin() const noexcept { return const_iterator(data()); }
_LIBCPP_INLINE_VISIBILITY constexpr const_iterator cend() const noexcept { return const_iterator(data() + size()); }
_LIBCPP_INLINE_VISIBILITY constexpr reverse_iterator rbegin() const noexcept { return reverse_iterator(end()); }
_LIBCPP_INLINE_VISIBILITY constexpr reverse_iterator rend() const noexcept { return reverse_iterator(begin()); }
_LIBCPP_INLINE_VISIBILITY constexpr const_reverse_iterator crbegin() const noexcept { return const_reverse_iterator(cend()); }
_LIBCPP_INLINE_VISIBILITY constexpr const_reverse_iterator crend() const noexcept { return const_reverse_iterator(cbegin()); }
_LIBCPP_INLINE_VISIBILITY constexpr void swap(span &__other) noexcept
{

View File

@ -22,22 +22,17 @@ template <class Span>
constexpr bool testConstexprSpan(Span s)
{
bool ret = true;
typename Span::iterator b = s. begin();
typename Span::const_iterator cb = s.cbegin();
typename Span::iterator b = s.begin();
if (s.empty())
{
ret = ret && ( b == s.end());
ret = ret && (cb == s.cend());
ret = ret && (b == s.end());
}
else
{
ret = ret && ( *b == s[0]);
ret = ret && ( &*b == &s[0]);
ret = ret && ( *cb == s[0]);
ret = ret && (&*cb == &s[0]);
ret = ret && ( *b == s[0]);
ret = ret && (&*b == &s[0]);
}
ret = ret && (b == cb);
return ret;
}
@ -45,22 +40,17 @@ constexpr bool testConstexprSpan(Span s)
template <class Span>
void testRuntimeSpan(Span s)
{
typename Span::iterator b = s. begin();
typename Span::const_iterator cb = s.cbegin();
typename Span::iterator b = s.begin();
if (s.empty())
{
assert( b == s.end());
assert(cb == s.cend());
assert(b == s.end());
}
else
{
assert( *b == s[0]);
assert( &*b == &s[0]);
assert( *cb == s[0]);
assert(&*cb == &s[0]);
assert( *b == s[0]);
assert(&*b == &s[0]);
}
assert(b == cb);
}
struct A{};

View File

@ -22,52 +22,38 @@ template <class Span>
constexpr bool testConstexprSpan(Span s)
{
bool ret = true;
typename Span::iterator e = s. end();
typename Span::const_iterator ce = s.cend();
typename Span::iterator e = s.end();
if (s.empty())
{
ret = ret && ( e == s.begin());
ret = ret && (ce == s.cbegin());
ret = ret && (e == s.begin());
}
else
{
typename Span::const_pointer last = &*(s.cbegin() + s.size() - 1);
ret = ret && ( e != s.begin());
ret = ret && (ce != s.cbegin());
typename Span::const_pointer last = &*(s.begin() + s.size() - 1);
ret = ret && (e != s.begin());
ret = ret && (&*( e-1) == last);
ret = ret && (&*(ce-1) == last);
}
ret = ret && (static_cast<size_t>( e - s.begin()) == s.size());
ret = ret && (static_cast<size_t>(ce - s.cbegin()) == s.size());
ret = ret && (e == ce);
ret = ret && (static_cast<size_t>(e - s.begin()) == s.size());
return ret;
}
template <class Span>
void testRuntimeSpan(Span s)
{
typename Span::iterator e = s. end();
typename Span::const_iterator ce = s.cend();
typename Span::iterator e = s.end();
if (s.empty())
{
assert( e == s.begin());
assert(ce == s.cbegin());
assert(e == s.begin());
}
else
{
typename Span::const_pointer last = &*(s.cbegin() + s.size() - 1);
assert( e != s.begin());
assert(ce != s.cbegin());
assert( &*( e-1) == last);
assert( &*(ce-1) == last);
typename Span::const_pointer last = &*(s.begin() + s.size() - 1);
assert(e != s.begin());
assert(&*( e-1) == last);
}
assert(static_cast<size_t>( e - s.begin()) == s.size());
assert(static_cast<size_t>(ce - s.cbegin()) == s.size());
assert(e == ce);
assert(static_cast<size_t>(e - s.begin()) == s.size());
}

View File

@ -22,22 +22,17 @@ template <class Span>
constexpr bool testConstexprSpan(Span s)
{
bool ret = true;
typename Span::reverse_iterator b = s. rbegin();
typename Span::const_reverse_iterator cb = s.crbegin();
typename Span::reverse_iterator b = s.rbegin();
if (s.empty())
{
ret = ret && ( b == s.rend());
ret = ret && (cb == s.crend());
}
else
{
const typename Span::size_type last = s.size() - 1;
ret = ret && ( *b == s[last]);
ret = ret && ( &*b == &s[last]);
ret = ret && ( *cb == s[last]);
ret = ret && (&*cb == &s[last]);
ret = ret && ( *b == s[last]);
ret = ret && (&*b == &s[last]);
}
ret = ret && (b == cb);
return ret;
}
@ -45,22 +40,17 @@ constexpr bool testConstexprSpan(Span s)
template <class Span>
void testRuntimeSpan(Span s)
{
typename Span::reverse_iterator b = s. rbegin();
typename Span::const_reverse_iterator cb = s.crbegin();
typename Span::reverse_iterator b = s.rbegin();
if (s.empty())
{
assert( b == s.rend());
assert(cb == s.crend());
assert(b == s.rend());
}
else
{
const typename Span::size_type last = s.size() - 1;
assert( *b == s[last]);
assert( &*b == &s[last]);
assert( *cb == s[last]);
assert(&*cb == &s[last]);
assert( *b == s[last]);
assert(&*b == &s[last]);
}
assert(b == cb);
}

View File

@ -22,46 +22,34 @@ template <class Span>
constexpr bool testConstexprSpan(Span s)
{
bool ret = true;
typename Span::reverse_iterator e = s. rend();
typename Span::const_reverse_iterator ce = s.crend();
typename Span::reverse_iterator e = s.rend();
if (s.empty())
{
ret = ret && ( e == s.rbegin());
ret = ret && (ce == s.crbegin());
ret = ret && (e == s.rbegin());
}
else
{
ret = ret && ( e != s.rbegin());
ret = ret && (ce != s.crbegin());
ret = ret && (e != s.rbegin());
}
ret = ret && (static_cast<size_t>( e - s.rbegin()) == s.size());
ret = ret && (static_cast<size_t>(ce - s.crbegin()) == s.size());
ret = ret && (e == ce);
ret = ret && (static_cast<size_t>(e - s.rbegin()) == s.size());
return ret;
}
template <class Span>
void testRuntimeSpan(Span s)
{
typename Span::reverse_iterator e = s. rend();
typename Span::const_reverse_iterator ce = s.crend();
typename Span::reverse_iterator e = s.rend();
if (s.empty())
{
assert( e == s.rbegin());
assert(ce == s.crbegin());
assert(e == s.rbegin());
}
else
{
assert( e != s.rbegin());
assert(ce != s.crbegin());
assert(e != s.rbegin());
}
assert(static_cast<size_t>( e - s.rbegin()) == s.size());
assert(static_cast<size_t>(ce - s.crbegin()) == s.size());
assert(e == ce);
assert(static_cast<size_t>(e - s.rbegin()) == s.size());
}

View File

@ -49,20 +49,6 @@ void testIterator()
ASSERT_SAME_TYPE(typename ItT::difference_type, typename S::difference_type);
}
template <typename S, typename Iter>
void testConstIterator()
{
typedef std::iterator_traits<Iter> ItT;
ASSERT_SAME_TYPE(typename ItT::iterator_category, std::random_access_iterator_tag);
ASSERT_SAME_TYPE(typename ItT::value_type, typename S::value_type);
// I'd like to say 'const typename S::pointer' here, but that gives me
// a const pointer to a non-const value, which is not what I want.
ASSERT_SAME_TYPE(typename ItT::reference, typename S::element_type const &);
ASSERT_SAME_TYPE(typename ItT::pointer, typename S::element_type const *);
ASSERT_SAME_TYPE(typename ItT::difference_type, typename S::difference_type);
}
template <typename S, typename ElementType, std::size_t Size>
void testSpan()
{
@ -79,8 +65,6 @@ void testSpan()
testIterator<S, typename S::iterator>();
testIterator<S, typename S::reverse_iterator>();
testConstIterator<S, typename S::const_iterator>();
testConstIterator<S, typename S::const_reverse_iterator>();
}

View File

@ -521,7 +521,7 @@
<tr><td><a href="https://wg21.link/LWG3317">3317</a></td><td>Incorrect <tt>operator&lt;&lt;</tt> for floating-point durations</td><td>Prague</td><td></td></tr>
<tr><td><a href="https://wg21.link/LWG3318">3318</a></td><td>Clarify whether clocks can represent time before their epoch</td><td>Prague</td><td></td></tr>
<tr><td><a href="https://wg21.link/LWG3319">3319</a></td><td>Properly reference specification of IANA time zone database</td><td>Prague</td><td></td></tr>
<tr><td><a href="https://wg21.link/LWG3320">3320</a></td><td><tt>span::cbegin/cend</tt> methods produce different results than <tt>std::[ranges::]cbegin/cend</tt></td><td>Prague</td><td></td></tr>
<tr><td><a href="https://wg21.link/LWG3320">3320</a></td><td><tt>span::cbegin/cend</tt> methods produce different results than <tt>std::[ranges::]cbegin/cend</tt></td><td>Prague</td><td>Complete</td></tr>
<tr><td><a href="https://wg21.link/LWG3321">3321</a></td><td><tt>uninitialized_construct_using_allocator</tt> should use <tt>construct_at</tt></td><td>Prague</td><td></td></tr>
<tr><td><a href="https://wg21.link/LWG3323">3323</a></td><td><tt><i>has-tuple-element</i></tt> helper concept needs <tt>convertible_to</tt></td><td>Prague</td><td></td></tr>
<tr><td><a href="https://wg21.link/LWG3324">3324</a></td><td>Special-case <tt>std::strong/weak/partial_order</tt> for pointers</td><td>Prague</td><td></td></tr>