c ++ 0x:解决函数定义后跟空声明和简单声明之间的歧义

mil*_*anw 15 c++ parsing specifications c++11

我在c ++ 0x规范中明显含糊不清时遇到了问题,另请参阅:http://www.nongnu.org/hcb/

假设我们有代码

void foo() {};
Run Code Online (Sandbox Code Playgroud)

我个人将代码解释为a function-definition后跟a empty-declaration.但是,看一下语法规范,我会说这可以很容易地被解释为a simple-declaration,这是...的一部分,block-declaration因此在declaration...... 的列表中提到的更快.

以下是我如何将其解析为简单声明的解释:

void foo() {};"
Run Code Online (Sandbox Code Playgroud)

- >简单声明

void
Run Code Online (Sandbox Code Playgroud)

- > decl-specifier-seq - > decl-specifier - > type-specifier - > trailing-type-specifier - > simple-type-specifier

foo() {}
Run Code Online (Sandbox Code Playgroud)

- > init declarator-list - > init-declarator

foo()
Run Code Online (Sandbox Code Playgroud)

- > declarator - > ptr-declarator - > noptr-declarator

foo
Run Code Online (Sandbox Code Playgroud)

- > declarator-id - > ...

()
Run Code Online (Sandbox Code Playgroud)

- >参数和限定符

{} 
Run Code Online (Sandbox Code Playgroud)

- > initializer - > braced-init-list

所以这应该可以解析为简单声明.

我被告知应该使用6.8的规范来消除这种情况的歧义,但我不太明白为什么.是simple-declarationexpression-statement,因为它有结束;

Joh*_*itb 9

我想你是对的.这是一个含糊不清的问题,我不知道在规范中解决它的段落.

C++ 0x规范中还有其他未明确解决的歧义,但(希望)将由编译器以直接的方式实现.例如,以下内容既可以解析为嵌套类的定义,也可以解析为B具有0基础类型大小的未命名位域的定义struct B.后一种解释会使程序无效).

struct C { constexpr operator int() { return 0; } }; 
struct A { struct B : C { }; };
Run Code Online (Sandbox Code Playgroud)

另一个例子

struct A {
  // is 0 a 'brace-or-equal-initializer' or a 'pure-specifier'?
  virtual void f() = 0;
};
Run Code Online (Sandbox Code Playgroud)

Clang最近不得不修复以下内容,因为它得到了错误的方法(它将其解析为初始化变量f,而不是使函数变为纯粹).

typedef void T();
struct B : A {
  // B::f overrides A::f
  T f = 0;
};
Run Code Online (Sandbox Code Playgroud)

  • @Alex`C {}`是一个构造为`C`对象的值. (3认同)
  • @Nicol不调用`C`的构造函数.这是值初始化,而`C`的默认构造函数是微不足道的.因此,根据第8.5条的规则,我们不会调用任何构造函数.但是无视这一点,`C`*的隐式声明的构造函数是由12.1p6和7.1.5规则的*`constexpr`.但无论如何,这些都是语义上的考虑因素.在任何情况下,代码在语义上都是错误的.`C {}`是否是有效的const表达式是无关紧要的.它可以解析为一个. (2认同)