在我公司的 C++ 代码库中,我看到很多这样定义的类:
// FooApi.h
class FooApi {
public:
virtual void someFunction() = 0;
virtual void someOtherFunction() = 0;
// etc.
};
// Foo.h
class Foo : public FooApi {
public:
virtual void someFunction();
virtual void someOtherFunction();
};
Foo
是唯一继承自 FooApi
的类,接受或返回指向 Foo
对象的指针的函数使用 FooApi *
代替。它似乎主要用于单例类。
这是编写 C++ 代码的常见命名方式吗?这有什么意义呢?我看不出拥有一个仅定义类接口(interface)的单独的纯抽象类有何用处。
编辑[0]:抱歉,澄清一下,只有一个类派生自 FooApi
,以后无意添加其他类。
编辑[1]:我理解抽象和继承的一般意义,但不理解继承的这种特殊用法。
最佳答案
我能理解他们这样做的唯一原因是为了封装目的。这里的要点是,代码库中的大多数其他代码仅 需要包含“FooApi.h”/“BarApi.h”/“QuxxApi.h” header 。实际上,只有创建 Foo 对象的代码部分需要包含“Foo.h” header (并链接到包含类函数定义的目标文件)。对于单例,通常创建 Foo 对象的唯一位置是在“Foo.cpp”文件中(例如,作为 Foo 类的静态成员函数中的局部静态变量,或类似的东西)。
这类似于使用前向声明来避免包含包含实际类声明的 header 。但是当使用前向声明时,您仍然需要最终包含标题以便能够调用任何成员函数。但是当使用这种“抽象+实际”的类模式时,您甚至不需要包含“Foo.h”头文件就能够调用 FooApi 的成员函数。
换句话说,这种模式提供了对 Foo 类实现(和完整声明)的非常强大的封装。您获得的好处与使用 Compiler Firewall idiom 大致相同。 . Here是关于这些问题的另一本有趣的读物。
我不知道那个图案的名字。与我刚才提到的其他两种模式(编译器防火墙和前向声明)相比,它不是很常见。这可能是因为此方法比其他两种方法有更多的运行时开销。
关于c++ - 这个 C++ 模式的名称及其背后的原因是什么?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/22650736/