用户想要通过复制传递,但它被封装库的[&]
阻止,这里是coliru MCVE :-
#include <iostream>
#include <string>
#include <type_traits>
#include <vector>
#include <functional>
int main(){
std::vector<std::function<void()>> funcs;
for(int n=0;n<3;n++){
auto func=[&,n](){ //[=] for n
std::cout<<""<<n; // user's code
};
//v library (actually inside another utility function)
funcs.push_back([&](){ //user's "n" is blocked ??
//(some library-related code here)
func();
});
//^ library
}
//v library
for(int m=0;m<3;m++){
funcs[m]();
}
}
它打印222
而不是012
。
为什么,以及如何解决它?
请注意,库无法知道n
。
根据相关问题(按值捕获 c++ lambda(,应正确复制该值。
这是一个更复杂的MCVE,它做同样的事情,但可以更好地描述我实际如何使用它:-
#include <iostream>
#include <string>
#include <type_traits>
#include <vector>
#include <functional>
std::vector<std::function<void()>> libraryStuff;
template<class F>void addToLibrary(F f){
libraryStuff.push_back([&](){ //user's "n" is blocked ??
//some code library related
f();
});
}
void libraryDoNow(){
for(int m=0;m<libraryStuff.size();m++){
libraryStuff[m]();
}
}
int main(){
std::vector<std::function<void()>> funcs;
for(int n=0;n<3;n++){
auto func=[&,n](){
std::cout<<""<<n; // user's code
};
addToLibrary(func);
}
libraryDoNow();
}
您正在通过引用捕获func
funcs.push_back([&](){..};
这会导致引用悬而未决,因为func
在稍后调用之前超出了范围:
//v library
for(int n=0;n<3;n++)
funcs[n]();
您需要按值捕获局部变量func
以获取它的副本(它包含在 -valuen
(。