In what kind of scenarios would we declare a member function as a 'friend function' ?..What exact purpose does 'friend function' which defies one of central concept of 'Encapsulation' of OOP serve?
You would use a friend function for the same sort of reasons that you would use a friend class, but on a member function (rather than entire class) basis. Some good explanations are in this thread.
While friend functions and classes do violate encapsulation, they can be useful in some scenarios. For example, you may want to allow a test harness to access class internals to allow you to do whitebox testing. Rather than opening up the entire class to the test harness, you could open up a particular function which accesses the internals required by the test harness. While this still violates encapsulation, it's less risky than opening up the entire class.
Also see this article for some more information about friend classes and functions.
Sometimes public/private/protected protection level is not quite enough for real world situations. So thus we give a small get-out clause that helps without having to make methods publicly accessible.
I personally use this the same way that Java uses the 'Package' protection level.
If I have a class in the same package that needs access I will consider using friend. If it is a class in another package then I will wonder why on earth is this other class needing access and look at my design.
See C++ FAQ Lite:
Sometimes friends are syntactically better (e.g., in class Fred, friend functions allow the Fred parameter to be second, while members require it to be first). Another good use of friend functions are the binary infix arithmetic operators. E.g., aComplex + aComplex should be defined as a friend rather than a member if you want to allow aFloat + aComplex as well (member functions don't allow promotion of the left hand argument, since that would change the class of the object that is the recipient of the member function invocation).
Friend functions and classes do not violate encapsulation when you are trying to build an abstraction or interface that must physically span multiple C++ classes or functions! That is why friend was invented.
Those types of cases don't come up often, but sometimes you are forced to implement an abstraction or interface with disparate classes and functions. The classic example is implementing some type of complex number class. The non-member operator functions are given friendship to the main complex number class.
I also recall doing this when programming with CORBA in C++. CORBA forced me to have separate classes to implement CORBA servants. But for a particular part of our software, I needed to marry these together as one interface. Friendship allowed these two classes to work together to provide a seamless service to one part of our software.
Having the ability to mark a particular member function on another class as a friend to your class may seem even stranger, but it is just a way of tightly controlling the friendship. Instead of allowing the entire other class "in" as your friend, you only allow one of its member functions access. Again, this isn't common, but very useful when you need it.
One point that I find relevant: member classes have access to the private parts of the containing class. This may sometimes be a better alternative to "friend".
class A
{
private:
int b;
public:
class MemberNotFriend {
public:
static void test() {
A a;
a.b = 0;
}
};
};
void test()
{
A::MemberNotFriend::test();
}
Here is a simple, concrete example of how I am using a friend function:
I have a game where each sprite object stores its info like X,Y position as private members. However, I wish to separate the game objects from the rendering: a game object does not need the exact details of how it is rendered. A game object only stores game state, and this game state may be rendered in a number of different ways.
Thus the game object class has a friend function: render(). The render() function is implemented outside the game object class, but it can access the X,Y position position membefrs as needed to render the game object.