一个类使用protected关键字来声明是希望与派生类分享但是不想被其他公共访问使用的成员。所以protected可以看做public和private的中间产物
解析protected
1.类似于私有成员,受保护的成员对于类的用户(类的用户即类的对象)来说是不可访问的,也就是说可以通过类的成员函数访问而不能通过类的对象来访问
2.类似于公有成员,受保护的成员对于派生类的成员和友元来说是可访问的,而private基类成员对于派生类成员和友元是不能访问的
3.派生类的成员或友元只能通过派生类的对象来访问基类受保护成员,而派生类对基类的对象受保护成员—无权限
代码解析第三点
1.
#include <iostream>
using namespace std;
class Base
{
protected:
int prot_mem;
};
class Derive:public Base
{
public:
friend void Call(Derive &a);//能访问Derive::prot_mem
//friend void Call(Base &b);//不能访问Base::prot_mem
private:
int j;
};
void Call(Derive &a)
{
a.j=a.prot_mem=0;
cout<<a.j<<endl;
}
//void Call(Base &b)
//{
// b.prot_mem=0;
// cout<<b.prot_mem=0;
//}
int main()
{
Derive c;
Call(c);
//Base d;
//Call(d);
return 0;
}
//友元或派生类可以访问Derive对象的private和protected成员(这里的成员包括基类中的)
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
- 18
- 19
- 20
- 21
- 22
- 23
- 24
- 25
- 26
- 27
- 28
- 29
- 30
- 31
- 32
- 33
- 34
- 35
- 36
- 37
- 38
- 39
- 40
结果
2.
若检查是否能访问Base对象的protected
#include <iostream>
using namespace std;
class Base
{
protected:
int prot_mem;
};
class Derive:public Base
{
public:
friend void Call(Derive &a);//能访问Derive::prot_mem
friend void Call(Base &b);//不能访问Base::prot_mem
private:
int j;
};
void Call(Derive &a)
{
a.j=a.prot_mem=0;
cout<<a.j<<endl;
}
void Call(Base &b)
{
b.prot_mem=0;
cout<<b.prot_mem=0;
}
int main()
{
Derive c;
Call(c);
Base d;
Call(d);
return 0;
}
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
- 18
- 19
- 20
- 21
- 22
- 23
- 24
- 25
- 26
- 27
- 28
- 29
- 30
- 31
- 32
- 33
- 34
- 35
- 36
- 37
- 38
**这段代码是不能通过编译的因为在派生类中的友元函数访问Base对象的protected了即
浅谈代码
重点在于两个友元(不用也可以)能否访问Derive对象的private和protected成员和能否访问Base对象的protected成员
权限解释
- 因为派生类(及其友元)但友元又不是基类的友元,那么若派生类(及其友元)能改变Base对象的内容,那我们只要定义一个形如Derive的新类就能简单躲避protected提供的访问权限了,但这显然是不对的,并不是protected的初衷
- 派生类的成员和友元只能访问派生类对象中其类受保护成员,对于普通的基类对象中的成员不具备特殊访问权限