I have a template that is just that - a very basic class template; something like:
Tmpl.h
template <typename Base>
class Tmpl: public Base
{
public:
Tmpl(): Base()
{
this->methodOfBase();
}
};
I would like to be able to forward-declare specialized versions of this Templ. I typically just store a (shared) pointer, so in my simple mind, all the compiler needs to know is that this is a pointer to a class; why am I not allowed to do this:
PublicClass.h
#pragma once
class MyClass;
class PublicClass {
// ....
private:
MyClass* test;
};
(I know pragma once isn't in the standard...)
PublicClass.cpp
#include "MyClass.h"
#include "Tmpl.h"
class SomeClass
{
public:
void methodOfBase()
{
}
};
using MyClass = Tmpl<SomeClass>;
int main()
{
PublicClass c;
return 0;
}
On Visual Studio (2022) I get an error: error C2371: 'MyClass': redefinition; different basic types.
I know that as a workaround I can change MyMethod.h to
#include "Tmpl.h"
class SomeClass;
using MyClass = Tmpl<SomeClass>;
void myMethod(MyClass* test);
But I do not understand why the fact that MyClass is using a template needs to be visible to the users of PublicClass (all users of that class need to know about it).
I get that the compiler needs to know if a class is templated, i.e., needs a template parameter. But in this case, MyClass is just an "instance" of a template, and shouldn't need special handling, or does it?
And what does the "different basic type" in the error refer to?
The first declaration says that MyClass is a class. The second one says that it is not, it is an alias. Those are different.
The problem is not realated to templates. You get the same error for
class A;
class B
{};
using A = B;
One possible workaround would be to let MyClass really be a class, but derive it from the template instance.
class MyClass;
class MyClass : public Tmpl<SomeClass>
{ };
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With