3

使用带有 -std=c++0x 的 Eclipse/gcc 在 Ubuntu 上进行开发。

我似乎遇到了对象切片问题,这不属于我在这里看到的其他问题。我有一个非常简单的基类/子类继承模型。基类有一个纯虚函数,显然子类实现了它:

class Parent{
public:
    Parent();
    virtual ~Parent();
    virtual void DoStuff() = 0;
};

class Child : public Parent{
public:
    Child();
    virtual ~Child();
    virtual void DoStuff(); //Child can have "grandchildren"
};

我想要的是有一个队列,我可以在其中存储这些对象以供工作线程处理。我知道我应该存储指针,否则我会保证切片。因此,在执行此操作的类(“处理器”)中,我有:

typedef queue<Parent*> MYQUEUE; //#include <queue>
static MYQUEUE myQueue;

//Call this after creating "Child c;" and passing in &c:
void Processor::Enqueue(Parent* p) 
{
    myQueue.push(p);
}

void* Process(void* args) //function that becomes the worker thread
{
    while(true)
    {
        if(!myQueue.empty())
        {
            Parent* p = myQueue.front();
            p->DoStuff();
            myQueue.pop();
         }
    }
    return 0;
}

然后发生的是程序崩溃,说“调用了纯虚拟方法”,就好像继承/多态不能正常工作一样。我知道继承设置正确,因为当我测试时我确认这是有效的:

Child c;
Parent* p = &c;
p->DoStuff();

非常感谢任何指导!

4

2 回答 2

2

如果您将对象传递给工作线程,则无法在堆栈上创建它。当工作线程调用它时,父线程可能已经离开了该函数并销毁了该对象。您需要new在父线程中动态分配(可能通过)它,并且delete在完成后才在工作线程中释放()它。

另外需要注意的是,如果父进程能够在工作进程运行时将作业排入队列,则您需要锁定队列访问。

于 2013-02-19T16:58:24.093 回答
0

该错误意味着p在调用点指向的对象具有类型Parent。它是如何实现的取决于您未显示的代码。

于 2013-02-19T16:58:59.323 回答