在标准中,什么是“派生声明者类型”?

时间:2012-12-08 16:16:16

标签: c++ c++11 standards

在C ++(C ++ 11)标准的不同位置,声明是根据 derived-declarator-type-list 来描述的。我正在研究右值参考,在这种情况下使用这个术语是至关重要的(§8.3.2):

  

在声明中 T D ,其中 D 具有任何一种形式
  &安培; attribute-specifier-seq opt D1
  &安培;&安培; attribute-specifier-seq opt D1
以及声明 T D1 中的标识符类型是   “ derived-declarator-type-list T ,”然后是 D 标识符的类型   是“ derived-declarator-type-list T 的引用。”

不幸的是,类别“ derived-declarator-type ”从未在标准中定义。 (我查看了“衍生”一词的每次使用,此外,这可能已经确认herehere。)

因为“ derived-declarator-type-list ”是斜体,我认为它指的是一个类别,而不是一个变量标签,例如 T (因此,我不同意Doug Gwyn在我刚刚给出的第二个链接中的评估“我们可以使用 X 而不是' derived-declarator-type-list < / em>'“)。

C ++ 11标准中 derived-declarator-type 的定义是什么?

1 个答案:

答案 0 :(得分:12)

它正在那里被定义。这是将T之前的任何内容传递到下一个类型的方式,类似于:

<some stuff> T
<some stuff> reference to T

这只是T类型T D1之前的任何内容。

例如,如果您有声明int& (*const * p)[30]Tint,则D& (*const * p)[30]D1为{{1} }}。 (*const * p)[30]的类型是“指向指向30 int数组的const指针”。因此,根据您引用的规则,T D1的类型是“指向指向30引用数组的数组的const指针”。

当然,§3.4.2/ 5不允许这个声明:

  

不应引用引用,不引用引用数组,也不引用引用指针。

我认为它是派生的声明符类型列表的非正式术语来自C标准对派生类型的定义(类似于C ++中的复合类型):

  

可以从对象,函数和构造任意数量的派生类型   不完整的类型,如下:

     
      
  • 数组类型 [...]
  •   
  • 结构类型 [...]
  •   
  • 联合类型 [...]
  •   
  • 功能类型 [...]
  •   
  • 指针类型 [...]
  •   

回应评论:似乎你在类型和声明者之间感到困惑。例如,如果p是声明符,则int* p的类型是“指向int的指针”。类型表示为这些类似英语的句子。

示例1 p

这是一个声明int *(&p)[30],其中(§8.3.1指针):

  • T D - &gt; T
  • int - &gt; D

*(&p)[3]的格式为:

  

D attribute-specifier-seq opt cv-qualifier-seq opt {{ 1}}

其中*D1。这意味着D1的格式为(&p)[3],其类型为“引用数组3 T D1”(您可以递归地执行此操作,下一步使用§8.3.4数组等) 。 int (&p)[3]之前的所有内容都是 derived-declarator-type-list 。因此,我们可以推断出我们原始声明中的int类型为“引用指向int的3指针数组”。魔术!

示例2 p

这是一个声明int,其中(§8.3.4数组):

  • float (*(*(&e)[10])())[5] - &gt; T D
  • T - &gt; float

D具有以下形式:

  

(*(*(&e)[10])())[5] 常量表达式 opt D attribute-specifier-seq opt

其中D1 []。这意味着D1的格式为(*(*(&e)[10])()),其类型为“引用指向函数的10指针的数组”(返回指向float的指针)(您可以通过应用§8.3/ 6然后§来解决) 8.3.1指针等)。 T D1之前的所有内容都是 derived-declarator-type-list 。因此,我们可以推断出我们原始声明中的float (*(*(&e)[10])())类型为“引用指向函数的10指针的数组()返回指向5浮点数组的指针”。再次魔术!