A public getter or setter permits anybody access. They have some uses, notably for maintaining class invariants when some property is changed, but a getter / setter pair that look like the following code are no better than public member variables for constraining access:
class A {
public:
int getX() const { return x; };
void setX(int x_) { x = x_; };
private:
int x;
};
The getX()
and setX()
functions do nothing but provide access to x
. Everybody can use them, so anybody can change the value of x
. There's no point making it private, then.
If, instead, only some classes or functions need to be able to change x
, you can make them friends of class A
. This restricts the access to only those friends, rather than giving it to everybody.
As such, friend
is a tool for encapsulation, permitting the encapsulation to be wider than "just my own class" (private members) or "just my class and classes that derive from it" (protected members). A friend need not be in the same class hierarchy (it need not be a class at all; functions can be friends), but it still permits you to restrict access to only those things that actually need it.
Note that, like getters and setters, it should be used sparingly. Encapsulation is a good thing, and where possible the private members of your class should remain just that – private. friend
is a tool that allows you to selectively grant access, but you should always carefully consider whether that access needs to be granted, or whether the function / class that needs it would be better off as a member of your class, instead.
Drawable
class, which usesfriend
pretty cleverly. – Calliope