C++继承铸造,父母对孩子和回

问题描述:

只是不明白,如何实现这个原型。 我试图创建容器的基类的对象的Worker* 迭代容器,对象将调用虚拟方法->work()。根据派生类的指针应该叫他自己重写功能C++继承铸造,父母对孩子和回

class Worker { 
public: 
    Worker(...) { ... } 
    virtual void work() { /* justWork(); */ } 
}; 

class Professional : public Worker { 
public: 
    Professional(...) { ... } 
    virtual void work() override { /* workGood(); */ } 
}; 

class Workplace { 
public: 
    void train(Worker* worker) { 
     /* need to save object properties and 
      set pointer to derived class */ 

     // *worker = Professional(worker); 
     worker = new Professional(worker); 
     /* following compiles fine, but when I call worker->work() 
      outside of this body it calls simple Worker::work() 
      when I need to call Professional::work() */ 
    } 
    void fire(Worker* worker) { 
     /* need to save object properties 
      set pointer value back to 
      Parent/Base class Worker */ 

     // *worker = Worker(worker); 
    } 
}; 

int main() 
{ 
    Workplace workplace; 
    Worker* worker = new Worker(); 

    worker->work(); // Worker::work() => justWork() 

    workplace.train(worker); 
    worker->work(); 
    // should be Professional::work() => workGood(), 
    // but it calls Worker::work() => justWork() 

    workplace.fire(worker); 
    worker->work(); // Worker::work() => justWork() 

    return 0; 
} 
+0

你在这里通过'Worker *'值:void train(Worker * worker){'。我建议使用'std :: unique_ptr '来传递它们。 – user0042

+0

对于'Workplace :: train',您通过值*传递指针*。这意味着你有一个原始指针的*副本,所以这个分配只会改变副本,而不是你在'main'函数中创建的原始副本。 –

+0

@Someprogrammerdude所以我尝试过: 'Workplace :: train(Worker&worker){worker = Professional(); } workplace.train(* worker);' 也没有成功,我还在做错吗? –

我不能评论低于50代表,所以我必须写一个答案。 也许你解决了问题,但你也需要释放职场::火车()和工作场所::火(),你在main()已分配的内存空间:

Worker* worker = new Worker(); 

否则,你会得到内存泄漏。

class Workplace { 
public: 
    void train(Worker*& worker) { 
     Worker* temp = worker; 
     /* A temporary pointer to the allocated object. */ 

     worker = new Professional(temp); 
     /* Allocating memory for new object. */ 

     delete temp; 
     /* Destroying previous object. */ 
    } 
    void fire(Worker*& worker) {    
     Worker* temp = worker;    
     worker = new Worker(temp); 
     delete temp; 
    } 
}; 

Workplace::fire()您分配*worker = Worker(worker);是行不通的。 worker仍然指向相同的类型(在这种情况下:到Professional)。 另外,如果要通过Worker*指针删除Professional以避免内存泄漏,则需要在Worker类中使用虚拟析构函数。

class Worker { 
public: 
    /* other member functions */ 
    virtual ~Worker() {} 
}; 
+0

aww,我能覆盖指针,它是通过正确的传递参数声明在main中,而不是释放内存吗? –

+0

_overwriting_是什么意思?也许这个:'* worker = Professional(worker)'?因为它不会工作。如果您希望指针指向**另一个类型**,则必须为新对象分配内存,并删除前一个。 –

+0

另外,最好将引用传递给构造函数而不是指针,如下所示:'Professional(const Worker&)'和'Worker(const Professional&)'。并以这种方式调用它们:'worker = new Professional(* temp)'和'worker = new Worker(* temp)'。如果通过引用传递,则不会创建指针的副本。 –

它的参数传递错误的,固定的:

void train(Worker*& worker) { ... } 
void fire(Worker*& worker) { ... } 

现在它的工作原理, TNX到@Someprogrammerdude @ user0042