关于Java原子性操作的【错误】理解(赋值和自增自减)

关于Java原子性操作的【错误】理解(赋值和自增自减)

以下内容的错误之处

字节码并不是像其他原生程序构建产生的机器码一样,一条指令在CPU上就是执行一次,字节码需要JVM解析,一条字节码其实可能会对应多条CPU指令(具体取决于Java虚拟机的具体实现逻辑!!!),而原子操作要不一个操作可以在一条CPU指令执行完成,要不操作系统对这个操作做了处理,使其必须全部执行完毕,才能执行后续的其他操作。因此以下内容通过字节码来验证Java的原子性操作是完全错误的行为。

赋值操作是否是原子性?

不是,不管是基础数据类型还是引用数据类型,它都不是原子操作
【当然,如果以结果论的话,局部变量基本数据类型的赋值操作(long、double可能受到jvm、os等影响造成非原子性赋值),局部引用类型的null值赋值都是原子性的!】
int赋值int类型的赋值

booleanl类型的赋值
booleanl类型的赋值,果然JVM是将boolean当成int来处理呢,ture是1,false是0

double类型的赋值
double类型的赋值

引用类型的赋值
引用类型的赋值

由此可见,在Java中任何赋值操作都不是原子操作!它都具有先将被赋入的值加入到栈中,然后在赋值给变量。至于int a = b,这种方式的赋值则也不是原子操作,因为他需要先load b变量的值到栈中,然后在赋值给a,如下图所示:
int a = b
int a = b操作

自增自减操作是否是原子性的?

只有局部变量的int类型,且自增自减的幅度在-32768 ~ 32767时,局部变量的int类型的自增自减操作都是通过iinc或iinc_w一条指令完成的,而其他数据类型则一定需要有压栈、运算、存回的操作。

自增自减
局部变量int自增自减,幅度在-32768 ~ 32767

局部变量int自增自减,幅度超过-32768 ~ 32767
局部变量int自增自减,幅度超过-32768 ~ 32767

对象成员变量的自增自减操作
对象成员变量的自增自减操作

类变量的自增自减操作
类变量的自增自减操作

byte的自增自减操作
byte的自增自减操作

其他就不一一举例了,都是大同小异。

评论 6
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值