【发布时间】:2011-11-18 06:16:24
【问题描述】:
我在解决设计实现中的一些问题时遇到了麻烦。它是这样的:
我有一个模板基类,它有一个转换方法。
// Foo.h
class Bar;
template<typename T>
class Foo {
virtual const Bar toBar();
}
我希望派生类 Bar 从特定形式的 Foo 继承,例如:
// Bar.h
class Bar : public Foo<float> {
// Insert Bar methods here, Etc.
}
由于 Foo 是一个模板,因此必须在头文件中完全定义实现,这会导致 toBar() 方法的实现需要能够创建 Bar 类型的实例的问题。所以这告诉我我需要在 Foo 定义之后但在 Foo 实现之前包含 Bar.h 头文件。
但是,在 Bar.h 中,类 Bar 派生自 Foo,因此必须提供 Foo 的完整定义。这会导致问题,因为这两个文件具有循环依赖,无法通过前向声明解决,因为前向声明是派生类。
如果另一个类 SomeClass 有一个 Bar 类型的数据成员,这会变得更加复杂,因为这需要包括 Bar.h ,其中包括 Foo.h (因为它是一个模板) 包括 Bar.h。
哦,为了清楚起见,所有头文件都使用了包含保护
#ifndef _HEADER_NAME_H_
#define _HEADER_NAME_H_
...
#endif
其他人是如何解决此类复杂问题的?
作为一个更具体的例子,我有一个 Array 类,它有一个方法可以将它转换为人类可读的 String 类,例如 toString()...但是 String 类被声明为
class String : public Array<char> {...};
提前致谢。 加里。
【问题讨论】:
-
也许使用指针而不是实例本身作为返回值?
-
模板中的虚拟有点臭。似乎将两种不同的想法混合在一起(多态性与专业化)。
-
@Skizz 是为了让派生类有扩展和覆盖的能力。也许我可以使用 sspecialisation 和 typedef 来代替?例如:typedef Array
字符串;模板 类 Array { String toSting(); /* 字符串特定的特化方法(比如修剪等 */ } -
@Skizz:听说过基于混合模板和虚函数的类型擦除技术吗?并不是说这里似乎是 OP 案例。
-
@Gary:我的意思是,虚拟意味着一个通用的基类,模板是不同的类。所以我有:
template<typename T> class Foo : public IBaseClass { }并将IBaseClass定义为纯虚拟基类。
标签: c++ class templates forward derived