Udostępnij za pośrednictwem


subrange class (Standardowa biblioteka C++)

Udostępnia widok części elementów zakresu zgodnie z definicją iteratora rozpoczęcia i sentinel.

Składnia

template<input_or_output_iterator I, sentinel_for<I> S, subrange_kind K>
  requires (K == subrange_kind::sized || !sized_sentinel_for<S, I>)
class subrange : public view_interface<subrange<I, S, K>>

Parametry szablonu

I
Typ iteratora rozpoczęcia. Koncepcja input_or_output_iterator zapewnia iterator I , który może odczytywać wszystkie elementy.

K
Rodzaj podgrupy: służy subrange_kind::sized do określania podwojenia rozmiaru. Użyj sized_sentinel_for<S, I> , jeśli iterator i sentinel można odjąć, aby uzyskać rozmiar. Wymaganie subrange_kind::sized || !sized_sentinel_for<S, I> przechowuje rozmiar lokalnie w obiekcie podrzędnym i wymaga skonstruowania podloku przy użyciu konstruktora, który przyjmuje (dla którego określisz subrange_kind::sized tutaj) lub za pomocą konstruktora, który przyjmuje sized_range iteratorelement , sentineli size (więc należy określić sized_sentinel_for<S, I> tutaj).

S
Typ iteratora końcowego. Koncepcja sized_sentinel_for zapewnia, że S może być używana jako sentynel i I że można obliczyć odległość między elementy sentinel a bieżącą pozycją iteratora w I stałym czasie.

Właściwości widoku

Opis poniższych wpisów można znaleźć w temacie View class characteristics (Wyświetlanie właściwości klas)

Characteristic opis
Adapter zakresu views::counted
Zakres bazowy Dowolny zakres
Typ elementu iter_reference_t<I>
Wyświetl kategorię iteratora Tak samo jak Ikategoria s
Wielkości Jeśli K jest subrange::sized
Jest constiterowalne Jeśli I można skopiować
Wspólny zakres Jeśli I i S są tego samego typu.
Pożyczony zakres Tak

Elementy członkowskie

Funkcje składowe Opis
KonstruktoryC++20 Skonstruuj element subrange.
operator PairLikeC++20 subrange Przekonwertuj element na typ podobny do pary.
advanceC++20 Przenieś iterator na określoną odległość.
begin Pobierz iterator do pierwszego elementu.
emptyC++20 Sprawdź, czy element subrange jest pusty.
endC++20 Pobierz element sentinel na końcu obiektu subrange.
nextC++20 Tworzy kopię tego subrange obiektu, ale z zapisanym iteratorem przeniósł się do przodu określonej odległości.
prevC++20 Tworzy kopię tego subrange obiektu, ale z zapisanym iteratorem przeniósł się z powrotem określoną odległość.
sizeC++20 Pobierz liczbę elementów.
Dziedziczone z view_interface Opis
backC++20 Pobierz ostatni element.
dataC++20 Pobierz wskaźnik do pierwszego elementu.
frontC++20 Pobierz pierwszy element.
operator[]C++20 Pobierz element na określonej pozycji.
operator boolC++20 Sprawdź, czy element subrange jest pusty.

Uwagi

Element jest subrange przydatny w przypadku iteratora początku i końca, ale zamiast tego chcesz przekazać pojedynczy obiekt. Jeśli na przykład chcesz wywołać adapter zakresu, ale miał początek i zakończenie iteratorów, możesz użyć elementu , subrange aby je owinąć i przekazać subrange do adaptera zakresu.

Wymagania

Nagłówek: <ranges> (od C++20)

Przestrzeń nazw: std::ranges

Opcja kompilatora: /std:c++20 lub nowsza jest wymagana.

Konstruktory

Utwórz element subrange.

1) subrange() requires default_initializable<I> = default;
2) template <Convertible_to_non_slicing<I> It>
    constexpr subrange(It begin, S end) requires (!Store_size);
3) template <Convertible_to_non_slicing<I> It>
    constexpr subrange(It begin, S end, const Size_type size) requires (K == subrange_kind::sized);
4) template <Not_same_as<subrange> rg>
    requires borrowed_range<rg>
        && Convertible_to_non_slicing<iterator_t<rg>, I>
        && convertible_to<sentinel_t<rg>, S>
    constexpr subrange(rg&& r) requires (!_Store_size || sized_range<rg>);
5) template <borrowed_range rg>
        requires Convertible_to_non_slicing<iterator_t<rg>, I> && convertible_to<sentinel_t<rg>, S>
    constexpr subrange(rg&& r, const _Size_type sizeHint) requires (K == subrange_kind::sized)

Parametry

begin
Iterator wskazujący pierwszy element w podgrupie.

end
Sentinel, która wskazuje na koniec podwojenia. Element, do który wskazuje, nie jest uwzględniony w podgrupie.

sizeHint
Rozmiar zakresu w elementach. Jest to używane do optymalizacji funkcji składowej size i jest konieczne, jeśli chcesz utworzyć rozmiar subrange z iteratora i sentinel, którego typy nie modelują sized_sentinel_for.

Aby uzyskać informacje o typach parametrów szablonu, zobacz Parametry szablonu.

Wartość zwracana

subrangeWystąpienie.

Uwagi

1) Domyślna konstrukcja przechowywanego iteratora i sentinel. Wskazówka rozmiaru jest ustawiona na 0.
2) Używa std::move() metody , aby przenieść begin iterator i end sentinel do przechowywanego iteratora i sentynela.
3) Inicjuje przechowywany iterator za pomocą std::move(begin), przechowywanego sentynel z elementem std::move(end)i wskazówkę rozmiaru przechowywanego z wartością size, która powinna być równa odległości między pierwszym i drugim argumentem.
4) Konstruowanie elementu subrange z zakresu.
5) Zachowanie nie jest zdefiniowane, jeśli szHint != ranges::distance(rg).

Adapter counted zakresu może utworzyć subrangeelement . Ten adapter przyjmuje iterator rozpoczęcia i liczbę.

Przykład: counted

// requires /std:c++20 or later
#include <ranges>
#include <iostream>
#include <vector>

int main()
{
    std::vector<int> v{0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10};
    auto pos5 = std::ranges::find(v, 5);
    auto countedView = std::views::counted(pos5, 5);
    for (auto e : countedView) // outputs 5 6 7 8 9
    {
        std::cout << e << ' ';
    }
    std::cout << '\n';

    // You can pass the range directly if it supports input_or_output_iterator, in which case, the
    // count starts from the first element
    const char chars[] = { 'H','i',' ','t','h','e','r','e' };
    for (char c : std::views::counted(chars, 2))
    {
        std::cout << c; // outputs Hi
    }
}
5 6 7 8 9
Hi

operator PairLike

Przekonwertuj element subrange na typ, który modeluje pair-like.

template<not-same-as<subrange> PairLike>
requires pair-like-convertible-from<PairLike, const I&, const S&>
constexpr operator PairLike() const;

Parametry

Brak.

Aby uzyskać informacje o typach parametrów szablonu, zobacz Parametry szablonu.

Wartość zwracana

PairLike Wartość, która jest inicjowana bezpośrednio z przechowywanym iteratorem i sentinel. Ostatnią wartością w parze będzie sentinel.

Pamiętaj, że element sentinel jest przeszłością ostatniego elementu w podrange, jak pokazano w poniższym przykładzie.

Uwagi

Ta konwersja jest przydatna w przypadku starszego Boost::Ranges kodu, który akceptuje pary (pierwsze, ostatnie) w celu określenia zakresu.
Ta konwersja jest przydatna do konwertowania podgrupy na pair typ lub tuple lub inny, który modeluje pair_like. Oto kilka przykładów pair_like typów:

std::array<T, 2>
std::pair<T, U>
std::ranges::subrange<I, S, K>
std::tuple<T, U>

Przykład: operator PairLike()

// requires /std:c++20 or later
#include <iostream>
#include <ranges>
#include <vector>
#include <utility>

int main()
{
    constexpr int a[] = {0, 1, 2, 3, 4, 5};
    std::ranges::subrange rg(a);
    rg.advance(2);
    const std::pair<const int*, const int*> p = rg;
    for (auto e : rg)
    {
        std::cout << e << ' ';
    }

    // because the sentinel points after the last element, subtract one to get the last element
    std::cout << '\n' << *p.first << ':' << *(p.second - 1) << '\n'; // outputs 2:5
 }
2 3 4 5
2:5

advance

Dostosuj iterator dla tego subrange elementu według n elementów.

constexpr subrange& advance(const iter_difference_t<I> n);

Parametry

n
Ile elementów należy dostosować iterator. n może być dodatni (ruch do przodu) lub, jeśli I jest dwukierunkowy, ujemny (przesuń do tyłu).

Uwagi

Ta funkcja modyfikuje bieżący stan iteratora w elemencie subrange.

Jeśli przechodzisz obok końca subrange, iterator jest ustawiony na sentinel na końcu subrange.
Jeśli przejdziesz obok początku subrange elementu (przy użyciu wartości ujemnej n), otrzymasz nieprawidłowy wyjątek parametru, jeśli zakres, z którego utworzono subrange , nie ma elementu w miejscu.

Przykład: advance

// requires /std:c++20 or later
#include <iostream>
#include <ranges>
#include <string>
#include <vector>

void print(const std::string &msg, auto &&v)
{
    std::cout << msg << '\n';
    for (auto& x : v)
    {
        std::cout << x << ' ';
    }
    std::cout << '\n';
}

int main()
{
    std::vector v = { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10 };
    print("Original vector: ", v); // outputs 0 1 2 3 4 5 6 7 8 9 10

    // create a subrange 3 4 5 6
    std::ranges::subrange theSubrange{ std::ranges::find(v,3), std::ranges::find(v, 7) };
    print("The subrange: ", theSubrange); // outputs 3 4 5 6

    auto sr = theSubrange.advance(2); // get a subrange 2 positions to the right of the current iterator location
    print("theSubrange.advance(2): ", sr); // outputs 5 6
    print("Note that subrange's iterator moved during advance(): ", sr); // outputs 5 6
    sr = theSubrange.advance(-3); // Moving before the subrange, but onto a valid element in the original range 
    print("theSubrange.advance(-3): ", sr); // outputs 2 3 4 5 6
}
Original vector:
0 1 2 3 4 5 6 7 8 9 10
The subrange:
3 4 5 6
theSubrange.advance(2):
5 6
Note that subrange's iterator moved during advance():
5 6
theSubrange.advance(-3):
2 3 4 5 6

begin

Pobierz iterator do pierwszego elementu w pliku subrange.

1) constexpr I begin() const requires copyable<I>;
2) [[nodiscard]] constexpr I begin() requires (!std::copyable<I>);

Parametry

Brak.

Wartość zwracana

Iterator wskazujący pierwszy element w elemecie subrange. Jeśli iterator nie jest kopiowalny, jest zwracany za pomocą polecenia std::move(). Jeśli iterator zostanie przeniesiony, stan przechowywanego iteratora zależy od implementacji konstruktora przenoszenia dla elementu I.

Obraz wektora z elementami 10, 20 i 30. Pierwszy element zawiera wartość 10 i ma etykietę begin(). Ostatni element zawiera wartość 30 i ma etykietę

empty

Sprawdź, czy element subrange jest pusty.

constexpr bool empty() const;

Parametry

Brak.

Wartość zwracana

Zwraca wartość true , jeśli subrange element nie zawiera żadnych elementów. W przeciwnym razie zwraca wartość false.

end

Pobierz sentinel na końcu subrange

[[nodiscard]] constexpr S end() const;

Parametry

Brak.

Wartość zwracana

Sentinel, który jest zgodny z ostatnim elementem w pliku subrange:

Obraz wektora z elementami 10, 20 i 30. Pierwszy element zawiera wartość 10 i ma etykietę begin(). Ostatni element zawiera wartość 30 i ma etykietę

Sentinel jest skonstruowany z magazynu sentinel.

next

Tworzy kopię tego subrange obiektu, ale z zapisanym iteratorem przeniósł się do przodu określonej odległości.

1) [[nodiscard]] constexpr subrange next(iter_difference_t<I> n = 1) const & requires forward_iterator<I>;
2) [[nodiscard]] constexpr subrange next(iter_difference_t<I> n = 1) &&;

Parametry

n
Ile elementów ma przenieść iterator do przodu. Wartość domyślna to 1. Musi być dodatnia.

Wartość zwracana

Zwraca kopię elementu rozpoczynającego subrange się od *n*th.

Uwagi

W przeciwieństwie do advance()elementu nie next() zmienia lokalizacji iteratora przechowywanego w oryginalnym subrangeobiekcie . Zwrócony subrange element zawiera wszystkie elementy, które ma oryginalny podrange, ale iterator znajduje się w innej lokalizacji.

1) Wartość zwracana jest taka sama jak:

auto tmp = *this;
tmp.advance(n);
return tmp;

2) Wartość zwracana jest taka sama jak:

advance(n);
return std::move(*this);

Przykład: next

// requires /std:c++20 or later
#include <iostream>
#include <ranges>
#include <string>
#include <vector>

void print(const std::string &msg, auto &&v)
{
    std::cout << msg << '\n';
    for (auto& x : v)
    {
        std::cout << x << ' ';
    }
    std::cout << '\n';
}

int main()
{
    std::vector v = { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10 };
    print("Original vector:", v); // 0 1 2 3 4 5 6 7 8 9 10

    // create a subrange from the front of v up to (but not including) the element 7
    std::ranges::subrange theSubrange{ std::ranges::find(v,1), std::ranges::find(v, 7) };
    print("The subrange:", theSubrange); // 1 2 3 4 5 6

    auto forward = theSubrange.advance(3); // get a subrange 3 positions to the right of the current iterator location
    print("theSubrange.advance(3):", forward); // 4 5 6

    // prev()
    auto previous = theSubrange.prev(2); // move back 2
    print("theSubrange.prev(2):", previous); // 2 3 4 5 6    
    print("Note that the subrange's iterator did *not* move during prev():", theSubrange); // 4 5 6
}
Original vector:
0 1 2 3 4 5 6 7 8 9 10
The subrange:
1 2 3 4 5 6
theSubrange.next(3):
4 5 6
Note that the original subrange's iterator did *not* move during next():
1 2 3 4 5 6

prev

Tworzy kopię tego subrangeobiektu , ale z zapisanym iteratorem przeniósł się z powrotem określoną odległość.

[[nodiscard]] constexpr subrange prev(std::iter_difference_t<I> n = 1 ) const
    requires std::bidirectional_iterator<I>;

Parametry

n
Ile elementów ma przenieść iterator z powrotem. Wartość domyślna to 1. Musi być dodatnia.

Wartość zwracana

Zwraca kopię subrange elementu , ale z iteratorem przeniesiono elementy wstecz n .

Uwagi

W przeciwieństwie do advance()elementu nie prev() zmienia lokalizacji iteratora przechowywanego w oryginalnym subrangeobiekcie .
Zwrócony subrange element zawiera wszystkie elementy, które ma oryginalny podrange, ale iterator znajduje się tylko w innej lokalizacji. Wartość zwracaną można traktować jako:

auto tmp = *this;
tmp.advance(-n);
return tmp;

Przykład: prev

// requires /std:c++20 or later
#include <iostream>
#include <ranges>
#include <string>
#include <vector>

void print(const std::string &msg, auto &&v)
{
    std::cout << msg << '\n';
    for (auto& x : v)
    {
        std::cout << x << ' ';
    }
    std::cout << '\n';
}

int main()
{
    std::vector v = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10};
    print("Original vector:", v); // 0 1 2 3 4 5 6 7 8 9 10

    // create a subrange from the front of v up to (but not including) the element 7
    std::ranges::subrange theSubrange{std::ranges::find(v,1), std::ranges::find(v, 7)};
    print("The subrange: ", theSubrange); // 1 2 3 4 5 6

    auto forward = theSubrange.advance(3); // get a subrange 3 positions to the right of the current iterator location
    print("theSubrange.advance(3):", forward); // 4 5 6

    // prev()
    auto previous = theSubrange.prev(2); // move back 2
    print("theSubrange.prev(2):", previous); // 2 3 4 5 6    
    print("Note that the subrange's iterator did *not* move during prev():", theSubrange); // 4 5 6
}
Original vector:
0 1 2 3 4 5 6 7 8 9 10
The subrange:
1 2 3 4 5 6
theSubrange.advance(3):
4 5 6
theSubrange.prev(2):
2 3 4 5 6
Note that the subrange's iterator did *not* move during prev():
4 5 6

size

Pobierz liczbę elementów w elemecie subrange.

constexpr size() const
    requires (K == ranges::subrange_kind::sized);

Parametry

Brak.

Wartość zwracana

Liczba elementów w elem.subrange

Jeśli rozmiar nie jest przechowywany, czyli w przypadku subrange utworzenia obiektu z K == ranges::subrange_kind::sized określonym i std::sized_sentinel_for<S, I> nie jest spełniony, rozmiar jest zwracany jako odległość między iteratorami początkowymi i końcowymi.

Zmiana położenia iteratora begin advance, na przykład zmienia rozmiar zgłoszonego rozmiaru.

Zobacz też

<ranges>
counted
Klasy widoków