473,325 Members | 2,860 Online
Bytes | Software Development & Data Engineering Community
Post Job

Home Posts Topics Members FAQ

Join Bytes to post your question to a community of 473,325 software developers and data experts.

partial specialization of template member function

Hi,

Why doesn't this work? (tried with gcc 3.3.3 and VC++ 7.1):

#include <iostream>
template<class T, unsigned N>
struct Foo {
void func();
};
template<class T, unsigned N>
void Foo<T,N>::func() {
std::cout << "Primary -- "
<< "T is " << typeid(T).name() << " -- "
<< "N=" << N
<< std::endl;
}
template<class T>
void Foo<T,3>::func() {
std::cout << "Specialized for N=3 -- "
<< "T is " << typeid(T).name() << " -- "
<< std::endl;
}

int main() {
Foo<double,3> d;
Foo<int,5> i;
d.func();
i.func();
return 0;
}

gcc compiler error: no `void Foo<T, 3>::func()' member function declared in
class `Foo<T, 3>'
(VC7.1 error is similar)

On the other hand, full specialization of the member works (without
specializing the whole class). (try replacing `template<class T> void
Foo<T,3>::func()' with `template<> void Foo<double,3>::func()')

If this behaviour is how it is defined in the standard, what may be a
possible workaround to achieve partial specialization on member functions?

thank you
- sly.
Jul 23 '05 #1
5 6547
Levent wrote:
Why doesn't this work? (tried with gcc 3.3.3 and VC++ 7.1):
[..]
Because you have to first define the partial specialisation of the
enclosing class template.
On the other hand, full specialization of the member works (without
specializing the whole class). (try replacing `template<class T> void
Foo<T,3>::func()' with `template<> void Foo<double,3>::func()')

If this behaviour is how it is defined in the standard, what may be a
possible workaround to achieve partial specialization on member functions?


This is as specified. There are no partial specialisations of function
templates, and to partially specialise a member you need to first
partially specialise the class template.

V
Jul 23 '05 #2
> VB: There are no partial specialisations of function templates ....
When you say this you do not mean any function, right? 'cause non-member
function templates *can* be specialized. And I should admit that partial
specialization of member function w/o partial spec of full class is
somewhat ill-conditioned design (can't explain why, just fells like that
way...).

However, I came up with a workaround: Use non-member friend template
functions.

Before listing the code that does this I want to note a gotcha of
VC++7.1 (actually this is somewhat the reason I am posting this
follow-up) which probably is a good example of how unreliable this
compiler is.

Here is how I implemented non-member friend template (tried to trim as
much as I can):

================================================== =
#include <iostream>

using namespace std;

template<class T, unsigned N> class Foo;
template<class T, unsigned N> void print(Foo<T,N> &f);

template<class T, unsigned N>
class Foo {
int i;
public:
friend void print<>(Foo &);
Foo(int i_) :i(i_) {};
};

template<class T, unsigned N>
void print(Foo<T,N> &f) {
cout << "Foo<" << typeid(T).name() << ", " << N << ">"
<< ".i=" << f.i << endl;
}
template<class T>
void print(Foo<T,4> &f) {
cout
<< "Specialized for N=4: "
<< "Foo<" << typeid(T).name() << ", " << 4 << ">"
<< ".i=" << f.i << endl;
}

int main() {
Foo<int,4> a(9); // specialized <> instantiation
// Foo<double,4> b(9); // another specialized <> instantiation
Foo<double,5> c(10); // primary <> instantiation
print(a);
// print(b);
print(c);
return 0;
}
================================================== ===

This compiles (and runs) fine with gcc 3.3.3 and intel 8.1.

However, with VC++7.1, it gives `print cannot access private member'
compile error.

Even worse happens: Commentting out the 1st and 4th lines of main() and
uncommenting 2nd and 5th, VC++ _does_ compile... But very wrong things
happen during run: c acts as if Foo<double,5> !!!

can anyone confirm that this is the case?

Victor Bazarov wrote:
Levent wrote:
Why doesn't this work? (tried with gcc 3.3.3 and VC++ 7.1):
[..]

Because you have to first define the partial specialisation of the
enclosing class template.
On the other hand, full specialization of the member works (without
specializing the whole class). (try replacing `template<class T>
void Foo<T,3>::func()' with `template<> void Foo<double,3>::func()')

If this behaviour is how it is defined in the standard, what may be a
possible workaround to achieve partial specialization on member
functions?

This is as specified. There are no partial specialisations of function
templates, and to partially specialise a member you need to first
partially specialise the class template.

V

Jul 23 '05 #3
Levent wrote:
VB: There are no partial specialisations of function templates ....
When you say this you do not mean any function, right? 'cause non-member
function templates *can* be specialized.


Not partially. Only fully. There are no partial specialisations of
function templates. Period. And when I say this I mean any function,
member or non-member.

You can partially specialise a class template. You can then define
a member of that specialisation. That's not the same as partially
specialising a function template.
[...]


V
Jul 23 '05 #4
What I meant was *partial* specializations of template functions are
possible. Please, take a look at this (valid) code:

using namespace std;
template<class T1, class T2>
void foobar(T1 &t1,T2 &t2) {
cout << "Primary <> instantiation -- foobar<"
<< typeid(t1).name() << "," << typeid(t2).name() << ">"
<< endl;
}
template<class T>
void foobar(T &t1,double &t2) {
cout << "Specialized <> instantiation -- foobar<"
<< typeid(t1).name() << "," << typeid(double).name() << ">"
<< endl;
}

int main() {
double k,l; int i,j;
foobar(i,j);
foobar(k,j);
foobar(i,k);
return 0;
}

This obviously works. But maybe it is my confusion with terminology:
What I assume as specialization is nothing but overloading, somewhat :?...

If you are referring to the standard when you assert that
There are no partial specialisations of function templates. Period.
I should take your word for it... But then, isn't it the case that
explicit (full) specialization, is also in fact overloading?

BTW, what do you think of the code in my previous post? Don't you think
it is interesting that VC++7.1 fails with this?

Victor Bazarov wrote:
Levent wrote:
VB: There are no partial specialisations of function templates ....



When you say this you do not mean any function, right? 'cause
non-member function templates *can* be specialized.

Not partially. Only fully. There are no partial specialisations of
function templates. Period. And when I say this I mean any function,
member or non-member.

You can partially specialise a class template. You can then define
a member of that specialisation. That's not the same as partially
specialising a function template.
[...]


V

Jul 23 '05 #5
Levent wrote:
What I meant was *partial* specializations of template functions are
possible. Please, take a look at this (valid) code:

using namespace std;
template<class T1, class T2>
void foobar(T1 &t1,T2 &t2) {
cout << "Primary <> instantiation -- foobar<"
<< typeid(t1).name() << "," << typeid(t2).name() << ">"
<< endl;
}
template<class T>
void foobar(T &t1,double &t2) {
cout << "Specialized <> instantiation -- foobar<"
<< typeid(t1).name() << "," << typeid(double).name() << ">"
<< endl;
}
This is not a specialisation. It's just another template. If it were
a specialisation, it would have <???> after the function name.
int main() {
double k,l; int i,j;
foobar(i,j);
foobar(k,j);
foobar(i,k);
return 0;
}

This obviously works. But maybe it is my confusion with terminology:
What I assume as specialization is nothing but overloading, somewhat :?...
Exactly. Two different templates, both contribute to overloading
resolution.
If you are referring to the standard when you assert that
There are no partial specialisations of function templates. Period.

I should take your word for it... But then, isn't it the case that
explicit (full) specialization, is also in fact overloading?


Yes.
BTW, what do you think of the code in my previous post? Don't you think
it is interesting that VC++7.1 fails with this?


I didn't look.

V

P.S. Please don't top-post.
Jul 23 '05 #6

This thread has been closed and replies have been disabled. Please start a new discussion.

Similar topics

17
by: Paul MG | last post by:
Hi Template partial specialization always seems like a fairly straightforward concept - until I try to do it :). I am trying to implement the input sequence type (from Stroustrup section...
8
by: Agent Mulder | last post by:
Hi group, I have a problem with partial template specialization. In the code below I have a template struct Music with one method, play(), and three kinds of music, Jazz, Funk and Bach. When I...
1
by: SainTiss | last post by:
Hi, I've been looking into the standard for a clear statement on whether partial specialization of member functions of class templates is allowed or not. 14.7.3/4 says that explicit...
1
by: Kai-Uwe Bux | last post by:
Hi folks, I would like to know which clause of the standard rules out this: template < typename eval > struct recursive_template { typedef typename eval::enum_type Enum;
6
by: wkaras | last post by:
I tried a couple of compilers, and both gave errors compiling this: template <bool fin, typename T> T foo(T val); template <typename T> T foo<true, T>(T val) { return(val); } But both gave...
9
by: Marek Vondrak | last post by:
Hello. I have written the following program and am curious why it prints "1" "2". What are the exact effects of explicitly providing function template parameters at the call? Is the second...
5
by: cpunerd | last post by:
I'm confused as to the syntax for partial template specialization. Below is a very small example. Can someone tell me what I should do to make this compile properly on an ISO-compliant compiler? ...
4
by: Olaf | last post by:
Hi, I'm writing a small wrapper for libcurl. For Options I use: template<typename T, long CURLOPT_ID> class CurlOption: boost::noncopyable { public: typedef typename...
10
by: jason.cipriani | last post by:
I never seem to be able to get this right. Here I have some code: template <typename T, int Nclass A { void f (T); }; template <typename Tvoid A<T,1>::f (T) { } template <typename Tvoid...
0
by: ryjfgjl | last post by:
ExcelToDatabase: batch import excel into database automatically...
0
isladogs
by: isladogs | last post by:
The next Access Europe meeting will be on Wednesday 6 Mar 2024 starting at 18:00 UK time (6PM UTC) and finishing at about 19:15 (7.15PM). In this month's session, we are pleased to welcome back...
1
isladogs
by: isladogs | last post by:
The next Access Europe meeting will be on Wednesday 6 Mar 2024 starting at 18:00 UK time (6PM UTC) and finishing at about 19:15 (7.15PM). In this month's session, we are pleased to welcome back...
0
by: Vimpel783 | last post by:
Hello! Guys, I found this code on the Internet, but I need to modify it a little. It works well, the problem is this: Data is sent from only one cell, in this case B5, but it is necessary that data...
0
by: ArrayDB | last post by:
The error message I've encountered is; ERROR:root:Error generating model response: exception: access violation writing 0x0000000000005140, which seems to be indicative of an access violation...
1
by: PapaRatzi | last post by:
Hello, I am teaching myself MS Access forms design and Visual Basic. I've created a table to capture a list of Top 30 singles and forms to capture new entries. The final step is a form (unbound)...
1
by: Shællîpôpï 09 | last post by:
If u are using a keypad phone, how do u turn on JavaScript, to access features like WhatsApp, Facebook, Instagram....
0
by: af34tf | last post by:
Hi Guys, I have a domain whose name is BytesLimited.com, and I want to sell it. Does anyone know about platforms that allow me to list my domain in auction for free. Thank you
0
isladogs
by: isladogs | last post by:
The next Access Europe User Group meeting will be on Wednesday 3 Apr 2024 starting at 18:00 UK time (6PM UTC+1) and finishing by 19:30 (7.30PM). In this session, we are pleased to welcome former...

By using Bytes.com and it's services, you agree to our Privacy Policy and Terms of Use.

To disable or enable advertisements and analytics tracking please visit the manage ads & tracking page.