gpt4 book ai didi

c++ - 为什么子类对象调用母类的成员函数?

转载 作者:太空宇宙 更新时间:2023-11-04 15:12:03 25 4
gpt4 key购买 nike

我想用一个方法“execute()”创建一个基类“process”,它在线程中运行一个任务“work()”。例如,当我创建一个派生类“product”和一个对象“p”时,p.execute() 运行基类的“work()”,即使它是虚拟的。谁能告诉我为什么?

这是我的代码:1-对于基类:

#include <thread>
#include <iostream>


class process
{

private:

std::thread *th;
public:
virtual void work();
virtual void execute();

//Delete the copy constructor
process(const process&) = delete;

//Delete the Assignment opeartor
process& operator=(const process&) = delete;

// Parameterized Constructor
process();

// Move Constructor
process(process && obj);

//Move Assignment Operator
process & operator=(process && obj);

//Destructor
~process();

};

// Parameterized Constructor
process::process()
{
th!=NULL;
}

// Move Constructor
process::process(process && obj) : th(std::move(obj.th))
{
std::cout << "Move Constructor is called" << std::endl;
}

//Move Assignment Operator
process & process::operator=(process && obj)
{
std::cout << "Move Assignment is called" << std::endl;
if (th->joinable())
th->join();
th = std::move(obj.th);
return *this;
}


// Destructor
process::~process()
{
if(th!=NULL){
if (th->joinable())
th->join();
}
}



void process::work()
{
printf("work of base class \n");
}


void process::execute()
{
printf("execute of base class \n");
th=new std::thread(&process::work, this);
}

2-派生类:

class product : public process 
{
public:
void work();
};


void product::work() {
printf("work of product class\n");
}

3-主要功能:

int main()
{
product p;
p.execute();

return 0;
}

我希望得到:

execute of base class 
work of product class

但我实际上得到:

execute of base class 
work of base class

最佳答案

你的代码有未定义的行为,因为你在错误的地方加入。

尽管您的类在销毁时正确地加入了线程,但要确保 process在线程的持续时间内仍然存在,the derived sub-object is already dead by then .

因此,您可能会看到 product::execute被调用,或 process::execute被调用,或者猫从你的显示器中涌出并开始输入它们自己的程序。

您需要在任何对象被销毁之前加入,无论是从 main 中或者将此代码也添加到 product析构函数。

进行此更改时,我得到了预期的结果。


tl;dr:虚拟调用工作正常,但您的加入位置错误。


此外,您还包括 <iostream>但永远不要使用它,你存储(并移动!)一个指向 std::thread 的指针而不是简单地拥有 std::thread ,并且您的“参数化构造函数”不接受任何参数(并且有一个无用的 th!=NULL ,并且什么都不做)。

以下是针对上述所有问题的快速修复:

#include <thread>
#include <iostream>

class process
{
private:
std::thread th;

public:
virtual void work();
virtual void execute();
void endExecution();

~process();
};

process::~process()
{
// Just in case, but you don't want to rely on this!
// See main() -- or do this also in ~product().
endExecution();
}

void process::work()
{
std::cerr << "work of base class\n";
}

void process::execute()
{
std::cerr << "execute of base class\n";
th = std::thread(&process::work, this);
}

void process::endExecution()
{
if (th.joinable())
th.join();
}

class product : public process
{
public:
virtual void work() override;
};


void product::work() {
std::cerr << "work of product class\n";
}

int main()
{
product p;
p.execute();
p.endExecution();
}

( live demo )

更好的类设计应该允许您以不易出错的方式执行此操作。

关于c++ - 为什么子类对象调用母类的成员函数?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/54006799/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com