名稱空間
變體
操作

std::strided_slice

來自 cppreference.com
< cpp‎ | 容器‎ | mdspan
 
 
 
 
定義於標頭檔案 <mdspan>
template< class OffsetType, class ExtentType, class StrideType >
struct strided_slice;
(C++26 起)

strided_slice 的每個特化例項都是一個切片說明符,用於 std::submdspan,透過在 std::mdspan 的指定維度上使用一組等間距的索引來選擇元素的子集。

每個 strided_slice 物件 s 由三個資料成員定義:偏移索引 s.offset,範圍 s.extent 和步長 s.stride

給定 s.stride 大於零,如果 s.extent 非零,則由 N 表示的選定索引數由 1 + (s.extent - 1) / s.stride 確定,否則為 0。將選擇索引的半開區間由 [s.offsets.offset + s.extent) 給出。選定索引的序列如下生成: s.offset, ..., s.offset + (N - 1) * s.stride

除了下面所示的成員外,此類模板沒有基類或宣告的成員。

目錄

[編輯] 模板引數

OffsetType - 偏移的型別
ExtentType - 範圍的型別
StrideType - 步長的型別
型別要求
-
所有模板引數必須是無符號或有符號整數型別,或者必須滿足 integral-constant-like

如果型別要求未滿足,則程式格式錯誤。

[編輯] 成員型別

成員型別 定義
offset_type OffsetType
extent_type ExtentType
stride_type StrideType

[編輯] 資料成員

成員名稱 (Member name) 定義
offset
型別為 offset_type 的起始索引
(公有成員物件)
extent
型別為 extent_type 的值,新增到偏移量以定義索引的上限
(公有成員物件)
stride
型別為 stride_type 的增量值,等同於兩個索引之間的距離
(公有成員物件)

所有這些成員都使用 [[no_unique_address]] 屬性宣告,並具有預設成員初始化器,其中每個資料成員都進行值初始化。

[編輯] 注意

strided_slice 的每個特化都是一個聚合類,它允許對資料成員進行聚合初始化(包括指定初始化)(例如,std::strided_slice{.offset = 2, .extent = 10, .stride = 3})。

strided_slice 的切片規範利用了資料成員 extent,而不是使用 end 來指示上限值的其他切片規範。這是因為如果 extentstride 的型別都滿足 integral-constant-like,它可以直接為 std::mdspan 的子檢視生成靜態範圍。這使得透過將編譯時值與 offset 的執行時值混合來高效提取具有靜態範圍的子檢視成為可能。

[編輯] 示例

#include <mdspan>
#include <print>
 
template <typename View, typename O = int, typename E = int, typename S = int>
    requires (View::extents_type::rank() == 1)
void print_sliced_view(View v, std::strided_slice<O, E, S> s)
{
    using index_type = View::index_type;
    auto subview = std::submdspan(v, s);
    const auto& submap = subview.mapping();
 
    std::print("[");
    bool uses_comma = false;
    for (index_type i = 0; i != subview.extent(0); ++i)
    {
        if (uses_comma)
            std::print(", ");
        std::print("{}", subview[i]);
        uses_comma = true;
    }
    uses_comma = false;
    std::print("] extracted from indices [");
    for (index_type i = 0; i != subview.extent(0); ++i)
    {
        if (uses_comma)
            std::print(", ");
        std::print("{}", submap(i) + s.offset);
        uses_comma = true;
    }
    std::println("]");
}
 
int main()
{
    static constexpr char letters[]
    {
        'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'J',
        'K', 'L', 'M', 'N', 'O', 'P', 'Q', 'R', 'S', 'T',
        'U', 'V', 'W', 'X', 'Y', 'Z'
    };
    constexpr std::mdspan md(letters, 26);
    print_sliced_view(md, {.offset = 0, .extent = 10, .stride = 1});
    print_sliced_view(md, {.offset = 2, .extent = 10, .stride = 1});
    print_sliced_view(md, {.offset = 0, .extent = 5,  .stride = 1});
    print_sliced_view(md, {.offset = 2, .extent = 5,  .stride = 1});
    print_sliced_view(md, {.offset = 0, .extent = 10, .stride = 2});
    print_sliced_view(md, {.offset = 2, .extent = 10, .stride = 3});
    print_sliced_view(md, {.offset = 0, .extent = 15, .stride = 5});
    print_sliced_view(md, {.offset = 6, .extent = 15, .stride = 5});
}

輸出

[A, B, C, D, E, F, G, H, I, J] extracted from indices [0, 1, 2, 3, 4, 5, 6, 7, 8, 9]
[C, D, E, F, G, H, I, J, K, L] extracted from indices [2, 3, 4, 5, 6, 7, 8, 9, 10, 11]
[A, B, C, D, E] extracted from indices [0, 1, 2, 3, 4]
[C, D, E, F, G] extracted from indices [2, 3, 4, 5, 6]
[A, C, E, G, I] extracted from indices [0, 2, 4, 6, 8]
[C, F, I, L] extracted from indices [2, 5, 8, 11]
[A, F, K] extracted from indices [0, 5, 10]
[G, L, Q] extracted from indices [6, 11, 16]

[編輯] 參閱

valarray 的類 BLAS 切片:起始索引、長度、步長
(類) [編輯]
(C++26)
返回一個現有 mdspan 的子集檢視
(函式模板) [編輯]