【发布时间】:2009-05-12 22:07:49
【问题描述】:
在我正在使用 C++ 处理的项目中,我需要为通过网络传入的消息创建对象。我目前正在使用factory method pattern 来隐藏对象的创建:
// very psuedo-codey
Message* MessageFactory::CreateMessage(InputStream& stream)
{
char header = stream.ReadByte();
switch (header) {
case MessageOne::Header:
return new MessageOne(stream);
case MessageTwo::Header:
return new MessageTwo(stream);
// etc.
}
}
我的问题是我很懒,不喜欢在两个地方写类名!
在 C# 中,我会在第一次使用工厂时进行一些反思(额外的问题:这是可以使用反射的,对吗?)但由于 C++ 缺乏反射,所以这不在讨论范围内。我考虑过使用某种注册表,以便消息在启动时向工厂注册,但这受到non-deterministic (or at least implementation-specific) static initialization order problem 的阻碍。
那么问题是,在尊重开闭原则的情况下,是否可以在 C++ 中实现这种类型的工厂,以及如何实现?
编辑:显然我想多了。我打算将这个问题作为“你将如何在 C++ 中做到这一点”,因为在其他语言中使用反射真的很容易。
【问题讨论】:
-
使用 python 也很容易,因为您可以读取字符串(如消息标签/id)并在文件中查找类名,然后实例化您可以从中实例化对象的类。不过,我认为在 C++ 中没有一种“简单”的方法。
-
我不明白为什么静态初始化顺序会阻止注册表。首先,它不必(并且可能不应该)是静态的,其次,即使是,初始化顺序只有在从其他静态访问时才会成为问题。如果是这样,那么您遇到的问题(过度使用全局变量)比这要严重得多。
-
我的意思是,如果不使用单例或依赖静态初始化顺序,您将无法执行类似于 epatel 建议的操作。但现在这一切都没有实际意义,因为它过度设计了。
标签: c++