std::ranges::equal
| Definido en la cabecera <algorithm>
|
||
| Firma de llamada |
||
template< std::input_iterator I1, std::sentinel_for<I1> S1,
std::input_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>
constexpr bool
equal( I1 first1, S1 last1, I2 first2, S2 last2, Pred pred = {},
Proj1 proj1 = {}, Proj2 proj2 = {} );
|
(1) | (desde C++20) |
template< ranges::input_range R1, ranges::input_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>
constexpr bool
equal( R1&& r1, R2&& r2, Pred pred = {}, Proj1 proj1 = {}, Proj2 proj2 = {} );
|
(2) | (desde C++20) |
true si los valores proyectados del rango [first1, last1) son iguales a los valores proyectados del rango [first2, last2), y false en caso contrario.r como el rango fuente, como si se usara ranges::begin(r) como first y ranges::end(r) como last.Dos rangos se consideran iguales si tienen el mismo número de elementos y cada par de elementos proyectados correspondientes satisface pred. Es decir, std::invoke(pred, std::invoke(proj1, *first1), std::invoke(proj2, *first2)) devuelve true para todos los pares de elementos correspondientes en ambos rangos.
Las entidades similares a funciones descritas en esta página son objetos función de algoritmo (informalmente conocidos como niebloids), es decir:
- No se pueden especificar listas explícitas de argumentos de plantilla al llamar a cualquiera de ellos.
- Ninguno de ellos es visible para la búsqueda dependiente de argumentos.
- Cuando alguno de ellos se encuentra mediante búsqueda normal no calificada como el nombre a la izquierda del operador de llamada a función, la búsqueda dependiente de argumentos se inhibe.
Parámetros
| first1, last1 | - | el par iterador-centinela que define el primer rango de elementos a comparar |
| r1 | - | el primer rango de los elementos a comparar |
| first2, last2 | - | el par iterador-centinela que define el segundo rango de elementos a comparar |
| r2 | - | el segundo rango de los elementos a comparar |
| pred | - | predicado binario a aplicar a los elementos proyectados |
| proj1 | - | proyección a aplicar al primer rango de elementos |
| proj2 | - | proyección a aplicar al segundo rango de elementos |
Valor devuelto
Si la longitud del rango [first1, last1) no es igual a la longitud del rango [first2, last2), devuelve false.
Si los elementos en los dos rangos son iguales después de la proyección, devuelve true.
De lo contrario devuelve false.
Notas
ranges::equalranges::equal no debe usarse para comparar los rangos formados por los iteradores de std::unordered_set, std::unordered_multiset, std::unordered_map, o std::unordered_multimap porque el orden en que se almacenan los elementos en esos contenedores puede ser diferente incluso si los dos contenedores almacenan los mismos elementos.
Al comparar contenedores completos o vistas de cadenas para igualdad, normalmente se prefiere operator==operator== para el tipo correspondiente.
ranges::equalranges::equal no está garantizado para ser de cortocircuito. Por ejemplo, si los primeros pares de elementos de ambos rangos no se comparan iguales, el resto de elementos también pueden ser comparados. La comparación sin cortocircuito puede ocurrir cuando los rangos se comparan con std::memcmp o algoritmos vectorizados específicos de la implementación.
Complejidad
Como máximo min(last1 - first1, last2 - first2) aplicaciones del predicado y las proyecciones correspondientes.
Sin embargo, si S1 y S2 modelan ambos std::sized_sentinel_for sus respectivos iteradores, y last1 - first1 != last2 - first2 entonces no se realiza ninguna aplicación del predicado (la discrepancia de tamaño se detecta sin mirar ningún elemento).
Posible implementación
struct equal_fn
{
template<std::input_iterator I1, std::sentinel_for<I1> S1,
std::input_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>
constexpr bool
operator()(I1 first1, S1 last1, I2 first2, S2 last2,
Pred pred = {}, Proj1 proj1 = {}, Proj2 proj2 = {}) const
{
if constexpr (std::sized_sentinel_for<S1, I1> and std::sized_sentinel_for<S2, I2>)
if (std::ranges::distance(first1, last1) != std::ranges::distance(first2, last2))
return false;
for (; first1 != last1; ++first1, (void)++first2)
if (!std::invoke(pred, std::invoke(proj1, *first1), std::invoke(proj2, *first2)))
return false;
return true;
}
template<ranges::input_range R1, ranges::input_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>
constexpr bool
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::ref(pred), std::ref(proj1), std::ref(proj2));
}
};
inline constexpr equal_fn equal;
|
Ejemplo
El siguiente código usa ranges::equal para probar si una cadena es un palíndromo.
#include <algorithm>
#include <iomanip>
#include <iostream>
#include <ranges>
#include <string_view>
constexpr bool is_palindrome(const std::string_view s)
{
namespace views = std::views;
auto forward = s | views::take(s.size() / 2);
auto backward = s | views::reverse | views::take(s.size() / 2);
return std::ranges::equal(forward, backward);
}
void test(const std::string_view s)
{
std::cout << std::quoted(s) << " is "
<< (is_palindrome(s) ? "" : "not ")
<< "a palindrome\n";
}
int main()
{
test("radar");
test("hello");
static_assert(is_palindrome("ABBA") and not is_palindrome("AC/DC"));
}
Salida:
"radar" is a palindrome
"hello" is not a palindrome
Véase también
(C++20)(C++20)(C++20) |
encuentra el primer elemento que satisface criterios específicos (objeto función de algoritmo) |
| compara dos rangos lexicográficamente (objeto función de algoritmo) | |
(C++20) |
encuentra la primera posición donde dos rangos difieren (objeto función de algoritmo) |
(C++20) |
busca la primera ocurrencia de un rango de elementos (objeto función de algoritmo) |
(C++20) |
encuentra el rango de elementos que coinciden con un valor dado usando búsqueda binaria (objeto función de algoritmo) |
objeto función que implementa x == y (plantilla de clase) | |
| determina si dos conjuntos de elementos son iguales (plantilla de función) |