synchronized 同步的机制可以解决多线程并发问题,这种解决方案下,多个线程访问到的都是同一份变量的内容。为了防止在多线程访问的过程中,可能会出现的并发错误。不得不对多个线程的访问进行同步,这样也就意味着,多个线程必须先后对变量的值进行访问或者修改,这是一种以延长访问时间换取线程安全性的策略。

ThreadLocal类为每一个线程都维护了自己独有的变量拷贝。每个线程都拥有了自己独立的一个变量,竞争条件被彻底消除了,那就没有任何必要对这些线程进行同步,它们也能最大限度的由CPU调度,并发执行。由于每个线程在访问该变量时,读取和修改的,都是自己独有的那一份变量拷贝,变量被彻底封闭在每个访问的线程中,并发错误出现的可能也完全消除了。这是一种以空间来换取线程安全性的策略

ThreadLocal适用于资源共享但不需要维护状态的情况,也就是一个线程对资源的修改,不影响另一个线程的运行。

ThreadLocal类接口说明:

  • void set(Object value)

    • 设置当前线程的线程局部变量的值。
  • public Object get()             
    • 返回当前线程所对应的线程局部变量。
  • protected Object initialValue()          
    • 返回该线程局部变量的初始值,该方法为了让子类覆盖而设计的。
    • 这个方法在线程第1次调用get()或set(Object)时才执行,并且仅执行1次。
    • ThreadLocal中的缺省实现直接返回一个null。
  • public void remove()                       
    • 将当前线程局部变量的值删除,目的是为了加快内存回收的速度,减少内存的占用。

每个Thread都有自己独立的ThreadLocalMap对象,用来存放各自独立的对象集合。

在ThreadLocalMap中是以ThreadLocal作为key存储的,所以一个ThreadLocal代表一个隔离变量。

我们无法直接操纵ThreadLocalMap对象,只能通过ThreadLocal对象用来维护ThreadLocalMap中的变量。

示意图:

ThreadLocal示例

package org.apollo.demo01.demo;

public class ThreadLocalDemo {

    static class Countor{

        ThreadLocal<Integer> threadLocal1=new ThreadLocal<Integer>(){
protected Integer initialValue() {
return 0;
};
};
/**
* 往ThreadLocalMap中放入Integer用来计数
*/
public void add(){
Integer i=threadLocal1.get();
i++;
threadLocal1.set(i);
}
public void print(){
Integer i=threadLocal1.get();
System.out.println(i);
}
}
public static void main(String[] args) { Runnable runnable=new Runnable() { Countor countor=new Countor();
public void run() {
for(int i=0;i<10;i++){
//多个线程共享countor变量,但不共享计数,计数器会为每个线程单独计数
countor.add();
countor.print();
}
}
};
for(int i=0;i<3;i++){
Thread t=new Thread(runnable);
t.start();
} }
}

ThreadLocal 笔记的更多相关文章

  1. ThreadLocal笔记

    1.ThreadLocal的作用是什么?        ThreadLocal是一个泛型类,将保存在其中的值与当前的线程关联起来,这样每个线程看到的值对于其他线程来说都是不可见的,这个技术被称为线程封 ...

  2. ThreadLocal 的机制与内存泄漏

    ThreadLocal笔记 如上图所示 每个Thread 都有一个map,里面存着Entry<Key,value>,而key是实现了WeakReference的ThreadLocal,如果 ...

  3. java笔记--用ThreadLocal管理线程,Callable<V>接口实现有返回值的线程

    用ThreadLocal管理线程,Callable<V>接口实现有返回值的线程 ThreadLocal在我的笔记"关于线程同步"的第5种方式里面有介绍,这里就不多说了. ...

  4. 多线程学习笔记九之ThreadLocal

    目录 多线程学习笔记九之ThreadLocal 简介 类结构 源码分析 ThreadLocalMap set(T value) get() remove() 为什么ThreadLocalMap的键是W ...

  5. 并发编程学习笔记(8)----ThreadLocal的使用及源码分析

    1. ThreadLocal的理解 ThreadLocal,顾名思义,就是线程的本地变量,ThreadLocal会为每个线程创建一个本地变量副本,使得使用ThreadLocal管理的变量在多线程的环境 ...

  6. SpringMVC:学习笔记(12)——ThreadLocal实现会话共享

    SpringMVC:学习笔记(12)——ThreadLocal实现会话共享 ThreadLocal ThreadLocal,被称为线程局部变量.在并发编程的情况下,使用ThreadLocal创建的变量 ...

  7. 0041 Java学习笔记-多线程-线程池、ForkJoinPool、ThreadLocal

    什么是线程池 创建线程,因为涉及到跟操作系统交互,比较耗费资源.如果要创建大量的线程,而每个线程的生存期又很短,这时候就应该使用线程池了,就像数据库的连接池一样,预先开启一定数量的线程,有任务了就将任 ...

  8. ThreadLocal类学习笔记

    这个类在java1.2中就出现了,线程独有的变量(每个线程都有一份变量),使用它的好处之一就是可以少传许多参数. 在哪里用到它呢?有连接池的地方就有它的身影,连接池包括数据库连接池,网络连接池等. i ...

  9. java concurrency in practice读书笔记---ThreadLocal原理

    ThreadLocal这个类很强大,用处十分广泛,可以解决多线程之间共享变量问题,那么ThreadLocal的原理是什么样呢?源代码最能说明问题! public class ThreadLocal&l ...

随机推荐

  1. eclipse安装CDT插件遇到的问题

    转自eclipse安装CDT插件遇到的问题 已经安装了集成java版本的eclipse,eclipse-java-indigo-SR1-win32.zip,在添加CDT插件时,遇到了问题. cdt-m ...

  2. [转贴]怎样在LINQ实现 LEFT JOIN 或者RIGHT JOIN

    In this post let us see how we can handle Left Join and Right Join when using LINQ. There are no key ...

  3. Python自然语言处理学习笔记(69)

    http://www.cnblogs.com/yuxc/archive/2012/02/09/2344474.html Chapter8    Analyzing Sentence Structure ...

  4. C++ Prime:指针和const

    与引用一样,也可以令指针指向常量或非常量,类似于常量引用,指向常量的指针不能用于改变其所指对象的值.要想存放常量对象的地址,只能使用指向常量的指针: const double pi = 3.14; / ...

  5. [LeetCode#156] Binary Tree Upside Down

    Problem: Given a binary tree where all the right nodes are either leaf nodes with a sibling (a left ...

  6. C#实例:5个.net经典例子(窗体与界面设计)

    实例001  带历史信息的菜单 实例说明 在开发图纸管理软件时,要求在菜单上记录用户最近打开的档案或图纸,以方便下次使用.如图1.1所示,单击“文件”菜单下的“打开文件”子菜单,打开需要查阅的图纸.下 ...

  7. oracle 大表删除数据后,回收空间的问题。

    在oracle中由于表结构设计不合理或者需要清楚老数据的时候,经常需要对大表数据进行清理. 一般有一下几种方法: 1. 删除大部分数据,留下小部分数据.我们可以把需要保留的数据转移到别的表,然后再把大 ...

  8. createElement

    <!DOCTYPE html> <html> <head> <meta charset="utf-8"> <title> ...

  9. PrintWriter out = response.getWriter() 输出中文乱码问题

    HttpServletResponse response = ServletActionContext.getResponse();        response.setCharacterEncod ...

  10. 【Android 复习】:Android五种布局的使用方法

    ---恢复内容开始--- 在Android布局中,有五种常用的布局,下面我们就来学习一下这几种布局的使用方式 1) 线性布局:LinearLayout 2) 帧布局:  FrameLayout 3)  ...