提问人:Immanuel Kant 提问时间:6/28/2022 最后编辑:Vlad from MoscowImmanuel Kant 更新时间:6/28/2022 访问量:195
为什么 C++ 模板数组长度推导需要像 “f(T (&a)[N]” ?
Why C++ template array length deduction need to be like "f(T (&a)[N]"?
问:
使用 C++ 模板知道 C 样式数组的长度,我们需要这个:
#include<stdio.h>
template<class T,size_t N>
size_t length(T (&a)[N]){ return N; }
int main() {
int fd[2];
printf("%lld\n", length(fd));;
return 0;
}
它有效,打印.我的问题是关于语法的。2
在 的声明中,为什么参数应该像 一样,而不起作用?length
(&a)[N]
a[N]
如果我更改为
template<class T,size_t N>
size_t length(T a[N]){ return N; }
GCC会说:
template argument deduction/substitution failed:
couldn't deduce template parameter 'N'
为什么这里需要一个额外的数组标识符和一对大括号,这背后的模板规则/语法规则是什么?&
欣赏详细的解释。
答:
6赞
Vlad from Moscow
6/28/2022
#1
在此函数声明中
template<class T,size_t N>
size_t length(T a[N]){ return N; }
编译器将具有数组类型的参数调整为指向数组元素类型的指针。
也就是说,这个声明实际上等同于
template<class T,size_t N>
size_t length(T *a){ return N; }
另一方面,在此调用中用作参数表达式的数组
length(fd)
隐式转换为指向其第一个元素的指针。
所以编译器无法推导出模板非类型参数 N 的值。
当参数被声明为引用时,不会发生上述调整和隐式转换。引用用作数组的别名。
请注意,要使用 C 函数输出无符号整数类型的对象,您需要使用转换说明符而不是 .size_t
printf
zu
lld
评论
&
%lld
size_t
%zu
%lld