我目前正試圖理解如何通過在程序集中左移來乘法,從而解決一些任務。 我被要求重寫一些計算,不使用mul
或div
。左移乘法程序集
例子:
mul $2, %eax
我的回答:
sal $1, %eax
我明白,左移一次,這個人是回答。 但另一個例子說
mul $3, %eax
和
mul $5, %eax
我該怎麼解決呢?從我所學到的東西中分裂出來,然後以某種方式加在一起。
有人嗎?謝謝!
我目前正試圖理解如何通過在程序集中左移來乘法,從而解決一些任務。 我被要求重寫一些計算,不使用mul
或div
。左移乘法程序集
例子:
mul $2, %eax
我的回答:
sal $1, %eax
我明白,左移一次,這個人是回答。 但另一個例子說
mul $3, %eax
和
mul $5, %eax
我該怎麼解決呢?從我所學到的東西中分裂出來,然後以某種方式加在一起。
有人嗎?謝謝!
您需要通過加法和移位操作分解乘法,如
x*3 == x*2 + x
然後,它變得微不足道
mov %eax, %ebx # tmp = eax
sal $1, %eax # eax <<= 1
add %ebx, %eax # eax += tmp
通過由權力轉移,你只能乘法/除法2
。
x * (2^n) = x << n
x/(2^n) = x >> n
如果你想乘x * y
,而y
不是2的冪,則需要「分解」它的兩個大國,每個組件乘法和加法的結果。幸運的是,任何數字都可以表示爲兩個冪的和。你猜怎麼着?二進制表示告訴你如何。例如:
y = 12 (not a power of two).
二進制表示將
y = 1100
現在來這裏的人都是位置:2, 3
(開始0
右側)。這意味着
y = 2^2 + 2^3.
現在,乘x
由y
你只需要:
x * y = x * (2^2) + x * (2^3) = (x << 2) + (x << 3)
而且你已經取代了乘法與移位和加法。
(順便說一句,如果你是熟悉的二進制文件長乘法方法,在這裏你會認識到它...)
這個問題是最近剛剛提出和回答...
從小學我們知道
n * 3 = n * (2 + 1) = n * ((2^1) + (2^0)) = (n*(2^1)) + (n*(2^0))
,然後您可以將換擋
(n<<1)+(n<<0)
同爲5分0b101時或2^2 + 2^0。
您還可以從gradeschool但二進制再次做到這一點,長乘法是簡單得多
nmop
* 0101
=========
nmop
0000
nmop
+0000
=========
(其中N,M,OP是各個位)十進制(小學)你拿了位上底部並將其乘以整個頂部,將其移到底部每10次方的一列上,二進制相同但基數爲2時,只有兩個選擇乘以0或乘以1,所以要麼不添加任何東西在或者你添加一個數字移動了正確的列數。
無論哪種方式,最終都會得到相同的結果,選擇其中一個操作數,對於每個二進制位是一個,您將其他操作數轉移到該位置,然後將其全部添加。
劃分是一個完全不同的野獸,你可以右移兩個冪,但它不會以相同的方式分佈n = 5!= n/4 + n/1。通過一些技巧讓黑客高興。另外請注意,如果它是2的冪,那麼它通常只適用於無符號數字,對於有符號數字,您經常會看到零從左側移入,而不是符號位的重複。在某些體系結構的彙編中,算術右移與邏輯右移相比,邏輯經常在零點處移動,這是高級語言經常使用的轉換,算術理想地重複了符號位。允許您使用正確的右移作爲兩個除數的符號(但不一定是未簽名)