我有一个GameCore类
有一个Player类
其中GameCore包含一个IList <Player> Players的引用
在某些情况下GameCore需要根据Player属性改变而触发某些操作(这里我是用的有限状态机实现的状态切换,所以游戏逻辑不在GameCore中,所有问题存在)
比如:
比如如果某用户点击了准备按钮,而且已准备人数等于准许开始游戏的人数。比如斗地主中的3人
那么就要开始游戏。
我现在有2个做法
1:用线程去轮询
代码: //context为GameCore,代码段位于PlayerFull:State类中
BackgroundWorker worker = new BackgroundWorker();
worker.DoWork += new DoWorkEventHandler(delegate(object sender, DoWorkEventArgs e)
{
PlayerCollection players = e.Argument as PlayerCollection;
while (true)
{
if (players.IsAllReady())
break;
}
});
worker.RunWorkerCompleted += new RunWorkerCompletedEventHandler(delegate(object sender, RunWorkerCompletedEventArgs e)
{
if (!worker.CancellationPending)
context.StartGame(); });
worker.RunWorkerAsync(context.Players);
好处是稍微低了一点耦合,但我总感觉有点浪费而且不合适
2:用事件驱动方式
在GameCore类中添加PlayerReady事件
在Player中添加PlayerPropertyChanged事件
然后在玩家加入游戏时添加PlayerPropertyChanged事件处理方法
在退出游戏时移除
在PlayerPropertyChanged事件处理方法中判断如果Player改变的是IsReady属性,而且为True
那么就引发PlayerReady事件
在PlayerFull中处理此事件
这种方法优点和缺点都很明显,事件驱动方式,性能很高,更容易控制,也不会出现脏数据、死锁等烦人的多线程问题
缺点是GameCore和Player太耦合,简直有点无法忍受啊,而且在主类中去引用客户端很容易改变的Player似乎也不太安全
有什么好方法,或者怎么改进,请各抒己见吧