Home > Net >  Template a member variable in a class
Template a member variable in a class

Time:09-13

I am doing some refactoring on some older/messy code. I am trying to improve things little by little. Because it fit the project, I started implementing CRTP (for static polymorphism) on some class, let's call it sensor. Through CRTP, there is now a real and a fake implementation.

Now, I am trying to put templates in a class (interface_actions) that uses sensor. I arrived at something like that:

class interface_actions
{
public:
    template <class implementation>
    interface_actions(sensor<implementation> detector)
    : _detector(detector)
    {}

    // Lots of stuff that I don't want to touch

private:
#if (SOMETHING)
    sensor<real> _detector;
#else
    sensor<fake> _detector;
#endif
};

As you can see, I did not know what to do with _detector without having to make the entire class a template, so I used the preprocessor ...

This is more of an architectural question I guess, but how would you go about making _detector take sensor without making the entire class a template? It seems to me that I would have to fundamentally rewrite this part of the code, but maybe there is a simpler way?

CodePudding user response:

you can use std::conditional_t:

class interface_actions
{
    std::conditional_t<SOMETHING, sensor<real>, sensor<fake>> _detector;
};

if SOMETHING yields true, _detector will be of type sensor<real>, sensor<fake> otherwise.

but this only works if SOMETHING is outside of the scope of class interface_actions, otherwise you have to make the class take a template. As pptaszni suggested you could make a default template parameter to "hide" the template argument, so your old code that says interface_actions object; won't be affected:

template<bool is_real = true>
class interface_actions
{
    std::conditional_t<is_real, sensor<real>, sensor<fake>> _detector;
};


int main() {
    interface_actions foo;
    static_assert(std::is_same_v<decltype(foo._detector), sensor<real>>);
}
  • Related