加入收藏 | 设为首页 | 会员中心 | 我要投稿 湖南网 (https://www.hunanwang.cn/)- 科技、建站、经验、云计算、5G、大数据,站长网!
当前位置: 首页 > 教程 > 正文

正确领略Thread Local的道理与合用场景

发布时间:2018-08-17 13:17:49 所属栏目:教程 来源:郭俊
导读:技能沙龙 | 邀您于8月25日与国美/AWS/转转三位专家配合切磋小措施电商拭魅战 一、ThreadLocal办理什么题目 因为 ThreadLocal 支持范型,如 ThreadLocal StringBuilder ,为表述利便,后文用 变量 代表 ThreadLocal 自己,而用 实例 代表详细范例(如 StringBui
副问题[/!--empirenews.page--] 技能沙龙 | 邀您于8月25日与国美/AWS/转转三位专家配合切磋小措施电商拭魅战

一、ThreadLocal办理什么题目

因为 ThreadLocal 支持范型,如 ThreadLocal< StringBuilder >,为表述利便,后文用 变量 代表 ThreadLocal 自己,而用 实例 代表详细范例(如 StringBuidler )的实例。

1. 不适当的领略

写这篇文章的一个缘故起因在于,网上许多博客关于 ThreadLocal 的合用场景以及办理的题目,描写的并不清晰,乃至是错的。下面是常见的对付 ThreadLocal的先容

  • ThreadLocal为办理多线程措施的并发题目提供了一种新的思绪
  • ThreadLocal的目标是为了办理多线程会见资源时的共享题目

尚有许多文章在比拟 ThreadLocal 与 synchronize 的异同。既然是作较量,那应该是以为这两者办理沟通或相同的题目。

上面的描写,题目在于,ThreadLocal 并不办理多线程 共享 变量的题目。既然变量不共享,那就更谈不上同步的题目。

2. 公道的领略

ThreadLoal 变量,它的根基道理是,统一个 ThreadLocal 所包括的工具(对ThreadLocal< String >而言即为 String 范例变量),在差异的 Thread 中有差异的副本(现实是差异的实例,后文会具体叙述)。这里有几点必要留意

  • 由于每个 Thread 内有本身的实例副本,且该副本只能由当前 Thread 行使。这是也是 ThreadLocal 定名的由来
  • 既然每个 Thread 有本身的实例副本,且其余 Thread 不行会见,那就不存在多线程间共享的题目
  • 既无共享,何来同步题目,又何来办理同步题目一说?

那 ThreadLocal 到底办理了什么题目,又合用于什么样的场景?

焦点意思是

总的来说,ThreadLocal 合用于每个线程必要本身独立的实例且该实例必要在多个要领中被行使,也即变量在线程中断绝而在要领或类间共享的场景。后文会通过实例具体叙述该概念。其它,该场景下,并非必需行使 ThreadLocal ,其余方法完全可以实现同样的结果,只是 ThreadLocal 使得实现更简捷。

二、ThreadLocal用法

1. 实例代码

下面通过如下代码声名 ThreadLocal 的行使方法

  1. public class ThreadLocalDemo { 
  2.   public static void main(String[] args) throws InterruptedException { 
  3.     int threads = 3; 
  4.     CountDownLatch countDownLatch = new CountDownLatch(threads); 
  5.     InnerClass innerClass = new InnerClass(); 
  6.     for(int i = 1; i <= threads; i++) { 
  7.       new Thread(() -> { 
  8.         for(int j = 0; j < 4; j++) { 
  9.           innerClass.add(String.valueOf(j)); 
  10.           innerClass.print(); 
  11.         } 
  12.         innerClass.set("hello world"); 
  13.         countDownLatch.countDown(); 
  14.       }, "thread - " + i).start(); 
  15.     } 
  16.     countDownLatch.await(); 
  17.   } 
  18.   private static class InnerClass { 
  19.     public void add(String newStr) { 
  20.       StringBuilder str = Counter.counter.get(); 
  21.       Counter.counter.set(str.append(newStr)); 
  22.     } 
  23.     public void print() { 
  24.       System.out.printf("Thread name:%s , ThreadLocal hashcode:%s, Instance hashcode:%s, Value:%sn", 
  25.       Thread.currentThread().getName(), 
  26.       Counter.counter.hashCode(), 
  27.       Counter.counter.get().hashCode(), 
  28.       Counter.counter.get().toString()); 
  29.     } 
  30.     public void set(String words) { 
  31.       Counter.counter.set(new StringBuilder(words)); 
  32.       System.out.printf("Set, Thread name:%s , ThreadLocal hashcode:%s,  Instance hashcode:%s, Value:%sn", 
  33.       Thread.currentThread().getName(), 
  34.       Counter.counter.hashCode(), 
  35.       Counter.counter.get().hashCode(), 
  36.       Counter.counter.get().toString()); 
  37.     } 
  38.   } 
  39.   private static class Counter { 
  40.     private static ThreadLocal<StringBuilder> counter = new ThreadLocal<StringBuilder>() { 
  41.       @Override 
  42.       protected StringBuilder initialValue() { 
  43.         return new StringBuilder(); 
  44.       } 
  45.     }; 
  46.   } 

2. 实例说明

(编辑:湖南网)

【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容!

热点阅读