编辑
2025-09-24
C#
00

摘要

在C#中,线程同步是一种机制,用于控制多个线程访问共享资源的顺序,以避免数据竞争和不一致性问题。C#提供了多种线程同步技术,包括但不限于锁(lock)、监视器(Monitor)、信号量(Semaphore)、事件(EventWaitHandle、AutoResetEvent、ManualResetEvent)和互斥体(Mutex)。

正文

AutoResetEvent

AutoResetEvent是.net线程简易同步方法中的一种。AutoResetEvent 常常被用来在两个线程之间进行信号发送

两个线程共享相同的AutoResetEvent对象,线程1可以通过调用AutoResetEvent对象的WaitOne()方法进入等待状态,然后另外一个线程2通过调用AutoResetEvent对象的Set()方法取消等待的状态。

AutoResetEvent如何工作的

在内存中保持着一个bool值,如果bool值为False,则使线程阻塞,反之,如果bool值为True,则使线程退出阻塞。当我们创建AutoResetEvent对象的实例时,我们在函数构造中传递默认的bool值,以下是实例化AutoResetEvent的例子。

WaitOne 方法

该方法阻止当前线程继续执行,并使线程进入等待状态以获取其他线程发送的信号。WaitOne将当前线程置于一个休眠的线程状态。WaitOne方法收到信号后将返回True,否则将返回False。

编辑
2025-09-24
C#
00

摘要

线程死锁通常发生在两个或更多的线程因为互相等待对方释放资源而无限期阻塞的情况。在C#中,死锁通常涉及到几种共享资源(例如锁、文件、数据库连接等)和线程之间的相互作用。造成线程死锁的原因主要包括以下几点:

  1. 相互排斥:每个资源要么已经分配给一个线程,要么就是可用的。如果一个资源已经分配给了一个线程,其他的线程就必须等待直到资源被释放。
  2. 占有和等待:一个线程至少已经持有一个资源,并且正在等待获取额外的资源,而这些额外的资源可能被其他线程占有。
  3. 非抢占:资源只能由占有它的线程自愿释放,不能被抢占。
  4. 循环等待:存在一种线程的等待循环,其中每个线程都在等待另一个线程所占有的资源。这形成了一个循环链,其中每个线程都在等待下一个线程释放资源。

正文

举例说明

假设有两个线程(线程A和线程B)以及两个资源(资源1和资源2)。线程A已经占有资源1,并且想要获取资源2。同时,线程B已经占有资源2,并且想要获取资源1。如果线程A和线程B都不释放它们各自已经占有的资源,那么它们都将无限期地等待对方,从而造成死锁。

如何避免死锁

  • 避免占有和等待:一种方法是确保线程在开始执行前一次性获取所有需要的资源。
  • 使用超时:在尝试获取资源时使用超时,这样线程在等待过长时间后可以放弃,释放已持有的资源,然后重试。
  • 资源排序:对资源进行排序,并强制每个线程按照相同的顺序请求资源,这可以避免循环等待的条件。
  • 使用锁的层级结构:通过定义锁的层级结构,并且规定线程可以按照从低到高的顺序获取锁,但不能反过来,以此来避免死锁。
编辑
2025-09-24
C#
00

摘要

启动线程的时候需要向线程函数中传递参数,一般有三种方式。

  • 将线程函数声明为一个类的成员函数,通过类的成员变量来传递参数。
  • 声明一个静态函数当作线程的执行函数,该函数接受一个object类型的参数param,这个参数可以通过Thread.Start(param)传递到线程中。
  • 通过lambda表达式的闭包机制传递参数。

正文

用object 传参数

image.png

编辑
2025-09-24
C#
00

摘要

在C#中,线程的生命周期是由多个状态组成的,这些状态包括线程的创建、启动、挂起、等待、恢复和终止。

正文

1. 创建线程

线程的生命周期从创建开始。在C#中,可以通过System.Threading.Thread类的实例化来创建一个线程。创建线程时,需要指定一个将在该线程上执行的方法。

C#
Thread myThread = new Thread(new ThreadStart(MyMethod));
编辑
2025-09-24
C#
00

摘要

线程可以理解为程序执行的路径。一个程序(进程)可以包含多个线程,这些线程可以并发(同时)执行,共享进程的资源(如内存空间)。每个线程都有自己的执行路径,以及执行上下文(如线程的堆栈、寄存器状态等)。在.NET中,System.Threading命名空间提供了创建和控制线程的类和接口。

正文

应用场景

  1. 并行计算:当需要执行大量的、独立的计算时,可以将这些计算分配到多个线程中并行执行,以缩短总的执行时间。例如,图像处理或大数据分析。
  2. 提高响应性:在图形用户界面(GUI)程序中,长时间的计算或IO操作(如文件读写、网络请求等)如果在主线程中执行,会导致界面冻结。通过将这些操作放在一个或多个后台线程中执行,可以保持界面的响应性。例如,一个文本编辑器在保存文件时,可以在一个后台线程中保存文件,同时允许用户继续编辑文本。
  3. 实现后台任务:应用程序常常需要执行一些不需要用户干预的任务,如定时检查更新、执行定时备份等。这些任务可以在后台线程中执行,不影响主程序的运行。
  4. 网络编程:在进行网络请求时,为了不阻塞主线程,通常会在一个独立的线程中进行网络通信,如处理HTTP请求、数据库操作等。
  5. 多核心处理:现代计算机通常都拥有多个CPU核心。通过多线程编程,能够充分利用多核心的计算能力,将不同的线程分配到不同的CPU核心上执行,从而提高程序的执行效率。