-3

我有一个名为 的类Actor,还有一个名为 的类Beast。我想在每个对象中有一个包含所有对象的Beast数组。假设我有两个: and , 和两个: and ,其中会有一个数组包含对, ,和的引用。这个相同的数组将在、和中。ActorActorBeastActorsa1a2Beastsb1b2a1a1a2b1b2a2b1b2

我将如何制作这个数组?

4

3 回答 3

3

您可以有两个静态类成员,两个向量,并在构造函数中将每个实例添加到此向量中。

class Animal {
    private:
        static std::vector<Animal*> animal_list;
    public:
        Animal() { animal_list.push_back(this); }
        void print_them() { 
            for (auto iter = animal_list.begin(); 
                    iter != animal_list.end(); 
                    iter++) {
                std::cout << *iter << std::endl;
            }
        }
};

std::vector<Animal*> Animal::animal_list;

int main() {
    Animal a1, b1; 
    a1.print_them();
    return 0;
}

当然,处理被破坏的实例、管理所有权和线程安全是一些进一步的考虑。

于 2013-10-30T14:06:55.020 回答
0

您有两个问题需要在这里解决:

  • 首先是从您的帖子来看,您似乎想在同一个数组中存储不同的类型(Actor 和 Beast)。如果两种类型都派生自同一个基类,则只能这样做,在这种情况下,数组需要是指向基类元素的指针数组。(旁注:仅根据您命名类的方式,Beast 可能从 Actor 派生,在这种情况下,您的数组可能包含 Actor* 元素。)
  • 您可能遇到的第二个问题是类型递归。您希望 Actors 具有对 Beasts 的引用,而 Beasts 具有对 Actors 的引用。如果不先声明 Beast,就不能完全声明 Actor 类,但是因为 Beast 也引用了 Actor,所以也不能先声明 Beast。在 C++ 中,您可以通过“前向声明”类来解决此类递归。前向声明一个类告诉编译器该类将在稍后声明,但现在它应该只接受它作为一个有效的类。在前向声明和完整声明之间,您将能够使用指向类的指针(并且只能在不取消引用的情况下使用),但只能使用指针,因为编译器尚不知道类的大小或成员将是什么。前向声明这两个类很简单:

    类演员;类野兽;

不过需要注意的是,如果您不将两个类存储在单独的数组中,而是使用基类实现我的第一点中的解决方案,那么您还应该将公共数组存储在基类中,并且无需转发 -声明演员和野兽。

于 2013-10-30T14:47:51.060 回答
0

There are a couple of conditions here to keep both Actors and Beasts in the same "array". They must both share a common base type, and the array must be an array of pointers.

On top of that, you should probably use a vector instead of an array.

One pattern would be a static vector in the base class, the derived classes could add and remove themselves from the vector when constructed or destroyed:

class Base
{
protected:
    void Add( Base* in )
    {
        m_Vec.push_back(this);
    }
    void Remove( Base* in )
    {
        m_Vec.erase(find(m_Vec.begin(), m_Vec.end(), this));
    }
private:
    static vector<Base*> m_Vec;
};

class Actor : public Base
{
public:
    Actor()
    {
        Add( this );
    }
    ~Actor()
    {
        Remove( this );
    }
};

class Beast : public Base
{
        // do as in Actor
};
于 2013-10-30T14:27:30.030 回答