- Title
- ranges::advance violates its preconditions
- Status
- new
- Section
- [range.iter.op.advance]
- Submitter
- Casey Carter

Created on **2019-10-27.00:00:00**
last changed **3 months ago**

Date: 2019-11-04.13:23:43

**Proposed resolution:**

This wording is relative to N4835.

Modify [range.iter.op.advance] as indicated:

template<input_or_output_iterator I, sentinel_for<I> S> constexpr void ranges::advance(I& i, S bound);

-3-

*Expects:*Either`assignable_from<I&, S> || sized_sentinel_for<S, I>`is modeled, or`[i, bound)`denotes a range.-4-

*Effects:*(4.1) — If

`I`and`S`model`assignable_from<I&, S>`, equivalent to`i = std::move(bound)`.(4.2) — Otherwise, if

`S`and`I`model`sized_sentinel_for<S, I>`, equivalent to`ranges::advance(i, bound - i)`.(4.3) — Otherwise, while

`bool(i != bound)`is`true`, increments`i`.

Date: 2019-11-04.13:23:43

*[ 2019-11 Priority to 2 during Monday issue prioritization in Belfast ]*

Date: 2019-10-27.00:00:00

Recall that "`[i, s)` denotes a range" for an iterator `i` and sentinel `s`
means that either `i == s` holds, or `i` is dereferenceable and `[++i, s)`
denotes a range ([iterator.requirements.general).

The three-argument overload `ranges::advance(i, n, bound)` is specified in
[range.iter.op.advance] paragraphs 5 through 7. Para 5 establishes a precondition that
`[bound, i)` denotes a range when `n < 0` (both `bound` and `i` must
have the same type in this case). When `sized_sentinel_for<S, I>` holds and
`n < bound - i`, para 6.1.1 says that `ranges::advance(i, n, bound)` is equivalent
to `ranges::advance(i, bound)`. Para 3, however, establishes a precondition for
`ranges::advance(i, bound)` that `[i, bound)` denotes a range. `[bound, i)` and
`[i, bound)` cannot both denote ranges unless `i == bound`, which is not the case for
all calls that reach 6.1.1.

The call in para 6.1.1 wants the effects of either 4.1 - which really has no preconditions - or 4.2,
which is well-defined if either `[i, bound)` or `[bound, i)` denotes a range. Para 3's
stronger precondition is actually only required by Para 4.3, which increments `i` blindly
looking for `bound`. The straight-forward fix here seems to be to relax para 3's precondition
to only apply when 4.3 will be reached.

History | |||
---|---|---|---|

Date | User | Action | Args |

2019-11-04 13:23:43 | admin | set | messages: + msg10726 |

2019-10-27 06:54:18 | admin | set | messages: + msg10709 |

2019-10-27 00:00:00 | admin | create |