JAVA并发编程笔记(2)

可见性

Visibility这玩意儿很微妙,很容易违反直觉。要在多线程之间读写内存保证可见性,需要使用同步:always use the proper synchronization whenever data is shared across threads.

Stale Data
public class MutableInteger {
    private int value;

    public int  get() { return value; }
    public void set(int value) { this.value = value; }
}

对于这个程序,即使对setter方法加上同步也是不够的,其它读的线程依然可能读到修改之前或之后的数据。

对于64位的数字型变量,double或long,则不止是stale data的问题,因为JVM会将64位的读写操作分成两个32位的操作。所以有可能读到完全错误的数据。

锁和可见性

可以用锁来保证可见性。Locking is not just about mutual exclusion; it is also about memory visibility. To ensure that all threads see the most up-to-date values of shared mutable variables, the reading and writing threads must synchronize on a common lock.

image

Volatile变量

也可以用volatile来保证可见性。要使用volatile变量,必须满足下面三个条件

  1. Writes to the variable do not depend on its current value, or you can ensure that only a single thread ever updates the value;
  2. The variable does not participate in invariants with other state variables; and
  3. Locking is not required for any other reason while the variable is being accessed.

锁既能保证原子性又能保证可见性,而volatile只能保证可见性。volatile最常用在表示完成、中断或者状态这样的标志位上。volatile不能保证像count++这种计数器的作用,除非能肯定只有一个线程去更新它。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值