【问题标题】:Class Name Injection and Constructors类名注入和构造函数
【发布时间】:2018-03-06 20:50:53
【问题描述】:

最近,在将库更新到 Clang 5.x 时,我注意到我之前在 Clang 4.x、GCC 5.x-6.x 以及 MSVC 2015 和 2017 上编译的代码中有一个错误。

#include <iostream>
#include <typeinfo>
#include <vector>

int main()
{
    using a = typename std::vector<int>::vector;
    std::cout << typeid(a).name() << std::endl;
    return 0;
}

Clang-5.x 会产生以下警告消息,而所有其他编译器都会静默编译上述代码:

a.cpp:7:42: warning: ISO C++ specifies that qualified reference to 'vector' is a
  constructor name rather than a type in this context, despite preceding
  'typename' keyword [-Winjected-class-name]
using a = typename std::vector<int>::vector;

哪个编译器有问题?我是否正确假设 Clang5.x 在这里具有正确的行为,并且所有其他编译器(和版本)都不正确。如果是这样,是否值得向 MSVC 和 GCC 提交错误报告?

【问题讨论】:

  • 另一方面,using a = class std::vector&lt;int&gt;::vector; 是合法的。如果你喜欢这样奇怪的东西。

标签: c++ clang language-lawyer


【解决方案1】:

Clang-5 非常正确。在[class.qual]/2:

在不忽略函数名的查找中, nested-name-specifier 指定一个类 C

  • 如果在嵌套名称说明符之后指定的名称,在 C 中查找时,是 C 的注入类名称
  • ...

该名称被认为是命名类 C 的构造函数

至于问题的另一部分。是的,提交错误报告绝对值得。 IMO 应鼓励遵守标准(或至少对其进行更多诊断)。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2019-04-02
    • 1970-01-01
    • 1970-01-01
    • 2011-04-02
    • 2016-08-11
    • 1970-01-01
    • 2013-01-30
    相关资源
    最近更新 更多