【问题标题】:Underscores, names and literal operators下划线、名称和文字运算符
【发布时间】:2012-12-10 01:58:26
【问题描述】:

我关于名称中的下划线的问题已部分回答here,,但要么答案不完整,要么我不完全理解。

教派。 C++11标准的2.14.8.7声明了这个literal operator作为例子:

long double operator "" _w(long double);

除了声明运算符之外,标准及其示例还做了两件事,如果分开来看,每件事都是有意义的:

  • 名称_w以下划线开头;和
  • 它将运算符置于全局命名空间中。

我的问题分为两部分:

  1. 根据the answer linked above,,名称_w 不是标识符, 或者标识符_w 不是名称, 或者...好吧,我我很困惑。
  2. 如果_w 可以,那么大写的_W 也可以——就像60.0_W,意思是60.0 瓦? 还是预处理器可能错误处理大写的版本?

毫无疑问,我和你一样,不习惯用下划线开头全局名称,这是标准教派的习惯。 17.6.4.3.2.1 似乎明确弃用。因此,如果您可以对下划线、名称和文字运算符的问题进行一些补充说明,我们将不胜感激。

【问题讨论】:

  • _W 会造成麻烦,因为在字面运算符定义之前的#define _W /*anything*/ 会导致_W 被替换。不是operator"" _W 中的_W 是保留的,而是实现很可能有一个像上面一样的宏_W。现在,有人可能想知道标准是否真的允许对文字运算符标识符进行宏替换,我会说是的,因为 _W 是一个单独的预处理器标记。
  • 预处理阶段/令牌主要是第 2.2 和 2.5 条。 _W 是一个 identifier,因此它是一个 preprocessing-token,如果它命名一个宏,则会在第 4 阶段进行扩展。
  • operator"" _W 中的 _W 肯定是 identifier,因此可以在没有警告的情况下将其重新定义为宏。这不会影响27_W 中的_W(这不是预处理令牌),但我认为如果无法定义operator"",那将是一种冷酷的安慰。 13.5.8 (8) 表明定义 operator ""_W (没有空格)是不合法的,因为 _W 在该上下文中不是标识符。另一方面,最后一个构造,afaics,不能在格式良好的程序中使用,这使得在不影响任何现有正确代码的情况下将其添加到语法中是可行的。 C++1y?
  • Johannes Schaub - litb 在 cmets 关于该答案的建议中,name 包含完整的 operator "" 部分(他说“总而言之,他的名字以o 而不是 _)。_w 是标识符,而 operator "" _w 是名称。或者至少这是我从问题中得到的...
  • 还想补充一点,Luc Danton 非常清楚地说明了哪个部分是名称:“literal-operator-id 是一个名称。它的标识符部分不是。” (根据他的回答,literal-operator-id 被定义为:operator "" identifier,其中identifier_w)。我也问过_W,看来这个版本确实可能有问题。

标签: c++ c++11 operator-overloading


【解决方案1】:

好的,我与 Clang 团队的 Richard Smith 进行了核对,您的文字运算符中的 _W 部分确实不是保留的标识符和/或名称,它也是一个单独的预处理器令牌,如果它会被扩展命名一个宏。这与标准子条款 2.5 一致,其中 identifier预处理器令牌,而 2.2 在预处理器令牌之前具有宏扩展作为阶段 4 的一部分替换为仅发生在阶段 7 的语言语法标记。

他还提到,since the Portland meeting of the committee,你可以说operator""_W,这将阻止宏扩展,因为_W 不再是一个单一的标识符。 Clang trunk 已经实现了这个并编译了以下 sn-p:

#define _W _x

int operator""_W(unsigned long long){ return 42; }

int main(){
  int i = 1337_W;
}

【讨论】:

  • 这也适用于 字符串文字 吗? "1337"_W 会起作用还是预处理器认为它是两个不同的令牌?
  • @K-ballo:记住,问题不在于用户定义文字的文字 ooerator 的使用,而是 _W 被替换的声明。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2018-05-31
  • 1970-01-01
  • 1970-01-01
  • 2016-11-02
  • 2019-06-06
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多