Velocity Reviews - Computer Hardware Reviews

Velocity Reviews > Newsgroups > Programming > C++ > template specialization problem, but only with char*

Reply
Thread Tools

template specialization problem, but only with char*

 
 
Adam
Guest
Posts: n/a
 
      11-02-2004
I'm trying to write a template specialization, and the char*
specialization is giving me some trouble. Here's a simplified example:

/**************************/
/* test.cpp */
#include "try.hpp"

int main(){}
/**************************/

/**************************/
/* try.hpp */

template <typename T> struct foo
{
void f(const T& param) const;
};

template <typename T>
void
foo<T>::f(const T& param) const
{}

template <> // works fine
void
foo<int>::f(const int& param) const
{}

/*
The following results in:

template-id `f<>' for `void foo<char*>::f(const char*&) const' does not
match any template declaration

template <>
void
foo<char*>::f(const char*& param) const
{}
*/

/*
The following results in:
template-id `f<>' for `void foo<char*>::f(const char*) const' does not
match any template declaration

template <>
void
foo<char*>::f(const char* param) const
{}
*/

/*
But the following works fine. That really confuses me....
*/
typedef char* Char;

template <>
void
foo<Char>::f(const Char& param) const
{}

/**************************/
Thanks for reading. Any help would be greatly appreciated.

- Adam

 
Reply With Quote
 
 
 
 
Victor Bazarov
Guest
Posts: n/a
 
      11-02-2004
Adam wrote:
> I'm trying to write a template specialization, and the char*
> specialization is giving me some trouble. Here's a simplified example:
>
> /**************************/
> /* test.cpp */
> #include "try.hpp"
>
> int main(){}
> /**************************/
>
> /**************************/
> /* try.hpp */
>
> template <typename T> struct foo
> {
> void f(const T& param) const;
> };
>
> template <typename T>
> void
> foo<T>::f(const T& param) const
> {}
>
> template <> // works fine
> void
> foo<int>::f(const int& param) const
> {}
>
> /*
> The following results in:
>
> template-id `f<>' for `void foo<char*>::f(const char*&) const' does not
> match any template declaration
>
> template <>
> void
> foo<char*>::f(const char*& param) const
> {}
> */
>
> /*
> The following results in:
> template-id `f<>' for `void foo<char*>::f(const char*) const' does not
> match any template declaration
>
> template <>
> void
> foo<char*>::f(const char* param) const
> {}
> */
>
> /*
> But the following works fine. That really confuses me....
> */
> typedef char* Char;
>
> template <>
> void
> foo<Char>::f(const Char& param) const
> {}
>
> /**************************/


'const' relates to the object, not to the type. In all fairness, it
should be placed to the right of the type. In your case, this is what
your [working] declaration should be

template<> void foo<char*>::f(char* const & param);

and you tried [unsuccessfully] to declare it as

template<> void foo<char*>::f(char const *& param);

Do you see the difference?

In your template, it's the object who is const. So, the reference that
'param' designates _refers_ to a constant something. In your 'char*'
specialisation, that something is a _pointer_to_char_. So, you have to
make your _pointer_ constant. You've been trying to make the _char_
constant and leave the pointer non-const. That's the mistake.

V
 
Reply With Quote
 
 
 
 
Adam
Guest
Posts: n/a
 
      11-02-2004

Victor Bazarov wrote:
> Adam wrote:
> >

<snip>
> 'const' relates to the object, not to the type. In all fairness, it
> should be placed to the right of the type. In your case, this is

what
> your [working] declaration should be
>
> template<> void foo<char*>::f(char* const & param);
>
> and you tried [unsuccessfully] to declare it as
>
> template<> void foo<char*>::f(char const *& param);
>
> Do you see the difference?
>


I do.

Thanks, Victor.

It is no longer relevant to this particular problem, but I am curious
as to why the following worked:

typedef char* Char;
template<> void foo<Char>::f(const Char& param);

How is 'const Char &' different from 'const char* &' in this case? I'm
guessing that 'Char' is now seen only as a pointer, and that 'const
Char' is equivalent to 'Char const'. Is that correct?

- Adam

 
Reply With Quote
 
Victor Bazarov
Guest
Posts: n/a
 
      11-02-2004
Adam wrote:
> [...]
> It is no longer relevant to this particular problem, but I am curious
> as to why the following worked:
>
> typedef char* Char;
> template<> void foo<Char>::f(const Char& param);
>
> How is 'const Char &' different from 'const char* &' in this case? I'm
> guessing that 'Char' is now seen only as a pointer, and that 'const
> Char' is equivalent to 'Char const'. Is that correct?


Absolutely. You always should position the 'const' specifier to the right
of the type-id. In case of 'char*', the type-id is 'char', so the 'const'
moves between 'char' and '*'. In case of 'Char', the type-id is 'Char',
so the 'const' skips to the right. Once expanded again, it becomes this
peculiar thing 'char * const', which is not the same as 'char const *'.

It's not the clearest part of the language, but once you learn it, it will
serve you well.

V
 
Reply With Quote
 
 
 
Reply

Thread Tools

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is On
HTML code is Off
Trackbacks are On
Pingbacks are On
Refbacks are Off


Similar Threads
Thread Thread Starter Forum Replies Last Post
Full specialization of a member function template of a class template Dave C++ 4 06-04-2010 12:15 PM
template specialization overriding non-specialization? Joseph Turian C++ 2 04-16-2006 02:46 PM
Template specialization for templated and primitive type template parameters case2005 C++ 3 02-13-2005 06:53 PM
template specialization of a template class pit3k C++ 8 02-09-2005 02:39 AM
Specialization of a template within template David B. Held C++ 2 10-26-2003 11:59 AM



Advertisments
 



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 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57