Java利用位运算实现加减乘除的方法详解

 更新时间:2022年08月29日 15:29:08   作者:熬夜磕代码丶  
我们经常使用的加减乘除,我们所看到的只是表面的效果,那么加减乘除在底层究竟是怎么实现的?今天就让我们一探究竟

前言

我们经常使用的加减乘除,我们所看到的只是表面的效果,那么加减乘除在底层究竟是怎么实现的?今天就让我们一探究竟.今天用位运算实现的加减乘除不使用任何的加减乘除符号.

一、常见位运算

1. &运算

&运算二进制每一位全1为1,否则为0

public static void main(String[] args) {
        int a = 1;
        int b = 3;
        System.out.println(a & b);
    }

2. |运算

|运算二进制每一位有1为1,全0为0

public static void main(String[] args) {
        int a = 1;
        int b = 3;
        System.out.println(a | b);
    }

3. ^运算

^运算二进制每一位不同为1,相同为0

public static void main(String[] args) {
        int a = 1;
        int b = 3;
        System.out.println(a ^ b);
    }

4. ~运算

~运算是二进制每一位按位取反.

public static void main(String[] args) {
        int a = 1;
        System.out.println(~a);
    }

二、位运算实现加法

public static void main(String[] args) {
        int a = 1;
        int b = 3;
        System.out.println(a + b);
    }

下来我们用位运算实现一下加法.

我们进行一次异或运算就相当于进行一次无进位加法,那这样也不能实现加法,那我们得想办法,实现进位的数值.

进行一次与运算,只有同时为1才为1,也当同时为1时,我们需要进位,所以我们进行与运算后进行左移一位的操作,即可得到进位后的数值.

我们对异或运算和与运算后左移一位的结果进行相加即可,但我们只能进行位运算,所以我们只能再次进行异或运算与与运算,直到云运算的结果为0时,我们的异或运算的结果即为加法的结果.

public static int bitAdd(int a,int b) {
        int sum = 0;
        while(b != 0) {
            sum = a ^ b;
            b = (a & b) << 1;
            a = sum;
        }
        return sum;
    }

    public static void main(String[] args) {
        System.out.println(bitAdd(1,2));
    }

三、位运算实现减法

public static void main(String[] args) {
        int a = 1;
        int b = 3;
        System.out.println(a - b);
    }

下来我们用位运算实现一下减法.

在我们有了位运算实现加法的基础之后,我们的减法就变得简单了,a - b == a + ( -b ),所以我们只需要将b变为-b即可实现减法功能,但我们不能使用负号,那我们来用位运算来实现一下.

public static void main(String[] args) {
        System.out.println(~3);
    }

我们可以发现一个数取反与相反数差一,我们取反加一即可得到相反数.

public static void main(String[] args) {
        System.out.println(~3 + 1);
    }

public static int bitAdd(int a,int b) {
        int sum = 0;
        while(b != 0) {
            sum = a ^ b;
            b = (a & b) << 1;
            a = sum;
        }
        return sum;
    }

    public static int bitSub(int a,int b) {
        return bitAdd(a,~b+1);
    }

    public static void main(String[] args) {
        System.out.println(bitSub(1,3));
    }

四、位运算实现乘法

public static void main(String[] args) {
        int a = 1;
        int b = 3;
        System.out.println(a * b);
    }

我们小学的时候是怎么进行乘法的,按位相乘,每一位和每一位相乘.

二进制中也是一样的,按位相乘,如果被乘数二进制位是1则与乘数相乘.每次运算进行移位

public static int bitAdd(int a,int b) {
        int sum = 0;
        while(b != 0) {
            sum = a ^ b;
            b = (a & b) << 1;
            a = sum;
        }
        return sum;
    }
    public static int bitMul(int a,int b) {
        int sum = 0;
        while(b != 0) {
            if((b & 1) != 0) {
                sum += a;
            }
            a <<= 1;
            b >>>= 1;
        }
        return sum;
    }

    public static void main(String[] args) {
        System.out.println(bitMul(1,3));
    }

五、位运算实现除法

public static void main(String[] args) {
        int a = 7;
        int b = 2;
        System.out.println(a / b);
    }

我们在用位运算实现除法时,采用逆推的方式,a / b = c,

a = c * b。

我们只需要求出a减去b向左的移位,只要满足a <= b的移位即可,每次移动多少位即a / b的结果二进制中某一位为1,以此循环倒推即可.

public static int bitAdd(int a,int b) {
        int sum = 0;
        while(b != 0) {
            sum = a ^ b;
            b = (a & b) << 1;
            a = sum;
        }
        return sum;
    }
    public static int negNum(int n) {
        //转化为相反数
        return bitAdd(~n,1);
    }
    public static int minus(int a,int b) {
        //实现两个数相减
        return bitAdd(a,negNum(b));
    }
    public static boolean isNeg(int n) {
        //判断是否为负数
        return n < 0;
    }
    public static int bitDiv(int a,int b) {
        int x = isNeg(a) ? negNum(a) : a;
        int y = isNeg(b) ? negNum(b) : b;
        int res = 0;
        for (int i = 30; i >= 0 ; i = minus(i,1)) {
            if((x >> i) >= y) {
                res |= (1 << i);
                x = minus(x,y << i);
            }
        }
        return isNeg(a) != isNeg(b) ? negNum(res) : res;

    }

    public static void main(String[] args) {
        int a = 7;
        int b = 2;
        System.out.println(bitDiv(a,b));
    }

到此这篇关于Java利用位运算实现加减乘除的方法详解的文章就介绍到这了,更多相关Java位运算 加减乘除内容请搜索脚本之家以前的文章或继续浏览下面的相关文章希望大家以后多多支持脚本之家!

相关文章

  • Java简单实现动态代理模式过程解析

    Java简单实现动态代理模式过程解析

    这篇文章主要介绍了Java动态代理模式简单案例代码,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友可以参考下
    2020-07-07
  • Java spring AOP基础

    Java spring AOP基础

    本篇文章主要介绍了深入理解spring的AOP机制基础原理,小编觉得挺不错的,现在分享给大家,也给大家做个参考。一起跟随小编过来看看吧
    2021-11-11
  • Java中Arrays.sort()方法的比较器详解

    Java中Arrays.sort()方法的比较器详解

    这篇文章主要介绍了Java中Arrays.sort()方法的比较器详解,Arrays.sort(Object[] a)此方法看似没有要求我们实现比较器,对于基本数据类型,String类型确实如此,因为这些类型中已经自带了compareTo()方法,需要的朋友可以参考下
    2023-12-12
  • Spring5中SpringWebContext方法过时的解决方案

    Spring5中SpringWebContext方法过时的解决方案

    这篇文章主要介绍了Spring5中SpringWebContext方法过时的解决方案,具有很好的参考价值,希望对大家有所帮助。如有错误或未考虑完全的地方,望不吝赐教
    2022-01-01
  • idea中maven使用tomcat7插件运行run报错Could not start Tomcat问题

    idea中maven使用tomcat7插件运行run报错Could not start T

    这篇文章主要介绍了idea中maven使用tomcat7插件运行run报错Could not start Tomcat问题,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝赐教
    2024-09-09
  • Java中的自动装箱与自动拆箱的实现

    Java中的自动装箱与自动拆箱的实现

    自动装箱和自动拆箱使得我们在使用基本数据类型时更加方便,同时也提高了代码的可读性和健壮性,本文将详细介绍Java中的自动装箱和自动拆箱机制,感兴趣的可以了解一下
    2023-08-08
  • MyBatis的SQL执行结果和客户端执行结果不一致问题排查

    MyBatis的SQL执行结果和客户端执行结果不一致问题排查

    本文主要介绍了MyBatis的SQL执行结果和客户端执行结果不一致问题排查,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧
    2023-04-04
  • Spring AI源码分析流式回答(最新推荐)

    Spring AI源码分析流式回答(最新推荐)

    本文我们将重点讲解流式响应的概念与实现,毕竟,AI的流式回答功能与其交互体验密切相关,是提升用户满意度的重要组成部分,我们将通过代码示例来展示这一过程,帮助您更清晰地理解如何在实际应用中进行操作,感兴趣的朋友一起看看吧
    2024-11-11
  • Java中处理邮件附件的方法(本地文件和在线URL)

    Java中处理邮件附件的方法(本地文件和在线URL)

    这篇文章主要介绍了在Java中处理邮件附件的方法,针对本地文件和在线URL两种附件来源,提供了两种解决方案,并提供了下载文件和发送邮件的代码示例,需要的朋友可以参考下
    2025-03-03
  • Spring Boot DevTools 全局配置学习指南

    Spring Boot DevTools 全局配置学习指南

    这篇文章主要介绍了Spring Boot DevTools 全局配置,注意包括直接重启项目与devtools重启的区别,DevTools配置,DevTools全局配置及trigger-file控制重启行为的相关知识,需要的朋友可以参考下
    2022-03-03

最新评论