Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Template function specialization default [duplicate]

I'm trying to make a class which will work with specific data types and I want to have a compile-time error when data type is not supported.

I tried to specialize templates like this.

template<>
float Foo::get<float>(const std::string& key)
{
    return std::stof(key);
}

And put a std::static_assert in the generic function because I only need these types that are specified.

template<class T>
T Foo::get(const std::string&)
{
    static_assert(false, "unsupported data type");
    return T(0);
}

Unfortunately I get the compile error (static assert failed) even if I have a specialized function for this type.

I found a way to do it for the specific types only but it looks kinda stupid and its not generic.

T Foo::get(const std::string&)
{
    static_assert(
            std::is_same<T,float>::value ||
            std::is_same<T,double>::value ||
            std::is_same<T,bool>::value ||
            std::is_same<T,uint32_t>::value ||
            std::is_same<T,int32_t>::value ||
            std::is_same<T,std::string>::value,
            "unsuported data type");
    return T(0);
}
like image 817
Petar Velev Avatar asked Oct 30 '22 05:10

Petar Velev


2 Answers

You can make static_assert depending on the template parameter T, then it won't be evaluated until the time of instantiation, i.e. the time the exact type is explored as template argument. e.g.

template<class T>
T get(const std::string&)
{
    static_assert(!std::is_same<T, T>::value, "unsupported data type");
    return T(0);
}

LIVE

like image 70
songyuanyao Avatar answered Nov 15 '22 05:11

songyuanyao


You may do

template <typename> struct AlwaysFalse : false_type {};


template<class T>
T Foo::get(const std::string&)
{
    static_assert(AlwaysFalse<T>::value, "unsupported data type");
}

So the assert is template dependent.

like image 33
Jarod42 Avatar answered Nov 15 '22 05:11

Jarod42