• Class / Function / Type

      std::
    • Header file

      <>
    • Other / All

    最終更新日時(UTC):
    が更新

    履歴 編集

    function
    <ranges>

    std::ranges::subrange::コンストラクタ

    // (1)
    subrange() = default;
    
    // (2)
    constexpr subrange(convertible-to-non-slicing<I> auto i, S s) requires (!StoreSize);
    
    // (3)
    constexpr subrange(convertible-to-non-slicing<I> auto i, S s, make-unsigned-like-t<iter_difference_t<I>> n)
      requires (K == subrange_kind::sized);
    
    // (4)
    template<different-from<subrange> R>
      requires borrowed_range<R> && convertible-to-non-slicing<iterator_t<R>, I> && convertible_to<sentinel_t<R>, S>
    constexpr subrange(R&& r) requires (!StoreSize || sized_range<R>);
    
    // (5)
    template<borrowed_range R>
      requires convertible-to-non-slicing<iterator_t<R>, I> && convertible_to<sentinel_t<R>, S>
    constexpr subrange(R&& r, make-unsigned-like-t<iter_difference_t<I>> n)
      requires (K == subrange_kind::sized) : subrange{ranges::begin(r), ranges::end(r), n} {}
    

    概要

    • (1) : 空のsubrangeを構築する(デフォルトコンストラクタ)
    • (2) : イテレータiと番兵sが表すイテレータ範囲[i, s)で初期化する
    • (3) : イテレータiと番兵sが表すイテレータ範囲[i, s)で初期化し、subrangeの長さをnにする
    • (4) : 範囲 r で初期化する
    • (5) : 範囲 r で初期化し、subrangeの長さをnにする ((3)へ委譲)

    テンプレートパラメータ制約

    StoreSizeは次のように定義される説明専用メンバである。

    static constexpr bool StoreSize = (K == subrange_kind::sized && !sized_sentinel_for<S, I>);
    

    StoreSizeは、元のRangeから長さを求められないが、長さを別に指定することでsubrangesized_rangeにした場合に真となる。

    • (1): Iデフォルト構築可能であること
    • (2), (4): subrangesizedではない。または、元のRangeから長さを求められる
    • (3), (5): subrangesizedであり、元のRangeから長さを求められない
    • (4): 範囲は構築するsubrangeと同じ型ではない (つまり、(4)はムーブコンストラクタではない)

    事前条件

    • (2): [i, s)は有効なイテレータ範囲であること
    • (3): [i, s)は有効なイテレータ範囲であり、nはその範囲の長さ(ranges::distance(i, s))と等しいこと
    • (4): rは有効な範囲であること
    • (5): rは有効な範囲であり、nはその範囲の長さと等しいこと

    効果

    subrangeが内部で保持するイテレータと番兵を与えられた範囲で初期化する。 さらに、StoreSizeが真のときは大きさを与えられた値で初期化する。

    備考

    subrangeはコピー、ムーブ可能である。また、テンプレート引数が異なるsubrangeからは、(4)によって構築できる。

    #include <cassert>
    #include <ranges>
    #include <forward_list>
    #include <array>
    
    int main()
    {
      constexpr std::ranges::subrange<int*, int*, std::ranges::subrange_kind::sized> sub1;
      static_assert(sub1.empty());
    
      constexpr std::array arr= {1, 2, 3};
      const std::ranges::subrange sub2(arr.begin(), arr.begin() + 1);
      assert(sub2.size() == 1);
    
      const std::forward_list fwl = {1, 2, 3};
      const std::ranges::subrange sub3(fwl.begin(), ++fwl.begin(), 1);
      // forward_listはsized_rangeではないが、長さを指定しているのでsubrangesized_rangeとなり、sizeメンバ関数が定義される
      static_assert(std::ranges::sized_range<decltype(sub3)>);
      assert(sub3.size() == 1);
    
      const std::ranges::subrange sub4 = arr;
      assert(sub4.size() == 3);
    
      const std::ranges::subrange sub5(fwl, 3);
      // forward_listはsized_rangeではないが、長さを指定しているのでsubrangesized_rangeとなり、sizeメンバ関数が定義される
      static_assert(std::ranges::sized_range<decltype(sub5)>);
      assert(sub4.size() == 3);
    }
    

    出力

    バージョン

    言語

    • C++20

    処理系

    参照