Накапливаться на карте

Я не могу получить этот довольно простой код для компиляции. Я получаю ошибку, could not deduce template argument for 'std::basic_string<_Elem,_Traits,_Alloc> &&' from 'int', Нужно ли передавать какую-то пользовательскую функцию суммирования для накопления? Или, может быть, есть более простой способ получить сумму всех вторых значений на карте? Спасибо!

#include <iostream>
#include <math.h>
#include <map>
#include <numeric>int main()
{

map<int, int> m;

m[1] = 1;
m[2] = -1;
m[3] = 1;
m[4] = 2;

int sum = accumulate(m.begin(), m.end(), 0);
cout << sum;

return 0;
}

2

Решение

Вы не можете использовать алгоритм std :: accuulate в его простой форме для контейнера типа std :: map. Вам необходимо использовать алгоритм с двоичной операцией и, возможно, использовать лямбда-выражение в качестве двоичной операции.
Например

int sum = accumulate( m.begin(), m.end(), 0,
[]( int acc, std::pair<int, int> p ) { return ( acc + p.second ); } );
3

Другие решения

Тип элемента std::map<K,V> является std::pair<const K,V> для которого operator+ не определено. Вам нужно использовать 4 аргумента версии accumulate и добавьте свою собственную операцию сложения:

typedef std::pair<int, int> Pair;

int sum = accumulate(m.begin(), m.end(), 0,
[](int i, Pair p){ return i + p.second; });
1

std::map<int, int> содержит std::pair<const int, int> элементы. std::accumulate не знает что с ними делать. Но вы можете решить эту проблему, передав ей подходящий функтор. Например, чтобы накопить ключи:

int fun(int i, const std::pair<const int, int>& rhs)
{
return i + rhs.second;
}
int sum = accumulate(m.begin(), m.end(), 0, fun);

Обратите внимание, что вы можете упростить это с помощью лямбды, если вам не нужно использовать fun где-нибудь еще:

int sum = accumulate(m.begin(), m.end(),
[](int i, const std::pair<const int, int>& rhs)
{
return i + rhs.second;
});
1