如何减少C++20中模板类型名的重复书写?
减少C++模板矩阵类函数的类型冗余方案
你提到的Matrix类因模板参数导致函数接口重复冗余的问题,在现代C++里有几种简洁的解决方式,同时能满足替换uint8_t、使用rows()/columns()的要求,以下是具体方案:
1. 用auto返回值简化签名(C++14+)
这是最直接的优化方式,利用C++14的自动返回值推导,省去重复书写完整的Matrix模板类型:
template <uint8_t ROWS, uint8_t COLUMNS> auto operator*(const Matrix<ROWS, COLUMNS>& lhs, const Matrix<ROWS, COLUMNS>& rhs) noexcept { using MatrixType = Matrix<ROWS, COLUMNS>; using size_type = typename MatrixType::size_type; MatrixType result; for (size_type row = 0; row < lhs.rows(); ++row) { for (size_type col = 0; col < lhs.columns(); ++col) { for (size_type i = 0; i < lhs.columns(); ++i) { result(row, col) += lhs(row, i) * rhs(i, col); } } } return result; }
- 用
auto替代返回值的重复类型,编译器会自动推导返回类型为Matrix<ROWS, COLUMNS> - 函数内用
using定义MatrixType和size_type,避免重复书写模板类型和硬编码uint8_t - 循环条件改用
lhs.rows()和lhs.columns(),不再依赖模板参数,更贴合类的封装设计
2. 基于类型推导的模板参数简化(C++17+)
进一步把模板参数从具体的ROWS/COLUMNS改成直接推导Matrix类型,彻底消除接口处的模板参数冗余:
#include <type_traits> template <typename MatrixT> requires std::is_same_v<MatrixT, Matrix<MatrixT::rows_v, MatrixT::columns_v>> auto operator*(const MatrixT& lhs, const MatrixT& rhs) noexcept { using size_type = typename MatrixT::size_type; MatrixT result; for (size_type row = 0; row < lhs.rows(); ++row) { for (size_type col = 0; col < lhs.columns(); ++col) { for (size_type i = 0; i < lhs.columns(); ++i) { result(row, col) += lhs(row, i) * rhs(i, col); } } } return result; }
- 模板参数直接接收
MatrixT,编译器会自动推导传入的Matrix实例类型 - 用C++20的
requires约束确保MatrixT确实是Matrix模板的实例,避免传入其他无关类型 - 接口处完全看不到
ROWS/COLUMNS参数,可读性大幅提升 - 同样用
MatrixT::size_type替代uint8_t,循环依赖类的成员方法获取尺寸
3. 可选优化:用range-based for循环简化代码(C++20+)
如果Matrix类支持行/列迭代器,还可以用range-based for进一步简化循环逻辑(需Matrix类提供对应迭代器实现):
#include <type_traits> template <typename MatrixT> requires std::is_same_v<MatrixT, Matrix<MatrixT::rows_v, MatrixT::columns_v>> auto operator*(const MatrixT& lhs, const MatrixT& rhs) noexcept { using size_type = typename MatrixT::size_type; MatrixT result; for (size_type row_idx = 0; const auto& row : lhs) { for (size_type col_idx = 0; auto& val : result[row_idx]) { val = 0; for (size_type i = 0; i < lhs.columns(); ++i) { val += row[i] * rhs[i][col_idx]; } ++col_idx; } ++row_idx; } return result; }
- 这种方式减少手动管理循环变量的代码,让逻辑更聚焦于矩阵运算本身
内容的提问来源于stack exchange,提问作者ulfben
相关产品推荐
相关产品推荐

