c++templatesdefault-arguments

Forward declaration of a template type with a default template argument?


I have the following situation:

enum class Backend { ONE, TWO };

template <typename T, Backend backend = Backend::ONE>
struct SomeClass {};

Now, I want to forward declare it inside of another header:

// include the definition of Backend in header
template <typename T, Backend>
struct SomeClass;

std::unique_ptr<SomeClass<int>> my_pointer;

An error is given, because from this point of view the compiler doesn't know that the second template argument is defaulted. So, if I add that:

// include the definition of Backend in header
template <typename T, Backend backend = Backend::ONE>
struct SomeClass;

Because it's defaulted in its original place (it's definition), now I have a default template argument in two places, which isn't allowed:

'Backend': redefinition of default argument: parameter 2

How do I fix this?


Solution

  • You can let the header file that defines SomeClass include the header doing the forward declaration:

    SomeClass_fwd.h:

    #pragma once
    
    enum class Backend { ONE, TWO };
    
    template <typename T, Backend = Backend::ONE> // default here
    struct SomeClass;
    

    SomeClass.h:

    #pragma once
    #include "SomeClass_fwd.h"
    
    template <typename T, Backend backend>        // no default here
    struct SomeClass {
        // definition
    };