"parenthesized declarators"在C语法中是什么意思
What does "parenthesized declarators" mean in C syntax
C 标准指定了一些翻译限制。下面两个我看不懂:
12 pointer, array, and function declarators (in any combinations) modifying an arithmetic,
structure, union, or void type in a declaration
63 nesting levels of parenthesized declarators within a full declarator
有人可以解释并给出简单的例子吗:
- declarator 修改声明 and
- 完整声明符中带括号的声明符
C 2018 2.7.6 指定声明符,包括将声明符的语法定义显示为:
declarator: pointeropt direct-declarator
direct-declarator:
identifier
(
declarator )
direct-declarator [
… ]
direct-declarator (
… )
pointer:
*
type-qualifier-listopt
(用于此语法的语法在 6.1 中进行了简要讨论。更简要地说,“direct-declarator:”意味着,当编译器正在寻找一个 direct-declarator,它会接受下面几行列出的任何选项。下标“opt”表示一个项目是可选的。我把原来的多个选项合并为“...”,因为细节在这个问题中并不重要。例如,数组声明符可能为空或可能包含赋值表达式并且可能有 static
,等等。)
在int x;
中,x
是声明符。该声明导致 x
被声明为 int
.
在int *x
中,*x
是声明符。它导致 x
被声明为 int *
。所以它修改了声明。
在int (*x[3][4])(float, char);
中,x
是一个声明符(因为它是一个直接声明符,是一个标识符)。它位于 数组声明符 (6.7.6.2 中显示的术语,指代上面带有 [
和 ]
的选项),x[3]
。那是在另一个数组声明符 x[3][4]
中。那是 指针声明符 中的直接声明符(如 6.7.6.1 所示,指的是上面的指针选项),*x[3][4]
。那是在带括号的声明符 (*x[3][4])
内(一个未明确定义但很清楚的术语)。那是在 函数声明符 (6.7.6.3), (*x[3][4])(float, char)
中。因此,这个声明有五层嵌套的声明符来修改声明中的 int
类型,其中四个是指针、数组或函数声明符(一个是带括号的声明符)。它声明 x
是一个由 3
数组组成的数组,其中有 4 个指针指向一个接受 float
和 char
并返回 int
.
的函数
至此,“完整声明符中带括号的声明符的 63 层嵌套级别”应该清楚了。 int (((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((x)))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))));
在一个完整的声明符中有 63 层嵌套的括号声明符。这通常不会出现在直接起草声明中,但使用各种宏构建声明可能会导致多级括号。
该标准将指针、数组和函数声明符视为编译器必须跟踪的内容,因此受到 12 层嵌套的适度限制,而括号是一种表面语法结构,仅需要跟踪在解析期间,然后可以在内部丢弃,因此对编译器的负担更小,限制更宽松。
C 标准指定了一些翻译限制。下面两个我看不懂:
12 pointer, array, and function declarators (in any combinations) modifying an arithmetic, structure, union, or void type in a declaration
63 nesting levels of parenthesized declarators within a full declarator
有人可以解释并给出简单的例子吗:
- declarator 修改声明 and
- 完整声明符中带括号的声明符
C 2018 2.7.6 指定声明符,包括将声明符的语法定义显示为:
declarator: pointeropt direct-declarator
direct-declarator:
identifier
(
declarator)
direct-declarator[
…]
direct-declarator(
…)
pointer:
*
type-qualifier-listopt
(用于此语法的语法在 6.1 中进行了简要讨论。更简要地说,“direct-declarator:”意味着,当编译器正在寻找一个 direct-declarator,它会接受下面几行列出的任何选项。下标“opt”表示一个项目是可选的。我把原来的多个选项合并为“...”,因为细节在这个问题中并不重要。例如,数组声明符可能为空或可能包含赋值表达式并且可能有 static
,等等。)
在int x;
中,x
是声明符。该声明导致 x
被声明为 int
.
在int *x
中,*x
是声明符。它导致 x
被声明为 int *
。所以它修改了声明。
在int (*x[3][4])(float, char);
中,x
是一个声明符(因为它是一个直接声明符,是一个标识符)。它位于 数组声明符 (6.7.6.2 中显示的术语,指代上面带有 [
和 ]
的选项),x[3]
。那是在另一个数组声明符 x[3][4]
中。那是 指针声明符 中的直接声明符(如 6.7.6.1 所示,指的是上面的指针选项),*x[3][4]
。那是在带括号的声明符 (*x[3][4])
内(一个未明确定义但很清楚的术语)。那是在 函数声明符 (6.7.6.3), (*x[3][4])(float, char)
中。因此,这个声明有五层嵌套的声明符来修改声明中的 int
类型,其中四个是指针、数组或函数声明符(一个是带括号的声明符)。它声明 x
是一个由 3
数组组成的数组,其中有 4 个指针指向一个接受 float
和 char
并返回 int
.
至此,“完整声明符中带括号的声明符的 63 层嵌套级别”应该清楚了。 int (((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((x)))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))));
在一个完整的声明符中有 63 层嵌套的括号声明符。这通常不会出现在直接起草声明中,但使用各种宏构建声明可能会导致多级括号。
该标准将指针、数组和函数声明符视为编译器必须跟踪的内容,因此受到 12 层嵌套的适度限制,而括号是一种表面语法结构,仅需要跟踪在解析期间,然后可以在内部丢弃,因此对编译器的负担更小,限制更宽松。