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

### 3597. Unsigned integer types don't model `advanceable`

Section: 26.6.4.2 [range.iota.view] Status: WP Submitter: Jiang An Opened: 2021-09-23 Last modified: 2022-11-17

Priority: 3

View all other issues in [range.iota.view].

View all issues with WP status.

Discussion:

Unsigned integer types satisfy `advanceable`, but don't model it, since

> every two values of an unsigned integer type are reachable from each other, and modular arithmetic is performed on unsigned integer types,

which makes the last three bullets of the semantic requirements of `advanceable` (26.6.4.2 [range.iota.view]/5) can't be satisfied, and some (if not all) uses of `iota_view`s of unsigned integer types ill-formed, no diagnostic required.

Some operations that are likely to expect the semantic requirements of `advanceable` behave incorrectly for unsigned integer types. E.g. according to 26.6.4.2 [range.iota.view]/6 and 26.6.4.2 [range.iota.view]/16, `std::ranges::iota_view<std::uint8_t, std::uint8_t>(std::uint8_t(1)).size()` is well-defined IMO, because

> `Bound()` is `std::uint8_t(0)`, which is reachable from `std::uint8_t(1)`, and not modeling `advanceable` shouldn't affect the validity, as both `W` and `Bound` are integer types.

However, it returns `unsigned(-1)` on common implementations (where `sizeof(int) > sizeof(std::uint8_t))`, which is wrong.

Perhaps the semantic requirements of `advanceable` should be adjusted, and a refined definition of reachability in 26.6.4 [range.iota] is needed to avoid reaching `a` from `b` when `a > b` (the iterator type is also affected).

[2021-10-14; Reflector poll]

Set priority to 3 after reflector poll.

[Tim Song commented:]

The advanceable part of the issue is NAD. This is no different from NaN and `totally_ordered`, see 16.3.2.3 [structure.requirements]/8.

The part about `iota_view<uint8_t, uint8_t>(1)` is simply this: when we added "When `W` and `Bound` model ..." to 26.6.4.2 [range.iota.view]/8, we forgot to add its equivalent to the single-argument constructor. We should do that.

[2022-10-12; Jonathan provides wording]

[2022-10-19; Reflector poll]

Set status to "Tentatively Ready" after seven votes in favour in reflector poll.

[2022-11-12 Approved at November 2022 meeting in Kona. Status changed: Voting → WP.]

Proposed resolution:

This wording is relative to N4917.

1. Modify 26.6.4.2 [range.iota.view] as indicated:

   >     constexpr explicit iota_view(W value);

   > > -6- Preconditions: `Bound` denotes `unreachable_sentinel_t` or `Bound()` is reachable from `value`. When `W` and `Bound` model `totally_ordered_with`, then `bool(value <= Bound())` is `true`.

   > > -7- Effects: Initializes `value_` with `value`.

   >     constexpr iota_view(type_identity_t<W> value, type_identity_t<Bound> bound);

   > > -8- Preconditions: `Bound` denotes `unreachable_sentinel_t` or `bound` is reachable from `value`. When `W` and `Bound` model `totally_ordered_with`, then `bool(value <= bound)` is `true`.

   > > -9- Effects: Initializes `value_` with `value` and `bound_` with `bound`.