Java利用位運算實現(xiàn)乘法運算詳解
前言
在上一篇中,我們介紹了使用位運算實現(xiàn)加法和減法運算,接下來本文主要介紹如何用位運算實現(xiàn)乘法運算,在實現(xiàn)乘法時要用位運算實現(xiàn),并且不能出現(xiàn)加減乘除任何符號。
之前介紹過一篇如何用位運算實現(xiàn)加法和減法: 如何用位運算實現(xiàn)加減運算?
正文
在用位運算實現(xiàn)之前,我們先來回憶一下小學時,學乘法時用的十字相乘法。
十進制相乘
例如,26 * 15,在進行乘法操作時,我們一般這樣算,先用5乘以6得到30,把0寫下把3記在一邊,再用5乘以2得到10再加上之前的3寫在下面,得到130;計算完5再計算1分別乘以6和2把得到的結(jié)果26記在下面,然后把130和26相加(有錯位)得到390。

二進制相乘
看完了十進制的相乘,再來看下二進制的相乘,基本原理是一樣的,也是以十字相乘法為例,計算 5 * 7。
5的二進制為101,7的二進制為111,來看下二進制的十字相乘法。

可以看到二進制為101和二進制111用傳統(tǒng)的方式來計算,得到的結(jié)果為100011,而二進制100011對應(yīng)的十進制為35。
所以說,在計算的過程中,十進制和二進制的計算方式是一樣的,當然這里就不進行舉例和證明了。
思路分析
既然計算過程有了,那么怎么樣用代碼來實現(xiàn)呢?
我們再來看下上圖中二進制的計算過程:
- 先用二進制
111的最后一位1乘上101得到101。 - 再用二進制
111的倒數(shù)第2位1乘上101得到101。 - 再用二進制
111的倒數(shù)第3位1乘上101得到101。 - 得到的三個
101進行二進制相加,得到100011。
注意,第2步和第3步得到的結(jié)果101都往前挪了一位,相當于1010和10100,也就是最后相加的計算為:10100 + 1010 + 101 = 100011。
再來看得到最終相加的計算10100 + 1010 + 101 = 100011,也就是只要我們找到如何把數(shù)據(jù)轉(zhuǎn)換為幾位數(shù)的相加就可以了,因為之前已經(jīng)實現(xiàn)了如何用位運算實現(xiàn)加法操作。
這三個數(shù)101、1010、10100的數(shù)量剛好與二進制111的個數(shù)相同,也就是二進制(上圖下面那個乘數(shù)111)有幾位就會產(chǎn)生幾個數(shù)相加,如果是與11111相乘就會產(chǎn)生5個數(shù)相加。
再來看數(shù)據(jù)之前的關(guān)系:
- 第一次相乘結(jié)果:
101 = 101 + 0 - 第二次相乘結(jié)果:
1111 = 101 < 1 + 101 = 1010 + 101 - 第三次相乘結(jié)果:
100011 = 101 < 2 + 1111 = 10100 + 1010 + 101
從這里我們可以看到,每計算一次,101只需要向左移一次再加上上一次的計算結(jié)果就可以了。
那么,怎么知道要左移多少次呢?從這里例子中看,111每次計算后,向右移動一次,101也跟著向左移動一次,直到111只剩最后一位,則停止計算就好了。
代碼實現(xiàn)
根據(jù)上面的思路,來實現(xiàn)一下代碼:
// 用位運算實現(xiàn)加法
public static int add(int a, int b) {
int sum = 0;
while (b != 0) {
sum = a ^ b;
b = (a & b) << 1;
a = sum;
}
return sum;
}
// 用位運算實現(xiàn)減法
public static int multi(int a, int b) {
int res = 0;
while (b != 0) {
if ((b & 1) != 0) {
res = add(res, a);
}
a <<= 1;
b >>>= 1;
}
return res;
}運行一下代碼,看下結(jié)果:

可以看到計算是正確的,而且還支持負數(shù)。
總結(jié)
本文介紹了如何用純位運算實現(xiàn)乘法的運算,并介紹了實現(xiàn)思路以及分析,需要注意的是,位運算右移的時候需要使用無符號右移,否則的話,會出現(xiàn)死循環(huán)的。
另外,本文只是介紹利用位運算來實現(xiàn)乘法的實現(xiàn)過程、知識點的介紹,雖然是使用的位運算但是效率是不能和Java原生的加法運算相比的,并沒有原生的效率高。
到此這篇關(guān)于Java利用位運算實現(xiàn)乘法運算詳解的文章就介紹到這了,更多相關(guān)Java位運算實現(xiàn)乘法運算內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
springboot登錄攔截器+ThreadLocal實現(xiàn)用戶信息存儲的實例代碼
ThreadLocal 為變量在每個線程中創(chuàng)建了一個副本,這樣每個線程都可以訪問自己內(nèi)部的副本變量,這篇文章主要介紹了springboot登錄攔截器+ThreadLocal實現(xiàn)用戶信息存儲的實例代碼,需要的朋友可以參考下2024-03-03
SpringBoot整合redis+Aop防止重復提交的實現(xiàn)
Spring Boot通過AOP可以實現(xiàn)防止表單重復提交,本文主要介紹了SpringBoot整合redis+Aop防止重復提交的實現(xiàn),文中通過示例代碼介紹的非常詳細,對大家的學習或者工作具有一定的參考學習價值,需要的朋友們下面隨著小編來一起學習學習吧2023-07-07
SpringBoot中實現(xiàn)Druid前端監(jiān)控界面自動登錄功能
這篇文章主要介紹了SpringBoot中實現(xiàn)Druid前端監(jiān)控界面自動登錄功能,需要的朋友可以參考下2024-08-08
java數(shù)據(jù)結(jié)構(gòu)排序算法之樹形選擇排序詳解
這篇文章主要介紹了java數(shù)據(jù)結(jié)構(gòu)排序算法之樹形選擇排序,結(jié)合具體實例形式分析了java樹形選擇排序的原理、實現(xiàn)技巧與相關(guān)注意事項,需要的朋友可以參考下2017-05-05
Resty開發(fā)restful版本的Jfinal深入研究
這篇文章主要為大家介紹了Resty開發(fā)restful版本的Jfinal深入研究有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進步,早日升職加薪2022-03-03

