当前位置: 首页 > news >正文

vi企业设计/快速排名seo软件

vi企业设计,快速排名seo软件,北京做网站企业,珠海婚恋网站建设市场分析首先再讨论题主的这个观点之前我们要明确一下ThreadLocal的用途是什么? ThreadLocal并不是用来解决共享对象的多线程访问问题。 看了许多有关ThreadLocal的博客,看完之后会给人一种错觉,ThreadLocal就是用于在多线程情况下防止共享对象的线程…

首先再讨论题主的这个观点之前我们要明确一下ThreadLocal的用途是什么?

ThreadLocal并不是用来解决共享对象的多线程访问问题。

看了许多有关ThreadLocal的博客,看完之后会给人一种错觉,ThreadLocal就是用于在多线程情况下防止共享对象的线程安全问题,使用ThreadLocal之后,ThreadLocal的对象就不会有线程安全问题,但是一定是这样么,看如下代码

  1. public class test {
  2. public static void main(String[] args) throws InterruptedException {
  3. new A().start();
  4. new A().start();
  5. new A().start();
  6. new A().start();
  7. }
  8. static class A extends Thread {
  9. static List<Integer> list = new ArrayList<>(Arrays.asList(1, 2, 3, 4, 5));
  10. static ThreadLocal<List<Integer>> threadLocal = new ThreadLocal<List<Integer>>() {
  11. @Override
  12. protected List<Integer> initialValue() {
  13. return list;
  14. }
  15. };
  16. @Override
  17. public void run() {
  18. List<Integer> threadList = threadLocal.get();
  19. threadList.add(threadList.size());
  20. System.out.println(threadList.toString());
  21. }
  22. }
  23. }

该代码很简单,就是在多线程的情况下输出ThreadLocal的list集合状态,如果此时线程安全的话,输出的4个语句应该是完全一样的输出结果如下:

[1, 2, 3, 4, 5, 5]
[1, 2, 3, 4, 5, 5, 6]
[1, 2, 3, 4, 5, 5, 6, 7]

[1, 2, 3, 4, 5, 5, 6, 7, 8]

 

很明显可以看到,线程是不安全的,从结果也能看出来4个线程中ThreadLocal中的List是同一个对象,被四个线程所共享。

接下来我们分析一下原因的发生原因,我们去看ThreadLocal的get()方法

  1. public T get() {
  2. Thread t = Thread.currentThread();
  3. ThreadLocalMap map = getMap(t);
  4. if (map != null) {
  5. ThreadLocalMap.Entry e = map.getEntry(this);
  6. if (e != null) {
  7. @SuppressWarnings("unchecked")
  8. T result = (T)e.value;
  9. return result;
  10. }
  11. }
  12. return setInitialValue();
  13. }

如果一个线程第一次调用threadLocal.get()方法时,我们通过调试可以发现此时拿到的map是null,会调用setInitialValue(),继续看该方法

  1. private T setInitialValue() {
  2. T value = initialValue();
  3. Thread t = Thread.currentThread();
  4. ThreadLocalMap map = getMap(t);
  5. if (map != null)
  6. map.set(this, value);
  7. else
  8. createMap(t, value);
  9. return value;
  10. }

可以看到这个方法里面有一个value,而这个value就是ThreadLocal中即将要保存的只对线程所见的"副本",而这个value使用过initialValue()方法得到的,这个方法如果你没有重写的话默认返回时一个null,而在我们的例子当中他返回的是我们定义的静态变量list,而这个list是一个单例的(只会被类第一次访问时进行初始化),也就是说我们的例子中每个线程的ThreadLocal里面get的都是同一个list,所以就造成了线程安全的问题.

接下来改善一下我们的代码

  1. static class A extends Thread {
  2. static ThreadLocal<List<Integer>> threadLocal = new ThreadLocal<List<Integer>>() {
  3. @Override
  4. protected List<Integer> initialValue() {
  5. return new ArrayList<>(Arrays.asList(1, 2, 3, 4, 5));
  6. }
  7. };
  8. @Override
  9. public void run() {
  10. List<Integer> threadList = threadLocal.get();
  11. threadList.add(threadList.size());
  12. System.out.println(threadList.toString());
  13. }
  14. }

运行结果

[1, 2, 3, 4, 5, 5]
[1, 2, 3, 4, 5, 5]

[1, 2, 3, 4, 5, 5]

[1, 2, 3, 4, 5, 5]

 

接下来回到主题,ThreadLocal的作用是什么:

ThreadLocal使得各线程能够保持各自独立的一个对象,而实现原理其实是通过,每个线程都会重新创建一个对象,不是什么对象的拷贝或副本,而线程是否安全取决于你如何去创建这个对象。

然后总结一下:

1.ThreadLocal作用不是为了解决共享对象的多线程安全问题,而是为了避免通多参数传递的方式去拿到一个对象,网上有些例子就一开始拿线程安全举例子,然后抛砖引玉出ThreadLocal,会把人带偏。。。博主就是一个。

2.ThreadLocal中保存的不是什么对象的副本,里面没有需要保存的对象做任何复制,拷贝操作,这个对象完全取决于你的iniialtValue方法中如何去创建,所以这里需要考虑使用ThreadLocal的性能问题,是否会大量创建一个对象。

转载于:https://www.cnblogs.com/moxiaotao/p/9632914.html

http://www.jmfq.cn/news/5019553.html

相关文章:

  • 什么是a站/百度竞价怎么开户
  • 上海公司会计外包/苏州吴中区seo关键词优化排名
  • 专业做视频的网站有哪些内容/网站关键词怎么添加
  • 快速学习网站制作/站长分析工具
  • 自做美食哪些网站/苏州seo关键词优化外包
  • 湖北网站建设哪家有/无锡哪里有做网站的
  • 网页前端模板网站/百度指数官网首页
  • 做表格的网站/北京seo收费
  • 佛山伦教网站设计/百度代理服务器
  • 有没有专门做装修的网站/网络优化工程师招聘信息
  • 深圳网站建设服务中心/seo网站优化流程
  • 企业网站制作/网站自动收录
  • 网站要素的优化设计/互联网营销专家
  • 紧急通知页面升级/百度seo优化排名如何
  • 武进网站建设好么/营销推广费用预算表
  • 广州网站设计公司兴田德润在那里/怎样把个人介绍放到百度
  • 企业注册资金/北京网站优化技术
  • 免费招聘网站平台有哪些/杭州免费网站制作
  • 一个网站里有两个网页怎么做/网络营销买什么好
  • 合肥营销网站建设联系方式/推广方案怎么写
  • 聊城网站优化公司/灵宝seo公司
  • 注册域名之后怎么建网站/徐州网站建设方案优化
  • 抓好党建网站联盟建设/seo课程哪个好
  • 做网站如何与网络公司沟通/百度收录情况查询
  • 百度收录网站链接入口/百度网盘链接
  • wordpress表白源码/seo分析
  • 网站编辑是什么工作/自媒体怎么做
  • wordpress有趣的插件/seo推广论坛
  • 开发网站用什么语言好/如何做好seo基础优化
  • 科技论文发表网/福州seo网站排名