Search code examples
c++templatesfriend

Some problems about class template's friend


We have two class-templates: A and B, and a function-template f1(). Like this:

template< class T >
class A{};

template< class T >
class B
{
    friend class A<T>;          /* Expression 1 */
    friend void f1( B<T> &b );  /* Expression 2 */
};

template< class T >
void f1( B<T> &b ) {}

int main()
{
    A< int > a;
    B< int > b;

    f1( b );

    return 0;
}

problem 1: expression 1 make the specialization of A with argument T a friend of the specialization of B with argument T. But how to make every specialization of A all friends of specialization of B?

problem 2: how to define f1 outside the class definition? the code like this will generate an error:

undefined reference to `f1(B<int>&)'

problem 3: how to make all f1()s (who can receive all specialization of B as arguments) friends of every specialization of B?


Solution

  • Problem 1:

    Do you really want to do it? Do you want A<int> to access B<float>? Usually you don't, but if you really want:

    template <typename U>
    friend class A;
    

    Problem 2:

    The problem in 2 is that you are not making the instantiation of the f1 template a friend, but rather you are trying to make a non-templated free function f1 that takes a B<int> your friend. The correct syntax to befriend a particular instantiation is cumbersome:

    template <typename T> class B;
    template <typename T> void f( B<T>& );
    template <typename T>
    class B {
       friend void f<T>( B<T>& );
    };
    

    Problem 3:

    To make all specializations of f1 a friend (again, do you really want this?), you can do the same approach as for the class template:

    template <typename U>
    friend void f1( B<U>& );
    

    More on all those here