动态强制转换,对象列表转换,模板

时间:2011-02-19 14:22:14

标签: c++ templates dynamic-cast

有两个班级:

class A
{
   private:
        double a1, a2;
   ...
};

class B : public A
{
   private:
        double b1, b2;
};

和通用容器

template <typename Item>
struct TList
{
    typedef std::vector <Item> Type;
};


template <typename Item>
class GList
{
private:
            typename TList <Item>::Type items;

};

有4个物体容器

GList <A> A1;
GList <B> B1;
GList <A*> A2;
GList <B*> B2;

是否允许这些转化(上/下):

1] GList <B> B3 = dynamic_cast <GList <B> &> (A1);
2] GList <A> A3 = static_cast <GList <A> &> (B1);
3] GList <B*> B4 = dynamic_cast <GList <B*> &> (A2);
4] GList <A*> A4 = static_cast <GList <A*> &> (B2);

有没有办法如何将对象列表转换为父对象列表,反之亦然?

更新了问题

那么reinterpret_cast呢?

1] GList <B> B3 = reinterpret_cast <GList <B> &> (A1);
2] GList <A> A3 = reinterpret_cast <GList <A> &> (B1);
3] GList <B*> B4 = reinterpret_cast <GList <B*> &> (A2);
4] GList <A*> A4 = reinterpret_cast <GList <A*> &> (B2);

5 个答案:

答案 0 :(得分:1)

从根本上说,容器不是协变; std::vector<Base>std::vector<Derived>之间没有任何关系(std::vector<Base *>std::vector<Derived *>之间也没有关系。

对于值类型容器,通常存在基本问题sizeof(Derived) > sizeof(Base)。因此,std::vector中的所有内部指针数学如果你试图将一个强制转换为另一个,就会破坏。

对于指针类型的容器,这些转换可能“有效”(如果你可以让它们编译),但行为是未定义的。

答案 1 :(得分:0)

不,类型容器之间没有有效的转换,无论类型本身之间是否存在有效转换。

答案 2 :(得分:0)

GList <B> B3 = dynamic_cast <GList <B> &> (A1);

dynamic_cast仅适用于多态类型。这里GList不是多态的。因此它甚至不会编译!

如果你使这种多态,即使这样,这种演员也不行,因为GList<B><GList<A>之间没有关系。它们就像两种不同的不相关的类型。

事实上,它们的相关性与GList_BGList_A相关(假设,如果您定义了两个具有此类名称的不同类)。或者甚至更好,它们与Java和JavaScript,Car和Carpet相关的方式相关。

答案 3 :(得分:0)

如果对象具有关系(如A和B),则

dynamic_cast和static_cast有效。

但是模板创建了一个全新的类,没有办法使用这些类型。也许你可以尝试reinterpret_cast,但这不安全......

答案 4 :(得分:0)

您无法将对象列表转换为父对象列表。如果可以的话,我可以这样做:

GList<A>& a = convert_the_thing(B1);
a.add_a_element(A());

我会在你的B列表中插入一个A.