我有一个代表“世界状态”的课程。该类有许多其他对象的集合,这些对象又引用更多对象和对象集合,有时甚至引用它们在“世界层次结构”中的祖先。为了简化所说的,这里有一个例子(转换成 XML,细节省略):
<World>
<Country>
<City>
<Block>
...
</Block>
</City>
<City>
<Block>
...
</Block>
</City>
</Country>
...
<Country>
<City>
<Block> ... </Block>
...
<Block> ... </Block>
</City>
<City>
<Block> ... </Block>
</City>
</Country>
</World>
有两个线程,UI线程和后台线程(实际上是一个服务器)。
服务器接收修改“世界状态”(添加城市、街区等)的消息。
UI 线程每隔一段时间使用 PictureBox 对象将世界的状态绘制到屏幕上。表示层仅引用 IWorld 对象(World 实现),它无法访问其中的元素。
UI 线程应该锁定世界的完整状态,以便在绘制期间不能(通过服务器)更改世界(这会产生不一致的世界图片)。因为它只引用了 IWorld 对象,所以这是唯一要锁定的东西。
我的问题是这个锁是否足够(即,递归地锁定该对象具有的所有字段和属性),或者每个对象都应该单独锁定。解决这个问题的正确方法是什么?
注意: UI 无法联系服务器(意味着它不能告诉服务器停止改变世界,然后在渲染后告诉它恢复)。
编辑:如果 World 和层次结构中的所有类都实现 ILock 接口,该接口提供 Lock() 方法,该方法将在所有较低级别(递归地)调用 Lock(),这可能容易出现死锁(循环引用)或太昂贵。
我想设计更改是有序的。