使用嵌套lambda时出现奇怪的编译错误

时间:2012-01-19 08:53:38

标签: c++ lambda nested c++11

我在vc2010上使用lambda编写了一些代码。简化的代码结构如下:

template<typename Functor>
bool f1(int a, Functor& f)
{
    return f(a+1);
}

template<typename Functor>
bool f2(Functor& f)
{
    return f(1);
}

template<typename Functor>
bool f3(Functor& f)
{
    return f2([&](int a) -> bool {
        // (1) Works
        auto test = [&](int b) -> bool { return f(a+b); };
        return f1(a, test);

        // (2) Doesn't work         
        //return f1(a, [&](int b) -> bool { return f(a+b); });
    });
};

int main()
{
    int a = 100;

    f3([&](int b) { return (a+b)%2 == 0; });
}

首先,我将嵌套的lambda代码编写为(2),而vc10给出了一个难以理解的错误消息,如下所示

'f1' : cannot convert parameter number from 'int' to 'int &'

然而,代码(1)效果很好,除了左值之外,它与(2)是一致的。

我的问题是:

  1. 代码(2)是否符合C ++ 11标准?
  2. 如果没有,这种奇怪的编译行为的原因是什么?

2 个答案:

答案 0 :(得分:4)

GCC 4.6给出以下错误:

  

a.cpp:在函数“int main()”中:
  a.cpp:30:43:错误:没有匹配函数来调用“f3(main()::<lambda(int)>)”   a.cpp:30:43:注意:候选人是:
  a.cpp:14:6:注意:bool f3(Functor&) [Functor = main()::<lambda(int)>]
  a.cpp:14:6:注意:参数1从“main()::<lambda(int)>”到“main()::<lambda(int)>&”没有已知的转换

哪个更清楚:你的lambdas是临时的,你试图将它们绑定到l值引用。所以只使用r值引用或根本没有引用:

template<typename Functor>
bool f1(int a, Functor&& f)
{
    return f(a+1);
}

template<typename Functor>
bool f2(Functor&& f)
{
    return f(1);
}

template<typename Functor>
bool f3(Functor&& f)
{
    return f2([&](int a) -> bool {
        // (1) Works
        auto test = [&](int b) -> bool { return f(a+b); };
        return f1(a, test);

        // (2) Doesn't work         
        //return f1(a, [&](int b) -> bool { return f(a+b); });
    });
};

int main()
{
    int a = 100;

    f3([&](int b) { return (a+b)%2 == 0; });
}

不知道VS是否可以编译它,但是GCC做得对。

答案 1 :(得分:0)

正如其他人所说,你不能将临时绑定到非const引用。

有三种方法可以解决这个问题:

  1. 传递值:

    模板 bool f1(int a,Functor f) {     返回f(a + 1); }

  2. 通过右值:

    模板 bool f1(int a,Functor&amp; f) {     返回f(a + 1); }

  3. 通过左值:

    模板 bool f1(int a,const Functor&amp; f) {     返回f(a + 1); }

  4. 我会选择第3个选项(通过左值或const引用传递)。

相关问题