This page is a snapshot from the LWG issues list, see the Library Active Issues List for more information and the meaning of New status.

### 2858. LWG 2472: actually an incompatibility with C++03

Section: 23.5.1 [reverse.iterators] Status: New Submitter: Hubert Tong Opened: 2017-01-28 Last modified: 2020-09-06

Priority: 4

View all other issues in [reverse.iterators].

View all issues with New status.

Discussion:

Further to LWG 2472, the case of `reverse_iterator` comparisons is a regression introduced by LWG 280.

Consider the following program:

>     #include <utility>
>     #include <iterator>

>     using namespace std::rel_ops;

>     bool f(std::reverse_iterator<int *> it) { return it != it; }

Under C++03, the `operator!=` in lib.reverse.iterator is more specialized than the `operator!=` in `std::rel_ops`.

Following LWG 280, neither `operator!=` candidate is more specialized than the other. The program is observed to fail with libc++.

Online compiler example, see here.

Suggested resolution:

Reintroduce the homogeneous comparison operators from C++03 alongside the new ones.

[2017-03-04, Kona]

Set priority to 4. STL to write a paper deprecating `relops` Alisdair to provide an example for Annex C.

Proposed resolution:

This wording is relative to N4618.

1. Modify 23.5.1 [reverse.iterators], class template `reverse_iterator` synopsis, as indicated:

   >     template <class Iterator1, class Iterator2>
   >       constexpr bool operator==(
   >         const reverse_iterator<Iterator1>& x,
   >         const reverse_iterator<Iterator2>& y);
   >     template <class Iterator1, class Iterator2>
   >       constexpr bool operator<(
   >         const reverse_iterator<Iterator1>& x,
   >         const reverse_iterator<Iterator2>& y);
   >     template <class Iterator1, class Iterator2>
   >       constexpr bool operator!=(
   >         const reverse_iterator<Iterator1>& x,
   >         const reverse_iterator<Iterator2>& y);
   >     template <class Iterator1, class Iterator2>
   >       constexpr bool operator>(
   >         const reverse_iterator<Iterator1>& x,
   >         const reverse_iterator<Iterator2>& y);
   >     template <class Iterator1, class Iterator2>
   >       constexpr bool operator>=(
   >         const reverse_iterator<Iterator1>& x,
   >         const reverse_iterator<Iterator2>& y);
   >     template <class Iterator1, class Iterator2>
   >       constexpr bool operator<=(
   >         const reverse_iterator<Iterator1>& x,
   >         const reverse_iterator<Iterator2>& y);
   >     template <class Iterator>
   >       constexpr bool operator==(
   >         const reverse_iterator<Iterator>& x,
   >         const reverse_iterator<Iterator>& y);
   >     template <class Iterator>
   >       constexpr bool operator<(
   >         const reverse_iterator<Iterator>& x,
   >         const reverse_iterator<Iterator>& y);
   >     template <class Iterator>
   >       constexpr bool operator!=(
   >         const reverse_iterator<Iterator>& x,
   >         const reverse_iterator<Iterator>& y);
   >     template <class Iterator>
   >       constexpr bool operator>(
   >         const reverse_iterator<Iterator>& x,
   >         const reverse_iterator<Iterator>& y);
   >     template <class Iterator>
   >       constexpr bool operator>=(
   >         const reverse_iterator<Iterator>& x,
   >         const reverse_iterator<Iterator>& y);
   >     template <class Iterator>
   >       constexpr bool operator<=(
   >         const reverse_iterator<Iterator>& x,
   >         const reverse_iterator<Iterator>& y);

2. Modify [reverse.iter.op==] as indicated:

   >     template <class Iterator1, class Iterator2>
   >       constexpr bool operator==(
   >         const reverse_iterator<Iterator1>& x,
   >         const reverse_iterator<Iterator2>& y);
   >     template <class Iterator>
   >       constexpr bool operator==(
   >         const reverse_iterator<Iterator>& x,
   >         const reverse_iterator<Iterator>& y);

   > > -1- Returns: `x.current == y.current`.

3. Modify [reverse.iter.op<] as indicated:

   >     template <class Iterator1, class Iterator2>
   >       constexpr bool operator<(
   >         const reverse_iterator<Iterator1>& x,
   >         const reverse_iterator<Iterator2>& y);
   >     template <class Iterator>
   >       constexpr bool operator<(
   >         const reverse_iterator<Iterator>& x,
   >         const reverse_iterator<Iterator>& y);

   > > -1- Returns: `x.current > y.current`.

4. Modify [reverse.iter.op!=] as indicated:

   >     template <class Iterator1, class Iterator2>
   >       constexpr bool operator!=(
   >         const reverse_iterator<Iterator1>& x,
   >         const reverse_iterator<Iterator2>& y);
   >     template <class Iterator>
   >       constexpr bool operator!=(
   >         const reverse_iterator<Iterator>& x,
   >         const reverse_iterator<Iterator>& y);

   > > -1- Returns: `x.current != y.current`.

5. Modify [reverse.iter.op>] as indicated:

   >     template <class Iterator1, class Iterator2>
   >       constexpr bool operator>(
   >         const reverse_iterator<Iterator1>& x,
   >         const reverse_iterator<Iterator2>& y);
   >     template <class Iterator>
   >       constexpr bool operator>(
   >         const reverse_iterator<Iterator>& x,
   >         const reverse_iterator<Iterator>& y);

   > > -1- Returns: `x.current < y.current`.

6. Modify [reverse.iter.op>=] as indicated:

   >     template <class Iterator1, class Iterator2>
   >       constexpr bool operator>=(
   >         const reverse_iterator<Iterator1>& x,
   >         const reverse_iterator<Iterator2>& y);
   >     template <class Iterator>
   >       constexpr bool operator>=(
   >         const reverse_iterator<Iterator>& x,
   >         const reverse_iterator<Iterator>& y);

   > > -1- Returns: `x.current <= y.current`.

7. Modify [reverse.iter.op<=] as indicated:

   >     template <class Iterator1, class Iterator2>
   >       constexpr bool operator<=(
   >         const reverse_iterator<Iterator1>& x,
   >         const reverse_iterator<Iterator2>& y);
   >     template <class Iterator>
   >       constexpr bool operator<=(
   >         const reverse_iterator<Iterator>& x,
   >         const reverse_iterator<Iterator>& y);

   > > -1- Returns: `x.current >= y.current`.