了解线程同步前,我们先来了解几个相关的概念哦。
无关线程:线程之间没有任何的联系,它们各自独立运行,互不干扰。
相关线程:一个线程等待另一个线程的运算结果,两个线程共享一个资源等。
例如:我们在线观看视频,一个线程下载视频,另一个线程播放线程,这两个线程相互合作才能正常的观看视频。
临界资源:线程的相关性集中体现在同一资源的访问上,这个共享资源称为临街资源。
现实问题:有两个线程,一个writer向缓冲区写内容,一个线程reader从缓冲区读取内容,只有当writer写一个字符,然后reader读取一个字符,这样才是我们想要的结果。
同步(Synchronization):像这种需要这两个线程协同工作才能共同完成一项任务的情况。
保证线程的方法:
.NET框架为我们提供了一系列的同步类,常用的如下Interlocaked(互锁),Monitor(管程)和Mutex(互斥体)。
这里我们使用互锁,先来了解一下互锁哦。
要使用线程我们必须引入命名空间using System. Threading;
Interlocked.Read(ref long location);//读取计数器的值
Interlocked.Increment(ref int location );//使计数器的值增加1
Interlocked.Decrement(ref int location);//使计数器的值减少1
Interlocked.Add(ref int location,int value);//使计数器增加指定的值
Interlocked.Exchange(ref int location,int value);//把计数器的值设定为指定的值
Interlocked.CompareExchange(ref int location,int value_1k,int value_2);//先把计数器与某个值比较,若相等,则把计数器设定为指定的值
样例:我们有四句诗,想要使用两个协程,一个协程用来写,另一个协程用来读,只有二者同步进行时才能正常的输出这四句诗。代码如下哦:
string sentence = "胜败兵家事不期,包羞耻是男儿,江东弟子多才俊,卷土重来未可知";
//写入缓冲区
Thread writer = new Thread(delegate()
{
for (int i = 0; i < sentence.Length; i++)
{
/*写入缓冲区前检查缓冲区是否已满
* 如果已满,就进行等待,直到缓冲区的数据被Reader读取为止
*/
while (Interlocked.Read(ref numberOfUsedSpace)==1)
{
Thread.Sleep(10);//等待10毫秒
}
//向缓冲区写入数据
buffer = sentence[i];
//写入数据后把缓冲区标记为满(从0 到1)
Interlocked.Increment(ref numberOfUsedSpace);
}
});
//从缓冲区中读取
Thread Read = new Thread(delegate ()
{
for (int i = 0; i < sentence.Length; i++)
{
/*写入缓冲区前检查缓冲区是否有内容
* 如果没有,就进行等待,直到缓冲区中存有数据
*/
while (Interlocked.Read(ref numberOfUsedSpace) == 0)
{
Thread.Sleep(10);
}
//读取数据
char ch = buffer;
Debug.Log(ch);
//把缓冲区归零
Interlocked.Decrement(ref numberOfUsedSpace);
}
});
//开启两个线程
writer.Start();
Read.Start();