java线程封闭

线程封闭概念

多线程访问共享可变数据时,涉及到线程间数据同步的问题,并不是所有时候,都要用到共享数据,所以线程封闭的概念就提出来了。
数据都封闭在各自的线程之中,就不需要同步,这种通过将数据封闭在线程中而避免使用同步的技术称为线程封闭。
线程封闭具体的体现有:ThreadLocal、局部变量。

ThreadLocal

ThreadLocal 是Java里一种特殊的变量。
它是一个线程级别变量,每个线程都有一个ThreadLocal,就是每个线程都拥有自己独立的一个变量,竞争条件被彻底消除了,在并发模式下是绝对安全的变量。
用法:ThreadLocal var = new ThreadLocal();
会自动在每一个线程上创建一个T的副本,副本直接彼此独立,互不影响。跟游戏副本一样。
可以用ThreadLocal存储一些参数,以便在线程中多个方法中使用,用来代替方法传参的做法。

package com.ly.study.base;

/** 线程封闭示例 */
public class ThreadLocalTestClass {
    /** threadLocal变量,每个线程都有一个副本,互不干扰 */
    public static ThreadLocal<String> value = new ThreadLocal<>();

    /**
     * threadlocal测试
     *
     * @throws Exception
     */
    public void threadLocalTest() throws Exception {

        // threadlocal线程封闭示例
        value.set("这是主线程设置的123"); // 主线程设置值
        String v = value.get();
        System.out.println("线程1执行之前,主线程取到的值:" + v);

        new Thread(new Runnable() {
            @Override
            public void run() {
                String v = value.get();
                System.out.println("线程1取到的值:" + v);
                // 设置 threadLocal
                value.set("这是线程1设置的456");

                v = value.get();
                System.out.println("重新设置之后,线程1取到的值:" + v);
                System.out.println("线程1执行结束");
            }
        }).start();

        Thread.sleep(5000L); // 等待所有线程执行结束

        v = value.get();
        System.out.println("线程1执行之后,主线程取到的值:" + v);

    }

    public static void main(String[] args) throws Exception {
        new ThreadLocalTestClass().threadLocalTest();
    }
}

如何实现的?

每个线程都有一个ThreadLocalMap 容器,ThreadLocal.ThreadLocalMap;以ThreadLocal对象本身做为key。

//创建容器
    void createMap(Thread t, T firstValue) {
        t.threadLocals = new ThreadLocalMap(this, firstValue);
    }
    //获取容器
    ThreadLocalMap getMap(Thread t) {
        return t.threadLocals;
    }

//设置值
    public void set(T value) {
    //取当前线程的threadLocals 
        Thread t = Thread.currentThread();
        ThreadLocalMap map = getMap(t);
        if (map != null)
            map.set(this, value);
        else
        //为空就创建容器
            createMap(t, value);
    }

    public T get() {
        Thread t = Thread.currentThread();
        ThreadLocalMap map = getMap(t);
        if (map != null) {
            ThreadLocalMap.Entry e = map.getEntry(this);
            if (e != null) {
                @SuppressWarnings("unchecked")
                T result = (T)e.value;
                return result;
            }
        }
        //设置初始值 默认为空,可重新setInitialValue方法设置初始值。
        return setInitialValue();
    }

    private T setInitialValue() {
    //重写 initialValue 方法可以设置初始值
        T value = initialValue();
        Thread t = Thread.currentThread();
        ThreadLocalMap map = getMap(t);
        if (map != null)
            map.set(this, value);
        else
        //容器没生成就创建容器
            createMap(t, value);
        return value;
    }

栈封闭

局部变量的固有属性之一就是封闭在线程中。他们位于执行线程的栈中,其他线程无法访问这个栈。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 5
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 5
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值