我一直在玩C++
的内部课程,现在我有点困惑。
#include <iostream>
class outer{
private:
class inner{
private:
int something;
public:
void print(){
std::cout<< "i am inner"<<std::endl;
}
};
public:
inner returnInner(){
inner i;
return i;
}
};
int main(){
outer o;
//outer::inner i = o.returnInner(); (1)
//auto i = o.returnInner(); (2)
//i.print();
o.returnInner().print(); //(3)
return 0;
}
这是在Linux上使用clang++-3.5
和-std=c++14
编译的。
在(1)中我按预期收到编译错误,因为inner
是outer
的私有内部类。
但是,在(2)中使用auto
关键字时,编译成功并运行程序。
为什么会这样?我是否可以阻止从外部方法返回私有内部类的实例,同时保留在外部类中移动和/或复制它们的能力?
编译器是否应该在(2)和(3)中引发错误,就像在(1)中一样?
答案 0 :(得分:25)
为什么会如此 编译器不应该像(1)中那样在(2)和(3)中返回错误吗?
这是一个有趣的问题......对此的回答更有趣。
在您发布的代码中,inner
是类型的名称。 名称被声明为private
,而不是类型本身 1 - 类型的可访问性在C ++的上下文中没有意义; accessibilty仅适用于 name - 是 name 的类型, name 的功能, name 的数据。所以当你听到像“类型X是一个公共类”这样的东西时,它几乎总是意味着“名称X被声明为公共,它指的是一个类型,类型是无所不在,无处不在“。
回到为什么使用auto
不会出错,因为当您使用auto
时,您正在访问类型而不使用其名称,这是为什么它没有给出错误。
如何防止从外部方法返回私有内部类的实例,
没有办法。
1。 struct { int data; }
是一个类型,没有要引用的名称,但请注意这不是一个有效的声明,因为它缺少 name 。您要声明未命名类型的对象,如struct { int data; } obj;
中所示,或者将其命名为struct data_type { int data; };
答案 1 :(得分:1)
我不确定这是你想要的,但你可以删除那样的复制构造函数:
OnTriggerEnter