本文介绍了在被调用函数内部更改函数指针(std :: function)是否安全?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个 std :: function 指向一个函数。在此函数内,我将指针更改为另一个函数。

I have a std::function pointing to a function. Inside this function I change the pointer to another function.

std::function<void()> fun;

void foo() {
    std::cout << "foo\n";
}

void bar() {
    std::cout << "bar\n";
    fun = foo;
}

int main() {
    fun = bar;
    fun();
    fun();
}

我看不到任何问题,而且效果很好(请参阅),但是我不确定这样做是否合法。我有什么想念的吗?也许在c ++标准草案中(我检查很快,但到目前为止什么都没看到)。

I can't see any problem and it works just fine (see here), however I'm not sure if this is legal to do so. Is there anything I am missing? Maybe in the c++ standard draft (I checked quickly but didn't see anything so far).

推荐答案

这是合法的函数

当您为目标分配或构造一个 std :: function 时,它会创建一个复制目标。在为 std :: function 分配功能的情况下,这实际上将功能指针存储为目标对象。

When you assign or construct a std::function with a target, it creates a copy of the target. In the case of assigning a function to the std::function, this in effect stores a function pointer as the target object.

当您调用 operator()时,需要返回如果您使用参数调用目标时会发生的情况。

When you invoke operator(), it is required to return what would happen if you invoked that the target with the arguments.

在函数对象副本的主体中,如果您重新分配给<$,则该副本作为副本存储在 std :: function 中c $ c> std :: function ,这会破坏旧的目标函数对象。

Within that "body" of the copy of the function object stored as a copy in the std::function, if you reassign to the std::function, this destroys the old target function object.

销毁函数指针不会影响在指向的函数中执行的代码。

Destroying a function pointer has no impact on the validity of code executed within the function pointed to.

但是,如果您存储了函数 objects (lambda,手动值,其他 std :: function s, std :: bind 等),在分配时,您会遇到通常的运行规则 this 被销毁时的类中的方法。简而言之,您将无法执行依赖于实例的本地状态的任何操作。

However, if you had stored function objects (lambdas, manual ones, other std::functions, std::bind, etc), at the point of assignment you'd run into the usual rules of running a method in a class when this is destroyed. In short, you would no longer be able to do anything that relied on "local state" of your instance.

std::function<void()> fun;
struct bob {
  std::string name;
  bob* next = 0;
  void operator()() const {
    std::cout << name << "\n";
    if (next) fun = *next;
    // undefined behavior:
    // std::cout << name << "\n";
  }
};
bob foo = {"foo"};
bob bar = {"bar", &foo};

int main() {
  fun = bar;
  fun();
  fun();
}

因此您可以看到,这可能很脆弱。

So as you can see, this can be fragile.

这篇关于在被调用函数内部更改函数指针(std :: function)是否安全?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!

10-09 22:03