拥有多个 const 限定符是否合法?

Is it legal to have multiple const qualifiers?

作为对 const 放置的一些讨论的结果,我开始怀疑是否可以对同一类型使用多个 const 限定符:

#include <iostream>

int main()
{
    const const int a = 5;
    std::cout << a;
}

别担心,我不会写这样的代码

事实证明,clang 和 MSVC 接受带有警告的代码,但 GCC 拒绝它:https://godbolt.org/z/TdYnvc

哪个编译器是正确的?

我认为这是错误的。 [dcl.type]/2

As a general rule, at most one defining-type-specifier is allowed in the complete decl-specifier-seq of a declaration or in a defining-type-specifier-seq, and at most one type-specifier is allowed in a type-specifier-seq. The only exceptions to this rule are the following:

  • const can be combined with any type specifier except itself.
  • ...

所以不允许像const const int a = 5;那样按字面意思重复const。 (PS typedef 引入的冗余 cv 限定是允许的,但会被忽略)。

GCC 正确。

编译器不应编译代码。原因很明确 [dcl.type.cv]/1:

有两个 cv 限定符 constvolatile。每个 cv-qualifiercv-qualifier-seq.

中最多出现一次

允许将 const 添加到已经 const 的类型(如果这不可能,模板编程将很困难)。但是你不能按照上面的规则写const const

Is it legal to have multiple const qualifiers?

const const int a = 5;

没有。该规则已被其他罚款涵盖 and .

请注意,这仅适用于语法,一般不适用于类型系统。您可以将 const 应用于 const 类型别名:

using T = const int;
const T a = 5; // OK

多个 cv 限定符以这种方式“折叠”为一个。

Which compiler is right?

在“哪个编译器符合标准”的意义上:全部。

编译器不需要拒绝格式错误的程序,也不需要接受它们。由于所有编译器都会发出诊断消息,因此它们都符合标准。引用:

[intro.compliance.general]

Although this document states only requirements on C++ implementations, those requirements are often easier to understand if they are phrased as requirements on programs, parts of programs, or execution of programs. Such requirements have the following meaning:

  • If a program contains no violations of the rules in [lex] through [thread] and [depr], a conforming implementation shall, within its resource limits as described in [implimits], accept and correctly execute5 that program.
  • If a program contains a violation of any diagnosable rule or an occurrence of a construct described in this document as “conditionally-supported” when the implementation does not support that construct, a conforming implementation shall issue at least one diagnostic message.
  • If a program contains a violation of a rule for which no diagnostic is required, this document places no requirement on implementations with respect to that program.

5) “Correct execution” can include undefined behavior

故意接受格式错误的程序称为“语言扩展”。