I have an interface
std::string
get_string(Source const &s, std::string const &d);
int
get_int(Source const &s, int const &d);
bool
get_bool(Source const &s, bool const &d);
which I'd like to change to
template<class T>
T
get(Source const &s,开发者_运维问答 T const &d);
But there's no sensible base template, so the actual base definition is a legal but useless (return d;
). What can I do to force compile-time failure if the base is instantiated? Is there an idiomatic solution for this situation?
Don't define the template, just declare it and define the three specializations.
template <typename T>
T get(Source const &, T const &);
template<>
std::string get(Source const &s, std::string const &d) {
return d + s.stringval(); // or whatever
}
[Edit: removed stuff about overloads - just for once, template function specialization does actually seem to be better. Who woulda thunk?]
just do
string get(source, string);
int get (source, int);
bool get(source, bool);
If you are willing to pay for run-time polymorphism, you can do this...
template <typename T>
class Interface
{
virtual T get(Source const &s, T const &d) = 0;
};
class StringInterface : public Interface<std::string>
{
virtual std::string get(Source const& s, std::string const& d);
};
// etc.
Since your base is an abstract class, you will get a compile-time failure if you try to instantiate it directly.
Declare the baseclass (t) as abstract, that way an instance can never be created of that class.
精彩评论