C++ - 从向量中获取派生类变量
Posted
技术标签:
【中文标题】C++ - 从向量中获取派生类变量【英文标题】:C++ - Reach derived class variables from vector 【发布时间】:2012-11-26 17:08:00 【问题描述】:我真的很困惑,所以我不得不问这个。我尝试编写一个应用程序,但我不知道如何访问派生类的变量,这些变量位于基类的向量中。 代码是:
class A
public:
A() ;
std::vector<A> aVector;
void Foo();
class B : public A
public:
B() ;
int j;
void A::Foo()
aVector.push_back( B() );
// Here I would like to reach B::j, but only the members and variables of A comes in
aVector[0].j; // wrong
B b = aVector[0]; // no suitable user-defined conversion from "A" to "B" exists
// should I use cast? which one?
我目前正在通过应用程序编程学习继承和这类东西,现在我真的卡住了。
我查找了其他问题,但找不到任何可以解决我的问题的问题。如果有,我错过了,对不起。
【问题讨论】:
【参考方案1】:您需要将pointers
存储到A
,这样您的新B
对象在推入向量时不会被“切片”(参见说明here)。
另外,当您想在基类的指针上专门使用子方法/变量时,您需要将cast
转换为正确的类型
std::vector<A*> aVector;
aVector.push_back(new B());
B* b = (B*)aVector[0];
cout << b->j;
// remember to delete the content of aVector
如果您不能 100% 确定它是您要投射的类型,那么投射这样的对象可能会很危险。
请参阅this thread 了解更多关于选角的信息(C style
、dynamic_cast
和 static_cast
)
【讨论】:
理想情况下,您应该存储 smart 指向A
的指针。想象一个裸向量,里面有数百万个指针,突然发生异常。 :P
虽然我同意,但我认为我们正在远离最初的问题 :)
谢谢!我接受了这一点,因为这给了我一个可行的解决方案。但是现在我看到还有很多东西要学:)【参考方案2】:
由于vector
被声明为包含A
类型的对象,因此当您将B
推入向量时,所有B
-ness 都会从存储在@987654326 中的对象中剥离@。这被称为slicing problem。
当您稍后尝试访问存储在vector
中的对象的B
元素时,您无法访问,因为它们根本不存在。您没有 vector
的 B 个对象 - 您有 vector
的 A
对象。
为了解决这个问题,你需要存储A
对象,而不是通过值,而是通过引用或指针。您不能将引用存储在 vector
中,所以这会给您留下指针。
【讨论】:
【参考方案3】:这与向量无关。如果B
派生自A
,则以下代码:
A a;
B b = a;
是一个错误(除非有某种方法可以转换)。
这是正确的 - 您应该能够统一处理您的矢量项目。如果这意味着使用向量的代码期望所有项目都是B
,那么只需创建一个vector<B>
。如果不是,那么无论如何您都没有将A
转换为B
的业务。
【讨论】:
【参考方案4】:您不应该尝试从基类访问派生类成员。基类应该不知道派生类的实现细节。你正在做的不是多态的。换句话说,您的 B 实例不能像 A 实例那样运行,因为您没有提供任何虚拟方法并且没有覆盖任何虚拟方法。
整个设计和方法不正确。 A::Foo() 应该是一个虚拟方法(甚至可能是抽象的)。你应该在 B::Foo() 中工作。
还有一件事,你不应该只持有一个简单的旧 A 的向量。它应该是指向 A 的指针。所以 std::Vector。并且该成员应该以字母 m 为前缀,以表明它是该类的成员变量。所以 std::vector mSomething;
【讨论】:
以上是关于C++ - 从向量中获取派生类变量的主要内容,如果未能解决你的问题,请参考以下文章