編譯器優化 乘法優化

2022-02-23 16:05:45 字數 1189 閱讀 5674

由這個想到的;

31乘以某個數能不能寫成這個數乘以2的次冪 再減去這個數。

用數學語言表達一下就是:

設這個數為x

31*x=x*2^n-x

這個等式是否存在,如果存在,求n的值

那我們計算一下,

31=2^n -1

得2^n=32

得n=5

也就是說存在那麼乙個n使得,31乘以某個數的結果等於這個數乘以2的n次冪再減去乙個數。

所以,乙個乘法運算,最後就轉化成了乙個速度較快的移位運算了。 

我們再試試另外的數

63*i=i*2^n-i這個等式是寸存在,若存在,求出n的值。

最後得出n=6

有沒有發現規律,31等於2的n次方-1,63也等於2的n次方-1

所以乙個(2^n-1)乘以某個數的結果可以被優化為這個數乘以2的n次方再減去這個數。

然後我又做了幾個實驗。

因為9=2^4+1;

然後自然就想到了9乘以某個數是否能寫成這個數乘以2的n次冪,再加上這個數

9*i=i*2^n+i是否成立,如果成立,求n

n=4,也就是說9乘以某個數是等於這個數乘以2的n次冪再加上這個數的。

事實上,編譯器也是這麼優化的。

我寫了一段**,用來計算9和任意乙個整數的乘法。

int x =9;

int input = 0;

scanf_s("%d",&input);

printf("%d",9*input);

用ida檢視一下關鍵**,9是怎麼被優化的。

有一點必須直到,eax是作為printf的引數,printf的輸出結果就是eax的值,這需要一點彙編知識。

那我們看lea中eax是怎麼計算的。

用數學語言翻譯過來是不是就是這樣:

9*eax=eax*8 + eax;把eax換成i

9*i=i*2^n+i

和前面是相符的。

經過測試發現如果是單變數乘以某個常數這種情況的話,優化策略是這樣的:

如果這個常數可以被寫成2^n,(2^n)+1,(2^n)-1,2^n(1+2^m) 這幾種情況的話,那麼就被優化了。

2^n(2^m-1) 這種情況並不優化,直接用的是imul指令

編譯器優化

常量摺疊 a 1 2 由於結果可預見,編譯器直接生成a 3 常量傳播a 1 若後續 沒有更改a,則編譯器將a直接用其值1代替 減少變數 對於x和y的比較,可以轉換成if i j x i2 y j 2 if x y 複寫傳播 類似於常量長傳,不過傳播的是變數 若後續 未修改a的值,則編譯器用m代替a ...

編譯器優化問題

今天遇一程式,unsigned char a,b,c a 0x89 b a 1 c a b 在單步除錯的時候,觀察數值發現b的值為0,分析b的值應當為0x44,百思不得其解,通過檢視其彙編語句,發現問題所在。彙編語句如下 mov r7,tmod 0x89 mov a,r7 clr c rrc a a...

symbian gcc 編譯器 優化

1。公升級到gcce 4http www.cnblogs.com felixyeou archive 2009 02 18 1392847.html 2.gcce 優化引數,關於3rd mr和3rd fp1生成的安裝包大小http wiki.forum.nokia.com index.php e5 ...