繁体   English   中英

Visual C ++中模板参数的奇怪行为?

[英]Weird behavior of template arguments in Visual C++?

我从Nicolai M. Josuttis的“C ++模板 - 完整指南”中尝试了这个例子

#include <iostream>

using namespace std;

template< typename T >
class List {
};

typedef enum { RED, GREEN, BLUE } *color_ptr;

int main() {
    struct Local {
        int x;
    };

    List< Local > l; // error : local type in template argument
    List< color_ptr > l1; // error : unamed type in template argument.

    return 0;
}

使用Ubuntu 9.04下的g ++,我遇到了编译器错误。 但是,这段代码在Visual C ++ 2008中成功编译。正如我从书中读到的那样:“模板类型参数是为模板类型参数指定的”值“。最常用的类型可以用作模板参数,但是有两个例外:1。本地类和枚举(换句话说,在函数定义中声明的类型)不能涉及模板类型参数.2。涉及未命名类类型或未命名枚举类型的类型不能是模板类型参数(未命名类或者通过typedef声明给出名称的枚举都可以。)那么Visual C ++中是否存在错误?

在许多其他情况下,您会发现该书与VC ++的行为不同。 示例是typenametemplate ambiguity工具以及非const引用与rvalues的绑定。

在这种情况下,当然,正如书中所说,G ++的行为是正确的。 请尝试以下更改

typedef enum color_type { RED, GREEN, BLUE } *color_ptr;

template< typename T >
class List {
};

// not really local anymore :)
struct Local { int x; };
int main() {
  List< Local > l;
  List< color_type > l1;
}

下一个C ++标准(C ++ 0x)允许本地类型作为模板参数。


请注意本书的含义是为typedef类型命名。 这不适用于以下内容,因为名称A不命名枚举类型,而是指向它的指针类型。

typedef enum { X } *A;

因此,当您使用A或在您的示例中使用color_ptr ,您就不会安全了。 从技术上讲,该名称是指向没有链接的类型的指针类型,不允许作为模板参数。


请注意,您可以将Local放入一个未命名的命名空间,以使该类型为当前转换单元的本地类型,但仍具有可接受的类型作为类型模板参数。 这样,如果你只想为函数对象之类的东西设置一个“scratch”类型,那么struct不会与另一个文件中定义的struct冲突。

namespace {
  // not really local anymore, but "translation unit local" :)
  struct Local { int x; };
}

这些是MSVC标准的允许扩展。 MS在记录编译器的选项 ,一致性或偏离标准方面做得不错,并且c; 特别是,如此处所述/Za将告诉编译器标记为与标准的错误偏差(它特别称为“ansi C ++”而不是ISO ;-)。

检查您是否正在使用Microsoft扩展(/ Ze)进行编译。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM