Siempre trato de incorporar algoritmos STL siempre que puedo, en lugar de escribir bucles manuales. Sin embargo, tengo dificultades para entender cómo std::accumulate
es generalmente útil. Cada vez que necesito calcular sumas o promedios, casi siempre termino recurriendo a bucles manuales, porque tengo dificultades para obtener std::accumulate
para hacer lo que necesito.Uso de std :: accumulate
El problema es que rara vez tengo un vector simple de enteros que deben sumarse. Usualmente, quiero sumar una matriz de objetos usando una variable de miembro particular. Sí, sé que hay una versión de std::accumulate
que toma un BinaryFunction, pero el problema que veo es que esta función tiene que tomar dos valores de tipo T
, donde T
es el tipo de la suma, en lugar del tipo de la operandos. Tengo problemas para entender cómo esto es útil.
Considere un caso que supongo que es bastante común. Tengo la clase siguiente:
struct Foo
{
Foo(int cost_, int id_) : cost(cost_), id(id_)
{ }
int cost;
int id;
};
Ahora, digo que quiero para calcular la suma de una serie de objetos Foo
, utilizando Foo::cost
.
quiero decir:
std::vector<Foo> vec;
// fill vector with values
int total_cost = std::accumulate(vec.begin(), vec.end(), 0, sum_cost);
Y sum_cost
se define como:
int sum_cost(const Foo& f1, const Foo& f2)
{
return f1.cost + f2.cost;
}
El problema es que esto no funciona porque std::accumulate
espera un BinaryFunction que se lleva en dos instancias de la suma resultante tipo - que en este caso es solo int
. Pero, ¿cómo es eso útil para mí? Si mi BinaryFunction tiene dos int
s, no puedo especificar que quiero sumar el campo cost
.
Entonces, ¿por qué está diseñado el std::accumulate
de esta manera? ¿Acaso no estoy viendo algo obvio aquí?
Si su clase representa objetos que se pueden acumular, puede considerar agregar operadores + y + =. –
Nitpick: 'std :: accumulate' espera una BinaryFunction, no una BinaryPredicate. Los predicados devuelven un valor booleano. –
@Emile, gracias. Corregido – Channel72