深入浅出多线程系列之十四:线程的交会(Thread Rendezvous)

简介:

在上篇文章中我们使用了Wait和Pulse 实现了Countdown

接下来我们可以使用刚刚写的Countdown 类来实现两个线程的交会

 

复制代码
    class  Rendezvous
    {
        
static   object  _locker  =   new   object ();
        
static  Countdown _countdown  =   new  Countdown( 2 );

        
public   static   void  MainThread()
        {
            Random r 
=   new  Random();
            
new  Thread(Mate).Start(r.Next( 1000 ));
            Thread.Sleep(r.Next(
10000 ));  // 主线程睡眠一段时间

            _countdown.Singnal(); 
// 向_countdown注册信号,告知主线程已经来了。
            _countdown.Wait();     // 等待其他线程

            Console.WriteLine(
" Mate! " );
        }

        
static   void  Mate( object  delay)
        {
            Thread.Sleep((
int )delay); // 线程睡眠。

            _countdown.Singnal(); 
// 向_countdown注册信号,告知线程已经来了。
            _countdown.Wait();    // 等待其他线程。

            Console.WriteLine(
" Mate! " );

        }
}
复制代码

 

就像小时候去春游一样,这里的_countdown就是老师,线程就是学生。

学生A早上睡觉,然后起床来到交会点,然后告诉老师,我来了,接着等待老师的出发命令,因为老师知道有两个学生要去春游,所以现在只来了一个,还有一个没有来,所以老师会让学生A等待,阻塞。

学生B也是睡觉,接着也来到交会点,告诉老师,我也来了,然后等待老师的出发命令。

当学生B告诉老师我来了的时候,此时老师的剩余等待学生计数为0,所以老师告诉这两个学生,你们可以出发了。

 

.net framework 4.0 提供了Barrier 的构造来实现线程交会的功能。如图所示:

 

Thread1 调用SignalAndWait告知Barrier,我已经来了,然后阻塞。

Thread3调用SignalAndWait告知Barrier,我已经来了,然后阻塞。

Thread2 调用SignalAndWait告知Barrier,我已经来了,Barrier知道现在三个线程都来了,所以让他们继续并发执行。

 

Barrier的方法简介:

  • AddParticipants:增加参与者,也就是增加春游的人数。
  • RemoveParticipant :减少参与者,可能某人肚子痛,不能参加春游了。
  • SignalAndWait  :参与者已经来了,并等待其他参与者的到来。

 

下面是使用Barrier的示例:

 

复制代码
        static  Barrier _barrier  =   new  Barrier( 3 ); // 说明有三个参与者

        
public   static   void  Main()
        {
            
new  Thread(Speak).Start();
            
new  Thread(Speak).Start();
            
new  Thread(Speak).Start();
        }

        
static   void  Speak()
        {
            
for  ( int  i  =   0 ; i  <   5 ; i ++ )
            {
                Console.Write(i 
+   "   " );
                _barrier.SignalAndWait(); 
// 告知参与者已经来了,等待其他参与者
            }
        }
复制代码

 

输出如下:

0 0 0 1 1 1 2 2 2 3 3 3 4 4 4

 

Barrier 的另一个非常有用的特性是在每一个阶段完成的时候你都可以执行一个post-phase action委托。

什么是阶段呢??,阶段就是参与者全部都到了的时候。

如果我们修改Barrier的构造函数如下:

static Barrier _barrier = new Barrier(3, (barrier) => Console.WriteLine());

//说明有三个参与者,并且每次三个参与者完成任务的时候执行Console.WriteLine方法.

 

那么我们的输出如下所示:

0 0 0

1 1 1

2 2 2

3 3 3

4 4 4

 






本文转自LoveJenny博客园博客,原文链接:http://www.cnblogs.com/LoveJenny/archive/2011/06/05/2060961.html,如需转载请自行联系原作者
目录
相关文章
|
2天前
|
NoSQL Java Redis
Reactor实战,创建一个简单的单线程Reactor(理解了就相当于理解了多线程的Reactor)
本文通过一个简单的单线程Reactor模式的Java代码示例,展示了如何使用NIO创建一个服务端,处理客户端的连接和数据读写,帮助理解Reactor模式的核心原理。
10 0
Reactor实战,创建一个简单的单线程Reactor(理解了就相当于理解了多线程的Reactor)
|
12天前
|
NoSQL 网络协议 Unix
1)Redis 属于单线程还是多线程?不同版本之间有什么区别?
1)Redis 属于单线程还是多线程?不同版本之间有什么区别?
32 1
|
2天前
|
设计模式 Java 物联网
【多线程-从零开始-玖】内核态,用户态,线程池的参数、使用方法详解
【多线程-从零开始-玖】内核态,用户态,线程池的参数、使用方法详解
12 0
|
2天前
|
安全 Java 程序员
【多线程-从零开始-肆】线程安全、加锁和死锁
【多线程-从零开始-肆】线程安全、加锁和死锁
13 0
|
2天前
|
Java 程序员 编译器
【多线程-从零开始-叁】线程的核心操作
【多线程-从零开始-叁】线程的核心操作
11 0
|
2天前
|
Java 调度
【多线程-从零开始-贰】线程的构造方法和常见属性
【多线程-从零开始-贰】线程的构造方法和常见属性
13 0
|
13天前
|
Java
COMATE插件实现使用线程池高级并发模型简化多线程编程
本文介绍了COMATE插件的使用,该插件通过线程池实现高级并发模型,简化了多线程编程的过程,并提供了生成结果和代码参考。
|
2月前
|
存储 监控 Java
Java多线程优化:提高线程池性能的技巧与实践
Java多线程优化:提高线程池性能的技巧与实践
72 1
|
14天前
|
数据采集 负载均衡 安全
LeetCode刷题 多线程编程九则 | 1188. 设计有限阻塞队列 1242. 多线程网页爬虫 1279. 红绿灯路口
本文提供了多个多线程编程问题的解决方案,包括设计有限阻塞队列、多线程网页爬虫、红绿灯路口等,每个问题都给出了至少一种实现方法,涵盖了互斥锁、条件变量、信号量等线程同步机制的使用。
LeetCode刷题 多线程编程九则 | 1188. 设计有限阻塞队列 1242. 多线程网页爬虫 1279. 红绿灯路口
|
21天前
|
Java Spring
spring多线程实现+合理设置最大线程数和核心线程数
本文介绍了手动设置线程池时的最大线程数和核心线程数配置方法,建议根据CPU核数及程序类型(CPU密集型或IO密集型)来合理设定。对于IO密集型,核心线程数设为CPU核数的两倍;CPU密集型则设为CPU核数加一。此外,还讨论了`maxPoolSize`、`keepAliveTime`、`allowCoreThreadTimeout`和`queueCapacity`等参数的设置策略,以确保线程池高效稳定运行。
88 10
spring多线程实现+合理设置最大线程数和核心线程数

热门文章

最新文章