在不知道基类存在的情况下调用继承基类的每个类
本文关键字:基类 继承 情况下 不知道 存在 调用 | 更新日期: 2023-09-27 17:53:59
我正在尝试在websocket服务器中实现类似unity3d的系统。它们有一个叫做MonoBehavior的基类,所有的类都从这个基类继承。
这些类有特定的函数(start, ongui, update),这些函数在特定的时间间隔被调用。
每个从该类继承的类都有自己的函数被调用(update每帧被调用)
我想创建一个基类,然后调用它,让每个包含函数的类自动调用,就像unity3d那样。我试过谷歌搜索,但不知道这种类型的行为与类被调用,甚至得到一个有用的结果
为什么不实现一个静态Manager类呢?
public static class CallManager
{
public static HashSet<Callable> callables = new HashSet<Callable>();
// Other management code...
}
有一个基类,所有你的可调用类的子类,自动添加每个新的实例到你的CallManager
管理的可调用对象集:
public abstract class Callable
{
public Callable()
{
OnCreate();
}
protected void OnCreate()
{
CallManager.callables.Add(this);
}
public abstract void Start();
public abstract void OnGUI();
public abstract void Update();
}
现在,每当有人创建新的Callable
时,基础Callable
构造器将用新的Callable
更新CallManager
。完整的示例程序如下:
class Caller
{
public static void Main(string[] args)
{
Callee1 c1 = new Callee1();
Callee2 c2 = new Callee2();
foreach (Callable c in CallManager.callables)
{
c.Start();
c.OnGUI();
c.Update();
}
}
}
public abstract class Callable
{
public Callable()
{
OnCreate();
}
protected void OnCreate()
{
CallManager.callables.Add(this);
}
public abstract void Start();
public abstract void OnGUI();
public abstract void Update();
}
public static class CallManager
{
public static HashSet<Callable> callables = new HashSet<Callable>();
}
public class Callee1 : Callable
{
public Callee1()
{
}
public override void Start()
{
Console.WriteLine("Callee1::Start");
}
public override void OnGUI()
{
Console.WriteLine("Callee1::OnGUI");
}
public override void Update()
{
Console.WriteLine("Callee1::Update");
}
}
public class Callee2 : Callable
{
public Callee2()
{
}
public override void Start()
{
Console.WriteLine("Callee2::Start");
}
public override void OnGUI()
{
Console.WriteLine("Callee2::OnGUI");
}
public override void Update()
{
Console.WriteLine("Callee2::Update");
}
}
可以这样写:
public static class Caller {
public static event EventHandler Updating;
public static Update() {
var handler = Updating;
if (handler ¡= null) handler(null, EventArgs.Empty);
}
}
public abstract class Base {
protected Base() {
Caller.Updating += Caller_Updating;
}
void Caller_Updating(object sender, EventArgs e) {
Update();
}
protected abstract Update();
}
据我所知,您希望所有派生类都调用该方法。这样当你呼叫来电者时。
我相信您指的是模板方法设计模式,通常也称为钩子。它是很多很多框架的基石。它的工作原理是这样的:
public abstract class BaseClass
{
public void Start()
{
//execute start logic
DoThis();
DoThat();
//call base class's hook
OnStart();
}
protected abstract void OnStart();
}
你声明了一个派生类必须实现的抽象方法OnStart
。当基类的Start
方法被调用时,基类调用钩子,然后由派生类执行。
如果你想让重写钩子成为可选的,那么你可以用一个空的实现声明虚方法,即protected virtual void OnStart() { }
。
可能还值得一提的是,这是好莱坞原则的核心:"不要打电话给我们,我们会打电话给你!"(也就是说,你不调用框架的类——框架会调用你!)