c – 将lambdas与捕获传递给传统回调

我在C 11项目中使用C库,这个C库提供了一个需要函数指针的函数.我希望将C 11 lambda传递给它,除非我捕获变量,否则它会正常工作.这是一个简短的例子:

#include <cstdio>
#include <functional>

typedef int (*Callback)();

void legacy(Callback callback) {
    printf("%i\n", callback());
}

int stdCallback() {    
    return 1; 
}

int main(int argc, char* argv[]) {
    int number = 3;    

    // Standard C callback works
    legacy(stdCallback);

    // Lambda without capturing works
    legacy([]() { return 2; });    

    // Lambda with capturing doesn't work
    legacy([&]() { return number; });

    return 0;
}

GNU C编译器在第三次调用遗留函数时给出了以下错误消息:

test.cpp: In function ‘int main(int, char**)’:
test.cpp:24:36: error: cannot convert ‘main(int, char**)::<lambda()>’ to ‘Callback {aka int (*)()}’ for argument ‘1’ to ‘void legacy(Callback)’
 legacy([&]() { return number; });

我怎样才能解决这个问题?或者技术上不可能使用捕获lambda作为C函数指针?

最佳答案
不,如果它捕获了任何东西,你就无法将lamdba转换为函数指针.

C标准,第5.1.2 / 6节:[expr.prim.lambda],强调我的:

The closure type for a non-generic lambda-expression with no lambda-capture has a public non-virtual non-explicit const conversion function to pointer to function with C ++ language linkage (7.5) having the same parameter and return types as the closure type’s function call operator. The value returned by this conversion function shall be the address of a function that, when invoked, has the same effect as invoking the closure type’s function call operator

转载注明原文:c – 将lambdas与捕获传递给传统回调 - 代码日志