Notatka
Dostęp do tej strony wymaga autoryzacji. Może spróbować zalogować się lub zmienić katalogi.
Dostęp do tej strony wymaga autoryzacji. Możesz spróbować zmienić katalogi.
std::identity (wprowadzony w języku C++20) jest obiektem funkcji, którego operator() zwraca argument bez zmian.
Uwaga / Notatka
Istnieje struktura Microsoft specyficzna dla identity z <utility>, która jest przestarzała i nie jest dostępna w nowszych wersjach Visual Studio. W przypadku języka C++20 i nowszych należy użyć elementu std::identity from <functional> , który jest zgodny ze standardami odpowiednik opisany poniżej.
std::identity (C++20)
Wiele standardowych interfejsów API biblioteki ma wywoływany argument, taki jak funkcja projekcji lub transformacji. Jeśli musisz przekazać wywołanie, ale nie chcesz zmieniać danych, przekaż polecenie std::identity. Jest to powszechne w algorytmach zakresów. Wiele <algorithm> przeciążeń zakresów ma parametr projekcji, który domyślnie ma wartość std::identity{}.
Składnia
struct identity
{
template <class T>
_NODISCARD constexpr T&& operator()(T&& t) const noexcept;
using is_transparent = int;
};
Uwagi
Typ is_transparent elementu członkowskiego to tag, który oznacza std::identity jako obiekt funkcji przezroczystej. Jego obecność wskazuje, że algorytmy mogą wykonywać porównania lub projekcje bez konieczności wcześniejszego konwertowania typów na typową formę. Jest to przydatne w przypadku kontenerów i algorytmów kojarzeniowych, które obsługują wyszukiwanie heterogeniczne, co pozwala na bezpośrednie porównywanie różnych typów bez konstruowania obiektów tymczasowych.
Examples
#include <algorithm>
#include <functional>
#include <iostream>
#include <ranges>
#include <vector>
int main()
{
std::vector<int> v{3, 1, 4, 1, 5, 9, 2, 6};
// Ranges algorithms can apply a projection before comparison.
// But if you don't want to apply a projection, i.e. you don't want to modify the data
// before comparison, you can use std::identity to leave each element unchanged.
// Here, std::identity{} means "project each element as itself".
// So the comparator sees the original int values unchanged.
std::ranges::sort(v, std::less{}, std::identity{});
// This call is equivalent because std::identity{} is the default projection.
// In both calls, elements are sorted directly; no field extraction or
// value transformation happens first.
std::ranges::sort(v);
for (int n : v)
{
std::cout << n << ' ';
}
std::cout << '\n';
// Output: 1 1 2 3 4 5 6 9
}
W tym przykładzie std::string_view wyszukiwany jest std::vector<std::string> klucz. Ponieważ std::identity ma element członkowski is_transparent , algorytm wie, aby porównać te typy bezpośrednio. W ten sposób klucz nie jest konwertowany na tymczasowy std::string , aby wykonać porównanie.
#include <algorithm>
#include <functional>
#include <iostream>
#include <ranges>
#include <string>
#include <string_view>
#include <vector>
int main()
{
std::vector<std::string> words{"apple", "banana", "cherry", "date"};
std::string_view key = "cherry";
// `std::less<>` is transparent, so it can compare `std::string` and
// `std::string_view` directly.
// `std::identity` is also marked transparent (`is_transparent`), so the
// projection stays type-flexible instead of forcing one fixed type.
auto it = std::ranges::lower_bound(words, key, std::less<>{}, std::identity{});
if (it != words.end() && *it == key)
{
std::cout << "Found: " << *it << '\n';
}
}