Template friend functions of the template class

I have the following template class and a template function that is designed to access a private data member of a class:

#include <iostream>

template<class T>
class MyVar
{
    int x;
};

template<class T>
void printVar(const MyVar<T>& var)
{
    std::cout << var.x << std::endl;
}

template<class T>
void scanVar(MyVar<T>& var)
{
    std::cin >> var.x;
}

struct Foo {};

int main(void)
{
    MyVar<Foo> a;
    scanVar(a);
    printVar(a);
    return 0;
}

To declare two functions as MyVar<T>friend functions , I tried the following ways template<class T> class MyVarto declare friendships inside an declaration . None of them work. How should I do it?

template<class T> friend void printVar(const MyVar&);
template<class T> friend void scanVar(MyVar&);
// compilation error

template<class T> friend void printVar(const MyVar<T>&);
template<class T> friend void scanVar(MyVar<T>&);
// compilation error

friend void printVar(const MyVar<T>&);
friend void scanVar(MyVar<T>&);
// link error

friend void printVar(const MyVar&);
friend void scanVar(MyVar&);
// link error too
+4
source share
3 answers

The easiest way is to define a friend in the class:

template<class T>
class MyVar
{
    int x;

    friend void printVar(const MyVar & var) {
        std::cout << var.x << std::endl;
    }
    friend void scanVar(MyVar & var) {
        std::cin >> var.x;
    }
};

The disadvantage is that functions can only be called via argument-dependent searches. This is not a problem in your example, but it can be a problem if they do not have a suitable argument or if you want to specify a name without calling it.

, ( ), ( ). . , :

template <typename T> class MyVar;
template <typename T> void printVar(const MyVar<T> & var);

template<class T>
class MyVar
{
    int x;

    friend void printVar<T>(const MyVar<T> & var);
};

template <typename T> void printVar(const MyVar<T> & var) {
    std::cout << var.x << std::endl;
}
+4

#include <iostream>

template<class T>
class MyVar;

template<class T>
void printVar(const MyVar<T>& var);

template<class T>
void scanVar(MyVar<T>& var);

template<class T>
class MyVar
{
    int x;
    friend void printVar<T>(const MyVar<T>& var);
    friend void scanVar<T>(MyVar<T>& var);
};

template<class T>
void printVar(const MyVar<T>& var)
{
    std::cout << var.x << std::endl;
}

template<class T>
void scanVar(MyVar<T>& var)
{
    std::cin >> var.x;
}

struct Foo {};

int main(void)
{
    MyVar<Foo> a;
    scanVar(a);
    printVar(a);
    return 0;
}

UPD: http://en.cppreference.com/w/cpp/language/friend " ":

, , . operator<<(std::ostream&, const Foo<T>&) Foo<T>

, - operator<< T - operator<< Foo<T>

...

, Foo<T> operator<< T

+2

This one compiles on MSVC2013. Usually adds forward declarations to the class and functions in front of another

template<class T>   class MyVar ; // class forward declaration

template<class T> ; // function forward declarations
void printVar(const MyVar<T>& var);
template<class T>
void scanVar(MyVar<T>& var);

template<class T>
class MyVar
{
    friend void printVar<T>(const MyVar<T>&);
    friend void scanVar<T>(MyVar<T>&);
    int x;
};

template<class T>
void printVar(const MyVar<T>& var)
{
    std::cout << var.x << std::endl;
}

template<class T>
void scanVar(MyVar<T>& var)
{
    std::cin >> var.x;
}

struct Foo {};

int main1(void)
{
    MyVar<Foo> a;
    scanVar(a);
    printVar(a);
    return 0;
}
+1
source

All Articles