lambdas中的参考范围捕获

时间:2018-03-05 03:39:14

标签: c++ lambda c++14 pass-by-reference

是否可以从带有引用捕获的嵌套lambda函数中访问在封闭函数范围内定义的所有局部变量(作为参数和本地定义)?在以下代码的情况下(仅重现相关代码),我获得了未声明标识符的编译错误,这个问题已被提示:

template<typename T, typename C>
matrix<T,C>::matrix(C const& crC, unsigned short numElems){

    //lambda 
    function<void()> create_matrix = [&] (){

        if(current_index == sz){

            return;
        }

        auto row = make_unique<T[]>(numElems);
        auto count = 0;

        while(count < numElems){

            row[count++] = crC[current_index++];
        }
        objRef.push_back(row);
        create_matrix();
    };

    auto sz = crC.size();
    auto current_index = 0;
    ref_2_cont objRef = impl_matrix;

    create_matrix();
}

我在上面的代码的上下文中得到以下编译错误:

g++ -ggdb -std=c++14 -Wall main.cpp -o main.o
In file included from main.cpp:1:
./code.hpp:85:12: error: use of undeclared identifier 'current_index'
        if(current_index == sz){
           ^
./code.hpp:85:29: error: use of undeclared identifier 'sz'
        if(current_index == sz){
                            ^
./code.hpp:95:32: error: use of undeclared identifier 'current_index'
            row[count++] = crC[current_index++];
                               ^
./code.hpp:97:9: error: use of undeclared identifier 'objRef'
        objRef.push_back(row);

附录

已添加此代码段以与对等组共享另一个使用上下文,其中我使用嵌套的lambdas,其方式类似于原始帖子中隐含的用法。但是,在这种情况下,编译的代码没有任何错误或警告。

template<typename T1, typename T2> 
void tree<T1,T2>::reLinkNodes(iter_sp2node_cont Itr){

    //lambda defintion

    function<void(iter_sp2node_cont, r_sp2node_cont)> lnk_part_hier = [&] (iter_sp2node_cont Itr, r_sp2node_cont objRef){

        //lambda definition

        function<void(ptrdiff_t)> lnk_one_hier = [&] (ptrdiff_t diff){

              decltype(diff) index; 

              if(0 == diff){

                  (*Itr).get()->mark_as_root();

                  (*Itr).get()->setParent();

                  ++Itr;
                  (*Itr).get()->unmark_as_root();

                  --Itr;

                  auto cpyItr = Itr;

                  Itr = next(Itr);

                  (*cpyItr).get()->setLeftChild(*Itr);
                  (*Itr).get()->setParent(*cpyItr);

                  Itr = next(Itr);

                  (*cpyItr).get()->setRightChild(*Itr);
                  (*Itr).get()->setParent(*cpyItr);

                  Itr = cpyItr;
              }
              else if(1 == diff){

                  auto cpyItr = Itr;
                  index = 0;

                  (*Itr).get()->setParent(objRef[index]);
                  objRef[index].get()->setLeftChild(*Itr);

                  Itr = next(Itr);
                  (*Itr).get()->setParent(objRef[index]);
                  objRef[index].get()->setRightChild(*Itr);

                  Itr = cpyItr;
              }
              else if (diff > 2 && diff < objRef.size()/2){
                    if(diff % 2){
                        index = diff/2;
                    }
                    else{
                            index = diff/2 - 1;
                    }
                    (*Itr).get()->setParent(objRef[index]);
                  }

              if(diff > 0 && diff < objRef.size()/2){
                  {
                        auto idx = diff * 2 + 1;
                        if(idx < objRef.size())
                        {
                            (*Itr).get()->setLeftChild(objRef[idx]);
                            objRef[idx].get()->setParent(*Itr);
                        }

                        else{
                                (*Itr).get()->setLeftChild();
                        }
                        idx = diff * 2 + 2;
                        if(idx < objRef.size())
                        {
                            (*Itr).get()->setRightChild(objRef[idx]);
                            objRef[idx].get()->setParent(*Itr);
                        }
                        else{
                                (*Itr).get()->setRightChild();
                        }
                    }
                }

              return;
        };
        auto diff = distance(objRef.begin(), Itr);
       if(diff == objRef.size()){

            return;
        }
        else{

               lnk_one_hier(diff);

           }
        if(distance(Itr,objRef.end()) >= 2){
        Itr = next(Itr,2);
        lnk_part_hier(Itr,objRef);
        }
        else if(distance(Itr,objRef.end()) == 1){
            (*Itr).get()->setLeftChild();
            (*Itr).get()->setRightChild();

            return;
        }
        else{
                return;
        }

        return;
    };

    auto cpyItr = Itr;

    renameNodes(cpyItr);

    r_sp2node_cont objRef = hierarchy; 

    lnk_part_hier(Itr, objRef);
}

lambda lnk_one_hier()访问并使用在封闭的lambda lnk_part_hier()范围内定义的变量。

0 个答案:

没有答案