线程
线程有一个优先级、实际上正在处理的程序的位置计数器、一个存储其局部变量的栈
每个线程都有自己的栈,但程序代码的内存和堆由一个进程的所有线程共享
异步委托
创建线程的一种简单方式是定义一个委托,并异步调用它
投票 所创建的Delegate类提供了BeginInvoke()方法,BeginInvoke()方法总是有AsyncCallback和object类型的俩个额外参数
等待异步委托的结果的另一种方式是使用与IAsyncResult相关联的等待句柄
等待委托的结果的第三种方式是异步回调
Thread类
使用Thread类可以创建和控制线程
Thread类的构造函数重载为接受ThreadStart和ParameterizedThreadStart类型的委托参数
ThreadStart委托定义了一个返回类型为void的无参数方法
在创建了Thread对象后,就可以用Start()方法启动线程
给线程传递数据可以采用俩种方式。一种方式是使用带ParameterizedThreadStart委托参数的Thread构造函数
另一种方式是创建一个自定义类,把线程的方法定义为实例方法,这样就可以初始化实例的数据,之后启动线程
在默认情况下,用Thread类创建的线程是前台线程。
线程池中的线程总是后台线程
设置IsBackground属性,确定是前台线程还是后台线程
设置Priority属性,线程的优先级
Thread.ThreadState属性 线程状态
Thread.Sleep()、Thread.Abort()、Thread.Join()
线程池
由ThreadPool类托管
.线程池中的所有线程都是后台线程。如果进程的所有前台线程都结束了,所有的后台线程就会停止。不能把入池的线程改为前台线程。
.不能给入池的线程设置优先级或名称
.对于COM对象,入池的所有线程都是多线程单元(multithreaded apartment,MTA)线程。许多COM对象都需要单线程单元(single-threaded apartment,MTA)线程
.入池的线程只能用于时间较短的任务。如果线程一直要运行,就应使用thread类创建一个线程
任务
.NET 4包含新名称空间 System.Threading.Tasks
要启动任务,可以使用TaskFactory类或Task类的构造函数和Start()方法
Parallel类
在.NET 4中,另一个新增的抽象线程是Parallel类。
取消架构
.NET 4包含一个新的取消架构,允许以标准方式取消长时间运行的任务。
线程问题
如果两个或多个线程访问相同的对象,或者访问不同步的共享状态,就会出现争用条件
在死锁中,至少有俩个线程被挂起,并等待对象解除锁定
同步
C#为多个线程的同步提供了自己的关键字:lock语句。
WaitHandle是一个抽象基类,用于等待一个信号的设置。
Timer类
System.Threading名称空间中的Timer类提供了核心功能。在构造函数中,可以传递一个委托,该委托应按照指定的时间间隔调用。
System.Timers名称空间中的Timer类是一个组件,因为它派生自Component基类。
因此,可以把它从工具箱拖放到服务器应用程序的手机界面上。这个Timer类使用System.Threading.Timer,但提供了基于时间的机制,而不是基于委托的机制。
基于事件的异步模式
BackgroundWorker类是异步事件模式的一种实现方案。