Search code examples
c++templatesexternexplicit-instantiation

Prevent all instantiations of a template class - including supported types


If I have a template class MyClass<T> and if I explicitly instantiate for int and float (in a cpp file) then I can use extern template class MyClass<int> and extern template class MyClass<float> to prevent any compilation unit encountering this class from instantiating it for int and float unnecessarily. Of course, for any other type, the class will still get instantiated.

Now I have a class MyClass2<T> which only works with int, float, char, double, short and their unsigned variants where applicable. Since I know all the types beforehand, the definitions of all the methods in this class are in the cpp file. This is also where I explicitly instantiate MyClass2<T> for all the above mentioned types. In the header, I have static_assert preventing the user from creating MyClass2<T> with an unsupported type.

Is there any way to completely prevent MyClass2<T> from instantiating (e.g. extern template class MyClass2; although I know that doesn't work) for all types including supported types? Like a catch all for extern template? I want to avoid typing out extern template class MyClass2<int> for all the supported types.

Considering I have already explicitly instantiated the class for those types, it seems not only redundant but for big projects (like the one I am working on) yet another few lines that I need to maintain each time a new type is added.


Solution

  • This honestly sounds like the job for a macro:

    // explicit_instantiations.h
    #ifndef PERFORM_INSTANTIANTION
    #define EXTERNALLY_INSTANTIATED extern
    #else
    #define EXTERNALLY_INSTANTIATED
    #endif
    
    EXTERNALLY_INSTANTIATED template class MyClass<int>;
    EXTERNALLY_INSTANTIATED template class MyClass<float>;
    // etc.
    
    // header
    #include "explicit_instantiations.h"
    
    // cpp file
    #define PERFORM_INSTANTIATION
    #include "explicit_instantiations.h"