contributed by <CheHsuan
>
閱讀 重新理解數值 裡頭關於 count leading zero (clz) 的描述,設計實驗,比較 32-bit 數值對以下實做的效能差異:
老師給的版本有一個問題,就是沒有中止條件使程式跳出recursive call,所以必須改寫一下
這個寫法是類似binary search的方式,理論上時間複雜度為O(logN)
但這個版本的時間複雜度是O(N),而且比iteration版本的clz多出了function call的成本
時間複雜度為O(N)
此版本我是參考老師重新理解數值裡面的作法,從這個算法來看,時間複雜度為O(logN)
一樣參考重新理解數值,這版本的算法的時間複雜度和binary search technique一樣為時間複雜度為O(logN),只少了一次if比較,不過應該不會相差太多
修改table內數字,OK成功
參考compute-pi作法,使用clock_gettime()
函式
man一下
int clock_gettime(clockid_t clk_id, struct timespec *tp);
The clk_id argument is the identifier of the particular clock on which to act. A clock may be system-wide and hence visible for all processes, or per-process if it measures time only within a single process.
在manual裡面指出,clock_gettime可以指定量測system-wide time,也就是wall clock time,因此會因機器假如同時運行其他程式的話,會影響到時間量測的準確度,所以我們不考量使用這方法
利用系統的jiffies來計算時間,當發生time interrupt時,便把紀錄+1
計算整個process在kernel space和user space所花費的時間,假如是多執行緒,會將每個thread所花的時間加起來
計算單個thread在kernel space和user space所花費的時間
這次的實驗環境是計算0X0~0XFFFF的clz,每個方法都跑100次,數據如下
從圖中可以看出兩件事情
再把跑的次數拉大一點來看,一樣是0X0~0XFFFF各跑5000次
針對32 bits unsigned integer的極值(0~4294967296)各跑1次
演算法的重要性!recursive的版本花到487.10秒,也就是八分鐘,夠吃完一碗泡麵了
recursive | binary recursive | iteration | byte-shift | binary search technique | |
---|---|---|---|---|---|
0 | 486.492851 | 110.374512 | 264.005961 | 22.064742 | 21.832292 |
1 | 485.631612 | 110.86067 | 263.157863 | 22.039492 | 21.640222 |
OK,把recursive的版本用O(N)和O(logN)的方法來比較一下,執行時間相差了約4倍(486:110)
而同樣都是O(logN)的算法,recusive function call和one function call with multiple if-else的方法來比較,時間也差了大概5倍(110:22)
加入Harley
最後總測試
[WIP]