I'm trying to fix an "explicit specialization in non-namespace scope" error using the method described in this post. So I managed to move the templated functions into a separate namespace, and I'm calling these functions from my class (see the code below).
The code now compiles, however I'm getting linker errors " already defined in main.obj" for all the functions in the namespace. I thought that adding #ifndef STYLE_H
at the top would prevent the namespace from being included multiple times or am I missing something? How can I fix this error?
Below is my code (simplified):
#ifndef STYLE_H
#define STYLE_H
namespace hanzi {
namespace styleUtil {
template <class T>
T get(const QString& name, T defaultValue = T(), const Style* style = NULL, const Style* baseStyle = NULL) {
// ...
}
template <>
QColor get<QColor>(const QString& name, QColor defaultValue, const Style* style, const Style* baseStyle) {
// ...
}
template <>
ImagingEffect get<ImagingEffect>(const QString& name, ImagingEffect defaultValue, const Style* style, const Style* baseStyle) {
// ...
}
}
class Style : public QObject {
Q_OBJECT
public:
explicit Style(const QString& filePath);
template <class T>
T get(const QString& name, T defaultValue = T()) const {
return styleUtil::get<T>(name, defaultValue, this, baseStyle_);
};
};
}
#endif // STYLE_H
Regarding the original error,
I'm trying to fix an "explicit specialization in non-namespace scope" error
What that error means is that you cannot define member function template specializations inside a class definition. I.e. the following would be illegal:
struct Bar
{
template <typename T> void boo() { }
// template <> void boo<char>() { boo<int>(); } // Error! Cannot specialize here
};
However, this is solved by simply placing the specialisation outside the class definition:
template <> void Bar::boo<char>() { boo<int>(); } // Good.
(The latter position of the specialization is "at namespace scope", for example at global scope, which is what the error message wanted to tell you to do.)