避免虚拟调用循环的模式
Pattern to avoid looping on virtual calls
在我的游戏中,我通常让每个NPC/物品等都从基类"实体"派生。然后他们基本上都有一个名为"更新"的虚拟方法,我会在每一帧为游戏中的每个实体分类。我认为这种模式有很多缺点。还有哪些其他方法可以在整个游戏中管理不同的"游戏对象"?这方面还有其他众所周知的模式吗?我基本上是想找到比从基类派生所有东西更好的模型,基类将跨越一个巨大的继承树和遍布的虚拟函数
还有另一种模式涉及行为继承。
例如:一把剑(在幻想风格的游戏中)可以继承Describable
,使其能够被玩家描述;它还将继承DoDamage
,后者处理传球伤害;它进一步继承了Grabable
,因此玩家可以"抓取"它
一件盔甲反过来可以继承DamageReduction
,以降低所造成的伤害,以及Wearable
,这样玩家就可以穿上它。
你会得到许多更小、更浅的继承树,而不是一棵又大又深的继承树。当然,缺点是你必须创建很多类,并考虑可能发生的不同行为和事件。
让您的对象在未来的某个时间点请求更新。
struct UpdateToken {
UpdateToken() {}
/* ... */
};
class Updater {
// ...
struct UpdateEntry
{
UpdateToken token;
Time when;
bool repeats;
Time frequency
std::function<void()> callback;
};
// Various indexes into a collection of UpdateEntries
// sorted by when and by token so you can look up both ways quickly
public:
UpdateToken RegisterUpdate( Time t, std::function<void()> callback ); // once after time t
UpdateToken RegularUpdate( Time t, std::function<void()> callback ); // every time t
void UnregisterUpdate( UpdateToken );
};
Updater* GetUpdater();
// use:
class Foo
{
UpdateToken token;
void DoUpdate()
{
std::cout << "I did it!n";
}
void PlanRepeatingUpdate( Time t )
{
if (!GetUpdater())
return;
if (token.valid())
GetUpdater()->UnregisterUpdate(token);
token = GetUpdater()->RegularUpdate( t, [&]()->void
{
this->DoUpdate();
});
}
~Foo() { if (token.valid() && GetUpdater()) GetUpdater()->UnregisterUpdate(token); }
};
这里我们有一个未来事件的源(Updater())和j个随机类Foo,它可以在其中注册一个回调,用于一个重复或一系列重复。
您可以在0.1秒内、1秒内或1小时内要求更新。如果你碰巧被销毁,或者不想更新,你可以注销它,但它永远不会到达。
必须在Updater中投入一些精力,这样它既可以快速找到下一个要调用的事件,也可以通过令牌找到更新。我见过一个Boost双索引容器,或者你可以手动处理它,方法是有一个主std::set(或无序集),以及一个具有唯一顺序的第一个集合的辅助迭代器集合,你可以非常小心地管理它(你必须注意是什么使迭代器无效,并确保迭代器集不包含任何无效内容)。
上面还有效地使用了全局Updater()实例,这通常并不理想。
- C++ 无法在字符数组中使用 for 循环打印字母模式
- 如何在已定义的名称模式上循环
- 防止模式对话框中的事件循环阻塞
- C++ 是否可以使用对变量的引用来简化这种嵌套循环模式?
- 为什么在发布模式下无法访问 for 循环,但在调试中它工作正常
- 我似乎无法弄清楚这种嵌套循环模式C++
- 派生类中的部分专用化(加上奇怪的循环模式)
- 避免虚拟调用循环的模式
- Decorator设计模式:为什么调用链中的函数而不调用循环中的函数
- 非循环访客模式.将接受函数移动到一个位置
- 打破工厂模式中的循环依赖关系
- 使用嵌套 while 循环创建模式
- 嵌套循环:数字模式
- 专门用于访客模式的循环
- 在发布模式下测量Visual Studio(C++)中循环内方法的运行时时出错
- C++中Observer模式实现中的循环引用
- 使用循环和变量模式(序列)
- C/ c++模式:在超时时退出for()循环
- 奇怪的循环模板模式(CRTP),自动列表和c++
- 如何使用具有循环依赖性的组件模式正确地使用多态性