如何在一个数组/容器中使用不同的对象?

Posted

技术标签:

【中文标题】如何在一个数组/容器中使用不同的对象?【英文标题】:How to use different objects in one array/container? 【发布时间】:2014-03-18 18:00:21 【问题描述】:

我是一名 C++ 初学者,正在制作我的第一个 2d 游戏(只是为了学习该语言的基础知识,我不打算做任何大事 :P)。我遇到了第一个问题,在互联网上找不到解决方案: 实体有一个主类:

class entity

   //something there
;

还有一些用于具体怪物、玩家等的派生类。

class zombie : public entity

  //...
;
class mutant : public entity
...
class player : public entity
...

现在的问题是如何为所有类型的实体创建一个数组(或一些容器/任何东西)?我的意思是,如果所有怪物和玩家对象都来自“实体”类,例如,碰撞会很简单:

std::vector<entity> entityTbl;
entityTbl.push_back( entity(...) );
...
entityTbl.push_back( entity(...) );

for(int i=0;i<entityTbl.end();i++)
  for(int k=0;k<entityTbl.end();k++)
    entityTbl[i].collision(entityTbl[k]); //some collision function

但是,如果我有不同类型的“zombie”、“mutant”、“player”......在这种情况下,我不能再使用“实体”容器了,原因有两个:

    我希望“类实体”是抽象的 如果我使用这个容器来制作例如播放器对象,我不能使用“类播放器”中的函数。

我希望你能明白我的意思。 :) 感谢您的帮助建议,对任何语言错误深表歉意 - 英语不是我的母语。

【问题讨论】:

C++ 区分大小写。 改用std::vector&lt;entity*&gt; 或者更好的std::vector&lt;std::shared_ptr&lt;entity&gt; &gt;。但是您需要先修复许多其他错误才能使您的代码可编译。 【参考方案1】:

您不能拥有抽象类的实例。而不是您的示例,请尝试以下操作:

 std::vector<std::shared_ptr<entity> > entityTbl;
 entityTbl.push_back( new zombie(...) );     
 entityTbl.push_back( new mutant(...) );

由于上述示例仅适用于 c++11,因此您可以使用作为备用解决方案

 std::vector<entity*> > entityTbl;

填表的代码是一样的。但是您需要 delete entityTbl 中的项目,然后才能将其销毁(超出范围):

 for(std::std::vector<entity*> >::iterator it = entityTbl.begin(); 
     it != entityTbl.end();
     ++it) 
     delete *it;
 

【讨论】:

非常感谢!我没想到会这么简单。再次感谢您!【参考方案2】:

尝试使用抽象类对象将发生错误,就像您在代码中尝试做的那样。 您可以拥有的是指向抽象类(在您的情况下是实体)的指针。 指向基类的指针可以指向派生类。 例如:

class base 
public: virtual void func() = 0;
;

class derived : public virtual base 
    void func() override  std::cout << "\"base\" type pointer, but pointing to \"derived\"." << '\n'; 
;
int main()

    base *basep;
    basep = new derived;
    basep->func();
    system("PAUSE");
    return EXIT_SUCCESS;

顺便说一句,在你的循环中,i 是一个 int,它不是 vector::end() 的返回值。 end() 是一个返回迭代器类型的函数 迭代器是由 STL 容器成员函数生成的类似指针的对象。 我建议您将循环修改为:

for (auto i = entityTbl.begin(); i != entityTbl.end(); i++)
    for (auto k = entityTbl.begin(); i != entityTbl.end(); k++)

更多信息: http://www.learncpp.com/cpp-tutorial/121-pointers-and-references-to-the-base-class-of-derived-objects/

http://www.cprogramming.com/tutorial/stl/iterators.html

祝你好运。

【讨论】:

以上是关于如何在一个数组/容器中使用不同的对象?的主要内容,如果未能解决你的问题,请参考以下文章

如何更改数组状态容器中的对象属性? React Hooks 使用状态

如何让多个不同单词的数组在游戏屏幕上移动?

如何解析具有相同键的不同数据类型的改造对象的json数组

Java数组

如何使用 $push (Mongoose) 在数组中推送多个对象

Java。如何将一个LinkedList里的元素全部复制到另一LinkedList容器里?