In all examples discussed up to now, we've seen that tt(private) members are
only accessible by the members of their class. This is em(good), as it
enforces i(encapsulation) and i(data hiding). By encapsulating functionality
within a class we prevent that a class exposes multiple responsibilities; by
hiding data we promote a class's i(data integrity) and we prevent that other
parts of the software become i(implementation dependent) on the data that
belong to a class.

In this (very) short chapter we introduce the ti(friend) keyword and the
principles that underly its use. The bottom line being that by using the
tt(friend) keyword functions are granted access to a class's tt(private)
members. Even so, this does not imply that the principle of data hiding is
abandoned when the tt(friend) keyword is used.

In this chapter the topic of
    i(friendship among classes) is not discussed. Situations in which it is
natural to use friendship among classes are discussed in chapters
ref(NESTEDCLASSES) and ref(TEMPLATES) and such situations are natural
extensions of the way friendship is handled for functions.

There should be a well-defined conceptual reason for declaring friendship
(i.e., using the tt(friend) keyword). The traditionally offered definition of
the hi(class: definition) class concept usually looks something like
this:
    quote(em(A class is a set of data together with the functions that operate
        on that data.))

As we've seen in chapter ref(OVERLOADING) some functions have to be defined
outside of a class interface. They are defined outside of the class interface
to allow promotions for their operands or to extend the facilities of existing
classes not directly under our control. According to the above traditional
definition of the class concept those functions that cannot be defined in the
class interface itself should nevertheless be considered functions belonging
to the class. Stated otherwise: if permitted by the language's syntax they
would certainly have been defined inside the class interface. There are two
ways to implement such functions. One way consists of implementing those
functions using available public member functions. This approach was used,
e.g., in section ref(EXTRACTORS). Another approach applies the definition of
the class concept to those functions. By stating that those functions in fact
belong to the class they should be given direct access to the data members of
objects. This is accomplished by the tt(friend) keyword.

As a general principle
    hi(class: externally declared functions) we state that all functions
operating on the data of objects of a class that are declared in the same file
as the class interface itself belong to that class and may be granted direct
access to the class's data members.
