Page MenuHomePhabricator

Template Specialization
ActivePublic

Authored by bdlovy on Jan 23 2020, 5:28 PM.
/* test.hpp */
#ifndef TEST_HPP
#define TEST_HPP
namespace idksomefunctions
{
template <typename T>
int myIdentityFunction(T val)
{
return val;
}
template <>
int myIdentityFunction(int val)
{
return val * 2; // SNEAKY!!
}
};
#endif
/* test.cpp */
#include <iostream>
#include "test.hpp"
int main()
{
int someInt = 5;
int aCopyOfTheSameInt = idksomefunctions::myIdentityFunction(someInt);
std::cout << aCopyOfTheSameInt << "\n";
}

Event Timeline

@jcmcdonald this worked for me, what am I missing from the actual example?

Ah, never mind - it's when you don't have an implementation for the specialization, just the types.

It's when you define the generic form, and then specialize that form below it.

class Channel
{
public:
    template<typename T>
    channel& resolve_pointer(const T* rhs)
    {
        // ...
    }

    template<> channel& resolve_pointer<bool>(const bool*);
    template<> channel& resolve_pointer<unsigned char>(const unsigned char*);
    template<> channel& resolve_pointer<int>(const int*);
};

...versus outside of a class...

namespace stringy
{
    template<typename T>
    void itoa(char* str, T val, int base, int len, bool use_caps)
    {
        // ...
    }

    template void itoa<char>(char*, char, int, int, bool);
    template void itoa<unsigned char>(char*, unsigned char, int, int, bool);
    template void itoa<int>(char*, int, int, int, bool);
};

Did you end up resolving that last issue?

@jcmcdonald per @rogerzanoni on DEV you can just move the specializations outside of the class block: godbolt link. It's a yak shave and a half, but there it is.

That is deeply helpful!

I find it odd how this particular form of specialization is all but completely undocumented.

Meanwhile, I also figured out I can do a similar type-limiting with static_assert and #include <type_traits>