Topic: Template members of template class


Author: "Geo" <gg@remm.org>
Date: Tue, 18 Jul 2006 10:02:36 CST
Raw View
Greg Herlihy wrote:

> A (full) specialization of a template defines a single, unique
> instantation of a general template for a specific set of parameterized
> types. So in order to specialize a template member function of a class
> template in full, the parameterized types for both the class template
> and the member function must be supplied in order to arrive at a
> single, unambiguous instantiation of the member function template.

The member template parameter is not related to the class template
parameters, I don't see how any ambiguity can arise.

> call, they are not the same. In fact the existence of a specialization
> for a template function does not improve its chances of being called
> for a specific set of parameter types - an outcome that is often as
> surprising as it is unexpected. Therefore the change to make to the

Yes that is unexpected and surprising, I don't think I understand, are
you saying the compiler is free to ignore any specializations if it
feels like it  ?

> example code above (to have it work as expected) - would be to overload
> the operator<< member function instead of trying to specialize it:
>
>     Formatter__& operator<<(const char* s)
>     {
>         ss << do_stuff(s);
>         return *this;
>     }
>
> Greg

Yes that's what I did, but it looked like a cop out.

---
[ comp.std.c++ is moderated.  To submit articles, try just posting with ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu    ]
[              --- Please see the FAQ before posting. ---               ]
[ FAQ: http://www.comeaucomputing.com/csc/faq.html                      ]





Author: "Geo" <gg@remm.org>
Date: Tue, 11 Jul 2006 10:23:28 CST
Raw View
Having spent several hours trying to get the following code to compile
in GCC and failing

namespace test
{

    template<class U, class V=U&> class Formatter__
    {
    private:
 U ss;
    public:

 Formatter__(V out) : ss(out)
 {
 }

 template<typename T> Formatter__& operator<<(const T &item)
 {
     ss << item;
     return *this;
 }

 template<> Formatter__& operator<<(const char* s)
 {
            ss << do_stuff(s);
     return *this;
 }
    };
};

I eventually discovered that it was illegal in standard C++.

My question is, Why ?

I'm not to bothered with the fact that the template specialization
should be at namespace scope, but why can't I specialize operator<<
without specializing Formatter__. What problem does preventing this
solve ?

I can find lots of posts saying it is illegal, but none that explains
why ?

---
[ comp.std.c++ is moderated.  To submit articles, try just posting with ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu    ]
[              --- Please see the FAQ before posting. ---               ]
[ FAQ: http://www.comeaucomputing.com/csc/faq.html                      ]





Author: "Greg Herlihy" <greghe@pacbell.net>
Date: Wed, 12 Jul 2006 10:18:25 CST
Raw View
Geo wrote:
> Having spent several hours trying to get the following code to compile
> in GCC and failing
>
> namespace test
> {
>
>     template<class U, class V=U&> class Formatter__
>     {
>     private:
>  U ss;
>     public:
>
>  Formatter__(V out) : ss(out)
>  {
>  }
>
>  template<typename T> Formatter__& operator<<(const T &item)
>  {
>      ss << item;
>      return *this;
>  }
>
>  template<> Formatter__& operator<<(const char* s)
>  {
>             ss << do_stuff(s);
>      return *this;
>  }
>     };
> };
>
> I eventually discovered that it was illegal in standard C++.
>
> My question is, Why ?

A (full) specialization of a template defines a single, unique
instantation of a general template for a specific set of parameterized
types. So in order to specialize a template member function of a class
template in full, the parameterized types for both the class template
and the member function must be supplied in order to arrive at a
single, unambiguous instantiation of the member function template.

> I'm not to bothered with the fact that the template specialization
> should be at namespace scope, but why can't I specialize operator<<
> without specializing Formatter__. What problem does preventing this
> solve ?

A better question would be what problem would fully specialized member
functions for unspecialized class templates solve? It is easy to
mistake specializing a function template with overloading a function -
but because specializations of a template function are considered only
after a function has been already selected when resolving a function
call, they are not the same. In fact the existence of a specialization
for a template function does not improve its chances of being called
for a specific set of parameter types - an outcome that is often as
surprising as it is unexpected. Therefore the change to make to the
example code above (to have it work as expected) - would be to overload
the operator<< member function instead of trying to specialize it:

    Formatter__& operator<<(const char* s)
    {
        ss << do_stuff(s);
        return *this;
    }

Greg

---
[ comp.std.c++ is moderated.  To submit articles, try just posting with ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu    ]
[              --- Please see the FAQ before posting. ---               ]
[ FAQ: http://www.comeaucomputing.com/csc/faq.html                      ]