Android进程和线程 --消息队列模型--ThreadLocal (3)(2015-12-02 19:41)

来源:互联网 发布:淘宝商品降价提醒 编辑:程序博客网 时间:2024/06/07 12:29

ThreadLocal简介

  • 线程内部数据存储类
  • 不同的线程存储不同的数据副本时考虑用ThreadLocal
  • 数据是以线程为作用域
  • 应用场景
    • class下定义一个ThreadLocal对象mThreadLocal
    • 该类中开多了多个线程t1,t2,t3
    • t1 调用mThreadLocal.set(xxx) t2set(yyy) t3set(zzz)
    • get的时候 即mThreadLocal.get()该方法在不同的线程里面返回不同的值,即该线程对应的值

实现原理

  • ThreadLocal.Values localValues 存储线程的ThreadLocal数据
  • 底层是数组实现的
  • set即存数据时 把对应的线程和相应的值存放到数组中。
  • 值总是存放在数组中ThreadLocal的reference字段标识对象的下一个位置

set方法

 public void set(T value) {    Thread currentThread = Thread.currentThread();    Values values = values(currentThread);    if (values == null) {        values = initializeValues(currentThread);    }    values.put(this, value);}
  • 获取当前运行线程
  • 根据线程获取对应的数据,如果为空则初始化创建
  • put进数据

put方法

  void put(ThreadLocal<?> key, Object value) {        cleanUp();        // Keep track of first tombstone. That's where we want to go back        // and add an entry if necessary.        int firstTombstone = -1;        for (int index = key.hash & mask;; index = next(index)) {            Object k = table[index];            if (k == key.reference) {                // Replace existing entry.                table[index + 1] = value;                return;            }            if (k == null) {                if (firstTombstone == -1) {                    // Fill in null slot.                    table[index] = key.reference;                    table[index + 1] = value;                    size++;                    return;                }                // Go back and replace first tombstone.                table[firstTombstone] = key.reference;                table[firstTombstone + 1] = value;                tombstones--;                size++;                return;            }            // Remember first tombstone.            if (firstTombstone == -1 && k == TOMBSTONE) {                firstTombstone = index;            }        }    }
  • 不管如何key.reference存放在table中index位置
  • 则相应的value存放在index+1的下标索引

get方法

  public T get() {    // Optimized for the fast path.    Thread currentThread = Thread.currentThread();    Values values = values(currentThread);    if (values != null) {        Object[] table = values.table;        int index = hash & values.mask;        if (this.reference == table[index]) {            return (T) table[index + 1];        }    } else {        values = initializeValues(currentThread);    }    return (T) values.getAfterMiss(this);}
  • 获取当前线程
  • 取出table数组
  • 得到index
  • 取出index+1下标的值
0 0
原创粉丝点击