如何在Matrix类实例执行的lambda内访问其成员函数
问题根源
你当前在LinAlg::outer_product方法中捕获的this指针指向的是LinAlg类的实例,不是你创建的Matrix类对象matrix的指针,因此lambda内部找不到属于Matrix类的set_element成员函数。
另外还有一个隐藏的参数不匹配问题:iterate_over_matrix调用回调函数时传入的是row、column的临时右值,你的lambda参数定义为非const左值引用std::size_t&,无法绑定到右值,即使解决了成员函数访问问题也会编译报错。
解决方法
有两种常用的实现方案:
方案1:显式捕获Matrix实例调用成员函数
直接在lambda捕获列表中加入你创建的matrix对象,调用时显式指定调用该实例的set_element方法即可,同时修正lambda参数类型:
template <class T> Matrix<T> LinAlg::outer_product( const std::vector<T> &vector_1 , const std::vector<T> &vector_2 ) { Matrix<T> matrix = Matrix<T>( vector_1.size() , vector_2.size() ); matrix.iterate_over_matrix( [&matrix, &vector_1, &vector_2](std::size_t row, std::size_t col) { matrix.set_element( row, col, vector_1[row] * vector_2[col] ); } ); return matrix; }
这种方案改动量最小,不需要修改原有Matrix类的实现。
方案2:改造遍历方法自动传入Matrix实例
修改Matrix::iterate_over_matrix,将当前实例的引用作为第一个参数传给回调函数,后续调用时无需手动捕获Matrix实例:
- 先修改
iterate_over_matrix实现:
template<typename Func> void iterate_over_matrix(Func function) { for (std::size_t row = 0; row < rows; ++row) { for (std::size_t column = 0; column < columns; ++column) { function(*this, row, column); } } }
- 调用时lambda接收Matrix实例引用即可:
matrix.iterate_over_matrix( [&vector_1, &vector_2](Matrix<T>& mat, std::size_t row, std::size_t col) { mat.set_element( row, col, vector_1[row] * vector_2[col] ); } );
这种方案适合大量场景需要在遍历回调中操作Matrix成员的情况,避免每次调用都手动捕获Matrix实例。
额外注意
你原有Matrix构造函数的语法有错误,少了一个左大括号,修正后为:
Matrix(int rows, int columns) : rows(rows), columns(columns) { matrix = new T[columns * rows]; }
内容的提问来源于stack exchange,提问作者Markus
相关产品推荐
相关产品推荐

