簡體   English   中英

使用 STL 將向量元素乘以標量值

[英]Multiply vector elements by a scalar value using STL

嗨,我想(乘、加等)向量按標量值,例如myv1 * 3 ,我知道我可以用 forloop 做一個函數,但是有沒有辦法使用 STL 函數來做到這一點? {Algorithm.h :: 變換函數}之類的東西?

是的,使用std::transform

std::transform(myv1.begin(), myv1.end(), myv1.begin(),
               std::bind(std::multiplies<T>(), std::placeholders::_1, 3));

在 C++17 之前,您可以使用在 C++11 中已棄用的std::bind1st()

std::transform(myv1.begin(), myv1.end(), myv1.begin(),
               std::bind1st(std::multiplies<T>(), 3));

對於占位符;

#include <functional> 

如果您可以使用valarray而不是vector ,它具有用於執行標量乘法的內置運算符。

v *= 3;

如果您必須使用vector ,您確實可以使用transform來完成這項工作:

transform(v.begin(), v.end(), v.begin(), _1 * 3);

(假設您有類似於Boost.Lambda的東西,它允許您輕松創建匿名函數對象,例如_1 * 3 :-P)

您的問題的現代 C++ 解決方案。

#include <algorithm>
#include <vector>

std::vector<double> myarray;
double myconstant{3.3};
std::transform(myarray.begin(), myarray.end(), myarray.begin(), [&myconstant](auto& c){return c*myconstant;});

我認為當你想遍歷一個向量並根據某種模式操作每個元素時, for_each非常合適,在這種情況下,一個簡單的 lambda 就足夠了:

std::for_each(myv1.begin(), mtv1.end(), [](int &el){el *= 3; });

請注意,您想要捕獲以供 lambda 函數使用的任何變量(例如,您想要與某個預定的標量相乘),都會作為參考放入括號中。

如果您必須將結果存儲在一個新的 vector中,那么您可以使用<algorithm>標頭中的std::transform()

#include <algorithm>
#include <vector>

int main() {
    const double scale = 2;
    std::vector<double> vec_input{1, 2, 3};
    std::vector<double> vec_output(3); // a vector of 3 elements, Initialized to zero
    // ~~~
    std::transform(vec_input.begin(), vec_input.end(), vec_output.begin(),
                   [&scale](double element) { return element *= scale; });
    // ~~~
    return 0;
}

所以,我們在這里要說的是,

  • vec_input從開頭 ( vec_input.begin() ) 到結尾 ( vec_input.begin() ) 的值 ( element s),
    • 本質上,使用前兩個參數,您指定要轉換的元素范圍( [beginning, end) ),范圍
  • 將每個element傳遞給最后一個參數 lambda 表達式,
  • 獲取 lambda 表達式的輸出並將其放入vec_output從頭開始​​( vec_output.begin() )。
    • 第三個參數是指定目標向量的開始。

拉姆達表達式

  • 通過引用從外部捕獲比例因子 ( [&scale] ) 的值,
  • 將 double 類型的向量元素作為輸入(由std::transform()傳遞給它)
  • 在函數體中,它返回最終結果,
    • 正如我上面提到的,它將因此存儲在vec_input中。

最后說明:雖然沒有必要,但您可以通過以下 lambda 表達式:

[&scale](double element) -> double { return element *= scale; }

它明確指出 lambda 表達式的輸出是雙精度數。 但是,我們可以省略它,因為在這種情況下,編譯器可以自己推斷返回類型。

我知道這不是你想要的 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 */

此外,這不是一個“安全”功能,您必須在使用它之前進行類型/值檢查等。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM