你可以用C++帮我构建组合示例应用程序吗?

use*_*609 1 c++ composition

你能帮我用C++编写组合示例应用程序吗?

我需要这样的层次结构:类AppleCake继承自基类Cake,还有类CakePacket,它有4个Cakes.我写了一些代码,但问题是我不知道如何向CakePacket添加4个Cake对象.我是C++的初学者,所以如果会有一些愚蠢的错误,我很抱歉.

#include <iostream>
using namespace std;

class Cake {

protected:
  int cost;
public:
  void setCostr(int a) { cost = a; }
  int getCost() { return cost; }
  Cake(int x) { cost = x;  }
  ~Cake() {  }
};


class AppleCake : public Cake {
  int diameter;
public:
  int getDiameter() { return diameter; }

  AppleCake(int x, int y): Cake(x)
    { diameter = y; }

  ~AppleCake() {  }
};


class CakePacket 
{
private:
    Cake *cArr;

    CakePacket() { }

public:
    CakePacket(Cake *x)  //there have to be 4 Cake objects in CakePacket
    : cArr(new Cake[4]) {};
};
Run Code Online (Sandbox Code Playgroud)

最后一个问题是 - 如何创建CakePacket的对象?

稍后我将不得不再创建一个组合,一些类将包含1个CakePacket.但我希望将1个CakePacket对象添加到其他类中是没有问题的.

谢谢你的所有答案!

Bar*_*icz 6

因为在最后一个小时没有人做对了......实际上@ taylorc93是最接近的,但他仍然犯了一个错误.

所以,回到这个问题.CakePacket应该存储Cakes,对吧?Cake是一个基类,但它没有虚方法.在这种情况下,使用指针是完全没必要的,你唯一要做的就是使用一些容器.现在,您选择哪一个取决于CakePacket的预期用途.让我们以一般的方式写它,然后:

class CakePacket {
    // this can be whatever you might need; a list, set, unordered_set...
    // vector is a reasonable default
    vector<Cake> cakes;

public:
    // We'll also need a way to add them:
    void addCake(Cake cake) {
        // I'm moving the parameter to avoid copying
        // refer to "move semantics" to understand it deeper
        cakes.push_back(std::move(cake));
    }
};
Run Code Online (Sandbox Code Playgroud)

瞧!你已经问过如何创建一个CakePacket,这很简单.

CakePacket cp;

cp.addCake(Cake(1));
cp.addCake(Cake(2));
cp.addCake(Cake(3));
Run Code Online (Sandbox Code Playgroud)

当然你可以将它们移动到构造函数中CakePacket,但是......

CakePacket cp { Cake(1), Cake(2), Cake(3), Cake(4) };
Run Code Online (Sandbox Code Playgroud)

如果你想能够从类似数组的列表中创建,你需要提供aditional构造函数initializer_list<Cake>,但我会把它留作练习.(提示:你不会需要一个for循环).

CakePacket真的有必要吗?

这是一个学习问题,所以我不会对它挑剔,但我想指出CakePacket真正做到的事实......没有,至少在当前状态.有时简单地使用std容器更容易,而不是将其包装成一个全新的类型.这样可以避免使用多余的类来污染代码,并且您会惊讶于标准库提供了多少功能来使用它的容器.

警告

如果您尝试将AppleCake存储在其中,diameter则会切片,即只保存公共部分.在这种情况下,您需要将指针存储到基类(使用boost::ptr_vector<Cake>std::vector<std::unique_ptr<Cake>>),或使用类似的东西Boost.Variant.

你当然不想做什么

...正在存储原始指针.你必须销毁CakePacket dtor中添加的每个Cake,这很容易出错并且根本不需要.

使用C风格的数组也相当糟糕,因为它会限制你使用固定大小.