在从指向对象的指针调用成员函数指针时出现错误的函数调用。

问题描述 投票:0回答:1

所以我正在为一个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();
    }
};

如果在main中我要做以下事情

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();

它必然会导致以下错误:" Unhandled exception at 0x75284192 in lambda expression.exe: Microsoft C++异常。std::bad_function_call 在内存位置0x0058F710。"

而进入debug autos,我可以看到它将动作读作 "空"。

然而,切换顺序为

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; });

两者都能正常工作! (打印 "hello world")

注意:在这两种情况下,正常的指针对应的代码都不能工作。

有谁知道什么原因会导致这种情况?我打算研究一下,但似乎相当微妙!如果我找到了原因,我将把它发布在这个帖子上。谢谢您!谢谢您

在Visual Studio 2019版本16.4.3中工作。

c++ oop lambda smart-pointers member-function-pointers
1个回答
0
投票
foo obj= foo();

obj 是由默认构造函数构造的,所以在 std::function.

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

你创建新的实例 Foo 堆上,其寿命由智能指针管理 sp. 这个新设立的 Foo 对象中也没有一个目标。std::function因为 obj 在进行复制操作时,没有目标。Foo(const Foo&) 只是复制了空函数。

构建完 sp,这两个 Foo 实例是完全不相关的。通过访问 sp 你不修改 obj反之亦然。所以 obj.add_action 无法更新 std::functionFoo 所建 shared_ptr.

© www.soinside.com 2019 - 2024. All rights reserved.