我正在学习C ++ 11x中的lambda表达式,我用google搜索相同的内容,并在下面的代码片段中看到模板typename用作继承。
说,
template< class T >
struct MyType : T {
....
当我遵守代码时,它不会给出任何错误。但是,当我尝试为 struct MyType 创建实例时,它会导致错误。
// Example program
#include <iostream>
#include <string>
template< class T >
struct MyType : T {
static const auto data = 0;
static const size_t erm = sizeof(data);
};
int main()
{
struct MyType<int> my;
std::cout<<"\n test ";
return 0;
}
编译上述代码时出错:
In instantiation of 'struct MyType<int>':
15:22: required from here
6:8: error: base type 'int' fails to be a struct or class type In function 'int main()':
15:22: warning: unused variable 'my' [-Wunused-variable]
请为此添加一些亮点。为什么编译会在实例化结构时出错?另一方面为什么声明没有给出任何错误?
先谢谢。
答案 0 :(得分:4)
为什么编译会在实例化结构时出错?在另一 为什么声明不会出现任何错误?
这是因为严格来说模板声明不是代码。只有当您使用具体模板参数对其进行实例化时,编译器才会将模板转换为“真实”代码。你没有在模板声明中得到错误,因为对于任何结构或类类型,你的模板都没问题。只有当模板对于任何模板参数格式不正确时,编译器才会在实例化之前进行抱怨。例如。此
template <typename T>
void foo () { asdf(); }
将导致错误(假设范围内没有asdf
):
prog.cpp: In function ‘void foo()’:
prog.cpp:5:20: error: there are no arguments to ‘asdf’ that depend on a
template parameter, so a declaration of ‘asdf’ must be available
[-fpermissive] void foo () { asdf(); }
但是这个
template <typename T>
void foo() { T::asdf(); }
不会,因为可能会有T
导致模板格式正确。只有当您使用T
进行实例化时,才会出现错误。
答案 1 :(得分:3)
我认为编译器给出了很好的解释。简而言之,您无法从int
等基本类型派生出来。
宣言本身:
template< class T >
struct MyType : T {
static const auto data = 0;
static const size_t erm = sizeof(data);
};
绝对有效。所以编译器不会抱怨它。
但是当使用MyType<T>
实例化T = int
时,编译器会尝试生成代码,一般来说,这样的代码如下:
struct MyType : int {
static const auto data = 0;
static const size_t erm = sizeof(data);
};
无效 C ++ ,因为MyType
尝试从int
继承。
答案 2 :(得分:0)
问题是用您T
的实际类型替换struct MyType<int> my;
成为:
struct MyType : int
你可以看到为什么这是无效的。您不能继承非类的内容。 int
是简单内置类型。
为什么这是不可能的,有很多原因,但在我看来,所有这些都归结为继承,多态和封装不适用于内置基本类型。他们没有方法表,所以你不能覆盖它们......
编译器已经为您提供了一条很好的错误消息:
clang++
可能更清楚
test.cpp:9:17: error: base specifier must name a class
struct MyType : T {
icpc
test.cpp(9): error: not a class or struct name
struct MyType : T