Search code examples
c++friendaccess-controlforward-declaration

C++: granting member function friendship forward declaration?


I have a problem with friendship in c++. I have two classes, A and B, where the definition of B uses some instance of A. I also want to give a member function within B access to private data members in A, and so grant it friendship. But now, the conundrum is that for the friendship declaration in the definition of class A, class B is as yet undefined, so the IDE (VS 2010) doesn't know what to make of it.

#include <iostream>
using namespace std;

class B;

class A {
    friend int B::fun(A A);//B as yet undefined here
    int a;
};

class B {
    int b;
public:
    int fun(A inst);
};

int B::fun(A A)
{
    int N = A.a + b;//this throws up an error, since a is not accessible
    return N;
}

I have had a look at Why this friend function can't access a private member of the class? but the suggestion there of using a forward declaration of class B; doesn't seem to work. How can I solve this problem directly (i.e. without resorting to making class B a friend of class A, or making B inherited from A or introducing a getA() function)? I have also looked at Granting friendship to a function from a class defined in a different header, but my classes are in one .cpp file (and it would be preferable to keep it that way), not in separate header files, and I do not want to grant the entire class friendship anyway. Meanwhile, C++ Forward declaration , friend function problem provides the answer to a slightly simpler problem - I cannot just change the order of the definitions. Meanwhile, http://msdn.microsoft.com/en-us/library/ahhw8bzz.aspx provides another similar example, but the example fails to run on my computer, so do I need to check some compiler flags or something?


Solution

  • Swap it around?

    class A;
    
    class B
    {
    public:
    int fun(A inst);
    private:
    int b;
    };
    
    class A
    {
    friend int B::fun(A A);
    private:
    int a;
    };
    
    int B::fun(A A)
    {   int N = A.a + b;
    return N;
    }