Привет, я хочу (умножить, добавить и т.д.) вектор по скалярному значению, например myv1 * 3
, я знаю, что могу выполнять функцию с forloop, но есть ли способ сделать это с помощью функции STL? Что-то вроде функции {Algorithm.h:: transform}?
Умножить векторные элементы на скалярное значение с помощью STL
Ответ 1
Да, используя std::transform
:
std::transform(myv1.begin(), myv1.end(), myv1.begin(),
std::bind(std::multiplies<T>(), std::placeholders::_1, 3));
До С++ 17 вы могли использовать std::bind1st()
, что в С++ 11 устарело.
std::transform(myv1.begin(), myv1.end(), myv1.begin(),
std::bind1st(std::multiplies<T>(), 3));
Для заполнителей;
#include <functional>
Ответ 2
Если вы можете использовать valarray
вместо vector
, у него есть встроенные операторы для выполнения скалярного умножения.
v *= 3;
Если вам нужно использовать vector
, вы действительно можете использовать transform
для выполнения задания:
transform(v.begin(), v.end(), v.begin(), _1 * 3);
(предполагается, что у вас есть что-то похожее на Boost.Lambda, что позволяет вам легко создавать анонимные функциональные объекты, такие как _1 * 3
:-P)
Ответ 3
Просто: если вы можете иметь свои данные в массиве фиксированного размера (значения с плавающей запятой [N]), вы можете использовать встроенные функции SSE, чтобы сделать это быстрее, поскольку оно будет умножать последовательное поплавок на время (4).
Ответ 4
Более современное C++ решение для вашего вопроса.
std::vector<double> myarray;
double myconstant{3.3};
std::transform(myarray.begin(), myarray.end(), myarray.begin(), [myconstant](auto& c){return c*myconstant;});
Ответ 5
Я знаю, что это не STL, как вы хотите, но это то, что вы можете адаптировать по мере возникновения различных потребностей.
Ниже приведен шаблон, который вы можете использовать для расчета; "func" - это функция, которую вы хотите сделать: умножить, добавить и т.д.; Параметр 'parm' является вторым параметром функции func. Вы можете легко расширить это, чтобы использовать различные функции с большим количеством парм разных типов.
template<typename _ITStart, typename _ITEnd, typename _Func , typename _Value >
_ITStart xform(_ITStart its, _ITEnd ite, _Func func, _Value parm)
{
while (its != ite) { *its = func(*its, parm); its++; }
return its;
}
...
int mul(int a, int b) { return a*b; }
vector< int > v;
xform(v.begin(), v.end(), mul, 3); /* will multiply each element of v by 3 */
Кроме того, это не "безопасная" функция, вы должны выполнить проверку типов и значений и т.д., прежде чем использовать ее.
Ответ 6
Я думаю, что for_each
очень уместен, когда вы хотите пройти вектор и манипулировать каждым элементом в соответствии с каким-то шаблоном, в этом случае будет достаточно простой лямбды:
std::for_each(myv1.begin(), mtv1.end(), [](int &el){el *= 3; });
обратите внимание, что любая переменная, которую вы хотите захватить для использования лямбда-функции (скажем, что вы, например, хотели умножить на некоторый предопределенный скаляр), помещается в скобку в качестве ссылки.