std::ranges::search
Definido en el archivo de encabezado <algorithm> | ||
Signatura de la llamada | ||
template<std::forward_iterator I1, std::sentinel_for<I1> S1, std::forward_iterator I2, std::sentinel_for<I2> S2, | (1) | (desde C++20) |
template<ranges::forward_range R1, ranges::forward_range R2, class Pred =ranges::equal_to, | (2) | (desde C++20) |
[first2, last2)
en el rango [first1, last1)
. Los elementos se comparan usando el predicado binario pred
después de proyectarse con proj2
y proj1
, respectivamente.r1
como el primer rango fuente y r2
como el segundo rango fuente, como si usara ranges::begin(r1) como first1
, ranges::end(r1) como last1
, ranges::begin(r2) como first2
, y ranges::end(r2) como last2
.Las entidades similares a funciones descritas en esta página son niebloids, es decir:
- Las listas de argumentos de plantilla explícitas no se pueden especificar al llamar a cualquiera de ellas.
- Ninguna de ellas es visible para la búsqueda dependiente de argumentos.
- Cuando alguna de ellas se encuentra mediante la búsqueda normal no calificada como el nombre a la izquierda del operador de llamada a función, se inhibe la búsqueda dependiente de argumentos.
En la práctica, pueden implementarse como objetos función o con extensiones de compilador especiales.
Contenido |
[editar]Parámetros
first1, last1 | - | El rango de elementos a examinar (alias pajar). |
first2, last2 | - | El rango de la secuencia de elementos a buscar (alias aguja). |
r1 | - | El rango de elementos a examinar (alias pajar). |
r2 | - | El rango de la secuencia de elementos a buscar (alias aguja). |
pred | - | El predicado binario a aplicar a los elementos proyectados. |
proj1 | - | Proyección a aplicar a los elementos en el primer rango. |
proj2 | - | Proyección a aplicar a los elementos en el segundo rango. |
[editar]Valor de retorno
[first2, last2)
(alias aguja) en el rango [first1, last1)
(alias pajar), después de la aplicación de las proyecciones proj1
y proj2
a los elementos de ambas secuencias, respectivamente con la consiguiente aplicación del predicado binario pred
para comparar los elementos proyectados. Si no se encuentra tal ocurrencia, se devuelve ranges::subrange{last1, last1}.
Si el rango a buscar (alias aguja) está vacío, es decir first2 == last2, entonces se devuelve ranges::subrange{first1, first1}.[editar]Complejidad
A lo sumo S*N
aplicaciones del predicado correspondiente y cada proyección, donde
(1)S =ranges::distance(first2, last2) y N =ranges::distance(first1, last1);
(2)S =ranges::distance(r2) y N =ranges::distance(r1).
[editar]Posible implementación
struct search_fn {template<std::forward_iterator I1, std::sentinel_for<I1> S1, std::forward_iterator I2, std::sentinel_for<I2> S2, class Pred =ranges::equal_to, class Proj1 =std::identity, class Proj2 =std::identity> requires std::indirectly_comparable<I1, I2, Pred, Proj1, Proj2>constexprranges::subrange<I1> operator()(I1 first1, S1 last1, I2 first2, S2 last2, Pred pred ={}, Proj1 proj1 ={}, Proj2 proj2 ={})const{for(;;++first1){ I1 it1 = first1;for(I2 it2 = first2;;++it1, ++it2){if(it2 == last2)return{first1, it1};if(it1 == last1)return{it1, it1};if(!std::invoke(pred, std::invoke(proj1, *it1), std::invoke(proj2, *it2)))break;}}} template<ranges::forward_range R1, ranges::forward_range R2, class Pred =ranges::equal_to, class Proj1 =std::identity, class Proj2 =std::identity> requires std::indirectly_comparable<ranges::iterator_t<R1>, ranges::iterator_t<R2>, Pred, Proj1, Proj2>constexprranges::borrowed_subrange_t<R1> operator()(R1&& r1, R2&& r2, Pred pred ={}, Proj1 proj1 ={}, Proj2 proj2 ={})const{return(*this)(ranges::begin(r1), ranges::end(r1), ranges::begin(r2), ranges::end(r2), std::move(pred), std::move(proj1), std::move(proj2));}}; inlineconstexpr search_fn search{}; |
[editar]Ejemplo
#include <algorithm>#include <cctype>#include <iostream>#include <iterator>#include <string_view> usingnamespace std::literals; void imprimir(int id, constauto& pajar, constauto& aguja, constauto& encontrado){std::cout<< id <<"). search(\""<< pajar <<"\", \""<< aguja <<"\"); ";constauto first =std::distance(pajar.begin(), encontrado.begin());constauto last =std::distance(pajar.begin(), encontrado.end());if(encontrado.empty()){std::cout<<"no se encontró;";}else{std::cout<<"se encontró: \"";for(constauto x: encontrado){std::cout<< x;}std::cout<<"\";";}std::cout<<" subrango: {"<< first <<", "<< last <<"}\n";} int main(){constexprauto pajar {"abcd abcd"sv};constexprauto aguja {"bcd"sv}; // la búsqueda usa el par de iteradores begin()/end():constexprauto encontrado1 = std::ranges::search( pajar.begin(), pajar.end(), aguja.begin(), aguja.end()); imprimir(1, pajar, aguja, encontrado1); // la búsqueda usa los rangos r1, r2:constexprauto encontrado2 = std::ranges::search(pajar, aguja); imprimir(2, pajar, aguja, encontrado2); // el rango 'aguja' está vacío:constexprauto nada {""sv};constexprauto encontrado3 = std::ranges::search(pajar, nada); imprimir(3, pajar, nada, encontrado3); // 'aguja' no se encontrará:constexprauto punzon1 {"efg"sv};constexprauto encontrado4 = std::ranges::search(pajar, punzon1); imprimir(4, pajar, punzon1, encontrado4); // la búsqueda usa el comparador personalizado y proyecciones:constexprauto punzon2 {"234"sv};auto encontrado5 = std::ranges::search(pajar, punzon2, [](constint x, constint y){return x == y;}, // pred[](constint x){returnstd::toupper(x);}, // proj1[](constint y){return y +'A'-'1';}// proj2); imprimir(5, pajar, punzon2, encontrado5);}
Salida:
1). search("abcd abcd", "bcd"); se encontró: "bcd"; subrango: {1, 4} 2). search("abcd abcd", "bcd"); se encontró: "bcd"; subrango: {1, 4} 3). search("abcd abcd", ""); no se encontró; subrango: {0, 0} 4). search("abcd abcd", "efg"); no se encontró; subrango: {9, 9} 5). search("abcd abcd", "234"); se encontró: "bcd"; subrango: {1, 4}
[editar]Véase también
(C++20) | Encuentra dos primeros elementos contiguos idénticos (o que satisfagan un predicado dado). (niebloid) |
(C++20)(C++20)(C++20) | Encuentra el primer elemento que satisfaga un criterio específico. (niebloid) |
(C++20) | Encuentra la última secuencia de elementos en un cierto rango. (niebloid) |
(C++20) | Busca por cualquiera de un conjunto de elementos. (niebloid) |
(C++23)(C++23) | Comprueba si el rango contiene el elemento dado o un subrango. (niebloid) |
(C++20) | Devuelve true si una secuencia es una subsecuencia de otra. (niebloid) |
(C++20) | Encuentra la primera posición donde dos rangos difieren. (niebloid) |
(C++20) | Busca un número de copias consecutivas de un elemento en un rango. (niebloid) |
Busca una subsecuencia de elementos. (plantilla de función) |