Chapter 16: Access Levels¶
每个类成员都有一个确定成员可见性的访问级别。在C++中有三种:public,protected与private。类成员的默认访问级别为private。要修改类的某一部分的访问级别,使用访问修饰符,后跟冒号。此标签之后的所有域或方法具有指定的访问级别,直到另一个访问级别被设置或类声明结束。
class MyClass
{
int myPrivate;
public:
int myPublic;
void publicMethod();
};
private访问¶
在类内部可以访问所有成员,而无论其访问级别,这被称为封装类。这是唯一可以访问私有成员的地方。
class MyClass
{
// Unrestricted access
public: int myPublic;
// Defining or derived class only
protected: int myProtected;
// Defining class only
private: int myPrivate;
void test()
{
myPublic = 0; // allowed
myProtected = 0; // allowed
myPrivate = 0; // allowed
}
};
protected访问¶
受保护的成员也可以由派生类的内部访问,但是不能由不相关的类进行访问。
class MyChild : public MyClass
{
void test()
{
myPublic = 0; // allowed
myProtected = 0; // allowed
myPrivate = 0; // inaccessible
}
};
public访问¶
公开访问为代码中的任意位置提供无限制的访问。
class OtherClass
{
void test(MyClass& c)
{
c.myPublic = 0; // allowed
c.myProtected = 0; // inaccessible
c.myPrivate = 0; // inaccessible
}
};
访问级别规则¶
作为一条规则,当选择访问级别时,通常最好选择最严格的级别。这是因为成员能够为更多的位置访问,则会有更多的位置对其进行不正确的访问,从而使得代码更难于调试。使用严格的访问级别也可以使得代码更易于修改,而不会破坏使用该类的其他程序员的代码。
当在现实世界编程时,域应总是私有的,而仅通过public或protected的getter与setter方法提供接口。这可以使得域被正确地访问更为容易,因为setter可以检测所赋的值对特定的域合法。通过忽略getter或setter方法,可以限制一个域仅能由类外部进行写或读访问。
class Person
{
private:
int age;
public:
// Setter
void setAge(int a)
{
if (age > 200) age = 200;
else if (age < 0) age = 0;
else age = a;
}
// Getter
int getAge()
{
return age;
}
};
友元类与函数¶
通过将类声明为友元,可以允许该类访问另一个类的私有或受保护成员。这是通过使用friend修饰符来实现的。友元可以被允许访问友元定义所在的类的所有成员。
class MyClass
{
int myPrivate;
// Give OtherClass access
friend class OtherClass;
};
class OtherClass
{
void test(MyClass& c) {
c.myPrivate = 0; // allowed
}
};
类似地,另一个类的方法可以被标记为友元来允许它访问定义类的所有成员。
class MyClass;
class OtherClass
{
public:
void test(MyClass& c);
void test2(MyClass& c);
};
class MyClass
{
int myPrivate;
friend void OtherClass::test(MyClass&);
};
void OtherClass::test(MyClass& c) {
c.myPrivate = 0; // allowed
}
void OtherClass::test2(MyClass& c) {
c.myPrivate = 0; // not allowed
}
public,protected与private继承¶
在C++中,当一个类被继承时,它可以修改继承成员的访问级别。public继承允许所有成员保持其原始的访问级别。protected继承将public成员降为protected。private继承将所有的继承成员限制为私有访问。
class MyChild : private MyClass
{
// myPublic is private
// myProtected is private
// myPrivate is private
};
private是默认的继承级别,仅管public继承是几乎总是用到的继承方式。