QList::iterator: use templates for advancing operators
Because of the addition of the operator T*(), the expression "it + N"
where N was not exactly qsizetype but any other integer type was a
compilation failure because of ambiguous overload resolution.
With GCC it's apparently a warning:
warning: ISO C++ says that these are ambiguous, even though the worst conversion for the first is better than the worst conversion for the second:
note: candidate 1: ‘QList<T>::iterator QList<T>::iterator::operator+(qsizetype) const [with T = char; qsizetype = long long int]’
note: candidate 2: ‘operator+(char*, ptrdiff_t {aka long int})’ (built-in)
With Clang, it's an error:
error: use of overloaded operator '+' is ambiguous (with operand types 'QList<int>::const_iterator' and 'ptrdiff_t' (aka 'long'))
note: candidate function
inline const_iterator operator+(qsizetype j) const { return const_iterator(i+j); }
note: built-in candidate operator+(const int *, long)
Pick-to: 6.2
Fixes: QTBUG-96128
Change-Id: Ie72b0dd0fbe84d2caae0fffd16a06f23dd56b060
Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org>
Reviewed-by: Giuseppe D'Angelo <giuseppe.dangelo@kdab.com>
bb10
parent
2675c288e8
commit
878b2047b5
|
|
@ -162,13 +162,19 @@ public:
|
|||
inline iterator operator++(int) { T *n = i; ++i; return n; }
|
||||
inline iterator &operator--() { i--; return *this; }
|
||||
inline iterator operator--(int) { T *n = i; i--; return n; }
|
||||
inline iterator &operator+=(qsizetype j) { i+=j; return *this; }
|
||||
inline iterator &operator-=(qsizetype j) { i-=j; return *this; }
|
||||
inline iterator operator+(qsizetype j) const { return iterator(i+j); }
|
||||
inline iterator operator-(qsizetype j) const { return iterator(i-j); }
|
||||
friend inline iterator operator+(qsizetype j, iterator k) { return k + j; }
|
||||
inline qsizetype operator-(iterator j) const { return i - j.i; }
|
||||
inline operator T*() const { return i; }
|
||||
|
||||
template <typename Int> std::enable_if_t<std::is_integral_v<Int>, iterator>
|
||||
&operator+=(Int j) { i+=j; return *this; }
|
||||
template <typename Int> std::enable_if_t<std::is_integral_v<Int>, iterator>
|
||||
&operator-=(Int j) { i-=j; return *this; }
|
||||
template <typename Int> std::enable_if_t<std::is_integral_v<Int>, iterator>
|
||||
operator+(Int j) const { return iterator(i+j); }
|
||||
template <typename Int> std::enable_if_t<std::is_integral_v<Int>, iterator>
|
||||
operator-(Int j) const { return iterator(i-j); }
|
||||
template <typename Int> friend std::enable_if_t<std::is_integral_v<Int>, iterator>
|
||||
operator+(Int j, iterator k) { return k + j; }
|
||||
};
|
||||
|
||||
class const_iterator {
|
||||
|
|
@ -206,13 +212,19 @@ public:
|
|||
inline const_iterator operator++(int) { const T *n = i; ++i; return n; }
|
||||
inline const_iterator &operator--() { i--; return *this; }
|
||||
inline const_iterator operator--(int) { const T *n = i; i--; return n; }
|
||||
inline const_iterator &operator+=(qsizetype j) { i+=j; return *this; }
|
||||
inline const_iterator &operator-=(qsizetype j) { i-=j; return *this; }
|
||||
inline const_iterator operator+(qsizetype j) const { return const_iterator(i+j); }
|
||||
inline const_iterator operator-(qsizetype j) const { return const_iterator(i-j); }
|
||||
friend inline const_iterator operator+(qsizetype j, const_iterator k) { return k + j; }
|
||||
inline qsizetype operator-(const_iterator j) const { return i - j.i; }
|
||||
inline operator const T*() const { return i; }
|
||||
|
||||
template <typename Int> std::enable_if_t<std::is_integral_v<Int>, const_iterator>
|
||||
&operator+=(Int j) { i+=j; return *this; }
|
||||
template <typename Int> std::enable_if_t<std::is_integral_v<Int>, const_iterator>
|
||||
&operator-=(Int j) { i-=j; return *this; }
|
||||
template <typename Int> std::enable_if_t<std::is_integral_v<Int>, const_iterator>
|
||||
operator+(Int j) const { return const_iterator(i+j); }
|
||||
template <typename Int> std::enable_if_t<std::is_integral_v<Int>, const_iterator>
|
||||
operator-(Int j) const { return const_iterator(i-j); }
|
||||
template <typename Int> friend std::enable_if_t<std::is_integral_v<Int>, const_iterator>
|
||||
operator+(Int j, const_iterator k) { return k + j; }
|
||||
};
|
||||
using Iterator = iterator;
|
||||
using ConstIterator = const_iterator;
|
||||
|
|
|
|||
|
|
@ -2404,30 +2404,97 @@ void tst_QList::iterators() const
|
|||
idx = 0;
|
||||
auto it = v.begin();
|
||||
QCOMPARE(*it, idx);
|
||||
// idx == 0
|
||||
|
||||
std::advance(it, 7);
|
||||
idx += 7;
|
||||
QCOMPARE(*it, idx);
|
||||
// idx == 7
|
||||
|
||||
it++;
|
||||
idx++;
|
||||
QCOMPARE(*it, idx);
|
||||
// idx == 8
|
||||
|
||||
++it;
|
||||
++idx;
|
||||
QCOMPARE(*it, idx);
|
||||
// idx == 9
|
||||
|
||||
std::advance(it, -3);
|
||||
idx -= 3;
|
||||
QCOMPARE(*it, idx);
|
||||
// idx == 6
|
||||
|
||||
it--;
|
||||
idx--;
|
||||
QCOMPARE(*it, idx);
|
||||
// idx == 5
|
||||
|
||||
--it;
|
||||
--idx;
|
||||
QCOMPARE(*it, idx);
|
||||
// idx == 4
|
||||
|
||||
it = it + 1;
|
||||
idx = idx + 1;
|
||||
QCOMPARE(*it, idx);
|
||||
// idx == 5
|
||||
|
||||
it = it + ptrdiff_t(1);
|
||||
idx = idx + 1;
|
||||
QCOMPARE(*it, idx);
|
||||
// idx == 6
|
||||
|
||||
it = it + qsizetype(1);
|
||||
idx = idx + 1;
|
||||
QCOMPARE(*it, idx);
|
||||
// idx == 7
|
||||
|
||||
it = it - qsizetype(1);
|
||||
idx = idx - 1;
|
||||
QCOMPARE(*it, idx);
|
||||
// idx == 6
|
||||
|
||||
it = it - ptrdiff_t(1);
|
||||
idx = idx - 1;
|
||||
QCOMPARE(*it, idx);
|
||||
// idx == 5
|
||||
|
||||
it = it - 1;
|
||||
idx = idx - 1;
|
||||
QCOMPARE(*it, idx);
|
||||
// idx == 4
|
||||
|
||||
it -= 1;
|
||||
idx -= 1;
|
||||
QCOMPARE(*it, idx);
|
||||
// idx == 3
|
||||
|
||||
it -= qsizetype(1);
|
||||
idx -= 1;
|
||||
QCOMPARE(*it, idx);
|
||||
// idx == 2
|
||||
|
||||
it -= ptrdiff_t(1);
|
||||
idx -= 1;
|
||||
QCOMPARE(*it, idx);
|
||||
// idx == 1
|
||||
|
||||
it += ptrdiff_t(1);
|
||||
idx += 1;
|
||||
QCOMPARE(*it, idx);
|
||||
// idx == 2
|
||||
|
||||
it += qsizetype(1);
|
||||
idx += 1;
|
||||
QCOMPARE(*it, idx);
|
||||
// idx == 3
|
||||
|
||||
it += 1;
|
||||
idx += 1;
|
||||
QCOMPARE(*it, idx);
|
||||
// idx == 4
|
||||
|
||||
*it = idx + 1;
|
||||
QCOMPARE(*it, idx + 1);
|
||||
|
|
@ -2484,30 +2551,97 @@ void tst_QList::constIterators() const
|
|||
qsizetype idx = 0;
|
||||
auto it = v.cbegin();
|
||||
QCOMPARE(*it, idx);
|
||||
// idx == 0
|
||||
|
||||
std::advance(it, 7);
|
||||
idx += 7;
|
||||
QCOMPARE(*it, idx);
|
||||
// idx == 7
|
||||
|
||||
it++;
|
||||
idx++;
|
||||
QCOMPARE(*it, idx);
|
||||
// idx == 8
|
||||
|
||||
++it;
|
||||
++idx;
|
||||
QCOMPARE(*it, idx);
|
||||
// idx == 9
|
||||
|
||||
std::advance(it, -3);
|
||||
idx -= 3;
|
||||
QCOMPARE(*it, idx);
|
||||
// idx == 6
|
||||
|
||||
it--;
|
||||
idx--;
|
||||
QCOMPARE(*it, idx);
|
||||
// idx == 5
|
||||
|
||||
--it;
|
||||
--idx;
|
||||
QCOMPARE(*it, idx);
|
||||
// idx == 4
|
||||
|
||||
it = it + 1;
|
||||
idx = idx + 1;
|
||||
QCOMPARE(*it, idx);
|
||||
// idx == 5
|
||||
|
||||
it = it + ptrdiff_t(1);
|
||||
idx = idx + 1;
|
||||
QCOMPARE(*it, idx);
|
||||
// idx == 6
|
||||
|
||||
it = it + qsizetype(1);
|
||||
idx = idx + 1;
|
||||
QCOMPARE(*it, idx);
|
||||
// idx == 7
|
||||
|
||||
it = it - qsizetype(1);
|
||||
idx = idx - 1;
|
||||
QCOMPARE(*it, idx);
|
||||
// idx == 6
|
||||
|
||||
it = it - ptrdiff_t(1);
|
||||
idx = idx - 1;
|
||||
QCOMPARE(*it, idx);
|
||||
// idx == 5
|
||||
|
||||
it = it - 1;
|
||||
idx = idx - 1;
|
||||
QCOMPARE(*it, idx);
|
||||
// idx == 4
|
||||
|
||||
it -= 1;
|
||||
idx -= 1;
|
||||
QCOMPARE(*it, idx);
|
||||
// idx == 3
|
||||
|
||||
it -= qsizetype(1);
|
||||
idx -= 1;
|
||||
QCOMPARE(*it, idx);
|
||||
// idx == 2
|
||||
|
||||
it -= ptrdiff_t(1);
|
||||
idx -= 1;
|
||||
QCOMPARE(*it, idx);
|
||||
// idx == 1
|
||||
|
||||
it += ptrdiff_t(1);
|
||||
idx += 1;
|
||||
QCOMPARE(*it, idx);
|
||||
// idx == 2
|
||||
|
||||
it += qsizetype(1);
|
||||
idx += 1;
|
||||
QCOMPARE(*it, idx);
|
||||
// idx == 3
|
||||
|
||||
it += 1;
|
||||
idx += 1;
|
||||
QCOMPARE(*it, idx);
|
||||
// idx == 4
|
||||
|
||||
// stl-style reverse iterators
|
||||
idx = v.size() - 1;
|
||||
|
|
|
|||
Loading…
Reference in New Issue