zoukankan      html  css  js  c++  java
  • 并发问题引出ThreadLocal

    ThreadLocal

    Thread-->人类
    Runnable-->任务类

    多线程并发问题引出ThreadLocal
    多线程并发问题的原因:
    操作同一个对象,对对象具有读写权限(只读如拍照,不会改变什么),几乎或者同时操作
    解决这个问题的常规方式:
    同步锁,synchronized代码块。
    我们知道,使用同步锁的时候,程序运行到这个地方就需要等待,成为一个串。十分影响效率。专业人士测试过,效率慢了100多倍
    那么如何解决并发问题呢?
    我们将并发问题的原因分离出来。有些操作是必须并发的,有些操作是因为资源的位置等原因出现并发问题的。只要不会修改原来数据的内容,我们为什么不可以给它一个映像呢?
    当然,绝对的并发就必须牺牲效率。

    ThreadLocal是什么?
    ThreadLocal是一个容器。它有三个方法:
    void set(T value):保存值
    T get():获取值
    void remove():移除值
    ThreadLocal内部其实是一个Map集合。虽然在使用ThreadLocal的时候只使用了值没有给出键,其实它内部使用了当前线程作为键
    Map map=new HashMap<Thread,T>

    package cn.itcast.thread;
    
    import java.util.HashMap;
    import java.util.Map;
    
    import org.junit.Test;
    
    public class Demo1 {
    
        @Test
        public void fun1(){
            final ThreadLocal<String> t1=new ThreadLocal<String>();
            t1.set("hello");
            System.out.println(t1.get());
            t1.remove();
            System.out.println(t1.get());
        }
        @Test
        public void fun2(){
            final ThreadLocal<String> t1=new ThreadLocal<String>();
            
            new Thread(){
                public void run(){
                    t1.set("内部类");
                    System.out.println(t1.get());
                }
            }.start();
            
            try {
                Thread.sleep(1000);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
            System.out.println(t1.get());
        }
        @Test
        public void fun3(){
            final Map<Thread,String> map=new HashMap<Thread,String>();
            map.put(Thread.currentThread(), "hello");
            System.out.println(map.get(Thread.currentThread()));
            
            new Thread(){
                public void run(){
                    System.out.println(Thread.currentThread().getName());
                    System.out.println(map.get(Thread.currentThread()));
                }
            }.start();
        }
    }
    
    /**
     * 它内部是一个Map
     */
    class TL<T>{
        private Map<Thread,T> map=new HashMap<Thread,T>();
        
        public void set(T data){
            map.put(Thread.currentThread(),data);
        }
        
        public T get(){
            return map.get(Thread.currentThread());
        }
        
        public void remove(){
            map.remove(Thread.currentThread());
        }
    }
    /**
     * ThreadLocal通常用在一个类的成员上
     * 多个线程访问它时,每个线程都有自己的副本,互不干扰
     * Hibernate中把Session放到了ThreadLocal中!
     */
    class User{
        private ThreadLocal<String> usernameT1=new ThreadLocal<String>();
    }
  • 相关阅读:
    高度地形Unity3D 通过代码导入自定义格式地形的方法
    初始化提交CI跟swfupload结合 出现302的解决方案
    文件信息我的学习生涯(Delphi篇) 11
    相机三星如果我可以设计HTC ONE的相机
    数据数据库Apache Derby数据库
    安装索引源码阅读工具 lxr 安装配置初探
    模板替换php实战 第三天
    应用程序安装实验四十六微软应用程序虚拟化之一APPV 5.1服务器部署
    函数应用SAEPython教程(一) 在SAE上进行Python的开发
    消息方法熬之滴水穿石:Delphi曾经的利器(5)
  • 原文地址:https://www.cnblogs.com/aigeileshei/p/5715108.html
Copyright © 2011-2022 走看看