特征类的类型定义中的匿名结构
Anonymous struct in typedef of trait class
对不起,这个有趣的标题。
在 C++0x 之前,使用函数局部结构("局部类型")作为模板参数存在限制。我的问题本质上是类似的限制是否适用于匿名结构。具体来说,在特征类的上下文中:
template <typename T>
struct trait;
template <>
struct trait<int> {
typedef int type;
};
template <typename T>
struct trait<std::basic_string<T> > {
typedef struct {
T value;
} type;
};
trait<std::string>::type foo; // Is this valid?
template <typename T>
void f() { }
f<trait<std::string>::type> >(); // Is this?
template <typename T>
void g() { f<typename trait<T>::type>(); }
g<std::string>(); // And this?
这是否有效和可靠?它在最新版本的GCC和LLVM中编译,但我仍然不确定这是否严格有效,以及VC++和ICC是否理解它。
作为参考,引用了 14.3.1/2 中链接问题的引文:
本地类型,没有链接的类型, 未命名类型或复合类型 从任何这些类型都不应 用作模板参数 模板类型参数。
我的解释是,typedef struct
正在为未命名类型创建别名,因此它不能用作模板类型参数。进一步注意,另外,在C中,typedef struct {} Foo;
的处理方式与struct Foo {};
给出两种形式不等价的先例相当不同(尽管不可否认,这种差异在C++中没有出现)。
因此,您的第一个示例看起来有效(因为它没有使用未命名类型作为模板类型参数),而第二个和第三个示例在技术上无效(因为它们确实将其用作模板类型参数)。
最后,我不得不问,有没有理由你不能命名结构而不是typedef
它?
编辑:从7.1.3/1:
。因此,typedef-name 是 另一种类型。类型定义名称不 以类的方式引入新类型 声明 (9.1) 或枚举声明 难道...
这强烈意味着以这种方式使用 typedef
不会引入适合用作模板类型参数的类型。
在即将推出的标准中,该限制已从语言中删除。该标准说
14.3.1 [温度参数类型]/1
作为类型的模板参数的模板参数应为类型 ID。
typedef 是有效的类型 ID。事实上,下一段包含这样一个例子:
14.3.1 [温度参数类型]/2
template <class T> class X { };
template <class T> void f(T t) { }
void f() {
typedef struct { } B;
B b;
X<B> x3;
f(b);
}
(我已经修剪了大多数其他示例) 该示例显示,未命名类型可以在类模板和函数模板中用作类模板参数。
定义匿名类和该类的 typedef-name 的 typedef
声明,typedef-name 是用于链接目的的类的名称。因此,如果该类满足其他条件,则使用该类作为模板参数是合法的。
请参阅 C++03 标准的 7.1.3p5
如果 typedef 声明定义了 未命名的类(或枚举),第一个 由声明率声明为该类类型(或枚举)的类型定义名称 type)用于表示类类型 (或枚举类型)用于链接目的 仅 (3.5)。[示例:
typedef struct { } *ps, S; // S is the class name for linkage purposes
这是 C++0x FDIS 中的 7.1.3p9。
FWIW,此代码可以使用MSVC2010(模错别字)编译正常。
嗯,这相当于
template <typename T>
struct trait<std::basic_string<T> > {
struct type {
T value;
};
};
这是完全合法的。
- 我的超类中的模板问题与结构定义
- 为私有结构定义双参数运算符重载
- 可视化C++中的结构定义错误
- 如何在结构定义中组合__attribute__((dllexport))和[[nodiscard]]?
- COM 互操作结构定义与内存布局不匹配
- C 在标题文件中创建具有结构定义的结构的队列
- 如何将结构定义为结构的成员
- 在这个节点定义中,为什么我们在结构定义之后使用"Node"?
- 不同模块中的ambigus结构定义
- 有条件的C/C 结构定义
- C++ 初始化结构定义中的向量
- 字符串声明中的结构定义中的字符串声明
- 使用结构定义函数
- 为具有许多数据成员的结构定义 == 和<
- enableif结构定义和默认模板参数
- C 使用模板为结构定义别名
- C/C++ 中的套接字编程 - 接收由 typedef 结构定义的消息
- 为C++结构定义显式析构函数如何影响调用约定
- 当结构定义在头文件中时,如何在main()中创建结构数组
- C结构定义标准