【问题标题】:Bad function call in calling member function pointer from pointer to an object从指向对象的指针调用成员函数指针时调用错误的函数
【发布时间】:2020-04-23 20:20:39
【问题描述】:

所以我正在为 OOP 课程编写一个项目。我遇到了这种特殊性。 我有一个具有可自定义功能的类,例如:

#include<memory>  
#include<functional>
#include<iostream>
class foo 
{
private:
   std::function<void()> action = nullptr;
public:
    foo() = default;
    void add_action(std::function<void()> lambda_expression)
    {
        action = lambda_expression;
    }
    void do_action() 
    {
        action();
    }
};

如果我主要做以下事情

std::shared_ptr<foo> sp;
{
    foo obj= foo();
    sp = std::make_shared<foo>(obj);
    obj.add_action([]() {std::cout << "hello world" << std::endl; });
}
sp->do_action();

它将不变地导致以下错误:“在 lambda expression.exe 中的 0x75284192 处出现未处理的异常:Microsoft C++ 异常:std::bad_function_call 在内存位置 0x0058F710。”

进入调试汽车,我可以看到它将操作读取为“空”。

但是,这样切换顺序

obj.add_action([]() {std::cout << "hello world" << std::endl; });
sp = std::make_shared<foo>(obj);

或者使用共享指针调用add_action():

sp = std::make_shared<foo>(obj);
sp->add_action([]() {std::cout << "hello world" << std::endl; });

两者都工作正常! (打印“你好世界”)

注意:与此代码对应的普通指针在这两种情况下都不起作用。

有人知道是什么原因造成的吗?我要调查它,但似乎相当微妙! 如果我找到了将其发布在此线程上的原因。 谢谢!

在 Visual Studio 2019 版本 16.4.3 中工作

【问题讨论】:

    标签: c++ oop lambda smart-pointers member-function-pointers


    【解决方案1】:
    foo obj= foo();
    

    obj是默认构造函数构造的,所以std::function中没有目标。

    sp = std::make_shared<foo>(obj);
    

    您在堆上创建Foo 的新实例,其生命周期由智能指针sp 管理。这个新创建的Foo 对象在std::function 中也没有目标,因为在执行复制操作时obj 没有目标。 Foo(const Foo&amp;) 刚刚复制了一个空函数。

    sp 构造完成后,这两个Foo 实例完全不相关。通过访问sp,您不会修改obj,反之亦然。所以obj.add_action 无法更新Foostd::functionshared_ptr 构造。

    【讨论】:

      猜你喜欢
      • 2012-12-16
      • 1970-01-01
      • 2013-01-26
      • 2021-06-06
      • 1970-01-01
      • 2010-12-28
      • 2023-03-28
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多