线程本地存储(TLS:Thread Local Storage)
线程本地存储
这就简单的说明一下,有机会再详细的写,~(∠・ω< )⌒★
一、定义
在一个进程中,所有线程的堆内存是共享的(栈除外,线程的栈内存是相互隔离的)。线程局部存储技术是使每个线程与其它线程数据存储隔离。
.Net 提供了三个用于线程本地存储的方法 - 线程的静态字段(ThreadStatic) - ThreadLocal - 数据槽(LocalDataStoreSlot )
二、三种方法
线程的静态字段(ThreadStatic)
关键词:[ThreadStatic]
使用ThreadStaticAttribute标记的static字段 不会在线程之间共享。 每个执行线程都有单独的字段实例,并分别设置和获取该字段的值。 如果在不同的线程上访问该字段,则该字段将包含不同的值。
下面是使用案例:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27
| class Programe { [ThreadStatic] public static string Username = ""; static void Main() {
Username = "mainthread"; Thread thread1 = new Thread(() => { Username = "thread1"; Console.WriteLine($"Username:{Username}"); }); Thread thread2 = new Thread(() => { Username = "thread2"; Console.WriteLine($"Username:{Username}"); }); Thread thread3 = new Thread(() => { Username = "thread3"; Console.WriteLine($"Username:{Username}"); }); thread1.Start(); thread2.Start(); thread3.Start();
Console.WriteLine($"Username:{Username}"); } }
|
数据槽
据说用的不多,暂时先不写了 欸嘿~ 一般可以用ThreadLocal 类代替(ai说的)
ThreadLocal 类
这个类相当于将一个变量的值封装到这类中,各个线程在使用这个类型的时候,是各自独立的。
该类包装过的类型变量的只能在该线程中使用,其他线程包括子线程无法使用。即:
- 因为每个 Thread 内有自己的实例副本,且该副本只能由当前 Thread 使用。这是也是 ThreadLocal 命名的由来。
- 既然每个 Thread 有自己的实例副本,且其它 Thread 不可访问,那就不存在多线程间共享的问题。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15
| static void Main(string[] args) { ThreadLocal<int> threadLocal = new ThreadLocal<int>(); threadLocal.Value = 1; new Thread(() => Console.WriteLine($"托管线程ID:{Thread.CurrentThread.ManagedThreadId} 值为:{threadLocal.Value++}")).Start(); new Thread(() => Console.WriteLine($"托管线程ID:{Thread.CurrentThread.ManagedThreadId} 值为:{threadLocal.Value++}")).Start(); new Thread(() => Console.WriteLine($"托管线程ID:{Thread.CurrentThread.ManagedThreadId} 值为:{threadLocal.Value++}")).Start(); Console.WriteLine($"主线程ID:{Thread.CurrentThread.ManagedThreadId} 值为:{threadLocal.Value}"); }
|