std::ranges::size
定義於標頭檔案 <ranges> |
||
定義於標頭檔案 <iterator> |
||
inline namespace /* 未指定 */ { inline constexpr auto size = /* 未指定 */; |
(C++20 起) (定製點物件) |
|
呼叫簽名 (Call signature) |
||
template< class T > requires /* 見下文 */ |
(C++20 起) | |
以常數時間計算 t 中的元素數量。
給定 t 表示其(可能 具體化)結果物件的 子表示式 為 E,以及 E 的型別為 T
- 如果
T
是未知邊界的陣列,則 ranges::size(E) 格式錯誤。 - 否則,如果
T
是陣列型別,則 ranges::size(E) 表示式等價 於 decay-copy (std::extent_v<T>)(C++23 前)auto(std::extent_v<T>)(C++23 起)。 - 否則,如果滿足以下所有條件,則 ranges::size(E) 表示式等價於 decay-copy (t.size())(C++23 前)auto(t.size())(C++23 起)
- ranges::disable_sized_range<std::remove_cv_t<T>> 為 false。
- decay-copy (t.size())(C++23 前)auto(t.size())(C++23 起) 是 整數型別 的有效表示式。
- 否則,如果滿足以下所有條件,則 ranges::size(E) 表示式等價於 decay-copy (size(t))(C++23 前)auto(size(t))(C++23 起)
-
T
是類或列舉型別。 - ranges::disable_sized_range<std::remove_cv_t<T>> 為 false。
- decay-copy (size(t))(C++23 前)auto(size(t))(C++23 起) 是整數型別的有效表示式,其中
size
的含義如同僅透過執行實參依賴查詢來確定。
-
- 否則,如果滿足以下所有條件,則 ranges::size(E) 表示式等價於
to-unsigned-like
(ranges::end(t) - ranges::begin(t))-
T
滿足forward_range
。 - 給定 ranges::begin(t) 的型別為
I
,ranges::end(t) 的型別為S
,則sized_sentinel_for
<S, I> 和forward_iterator
<I> 都被滿足。 -
to-unsigned-like
(ranges::end(t) - ranges::begin(t)) 是一個有效表示式。
-
- 否則,ranges::size(E) 格式錯誤。
上述可診斷的格式錯誤情況,當 ranges::size(E) 出現在模板例項化的直接語境中時,會導致 替換失敗。
目錄 |
自定義點物件
名稱 ranges::size
表示一個定製點物件,它是一個 const 函式物件,型別為 字面量 semiregular
類。為便於說明,其 cv-unqualified 版本型別表示為 __size_fn
。
__size_fn
的所有例項均相等。對同一引數呼叫型別為 __size_fn
的不同例項的效果是等價的,無論表示例項的表示式是左值還是右值,以及是否具有 const 限定(但是,volatile 限定的例項不要求可呼叫)。因此,ranges::size
可以自由複製,其副本可以互換使用。
給定一組型別 Args...
,如果 std::declval<Args>()... 滿足上述 ranges::size
引數的要求,則 __size_fn
滿足
- std::invocable<__size_fn, Args...>,
- std::invocable<const __size_fn, Args...>,
- std::invocable<__size_fn&, Args...>,以及
- std::invocable<const __size_fn&, Args...>.
否則,__size_fn
的任何函式呼叫運算子不參與過載決議。
[編輯] 注意
當表示式 e 的 ranges::size(e) 有效時,返回型別是 整數型別。
C++20 標準要求,如果底層 size
函式呼叫返回一個純右值,則返回值將從具體化的臨時物件移動構造。所有實現都直接返回純右值。C++20 後提案 P0849R8 糾正了此要求以匹配實現。
ranges::distance(e) 表示式也可用於確定範圍 e 的大小。與 ranges::size(e) 不同,即使 e 是無大小的範圍,ranges::distance(e) 也能工作,代價是在這種情況下具有線性複雜度。
[編輯] 示例
#include <iostream> #include <ranges> #include <type_traits> #include <vector> int main() { auto v = std::vector<int>{}; std::cout << "ranges::size(v) == " << std::ranges::size(v) << '\n'; auto il = {7}; // std::initializer_list std::cout << "ranges::size(il) == " << std::ranges::size(il) << '\n'; int array[]{4, 5}; // array has a known bound std::cout << "ranges::size(array) == " << std::ranges::size(array) << '\n'; static_assert(std::is_signed_v<decltype(std::ranges::size(v))> == false); }
輸出
ranges::size(v) == 0 ranges::size(il) == 1 ranges::size(array) == 2
[編輯] 缺陷報告
下列更改行為的缺陷報告追溯地應用於以前出版的 C++ 標準。
缺陷報告 | 應用於 | 釋出時的行為 | 正確的行為 |
---|---|---|---|
P2602R2 | C++20 | 有機制禁止透過 ADL 找到某些非成員 size |
刪除了此類機制 |
[編輯] 參閱
(C++20) |
返回等於範圍大小的有符號整數 (定製點物件) |
(C++20) |
指定範圍在常數時間內知道其大小 (概念) |
(C++20) |
返回迭代器與哨兵之間,或範圍開頭與結尾之間的距離 (演算法函式物件) |
(C++17)(C++20) |
返回容器或陣列的大小 (函式模板) |