Home
Fractals
Tutorials
Books
My blog
My LinkedIn Profile

BOOKS i'm reading

Napoleon Hill Keys to Success: The 17 Principles of Personal Achievement, Napoleon Hill, ISBN: 978-0452272811
The 4-Hour Workweek: Escape 9-5, Live Anywhere, and Join the New Rich (Expanded and Updated), Timothy Ferriss, ISBN: 978-0307465351
The Fountainhead, Ayn Rand, ISBN: 0452273331
Web Hosting Canada

mailto:olivier@olivierlanglois.net

Archives for: July 2007, 09

07/09/07

Permalink 10:21:28 pm, by lano1106, 458 words, 4180 views   English (CA)
Categories: C++

friend function declaration in a class template

In my opinion, one of the most twisted part of the C++ standard (I am sure that there is more than just one twisted aspect) it is the friend function declaration in a class when you add templates to the mix. Even compiler implementers are having a hard time to get it right. I had the following code that used to compile fine in VC++6:

template< typename T >
class X
{
    friend ostream &operator<<( ostream &, const X<T> & );
};

template< typename T >
ostream &operator( ostream &os, const X<T> &t )
{
    // Print out t
    return os;
}

but now with VC++2003, I received this error message:

unresolved external symbol ostream &operator<<( ostream &, const X<T> & )

That code snippet is non conforming to the standard and in order to make the compiler happy, I had to write:

template< typename T >
class X
{
    /*
     * The '<>' is needed to say that the friend is a
     * function template.
     */
    friend ostream &operator<< <>( ostream &,
                                   const X<T> & );
};

and for those who wonder, no I did not find the solution by myself. I had to look into my book C++ Templates. From section 8.4.1 (Friend Functions):

"An instance of a function template can be made a friend by making sure the name of the friend function is followed by angle brackets...If the name is not followed by angle brackets, there are two possibilities:

1. If the name isn't qualified (in other words, it doesn't contain a double colon), it never refers to a template instance...
2. If the name is qualified (it contains ::), the name refer to a previously declared function or function template. A matching function is preferred over a matching function template..."

So my example fits case #1 description so because of a bug into VC++6 (or maybe the standard was even not complete at the time of its release...), the compiler was erroneously accepting the friend statement as referring to a function template.

So this is the whole story. What I find sad is that the rule is not intuitive at all. There is no way I can reason it next time I am in the same situation. I will either remember the rule or I will have to check back in my C++ Template book. Herb Sutter has also written an item on that topic in his book C++ exceptional Style if you are interested in a different point of view on the topic but he pretty much comes to the conclusion that this is a tricky C++ standard aspect and that a lot of compilers have troubles accepting such statements.

Olivier Langlois's blog

I want you to find in this blog informations about C++ programming that I had a hard time to find in the first place on the web.

July 2007
Sun Mon Tue Wed Thu Fri Sat
 << < Current> >>
1 2 3 4 5 6 7
8 9 10 11 12 13 14
15 16 17 18 19 20 21
22 23 24 25 26 27 28
29 30 31        

Search

Custom Search

Misc

XML Feeds

What is RSS?

Who's Online?

  • Guest Users: 8

powered by
b2evolution