代码之家  ›  专栏  ›  技术社区  ›  LoudNPossiblyWrong

lambda表达式能否作为函数指针传递?

  •  29
  • LoudNPossiblyWrong  · 技术社区  · 14 年前

    我正试图将lambda表达式传递给接受函数指针的函数,这是否可能?

    下面是一些示例代码,我使用的是VS2010:

    #include <iostream>
    using namespace std;
    
    void func(int i){cout << "I'V BEEN CALLED: " << i <<endl;}
    
    void fptrfunc(void (*fptr)(int i), int j){fptr(j);}
    
    int main(){
        fptrfunc(func,10); //this is ok
        fptrfunc([](int i){cout << "LAMBDA CALL " << i << endl; }, 20); //DOES NOT COMPILE
        return 0;
    }
    
    5 回复  |  直到 9 年前
        1
  •  26
  •   RiaD    9 年前

    在VC10RTM中,没有,但是在VC10中的lambda功能完成之后,标准委员会添加了允许无状态lambda降级为函数指针的语言。所以在未来这是可能的。

        2
  •  14
  •   fredoverflow    14 年前

    你可以使用 std::function 为此:

    void fptrfunc(std::function<void (int)> fun, int j)
    {
        fun(j);
    }
    

    或者完全通用:

    template <typename Fun>
    void fptrfunc(Fun fun, int j)
    {
        fun(j);
    }
    
        3
  •  4
  •   user222202    13 年前

    这在VS2010中有效:

    template<class FunctorT>
    void* getcodeptr(const FunctorT& f) {
      auto ptr = &FunctorT::operator();
      return *(void**)&ptr;
    } 
    
    void main() {
      auto hello = [](char* name){ printf("hello %s\n", name); };
      void(*pfn)(char*) = (void(*)(char*)) getcodeptr(hello);
      pfn("world");
    }
    
        4
  •  0
  •   Edward Strange    14 年前

    不,不行。至少不可靠。我知道VS2010将它们实现为对象函数。根据他们的工作方式,这可能是 先验的 要求。

        5
  •  0
  •   Sri    10 年前

    只要lambda不使用capture子句(即不从上面捕获变量),它就可以用作函数指针。VC编译器在内部生成具有不同调用约定的匿名函数,这样就可以毫无问题地使用它。