Christopher Glynn Christopher Glynn - 11 months ago 36
C++ Question

Forward Declaration of class as template param. Why does this work?

I have been playing around with some c++ template meta-programing and I have discovered situation which I think is rather peculiar.
Let say I have the following class.

template<typename T>
class Foo{

Then later I found I use a foward declaration of a class (I am assuming that is what it is being treated as) as the template argument as so

Foo<class bar> bar1;

I also found that the following also compile fine.

Foo<class bar()> bar2;
Foo<class bar(int a)> bar3;

So my question is, why does this work. What is going on in all three cases.

According to the standard I can not declare a class at this point so this fails:

Foo<class bar{}> bar4

My original assumption was this just a forward declaration and you could actually declare a class at that pointer (which I could see possible uses for).
However, you can not. So my second question what is the use of above? Is there any practical uses of it or is just a result of how c++ works that this is legal. One use I can see is you can use this to create tagging information on a type.

I am using the most recent version of g++

Answer Source

In all 3 cases, you are forward declaring the class bar, so you have to define it later one.

Foo<class bar> bar1;

This works because it is allowed to declare a class for the first time in a template argument, i.e. it is equivalent to

class bar;
Foo<bar> bar1;

Foo<class bar()> bar2;

This creates the class bar, just as before, and creates a function taking no parameters and returning a bar.

Foo<class bar(int a)> bar3;

This is really similar to the second one, just that here, it declares a function taking an int, instead of none. It is equivalent to

class bar;
Foo<bar(int)> bar3;