类模板中名称解析的实际结果与c 03标准不同

类模板中名称解析的实际结果与c 03标准不同,第1张

概述我在 Xcode 4.1和Visual Studio 2008上的c标准ISO / IEC 14882-03 14.6.1 / 9中测试代码.两个编译器的输出与标准的预期结果不同. 代码粘贴在下面. #include <stdio.h>#include <iostream>using namespace std;void f(char);template <class T > void 我在 Xcode 4.1和Visual Studio 2008上的c标准ISO / IEC 14882-03 14.6.1 / 9中测试代码.两个编译器的输出与标准的预期结果不同.

代码粘贴在下面.

#include <stdio.h>#include <iostream>using namespace std;voID f(char);template <class T > voID g(T t){    f(1);    f(T(1));    f(t);}voID f(int);voID h(){    g(2);    g('a');}voID f(int){     cout << "f int" << endl;}voID f(char){    cout << "f char" << endl;}int main() {     h();      return 0;}

作为标准的描述.预期产出应该是

f charf intf intf charf charf char

构建并运行Xcode 4.1上的代码.输出如下.在构建设置中,我尝试将“C/C++ / Object-C编译器”更改为Apple LLVM编译器2.1,Gcc 4.2和LLVM GCC 4.2.输出相同.

f charf charf charf charf charf char

构建并运行Microsoft Visual Studio 2008上的代码.输出如下.

f intf intf intf intf charf char

标准说明(14.6.1 / 9)如下.

如果一个名称不依赖于模板参数(如14.6.2所定义),该名称的声明(或一组声明)应在名称出现在模板定义中的范围内;该名称绑定到在该点发现的声明(或声明),并且该绑定不受在实例化点处可见的声明的影响. [例:

voID f(char);template<class T> voID g(T t){f(1); // f(char) f(T(1)); // dependent f(t); // dependent dd++; // not dependent}voID f(int);double dd;voID h(){// error: declaration for dd not foundg(2); // will cause one call of f(char) followed // by two calls of f(int)g(’a’); // will cause three calls of f(char)

-end示例]

代码对编译器的格式很好,但是输出是不同的.将此代码移植到不同的平台将是非常危险的.

有人有背景为什么这些编译器不符合标准?

在10/11/2011编辑

根据http://www.open-std.org/jtc1/sc22/wg21/docs/cwg_defects.html#197,标准中的例子是错误的.我测试下面的代码在Clang和Gcc.

#include <stdio.h>#include <iostream>using namespace std;voID f(char);template <class T > voID g(T t){    f(1);    f(T(1));    f(t);}enum E{ e };voID f(E );voID h(){    g(e);    g('a');}voID f(E ){    cout << "f E" << endl;}voID f(char){    cout << "f char" << endl;}int main() {     h();      return 0;}

输出如预期.

f charf Ef Ef charf charf char

谢谢,

杰弗里

解决方法 如第一个例子所述,这是一个两阶段名称查找的实例,GCC和Clang实现,但是MSVC没有.在这种情况下,GCC和Clang都是正确的:它实际上是错误的标准,如C core defect report #197中所述.C 11标准包含一个不同的示例.

这是从MSVC(从未实现两阶段名称查找)或从GCC(直到最近都不实现两阶段名称查找)将代码移植到Clang的most common problems之一.

总结

以上是内存溢出为你收集整理的类模板中名称解析的实际结果与c 03标准不同全部内容,希望文章能够帮你解决类模板中名称解析的实际结果与c 03标准不同所遇到的程序开发问题。

如果觉得内存溢出网站内容还不错,欢迎将内存溢出网站推荐给程序员好友。

欢迎分享,转载请注明来源:内存溢出

原文地址: https://www.outofmemory.cn/web/1063184.html

(0)
打赏 微信扫一扫 微信扫一扫 支付宝扫一扫 支付宝扫一扫
上一篇 2022-05-26
下一篇 2022-05-26

发表评论

登录后才能评论

评论列表(0条)

保存