[读书笔记]一些小记

以下内容大多来自周志明的《深入理解Java虚拟机》。

1. 线程本地存储Thread Local Storage

一个请求对应一个服务器线程,很多web服务端应用都可以使用线程本地存储来解决线程安全问题。每一个线程的Thread对象中都有一个ThreadLocalMap对象,这个对象存储了一组以ThreadLocal.threadLocalHashCode为键,以本地线程变量为值的K-V值对,ThreadLocal对象就是当前线程的ThreadLocalMap的访问入口,每一个ThreadLocal对象都包含了一个独一无二的threadLocalHashCode值,使用这个值就可以在线程k-v值对中找回对应的线程变量。

我们可以使用ThreadLocal把上下文信息存储的线程本地存储中,而不会和其他线程冲突。

 2. 原子性

    public static AtomicInteger race = new AtomicInteger(0);

    public static void increase() {
        race.incrementAndGet();
    }

    private static final int ThreadsCnt = 20;

    public static void main(String[] args) {
        Thread[] threads = new Thread[ThreadsCnt];
        for (int i = 0; i < ThreadsCnt; i++) {
            threads[i] = new Thread(new Runnable() {
                @Override
                public void run() {
                    for(int j = 0; j < 10000; j++) {
                        increase();
                    }
                }
            });
            threads[i].start();
        }

        while (Thread.activeCount() > 1) {
            Thread.yield();
        }
        System.out.println(race);
}

输出:

200000

  incrementAndGet原子操作,20个线程,每个线程1000次操作后,最后的结果是20000,保证了正确的结果。

  尽管CAS看起来很美,但是这种操作无法涵盖互斥同步的所有使用场景,并且CAS从语义上来说并不是完美的,存在这样一个逻辑漏洞:

  如果一个变量V初次读取的时候是A值,那我们就能说它的值没有被其他线程变过吗?如果这段期间它的值被改成了B,后来又被改回A,那CAS操作就会误认为它从来没有被改变过。这个漏洞称为CAS操作的ABA问题。J.U.C包为了解决这个问题,提供了一个带有标记的原子引用类"AtomicStampedReference",它可以通过控制变量值的版本来保证CAS的正确性。不过目前来说这个类比较鸡肋,大部分情况下ABA问题不会影响程序并发的正确性,如果需要解决ABA的问题,改用传统的互斥同步可能会比原子类更高效。

  以上内容来自原著,但是原著里incrementAndGet方法的源代码和我测试时候的源代码不同,1.7和1.8中的实现方式已经不同了,1.8是:

 /**
     * Atomically increments by one the current value.
     *
     * @return the updated value
     */
    public final int incrementAndGet() {
        return unsafe.getAndAddInt(this, valueOffset, 1) + 1;
    }

  之所以提到原子操作是因为原著提到了线程安全的实现方式。

  1. 互斥同步 悲观锁

    在java中,最基本的互斥同步手段就是synchonized关键词。原著中还提到了一个java.util.concurrent包中的重入锁ReentrantLock,有一点区别,这里就不陈述了。参考资料:http://tenyears.iteye.com/blog/48750

  2. 非阻塞同步 乐观锁

    需要硬件支持。乐观锁就是通过原子操作来实现的。

 

    

 

posted on 2016-05-07 15:04  往边界  阅读(199)  评论(0编辑  收藏  举报

导航