如何创建标记为WRONG的对象?它是一个部分专用模板类。
template<typename C, typename size_type = unsigned short>
struct MatrixDataRect {...};
template<typename T, size_t H, size_t W>
class MatrixDataRect<std::array<T,H*W>, size_t> {...};
int main()
{
MatrixDataRect<std::vector<double>> mat_data_vector;
MatrixDataRect<std::array<double,10*5>> mat_data_array; // WRONG!!!!
return 0;
}
这是错误的,因为WRONG行使用第一个模板类。不是第二个。 因为编译器不能分别为H和W分配10 * 5。
答案 0 :(得分:4)
template<typename T, size_t H, size_t W>
class MatrixDataRect<std::array<T,H*W>, size_t> {...};
MatrixDataRect<std::array<double,10*5>> mat_data_array;
问题是模板参数H和W不能从调用地推断出来。基本上,在实例化期间,copiler将乘以5*10
以生成50
,然后尝试实例化std::array<double,50>
,然后使用实例化类型来实例化MatrixDataRect<std::array<double,50>>
。此时,无法确定H
的{{1}}和W
的值是多少({1}}(5和10?,10和5?,25和2?)。 ..)
由于无法应用类型推导,编译器将回退到非专用版本并实例化主模板。
您可以使用的替代方法是:使专业化采用MatrixDataRect
和单一大小参数(作为主模板)。这适用于问题中的所有代码,如果您需要这两个维度,则可能不适用于其他成员。更改模板,以便明确传递大小。
答案 1 :(得分:2)
有两个问题:
10*5
被评估为50,然后编译器尝试推导出H*W
,这是无法完成的。它们可以是任何size_t
值乘以50。
您专门将size_t
作为第二个模板参数,必须在实例化时给出,因为它无法推断出来。否则,您只是实例化MatrixDataRect<std::array<double,10*5>, unsigned short>
。
以下方法可行:
template<typename C, typename size_type = unsigned short>
struct MatrixDataRect {...};
template<typename T, size_t S>
class MatrixDataRect<std::array<T,S>, size_t> {...};
int main()
{
MatrixDataRect<std::vector<double>> mat_data_vector;
MatrixDataRect<std::array<double,10*5>, size_t> mat_data_array;
return 0;
}