Solved

Specializing Template Functions

Posted on 2010-09-02
7
722 Views
Last Modified: 2012-08-13
Hey guys,

I'm having a strange problem with templates again.  So, I know that I can take a template function, say:

template <typename T>
void foo(T val)
{
    //Do whatever with val of type T.
}

and that I can specialize it with:

template<>
void foo<bool>(bool val)
{
    //Do whatever with specific type bool.
}

My problem is in a current project I did this and I'm getting:
-invalid explicit specialization before > token.  
-explicit specialization in non-namespace scope "class myclassname".
-invalid member function declaration.

I tailored the class name but that's the exact output.

The project uses namespaces, but the current file is not in a namespace.  It works fine as is (and it's using a template function).  It breaks when adding the specialization for the funciton.  I was originally trying to use a datatype which was defined in another namespace, but the same error occurs even if I just try bool, so I don't think that's the issue.

Oh, and my template brackets <> definitely line up despite the sound of the first error message.  Any ideas of what I'm messing up?

Thanks in advance!

-w00te
0
Comment
Question by:w00te
[X]
Welcome to Experts Exchange

Add your voice to the tech community where 5M+ people just like you are talking about what matters.

  • Help others & share knowledge
  • Earn cash & points
  • Learn & ask questions
  • 4
  • 3
7 Comments
 
LVL 12

Author Comment

by:w00te
ID: 33588006
[More Info]
Oh, and I ran across this comment which seems to address the issue (exact error messages noted).  I don't quite understand the nested class idea though.  
"Explicit template specialization is forbidden for nested classes.  As partial template specialization is not forbidden, you get around quite comfortable."
The class I was putting the template function in was not a template class.  The template specialization function was trying to use a class which contained std::strings, so that may lead to nesting... but I don't see why that's a problem considering the non-specialized template handles the type fine (I just wanted an additional action if it was this particular type).  
Also, since the specialization didn't work with a bool I really don't see a nesting issue.
Oh, and it should be clear from further up, but this template function and template specialization are both member functions of a class.
-w00te
0
 
LVL 40

Expert Comment

by:evilrix
ID: 33588231
Can you provide a representative example of the code that generates the error please? It's hard to diagnose just from the description.
0
 
LVL 12

Author Comment

by:w00te
ID: 33588499
Actually I can do one better.&nbsp; Again, we only have net on unclassed windows so this is not compiled but:

struct A
{
    template <typename T>
    void foo(T value)
    {
        //Do something with value of type T.
    }

    template<>
    void foo<bool>(bool value)
    {
        //Do somethign with value of type bool.
    }
};

int main()
{
    A a;
    bool x = true;
    float y = 123.456;
    a.foo(x);
    a.foo(y);
}

You should get the error I wrote before.

Now, it occurrs to me that I can just make the Update(bool) function a normal function and it chooses that overload when a bool type is passed in.  I tried it and it works, and the tempalte function is chosen for the other types so the solution works great.

But I don't understand why you can't specialize a template function (completely, not partially) within a structure or class definition.  If you remove the foo definitions from the class A, and write them standalone it works fine.

Check this thread:
http://bytes.com/topic/c/answers/168195-partial-but-not-full-explicit-specialization-non-namespace-scope

Gets to here:
"it2.cpp", line 5: error: explicit specialization is not allowed in the
current scope
template <>
^

This is as per Standard C++, since that line can't be in class scope.

0
Technology Partners: We Want Your Opinion!

We value your feedback.

Take our survey and automatically be enter to win anyone of the following:
Yeti Cooler, Amazon eGift Card, and Movie eGift Card!

 
LVL 40

Accepted Solution

by:
evilrix earned 500 total points
ID: 33588581
You need to change it like below (I think you realise this),

>>  don't understand why you can't specialize a template function (completely, not partially) within a structure or class definition.
Without wanting to be glib, because that's what the C++ standard prescribes :)

I'll try and find the actual working in the standards doc... just give be sometime as it's not the easiest doc to search :(



// scratch.cpp : Defines the entry point for the console application.
//
struct A 
{ 
    template <typename T>
    void foo(T value)
    {
        //Do something with value of type T.
    }

};

template<>
void A::foo<bool>(bool value)
{
    //Do somethign with value of type bool.
}

int main()
{
    A a;
    bool x = true;
    float y = 123.456f; 
    a.foo(x);
    a.foo(y);
}

Open in new window

0
 
LVL 12

Author Closing Comment

by:w00te
ID: 33588709
Actually, I did something a little different which is weird because I did what you just coded somewhere else in the project.

Funny how you do different things for the same problem without thinking, haha.  If you do get that stanards thing just toss it on here and I'll read it, I'm interested.  Don't worry about it if its too much of a pain in the *** though :)

Thanks for the code!
-w00te
0
 
LVL 40

Expert Comment

by:evilrix
ID: 33588744
Ok, it took some searching, but this is the explicit wording...

"An explicit specialization shall be declared in the namespace of which the template is a member, or, for member templates, in the namespace of which the enclosing class or enclosing class template is a member."

...and...

"An explicit specialization of a member function, member class or static data member of a class template shall be declared in the namespace of which the class template is a member."

So, that makes it about as clear as mud :)

I think the issue is one of consistency. The point of instantiation for implicit instantiations is always at namespace level so it follows that explicit ones should follow suit. I don't have a better answer than that I am afraid. It's one of those things that's always bugged me cos I really can't see why it is that way but it is what it is :(
0
 
LVL 12

Author Comment

by:w00te
ID: 33589588
Yeah, its a hard problem to track down at first because there doesn't seem to be anything logically wrong with it; it just doens't work.
Anyway, thanks for the standard reference, definitely no room for interperetation there!  At least I know where the rule comes from now :)
0

Featured Post

Enroll in June's Course of the Month

June's Course of the Month is now available! Every 10 seconds, a consumer gets hit with ransomware. Refresh your knowledge of ransomware best practices by enrolling in this month's complimentary course for Premium Members, Team Accounts, and Qualified Experts.

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

Article by: SunnyDark
This article's goal is to present you with an easy to use XML wrapper for C++ and also present some interesting techniques that you might use with MS C++. The reason I built this class is to ease the pain of using XML files with C++, since there is…
Many modern programming languages support the concept of a property -- a class member that combines characteristics of both a data member and a method.  These are sometimes called "smart fields" because you can add logic that is applied automaticall…
The goal of the video will be to teach the user the concept of local variables and scope. An example of a locally defined variable will be given as well as an explanation of what scope is in C++. The local variable and concept of scope will be relat…
The viewer will be introduced to the member functions push_back and pop_back of the vector class. The video will teach the difference between the two as well as how to use each one along with its functionality.

724 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question