[英]What does vectorization mean?
向量化代碼是一個好主意嗎? 在什么時候這樣做有什么好的做法? 下面會發生什么?
向量化意味着編譯器檢測到您的獨立指令可以作為一條SIMD指令執行。 通常的例子是,如果你做了類似的事情
for(i=0; i<N; i++){
a[i] = a[i] + b[i];
}
它將被矢量化為(使用矢量符號)
for (i=0; i<(N-N%VF); i+=VF){
a[i:i+VF] = a[i:i+VF] + b[i:i+VF];
}
基本上,編譯器選擇一個可以同時在陣列的VF元素上完成的操作,並執行N / VF次,而不是單次操作N次。
它提高了性能,但對架構提出了更高的要求。
如上所述,矢量化用於利用SIMD指令,SIMD指令可以執行打包到大寄存器中的不同數據的相同操作。
使編譯器能夠自動向量化循環的通用准則是確保在循環的不同迭代中沒有流和反依賴性的b / w數據元素。
http://en.wikipedia.org/wiki/Data_dependency
一些編譯器,如英特爾C ++ / Fortran編譯器,能夠自動生成代碼。 如果無法對循環進行矢量化,英特爾編譯器就能夠報告為什么它不能這樣做。 有報告可用於修改代碼,使其變得可矢量化(假設它是可能的)
“為現代架構優化編譯器:基於依賴的方法”一書深入介紹了依賴關系
這是SSE代碼生成。
你有一個帶有浮點矩陣代碼的循環:matrix1 [i] [j] + matrix2 [i] [j],編譯器生成SSE代碼。
矢量化不必限於可以容納大數據的單個寄存器。 就像使用'128'位寄存器來保存'4 x 32'位數據一樣。 這取決於架構限制。 某些體系結構具有不同的執行單元,這些執 在這種情況下,可以將一部分數據饋送到該執行單元,並且可以從對應於該執行單元的寄存器獲取結果。
例如,考慮以下情況。
for(i = 0; i <N; i ++)
{
a [i] = a [i] + b [i];
}
如果我正在開發一個有兩個執行單元的架構,那么我的矢量大小定義為兩個。 上面提到的循環將被重新定義為
for(i = 0; i <(N / 2); i + = 2)
{
a [i] = a [i] + b [i];
a [i + 1] = a [i + 1] + b [i + 1];
}注意:for語句中的2是從向量大小派生的。
由於我有兩個執行單元,循環內的兩個語句將被送入兩個執行單元。 總和將分別在執行單元中累計。 最后,將執行累積值的總和(來自兩個執行單元)。
好的做法是
1.在向量化循環之前,需要檢查依賴性(在循環的不同迭代之間)之類的約束。
2.需要防止函數調用。
3.指針訪問可以創建別名,需要防止它。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.