1、局部变量传参
在多线程环境下,局部变量只有线程自己能看到, 不会影响其他线程, 而全局变量的修改必须加锁 。每个线程都有自己独立的数据,若线程要执行的操作中有很多的函数,这些函数之间都需要用到某些局部变量,那么就避免不了参数的传递,以普通的方式传递参数会十分的繁琐,特别是函数非常多了时候,一层一层传递参数参数更是让人无法忍受,从下面的例子就可以看出:
std是局部变量, 但是每个函数都要用它, 因此必须传进去:在多线程中,每个函数一层一层调用都这么传参数那还得了? 定义成全局变量也不行, 因为每个线程处理不同的Student对象, 不能共享,那该如何解决多线程参数传递的问题呢?
2、全局字典
如果使用一个全局dict存放所有的Student对象, 然后以thread本身作为key获得线程对应的Student对象如何?
可以看出,通过设置一个全局字典,以当前进程作为键,以当前进程的stu对象作为值,通过键值对的查找,也能达到在线程内部函数之间查看局部变量的目的。这种方式理论上是可行的, 它最大的优点是消除了std对象在每层函数中的传递问题, 但是, 每个函数获取std的代码有点low。
3、ThreadLoacl
ThreadLocal应运而生, 不用查找dict, ThreadLocal帮你自动做这件事。
说明:
全局变量local_stu就是一个ThreadLocal对象, 每个Thread对它都可以读写stu属性, 但互不影响。 你可以把local_stu看成全局变量, 但每个属性如local_stu.name都是线程的局部变量, 可以任意读写且互不干扰, 也不用管理锁的问题, ThreadLocal内部会处理。
可以理解为全局变量local_stu是一个dict, 不但可以绑定local_stu.name属性, 还可以绑定其他变量, 如local_stu.teacher等等。
ThreadLocal最常用的地方就是为每个线程绑定一个数据库连接, HTTP请求, 用户身份信息等, 这样一个线程的所有调用到的处理函数都可以非常方便地访问这些资源。
4. 总结
local对象虽然是全局变量, 但每个线程都能读写自身单个线程的独一副本, 互不干扰。ThreadLocal解决了参数在一个线程中各个函数之间互相传递的问题。
网友评论