c++ - 不合格调用时 clang 和 gcc 均存在错误

标签 c++ gcc clang language-lawyer

标准 list :

6.4.1

The lookup for an unqualified name used as the postfix-expression of a function call is described in [basic.lookup.argdep]. [ Note: For purposes of determining (during parsing) whether an expression is a postfix-expression for a function call, the usual name lookup rules apply. In some cases a name followed by < is treated as a template-name even though name lookup did not find a template-name (see [temp.names]). For example,

namespace N {
  struct A {};
  template <class T> int f(T);
}

 int main() {
  int x = f<N::A>(N::A());        // OK: lookup of f finds nothing, f treated as template name
}

gcc 和 clang 都不会编译这个简单的程序,它们会发出类似的诊断信息:

no templated name f found did you mean N::f?

除非有什么不清楚的地方,否则这显然是一个实现错误。我应该填写缺陷报告吗?

最佳答案

您引用的规则在 C++17 中有所不同。变更建议:p0846r0 .如果您正在为 C++20 进行编译,那么该示例应该可以编译,如果没有,则编译器对 C++20 的支持不完整。

没有编译器对 C++20 有稳定的支持,它甚至还没有正式发布(虽然功能列表最近被卡住),所以一些错误是可以预料的,因为对 future 语言版本的支持可能不会完成。

GCC 和 Clang 的最新开发版本都成功编译了示例,因此不需要报告错误。


C++17 的标准草案说:

[basic.lookup.unqual]

The lookup for an unqualified name used as the postfix-expression of a function call is described in 6.4.2. [Note: For purposes of determining (during parsing) whether an expression is a postfix-expression for a function call, the usual name lookup rules apply. The rules in 6.4.2 have no effect on the syntactic interpretation of an expression. For example,

typedef int f;
namespace N {
    struct A {
        friend void f(A &);
        operator int();
        void g(A a) {
            int i = f(a); // f is the typedef, not the friend function: equivalent to int(a)
        }
    };
}

此示例在 clang 5.0.0-3~16.04.1 以及 GCC 8.2.0 中编译良好。

关于c++ - 不合格调用时 clang 和 gcc 均存在错误,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/57293304/

相关文章:

c++ - 从 C++ 调用 COM dll, "Class Not Registered"

c++ - 在 C++ 中继承和覆盖 ostream 运算符

python - Mesos ExamplesTest.PythonFramework 检查在 OSX 上失败

c - LLDB 调试器无法识别在远程机器上编译的可执行符号

c - Clang 5.0 上的 vsprintf 和 vsnprintf [-Wformat-nonliteral] 警告

.net - double.Epsilon 与 std::numeric_limits<double>::min()

c++ - Qt5:如何在进行大量计算时重新绘制

c++ - Qt5链接错误

c - 有没有办法将 C11 编译为 C89?

c - 检测 C 编译器是否支持语句表达式