A RetroSearch Logo

Home - News ( United States | United Kingdom | Italy | Germany ) - Football scores

Search Query:

Showing content from https://cplusplus.github.io/LWG/issue4059 below:

Leaky abstraction in join_with_view's iterator

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.

4059. Leaky abstraction in join_with_view's iterator

Section: 25.7.15.3 [range.join.with.iterator] Status: New Submitter: S. B. Tam Opened: 2024-03-23 Last modified: 2024-08-11

Priority: 3

View other active issues in [range.join.with.iterator].

View all other issues in [range.join.with.iterator].

View all issues with New status.

Discussion:

join_with_view's iterator is defined in terms of variant, visit and get, which implies that the iterator operations throw bad_variant_access if the underlying variant is valueless-by-exception (which can happen if an underlying iterator has a throwing copy constructor).

IMO, the variant is an implementation detail and shouldn't be exposed. It's confusing for users to get bad_variant_access when user code does not deal with variant. The spec of join_with_view is also inconsistent with concat_view as recently added to the working draft by P2542R8. The latter has "it_.valueless_by_exception() is false" as a precondition. I believe that join_with_view should similarly require that inner_it_.valueless_by_exception() is false for each iterator operation. (FWIW, MSVC STL implements join_with_view with a trimmed-down version of variant, and having to throw bad_variant_access causes a small maintenance burden.)

[2024-06-24; Reflector poll]

Set priority to 3 after reflector poll. We like the suggestion to require "not valueless" as a precondition.

[2024-08-08, Inbal Levi provides wording]

Proposed resolution:

This wording is relative to N4988.

  1. Modify 25.7.15.3 [range.join.with.iterator] as indicated:

    constexpr iterator(iterator<!Const> i)
        requires Const && convertible_to<iterator_t<V>, OuterIter> &&
                 convertible_to<iterator_t<InnerRng>, InnerIter> &&
                 convertible_to<iterator_t<Pattern>, PatternIter>;
    

    -?- Preconditions: inner_it_.valueless_by_exception() is false.

    -10- Effects: […]
    constexpr decltype(auto) operator*() const;
    

    -?- Preconditions: inner_it_.valueless_by_exception() is false.

    -12- Effects: Equivalent to: […]
    constexpr iterator& operator++();
    

    -?- Preconditions: inner_it_.valueless_by_exception() is false.

    -13- Effects: Equivalent to: […]
    constexpr void operator++(int);
    

    -?- Preconditions: inner_it_.valueless_by_exception() is false.

    -14- Effects: Equivalent to: ++*this.
    constexpr iterator operator++(int)
      requires ref-is-glvalue && forward_iterator<OuterIter> && forward_iterator<InnerIter>;
    

    -?- Preconditions: inner_it_.valueless_by_exception() is false.

    -15- Effects: Equivalent to: […]
    constexpr iterator& operator--()
      requires ref-is-glvalue && bidirectional_range<Base> &&
               bidirectional-common<InnerBase> && bidirectional-common<PatternBase>;
    

    -?- Preconditions: inner_it_.valueless_by_exception() is false.

    -16- Effects: Equivalent to: […]

RetroSearch is an open source project built by @garambo | Open a GitHub Issue

Search and Browse the WWW like it's 1997 | Search results from DuckDuckGo

HTML: 3.2 | Encoding: UTF-8 | Version: 0.7.4