如何阅读C/C++中的复杂类型声明呢?一般采用英语语序法。有以下规则:
- 从变量开始,读作
变量 is,然后先读右部的修饰符,再读左边的修饰符,如果遇到括号就跳出去重复这一动作。 - 对于
[N],读作an array of N; - 对于
(),读作a function that returns或者a function returning; - 对于
T *,读作a pointer to T; - 其他类型名按原意阅读,有
const修饰符就加上; - 按照处理顺序,将翻译出的所有语句连接起来,就是完整的类型声明;
- 如有余力,还可以处理一下指针/函数的单复数,以及函数的参数。
上述的规则用于C语言的类型声明,已经足够了,完全可以按照这个规则写一个小工具读声明。应用这一方法的现成网站是https://cdecl.org/。C++就复杂很多了,水太深难以把握。
下面就此给出几个示例。 比如 char * const (*(* const bar)[5])(int) :
- 变量是
bar,右边没有,左边是*const,读作bar is a const pointer to; - 遇到括号跳出,右边是
[5],读作an array of 5,左边是*,读作a pointer to,所以是an array of 5 pointers to; - 遇到括号跳出,右边是
(int),读作a function that returns,左边是char * const,读作const pointer to char; - 完整的类型声明大致是,
bar是a const pointer to an array of 5 pointers to a function that returns const pointer to char; - cdecl网站的翻译:
declare bar as const pointer to array 5 of pointer to function (int) returning const pointer to char,没有处理单复数(无a/an),对于[N]翻译得不够好。
再比如 int (*func(int i))[10] :
- 变量是
func,右边是(int i),读作a function returning,左边是*,读作a pointer to; - 遇到括号跳出,右边是
[10],读作an array of 10,左边是int; - 于是完整的类型声明,
func是a function returning a pointer to an array of 10 int; - 由于cdecl支持的是C89标准,会报错……其实这就是一个可改进之处。
再比如 int *((*i)())[5] :
- 变量是
i,于是i is; - 右边没有,左边是
*,读作a pointer to; - 遇到括号跳出,右边是
(),读作a function that returns; - 遇到括号跳出,右边是
[5],读作an array of 5,左边是int *,读作a pointer to int; - 完整的类型声明是,
i is a pointer to a function that returns an array of 5 pointers to int。
以后有时间,可能会写一个读C99/C++11类型声明的小工具吧,首先要看我到时候能不能掌握这些语法知识。
本文介绍了如何解读C/C++中的复杂类型声明,提供了一种类似英语语序的阅读规则,并通过示例解释了如何应用该规则。同时提到了C++的复杂性,并提到可以开发小工具来辅助解析。还给出了在线资源cdecl.org作为参考,但指出其在处理某些C99/C++11特性时可能不足。
5万+

被折叠的 条评论
为什么被折叠?



