c++ - How to specialize templated class methods based on type traits? Using std::enable_if works for non-class functions, but fails for class methods -
i've been trying create specializations of templated class methods such have different method definitions compiler selects based on whether argument integral type of enum class, clang gives me error:
out-of-line definition of 'parsestring' not match declaration in 'mydata'
while gcc gives following:
error: prototype 'typename std::enable_if::value, void>::type mydata::parsestring(t&, std::string)' not match in class 'mydata'
error: candidate is: template static void mydata::parsestring(t&, std::string)
the following code used produce these errors. i've experimented other ways of using enable_if
, such in template parameter rather return type, nothing far has worked. if make templated functions non-class functions instead of class methods, work fine. (removing static makes no difference.)
is there way use enable_if
templated class methods, or better way achieve same thing?
#include <string> #include <type_traits> #include <utility> class mydata { public: mydata() = default; mydata(std::pair<std::string, std::string> string_representations); std::pair<std::string, std::string> tostrings(); enum class myenum { = 0, b = 1 }; int integral_value; myenum enum_value; private: template<typename t> static void parsestring(t&, std::string); }; mydata::mydata(std::pair<std::string, std::string> string_representations) { parsestring(integral_value, string_representations.first); parsestring(enum_value, string_representations.second); } std::pair<std::string, std::string> mydata::tostrings() { return std::make_pair(std::to_string(integral_value), std::to_string((unsigned long)enum_value)); } template<typename t> typename std::enable_if<std::is_enum<t>::value, void>::type mydata::parsestring(t& setting, std::string representation) { setting = (t)std::stoul(representation); } template<typename t> typename std::enable_if<std::is_integral<t>::value, void>::type mydata::parsestring(t& setting, std::string representation) { setting = std::stoi(representation); }
(in example there's 1 integral , 1 enum member of class, if you're wondering why templated function useful, imagine if class had multiple different enum , integral type members.)
the error telling signature in definition of parsestring
method doesn't match found in declaration inside class. have copy enable_if
, use in declaration well.
template<typename t> static typename std::enable_if<std::is_integral<t>::value, void>::type parsestring(t&, std::string);
you need declaration of parsestring
uses enable_if<is_enum<t>>
in declaration, since define function uses it:
template<typename t> static typename std::enable_if<std::is_enum<t>::value, void>::type parsestring(t&, std::string);
Comments
Post a Comment