问题描述
我有一个 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::function
s, 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)是否安全?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!