如何自定义c ++列表容器,以便它可以容纳不同类型的结构?

时间:2014-05-18 14:31:24

标签: c++ c++11

如何自定义c ++列表容器,使其可以包含不同类型的struct?

例如

struct A
{
  int a;
  int b;
}

struct B
{
  float a;
  float b;
}


#include <list>
using namespace std;
int main()
{
   ...
   ...
   A a;
   a.a = 1;
   a.b = 2;

   B b;
   b.a = 123.444;
   b.b = 11.222;

   List.push_back(a);
   List.push_back(b);

   return 0;
}

3 个答案:

答案 0 :(得分:1)

为什么不polymorphism以及指向对象的指针列表? 关注对象的生命周期。一旦两个对象超出范围,列表中的指针将变为无效。完成后,您可以选择dynamically allocate)两个元素,删除,然后将其从列表中删除。

稍后编辑:我觉得你是C ++的新手。在研究动态分配后,我建议你查找智能指针。他们通过自己动手来解除手动管理内存的负担:

unique_ptrshared_ptr

您可以在列表中使用它们而不是裸指针。

struct Base
{
    virtual ~Base(){}
};
struct A : public Base
{
  int a;
  int b;
};

struct B : public Base
{
  float a;
  float b;
};


#include <list>
using namespace std;
int main()
{
   ...
   ...
   A a;
   a.a = 1;
   a.b = 2;

   B b;
   b.a = 123.444;
   b.b = 11.222;

   std::list<Base*> l;
   l.push_back(&a);
   l.push_back(&b);

   return 0;
}

答案 1 :(得分:1)

在某些情况下,将不同类型存储在容器中是有意义的。 C ++使用联合支持这些用例,但此功能非常基本。如果您确实需要在容器中存储不同类型,我建议使用 boost :: variant 而不是联合。我还建议使用std::vector代替std::list,因为否则使用此优化没有多大意义。

以下是 boost :: variant 的示例:

std::vector<boost::variant<A, B>> items;
A a = ...;
B b = ...;
items.push_back(a);
items.push_back(b);
struct get_length : boost::static_visitor<double>
{
    double operator()(const A& f) const { return calc(f.a, f.b); }
    double operator()(const B& b) const { return calc(b.a, b.b); }
    double calc(double a, double b) const { return std::sqrt(a * a + b * b); }
};
for (auto&& item : items) {
    double d = boost::apply_visitor(get_length(), item);
    std::cout << d << '\n';
}

答案 2 :(得分:0)

我建议boost:: any。但是真的,多态性不能解决你的问题吗?