標籤:

將"double"進行到底?

將"double"進行到底?

來自專欄 MATLAB39 人贊了文章

相信大部分MATLAB用戶(圖像處理專業或者搞硬體的用戶除外)和我一樣, 數值型變數一直使用默認的"double"型, 從未考慮過使用其他數值類似, 比如"float", signed或unsigned的各種位數(8位, 16位, 32位, 64位)的整數型.

今天, 我翻了一下文檔, 有一句話成功的引起了我的極大興趣:

MATLAB supports 1-, 2-, 4-, and 8-byte storage for integer data. You can save memory and execution time for your programs if you use the smallest integer type that accommodates your data. For example, you do not need a 32-bit integer to store the value100.

合理是使用數據類型, 可以節省內存空間(這是顯而易見的), 和提高運行效率(這點我在C/C++裡面經過證實的), 由於我一直在MATLAB使用double型數值變數, 所以, 使用其他數值類型在MATLAB里是否能提高運行效率呢? 我是有疑慮的,

不敢將C/C++裡面的規律簡單的套用到MATLAB裡面, 因為有前車之鑒, 比如C/C++裡面的位運算效率是極高的, 但是MATLAB的位運算函數(比如bitand, bitor, bitxor等)速度慢.

於是, 我寫了一個腳本進行了簡單的測試(使用10種不同的數值類似進行1+10運算):

%%loops = 1e6;a_double = 1*ones(100, 5);b_double = 10*ones(100, 5);a_single = single(1*ones(100, 5));b_single = single(10*ones(100, 5));a_i8 = int8(1*ones(100, 5));b_i8 = int8(10*ones(100, 5));a_u8 = uint8(1*ones(100, 5));b_u8 = uint8(10*ones(100, 5));a_i16 = int16(1*ones(100, 5));b_i16 = int16(10*ones(100, 5));a_u16 = uint16(1*ones(100, 5));b_u16 = uint16(10*ones(100, 5));a_i32 = int32(1*ones(100, 5));b_i32 = int32(10*ones(100, 5));a_u32 = uint32(1*ones(100, 5));b_u32 = uint32(10*ones(100, 5));a_i64 = int64(1*ones(100, 5));b_i64 = int64(10*ones(100, 5));a_u64 = uint64(1*ones(100, 5));b_u64 = uint64(10*ones(100, 5));%%tic;for ii = 1:loops t = a_double + b_double; %#ok<*VUNUS>endDouble = toc;%%tic;for ii = 1:loops t = a_single + b_single;endSingle = toc;%%tic;for ii = 1:loops t = a_i8 + b_i8;endInt8 = toc;%%tic;for ii = 1:loops t = a_u8 + b_u8;endUint8 = toc;%%tic;for ii = 1:loops t = a_i16 + b_i16;endInt16 = toc;%%tic;for ii = 1:loops t = a_u16 + b_u16;endUint16 = toc;%%tic;for ii = 1:loops t = a_i32 + b_i32;endInt32 = toc;%%tic;for ii = 1:loops t = a_u32 + b_u32;endUint32 = toc;%%tic;for ii = 1:loops t = a_i64 + b_i64;endInt64 = toc;%%tic;for ii = 1:loops t = a_u64 + b_u64;endUint64 = toc;%%T = table(Double, Single, Int8, Uint8, Int16, Uint16, Int32, Uint32, Int64, Uint64); Types = T.Properties.VariableNames;Times = T.Variables;[Times, idx] = sort(Times);Types = Types(idx);Types = categorical(Types, Types);figure;bar(Types, Times);ylabel(運行時間(秒));xlabel(數據類型);grid on;

運行結果為:

可以看到:

1 默認的數值類型double的排名是比較靠後的(倒數第三名).

2 同為浮點型, single快於double

3 整數型的話, 位數越小, 速度越快, 相同位數的話, unsigned的比signed的要快.

當然了, 這只是"1+10"運算的測試結果, 如果是其他運算的話, 排名有可能發生變化.

但是, 至少說明: 數值類型對於運算效率是有顯著影響的.

因此, 以後加速程序時, 試圖改變數值類型, 是一個可能的加速點, 不要一味的將"double"進行到底了.

更新:

感謝 @曲伽西 評論裡面的提醒. 現在加入了賦值變數t. 發現不同數值類型之間的差距更大了!

如果不加入賦值變數的話, 會花費很長時間賦值給ans. 不能真正體現出不同數值類型加法運算速度的差別.

這是原來文章的結果(加法運算不賦值, 比如"a + b;", 現在為"t = a + b"):

注意, 兩張圖的絕對值不能直接比較, 因為是不同電腦上運行的結果, 看相對值就好了.

不賦值版最快與最慢的倍數大概是7倍左右.

賦值版最快最慢的倍數大概是26倍左右.


推薦閱讀:

MATLAB的數據分析工具鏈
Matlab如何製作GUI
Matlab如何讀取PDF文件
用遺傳演算法實現求ZDT6最優解以及自動設計模擬電路
我國國債利率期限結構研究

TAG:MATLAB |