返回基类对象中的派生对象指针

时间:2014-06-12 13:31:40

标签: c++ pointers inheritance

我有以下问题,我不知道为什么这不起作用。编译器不会产生任何错误,但是当我执行代码时,它会崩溃。

我有一个基类Message和一个派生类MessageA。

class Message{

protected:

Message(){}

public:

virtual ~Message(){}

virtual void setType(int type) = 0;
virtual int  getType() = 0;

protected:

int type;

};

class MessageA : public Message

{
public:
MessageA(const uint32_t cid);
MessageA();

~CanMessage();


void setCID(const uint32_t cid);


void setType(int type);
int  getType();


uint32_t getCID();

private:

uint32_t cid;

};

为了灵活,我将提供哪种消息作为函数的参数接收我选择的参数类型Message *消息。

bool ReceiveSingle(Message* message)
{

message = new MessageA(0x53);

return true;

}

在另一个函数中调用该函数,其中应对返回的指针执行操作:

Message* temp_message; //Global variable

/*

....

*/

ReceiveSingle(temp_message)
{

    MessageA* temp = static_cast<MessageA*>(temp_message);

    int cid = temp->getCID();  // This operation does not work !!!!!       

}

所以我想保持ReceiveSingle的参数灵活并选择基类类型Message *。函数本身创建派生对象指针,并应通过全局基础对象指针temp_message*返回它。稍后应该可以访问派生对象的变量。静态转换工作,但当我执行getCID() te程序崩溃。我找不到任何解决这个错误的方法。

如果有人可以帮助我会很好!

非常感谢!!

3 个答案:

答案 0 :(得分:0)

取决于您为temp_message指定的内容,它可能只是Message而不是MessageA。 使用dynamic_cast而不是static_cast,然后检查temp是否为nullptr / NULL。如果为NULL,则temp_message为Message而不是MessageA。

答案 1 :(得分:0)

考虑到你要静态转换指针,你实际上并没有利用动态多态性。

我的建议是使用静态多态:

template<class Type>
auto func(const Type& t) {
    int cid = t.getCID();
    // ...
}   

然后在外面使用std::unique_ptr(或任何其他智能指针):

auto message = std::unique_ptr<MessageA>(new MessageA(0x53));
auto ret     = func(*message);

最初的问题是:

bool ReceiveSingle(Message* message) {
    message = new MessageA(0x53);
    return true;
}

实际上并没有修改传递的指针。快速修复:

bool ReceiveSingle(Message*& message) {
//                         ^
    message = new MessageA(0x53);
    return true;
}

但这是一个可怕的主意,主要是因为你使用的是裸指针。

答案 2 :(得分:0)

我找到了一个快速有效的解决方案:

ReceiveSingle(Message** message) {

    MessageA* new_message = new MessageA(0x53);

    *message = new_message;

    return true;

}

要使用ReceiveSingle(Message** message)使用

致电Message* temp_message
ReceiveSingle(&temp_message);

然后,要访问存储在temp_message中的MessageA对象,请使用静态强制转换:

MessageA* tempA = static_cast<MessageA*>(temp_message);