使用Barrier分三步将大象放入冰箱
class Program
{
//构造大象和冰箱
private static ElephantsAndFridges elephantsAndFridges = new ElephantsAndFridges(); static void Main(string[] args)
{
int taskCnt = ; //此处有3个Task来完成工作(注意多任务与多线程及堆栈数据边界)
//并将每个任务的执行结果返回
Task<PhaseTask>[] tasks = new Task<PhaseTask>[taskCnt]; //使多个任务能够采用并行方式依据某种算法在多个阶段中协同工作
// 参数:
// participantCount:
// 参与线程的数量。
//
// postPhaseAction:
// 每个阶段完成之后执行。 可传递 null ,以指示不执行任何操作
Barrier barrier = new Barrier(taskCnt, (b) =>
{
Console.WriteLine(string.Format("第{0}阶段已完成", b.CurrentPhaseNumber + ));
Console.WriteLine();
});
for (int i = ; i < taskCnt; i++)
{
//使用Task工厂启3个任务
tasks[i] = Task<PhaseTask>.Factory.StartNew((obj) =>
{
int cnt = (int)obj; //一个任务一个冰箱(冰箱具有打开和关闭冰箱门及放大象操作)
Fridge fridge = new Fridge(); //注:此处不能用i,存在执行顺序问题
//例如:还未开始从elephantsAndFridges中拿数据,i的值就已经加1了,此时拿的就是i+1位置,而非i位置的数据
fridge.ElephantName = elephantsAndFridges.elephants.ElementAtOrDefault(cnt).ElephantName;
fridge.FridgeName = elephantsAndFridges.fridges.ElementAtOrDefault(cnt).FridgeName; //第一步
fridge.PhaseTaskResult.FirstResult = fridge.OpenTheDoor();
//用信号通知的参与者已达到屏障和所有其他参与者到达屏障也会等待
barrier.SignalAndWait(); //第二步
fridge.PhaseTaskResult.SecondResult = fridge.EnterTheFridge();
barrier.SignalAndWait(); //第三步
fridge.PhaseTaskResult.ThirdResult = fridge.CloseTheDoor();
barrier.SignalAndWait(); //返回每个步骤得到的结果
return fridge.PhaseTaskResult; }, i);
} //最后ContinueWhenAll,输出每个任务记录的结果,释放Barrier
var continueTask = Task.Factory.ContinueWhenAll(tasks, (t) =>
{
foreach (var item in t)
{
Console.Write(string.Format("任务{0}:", t.ToList().IndexOf(item) + ));
Console.WriteLine(item.Result.FirstResult);
Console.Write(string.Format("任务{0}:", t.ToList().IndexOf(item) + ));
Console.WriteLine(item.Result.SecondResult);
Console.Write(string.Format("任务{0}:", t.ToList().IndexOf(item) + ));
Console.WriteLine(item.Result.ThirdResult);
}
Console.WriteLine();
Console.WriteLine("已将全部大象放入全部冰箱");
barrier.Dispose();
}); Console.ReadLine();
}
} /// <summary>
/// 大象
/// </summary>
public class Elephant
{
public String ElephantName { get; set; }
} /// <summary>
/// 冰箱
/// </summary>
public class Fridge
{
public String FridgeName { get; set; } public String ElephantName { get; set; } public PhaseTask PhaseTaskResult = new PhaseTask(); public String OpenTheDoor()
{
return PhaseTaskResult.FirstResult = PhaseTaskResult.PhaseFirst(ElephantName, FridgeName);
} public String EnterTheFridge()
{
return PhaseTaskResult.SecondResult = PhaseTaskResult.PhaseSecond(ElephantName, FridgeName);
} public String CloseTheDoor()
{
return PhaseTaskResult.ThirdResult = PhaseTaskResult.PhaseThird(ElephantName, FridgeName);
}
} /// <summary>
/// 构造大象和冰箱
/// </summary>
public class ElephantsAndFridges
{
public List<Elephant> elephants; public List<Fridge> fridges; public ElephantsAndFridges()
{
elephants = new List<Elephant>()
{
new Elephant() {ElephantName="大象甲" },
new Elephant() {ElephantName="大象乙" },
new Elephant() {ElephantName="大象丙" }
}; fridges = new List<Fridge>()
{
new Fridge(){ FridgeName="冰箱甲"},
new Fridge(){ FridgeName="冰箱乙"},
new Fridge(){ FridgeName="冰箱丙"}
};
}
} /// <summary>
/// 把大象放入冰箱,共需3步
/// 第一步,打开冰箱门
/// 第二步,把大象放进冰箱
/// 第三步,关闭冰箱门
/// 该类提供三个步骤和每个步骤得到的结果
/// </summary>
public class PhaseTask
{
public String FirstResult { get; set; } public String SecondResult { get; set; } public String ThirdResult { get; set; } public String PhaseFirst(string elephantName, string fridgeName)
{
string str = string.Format("第一步:为{0}打开{1}门", elephantName, fridgeName);
Console.WriteLine(str);
return FirstResult = str;
} public String PhaseSecond(string elephantName, string fridgeName)
{
string str = string.Format("第二步:把{0}放入{1}", elephantName, fridgeName);
Console.WriteLine(str);
return SecondResult = str;
} public String PhaseThird(string elephantName, string fridgeName)
{
string str = string.Format("第三步:为{0}关闭{1}门", elephantName, fridgeName);
Console.WriteLine(str);
return ThirdResult = str;
}
}
使用Barrier分三步将大象放入冰箱的更多相关文章
- Postman A请求的返回值作为B请求的入参( 拢共分三步)
- java 调用 C# 类库搞定,三步即可,可以调用任何类及方法,很简单,非常爽啊
java 调用 C# 类库搞定,三步即可,可以调用任何类及方法,很简单,非常爽啊 java 调用 C# 类库搞定,可以调用任何类及方法,很简单,非常爽啊 总体分三步走: 一.准备一个 C# 类库 (d ...
- [其它]iOS 12.2支持电信VoLTE了,中国电信教你如何开通:只要三步
iOS 12.2支持电信VoLTE了,中国电信教你如何开通:只要三步 link :https://baijiahao.baidu.com/s?id=1629039609897267682&wf ...
- 把大象装进冰箱的N种方法
作者:折剑头链接:https://www.zhihu.com/question/49214119/answer/115728034来源:知乎著作权归作者所有.商业转载请联系作者获得授权,非商业转载请注 ...
- Membership三步曲之进阶篇 - 深入剖析Provider Model
Membership 三步曲之进阶篇 - 深入剖析Provider Model 本文的目标是让每一个人都知道Provider Model 是什么,并且能灵活的在自己的项目中使用它. Membershi ...
- Membership三步曲之入门篇 - Membership基础示例
Membership 三步曲之入门篇 - Membership基础示例 Membership三步曲之入门篇 - Membership基础示例 Membership三步曲之进阶篇 - 深入剖析Pro ...
- EC笔记:第三部分:17、使用独立的语句将newed对象放入智能指针
一般的智能指针都是通过一个普通指针来初始化,所以很容易写出以下的代码: #include <iostream> using namespace std; int func1(){ //返回 ...
- java入门第三步之数据库连接
数据库连接可以说是学习web最基础的部分,也是非常重要的一部分,今天我们就来介绍下数据库的连接为下面学习真正的web打下基础 java中连接数据库一般有两种方式: 1.ODBC——Open Datab ...
- [转]Membership三步曲之入门篇 - Membership基础示例
本文转自:http://www.cnblogs.com/jesse2013/p/membership.html Membership三步曲之入门篇 - Membership基础示例 Members ...
随机推荐
- 基于LSTM + keras 的诗歌生成器
最近在github 上发现了一个好玩的项目,一个基于LSTM + keras 实现的诗歌生成器,地址是:https://github.com/youyuge34/Poems_generator ...
- Windows下遍历所有GIT目录更新项目脚本
将下面代码保存为.bat文件 @echo off set cdir=%~dp0 for /f "delims=" %%i in ('dir /ad/b/s "%cdir% ...
- 生成SSH秘钥连接github(详细教程)
第一步.首先,检查下自己之前有没有已经生成: 在开始菜单中打开git下的git bash(当然,在其他目录下打开git bash也是一样的): 然后执行 cd ~/.ssh 第二步.如果能进入到.ss ...
- shell备份脚本
#!/bin/bash #不存在的变量终止脚本执行 set -o nounset #执行出错终止脚本执行 set -o errexit #递归列出文件的绝对路径并执行压缩 delDir=`date - ...
- HashMap集合-遍历方法
# HashMap集合-遍历方法 先定义好集合: public static void main(String[] args) { Map<String,String> onemap=ne ...
- Hadoop环境搭建过程中遇到的问题以及解决方法
1.启动hadoop之前,ssh免密登录slave主机正常,使用命令start-all.sh启动hadoop时,需要输入slave主机的密码,说明ssh文件权限有问题,需要执行以下操作: 1)进入.s ...
- windows下memcache扩展安装和搭建
### windows下memcache扩展安装和搭建 背景:在做微信公众号的开发时,token的有效期为7200秒,所以需要对token进行保存,在这选择了memcache作为缓存工具 memcac ...
- PHP内存管理-zendMM
ZendMM 是zend memory manager zendMM可以分为三层: 1.存储层 维护者不同体量内存的hash表,已提供堆层使用,负责向os申请和释放内存 2.堆层 PHP内存管理的核心 ...
- Payload 实现分离免杀
众所周知,目前的杀毒软件的杀毒原理主要有三种方式,一种基于特征,一种基于行为,一种基于云查杀,其中云查杀的一些特点基本上也可以概括为特征码查杀,不管是哪一种杀毒软件,都会检查PE文件头,尤其是当后门程 ...
- 移动端测试之APP安全测试
现在APP测试已经是测试行业的一个重要分支,对APP测试技能和经验的要求也越来越高,看到一篇关于APP安全测试的总结,分享给需要的朋友.1.软件权限1)扣费风险:包括发送短信.拨打电话.连接网络等2) ...