我在每個方向創建了一個網格(N,N)單元,我想檢查哪些點對應哪個單元,這很容易,但是,有一些點可以離開網格,我希望它把它放到一個單元格中。哪種操作對性能,最小/最大或模數的影響最小?
這些都是在GPU中完成的,所以我的問題是關於什麼纔是映射點到有效單元格的最佳操作?
使用max(0,min(N,cell.x))的第一個選項我相信會引入內核的分歧。第二種選擇是使用模數(cell.x%N),我認爲這是GPU中非常昂貴的操作。
我怎樣才能決定使用哪一個?
我在每個方向創建了一個網格(N,N)單元,我想檢查哪些點對應哪個單元,這很容易,但是,有一些點可以離開網格,我希望它把它放到一個單元格中。哪種操作對性能,最小/最大或模數的影響最小?
這些都是在GPU中完成的,所以我的問題是關於什麼纔是映射點到有效單元格的最佳操作?
使用max(0,min(N,cell.x))的第一個選項我相信會引入內核的分歧。第二種選擇是使用模數(cell.x%N),我認爲這是GPU中非常昂貴的操作。
我怎樣才能決定使用哪一個?
GPU具有整數min()
和max()
的硬件指令。如果使用cuobjdump --dump-sass
從nvcc編譯的可執行文件中轉儲機器代碼,則可以識別這些指令,例如,它們被稱爲IMNMX
或VMNMX
(「mnmx」代表「最小值或最大值」,兩個操作之間的選擇是通過謂詞)。
對於N
這是一個編譯時常量冪的兩倍,模運算應該映射到一個單指令LOP.AND
。對於其他編譯時常量值N
,發出一個小指令序列,通常涉及整數乘法和移位。對於變量N
,即在運行時確定,模運算將基本上需要至少15條左右指令的全整數除法。
因此,除了編譯時常量N
是2的冪的情況之外,從性能角度看,使用min()
和max()
進行的鉗位似乎優於基於模的解決方案。但是,除非您的代碼頻繁執行此操作並受計算吞吐量限制,否則內核級別的性能差異可能很小或可能不存在(例如,如果代碼是內存帶寬受限的)。
你知道N嗎?例如,用兩個冪的modtros很便宜。 – Jez 2014-11-21 14:42:49
我在想這個,但我想在某些情況下,這意味着增加所需的內存是正確的?但是,呃...網格不應該那麼大,所以它可能是一個選擇。 – BRabbit27 2014-11-21 14:49:30
'使用max(0,min(N,cell.x))的第一個選項,我相信它會在內核中引入分歧「爲什麼你認爲這會引入分歧?這些函數應該映射到非常高效的無分支程序集,例如'min.s32'和'max.s32'。那裏沒有分歧。 – 2014-11-21 15:04:07