C++中的对象组合
Object composition in C++
我正在尝试在C++中实现某种对象组合。这个想法是创建一组所有数据结构,这些数据结构可以通过组合只知道基本数据结构操作的抽象类来创建。例如,通过组合带有波普尔的推送器来创建堆栈,通过将队列器与波普尔组合来创建队列,等等。
问题是,即使 Pusher、Popper 和 Queuer 只用作抽象类,因此从来都不打算实例化,但它们必须知道数据结构如何在内部存储数据。
目标是拥有不可知的抽象类,这些抽象类仅用于将方法定义传递给具体的数据结构类,如下所示:
class Pusher {
public:
void Push(int value) {
// Simulates internal logic of pushing a value.
elements.push_back(value);
}
}
class Popper {
public:
int Pop() {
// Simulates internal logic of popping a value.
int popped_value = elements.back();
elements.pop_back();
return popped_value;
}
}
class Stack: public Pusher, public Popper {
private:
vector<int> elements;
}
你可以看到,即使 Pusher 和 Popper 不知道元素,Stack 知道,这才是最重要的。但是,此代码无效,无法编译。我怎样才能写出具有相同效果的有效内容?
即使Pusher和Popper不知道元素,Stack知道,这才是最重要的。
不。就C++而言,这并不是最重要的,正如你清楚地看到的那样——而且有充分的理由。您的建议有许多缺点,因此是不允许的。但是,有几种方法可以解决此限制。
一种方法是使用虚拟继承,并定义一个抽象基类(称为,例如Store
(,它通过Stack
中实现的虚拟功能提供对Pusher
和Popper
运行的存储的访问。
但是,这种方法也存在许多问题,通常在C++中避免使用。一种更惯用的方法使用奇怪的重复模板模式(CRTP(。
将您的Pusher
和Popper
更改为将Stack
类作为模板参数的类模板:
template <typename T>
class Pusher {
public:
void Push(int value) {
// Simulates internal logic of pushing a value.
T::elements(*this).push_back(value);
}
};
template <typename T>
class Popper {
public:
int Pop() {
// Simulates internal logic of popping a value.
int popped_value = T::elements(*this).back();
T::elements(*this).pop_back();
return popped_value;
}
};
class Stack: public Pusher<Stack>, public Popper<Stack> {
public:
template <typename T>
static std::vector<int>& elements(T& s) {
return static_cast<Stack&>(s).elements_;
}
private:
std::vector<int> elements_;
};
不用说,这仍然相当复杂,因为您的数据依赖性是颠倒的。仔细考虑您的特征需要哪些依赖项,以及它们如何有用。
另一个实现,一个接近标准库的std::stack
容器适配器的实现,是实现Pusher
和Popper
作为装饰器:也就是说,它们从Stack
继承,而不是相反。这可能很有用,但前提是您更改名称:显然,拥有一个既不执行推送也不执行弹出的类Stack
是没有意义的。同样,查看std::stack
适配器类的接口以获取灵感。
- C++中的对象组合
- C++对象文件和程序文件组合编译的 Bashrc 别名
- clang libc :make_tuple与make_shared的组合导致早期对象破坏
- C++组合从 istream 获取的类对象
- 覆盖组合对象的<<运算符会给出错误 C++
- 使用 Arduino 中的构造函数进行对象组合
- Qt C++根据组合框中的选择创建一个对象
- 使用参数组合创建对象
- 面向对象编程和对象组合,如何放置组合属性?
- 如何在组合中在运行时更改成员对象?
- OpenCV中的矩阵乘法 - 组合CV :: MAT和CV ::标量对象
- 在列表中对对象进行排序并组合值
- 将具有默认值的构造函数定义为组合对象的私有字段
- C++ 组合,对象如何知道它所在的类
- c++ 在对象组合上使用重载构造函数
- 对象组合与提供显式包装器
- 在C++中定义许多组合对象的最佳方法
- 在c++中,当组合对象构造函数有依赖关系时,如何在初始化列表中强制它们的顺序
- C/C++.库相对于组合对象文件的优势
- 如何在使用 gcc(不是 g++)编译的 C 项目中组合C++对象文件