【问题标题】:C++/Qt Object to Vector & Back to ObjectC++/Qt 对象到向量 & 返回对象
【发布时间】:2013-07-13 07:45:18
【问题描述】:

简单地说,我无法从 Vector 中的对象调用非继承方法。

我正在使用 Qt Creator 2.7.0,据我所知,它还没有使用完整的 C++11(?) - 我不确定这是否是导致以下问题的原因(尽管我非常确定不是我的 IDE/编译器):

我有 3 个类继承自基类,每个类都有一个额外的原始/getter/setter。

简单地说,我的课程如下所示:

class A 
{
  public:
    virtual std::string getName() = 0 ;
    virtual void setName(std::string) = 0 ;
    virtual int getNumber() ;
    virtual void setNumber(int) ;
  protected:
    std::string name ;
    int number ;
}

class B : public A
{
  public:
    std::string getName() ;
    void setName(std::string) ;
    int getNumber() ;
    void setNumber(int) ;

    std::string getEmail() ;
    void setEmail(std::string) ;
  protected:
    std::string email ;
}

在我的主目录中,我有一个指针向量,即:

std::vector<A*> contacts ;

//Add Pointers to Vector
A *a ;
B *b ;
contacts.push_back(a) ;
contacts.push_back(b) ;

然后我Check Object Class Type,以确保它属于 B 类。

if (dynamic_cast<B*>(contacts.at(1)) != NULL) //nullptr not working in Qt yet
{

我可以访问 A 类的 getter 和 setter,但不能访问 B:

std::string name = contacts.at(1)->getName() ; //Works

std::string email = contacts.at(1)->getEmail() ; //Compiler Error: 'class A' has 
                                                 //no member named 'getEmail'

}

错误(“A 类”没有名为“getEmail”的成员)发生在编译时而不是运行时。

我看不到它是 Object Slicing,因为这应该都是多态的,我应该使用某种类型的 C++ Casting吗?

任何正确方向的帮助或踢球将不胜感激,谢谢。

【问题讨论】:

  • 请注意,Qt Creator 对您是否编写 C++11 代码没有发言权。例如,nullptr 工作得非常好,即使 Creator 没有将其突出显示为关键字,其他所有 C++11 功能也是如此。决定您可以使用什么的是您正在使用的编译器,而不是编辑器或 IDE。
  • 我以前在这里和 Qt 论坛上发现了相互矛盾的 cmets,这让我相信编译器和 IDE 之间存在问题。阅读您的评论后,我发现this compiler flag & 所以我可以使用'nullptr'

标签: c++ qt vector polymorphism


【解决方案1】:

您需要使用dynamic_cast 来获取指向派生类型的指针。您实际上并没有这样做,您是在 A* 上调用 B 方法:

contacts.at(1)->getEmail() ; // look, no dynamic_cast

你需要做同样的事情:

B* b = dynamic_cast<B*>(contacts.at(1));
std::string email = b ? b->getEmail() : "N/A";

【讨论】:

    【解决方案2】:

    contacts 属于基类 A。!您必须对派生的执行操作。!

    而不是 contacts.at(1)-&gt;getName 使用vector&lt;B*&gt; b-&gt;getName

    希望这能清除:)

    【讨论】:

      【解决方案3】:

      您的 contacts 向量包含 A*。 C++ 在编译时验证类型,因此在执行代码时没有问题。由于contacts 是A* 类型,所以只能调用A 类的方法。 在您的情况下,您想在可能是B 的对象上调用 B 方法,或者不是! C++ 确定它是 A,但它可能是 C(如果 C 类继承自 A)。 您要做的是获取向量中 B 对象的实例并将其转换为 B 以便您可以调用方法:B* b = dynamic_cast&lt;B*&gt;(contacts.at(1)); noyw 使用 b 来做任何您想做的事情。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2023-01-04
        • 1970-01-01
        • 2011-06-06
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多