Why is friend member function not recognized as function template automatically?
<p>c++ faq 35.16</p>

<p><a href="http://www.parashift.com/c++-faq-lite/template-friends.html">http://www.parashift.com/c++-faq-lite/template-friends.html</a></p>

<pre><code>#include &lt;iostream&gt;

template&lt;typename T&gt;
class Foo {
public:
  Foo(T const&amp; value = T());
  friend Foo&lt;T&gt; operator+ (const Foo&lt;T&gt;&amp; lhs, const Foo&lt;T&gt;&amp; rhs);
  friend std::ostream&amp; operator&lt;&lt; (std::ostream&amp; o, const Foo&lt;T&gt;&amp; x);
private:
  T value_;
};
</code></pre>

<p>The autor claims:</p>

<p>'The snag happens when the compiler sees the friend lines way up in the class definition proper. At that moment it does not yet know the friend functions are themselves templates <strong>(why is it? aren't class template member functions be function template by default?)</strong>; it assumes they are non-templates like this:'</p>

<pre><code>Foo&lt;int&gt; operator+ (const Foo&lt;int&gt;&amp; lhs, const Foo&lt;int&gt;&amp; rhs)
{ ... }  

std::ostream&amp; operator&lt;&lt; (std::ostream&amp; o, const Foo&lt;int&gt;&amp; x)
{ ... }
</code></pre>

<p><strong>Why are the above non-templates? aren't these templates that are instantiated via int?</strong></p>

<p>'When you call the operator+ or operator&lt;&lt; functions, this assumption causes the compiler to generate a call to the non-template functions, but the linker will give you an "undefined external" error because you never actually defined those non-template functions. '</p>

<p>In fact, to make compiler recognize the above as function template, programmer has to do this explicitly like below:</p>

<pre><code>template&lt;typename T&gt; class Foo;  // pre-declare the template class itself
template&lt;typename T&gt; Foo&lt;T&gt; operator+ (const Foo&lt;T&gt;&amp; lhs, const Foo&lt;T&gt;&amp; rhs);
template&lt;typename T&gt; std::ostream&amp; operator&lt;&lt; (std::ostream&amp; o, const Foo&lt;T&gt;&amp; x);
</code></pre>

<p>Could anyone explain? I find this quite vexing and do not know why compiler does not just instantiate a  instance of Class Foo by replacing T with 'int', and call it a day.</p>

<p>Thanks.</p>
