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

履歴 編集

function template
<iterator>

std::ranges::distance(C++20)

namespace std::ranges {
  template<input_or_output_iterator I, sentinel_for<I> S>
  constexpr iter_difference_t<I> distance(I first, S last);   // (1)

  template<range R>
  constexpr range_difference_t<R> distance(R&& r);            // (2)
}

概要

イテレータ間あるいは範囲の距離を求める。

引数

  • first -- 距離を求めたい範囲の開始イテレータ
  • last -- 距離を求めたい範囲の終端イテレータ(あるいは番兵)
  • r -- 範囲を示すrangeオブジェクト

事前条件

  • (1) : 次のいずれか
    • [first, last)は有効な範囲である
    • [last, first)は有効な範囲であり、S, Isame_as<S, I>およびsized_sentinel_for<S, I>のモデルとなる

効果

  • (1) : 次のいずれかによって、firstからlastまでの距離を求める。
    • S, Isized_sentinel_for<S, I>のモデルとなる : return (last - first)
    • それ以外の場合 : firstからlastに到達するのに必要なインクリメントの回数を返す。
  • (2) : 次のいずれかによって、範囲の長さを求める。
    • Rsized_range<R>のモデルとなる : return static_cast<range_difference_t<R>>(ranges::size(r));
    • それ以外の場合 : return ranges::distance(ranges::begin(r),ranges::end(r)) ((1)に委譲)

戻り値

  • (1) : firstからlastまでの距離
  • (2) : rの範囲の長さ(先頭から終端までの距離)

備考

この関数テンプレートは通常の名前探索で発見されている場合にADLを無効化する。詳しくは「ADLを無効にする関数定義」を参照のこと。

#include <iostream>
#include <iterator>
#include <vector>
#include <forward_list>

int main() {
  std::vector<int> vec = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10};
  std::forward_list<int> fl = {1, 2, 3, 4, 5, 6, 7};

  auto it = std::begin(vec);

  // (1) イテレータ間距離を求める
  std::cout << std::ranges::distance(it, std::end(vec)) << std::endl;
  std::cout << std::ranges::distance(it, std::next(it, 5)) << std::endl;
  std::cout << std::ranges::distance(std::next(it, 5), it) << std::endl;

  // (2) rangeの長さを求める
  std::cout << std::ranges::distance(vec) << std::endl;
  std::cout << std::ranges::distance(fl) << std::endl;
}

出力

10
5
-5
10
7

バージョン

言語

  • C++20

処理系

関連項目

参照