5

I'm working on an embedded project (only C++14 compiler available) and I would like to optimize the speed of execution.

Here is an example of what I am doing.

enum gpio_type{
  TYPE_1,
  TYPE_2
}

template <gpio_type T>
class test{
  test(){}

  void set_gpio(bool output)
  {
    switch (T)
    {
      case TYPE_1:
        do_something();
        break;

      case TYPE_2:
        do_something_else();
        break;
    }
  }
}

Will the compiler automatically remove the dead code at compile time? If it does, it is a standard feature or compiler dependent? If it does not, is it possible to write the code in a way that will force optimizing?

Zoe
  • 27,060
  • 21
  • 118
  • 148
Victor
  • 486
  • 3
  • 8

4 Answers4

5

You could specialize set_gpio for the different enum values - eg. :

template <gpio_type T>
class test{
  public:
    test(){}

    void set_gpio(bool output);
};

template<> void test<TYPE_1>::set_gpio(bool output) {
  do_something();
}

template<> void test<TYPE_2>::set_gpio(bool output) {
  do_something_else();
}

As other answers have indicated, you might not need to if your compiler is anywhere close to decent at optimizing. But the above might be more readable nevertheless.

Sander De Dycker
  • 16,053
  • 1
  • 35
  • 40
4

Constant propagation and dead code elimination are one of the simplest compiler optimizations. And since T is a compile time constant I would be extremely extremely surprised if the code isn't optimized by any compiler.

I have tested 15 compilers and platforms on godbolt from the venerable x86 to arm, avr, risc-v, raspberry and arduino (and more). All of them just compile to the equivalent of a tail call jump. No tests, no conditional jumps. Go check it out for yourself.

At this point I can say with reasonable confidence that there is no performance reason to modify your code.

bolov
  • 72,283
  • 15
  • 145
  • 224
3

That might depend on if you turn on optimization or not and how intelligent your compiler is. I guess current compilers would optimize in this case at least if they inline the function.

But if you want to be 100% sure

  • specialize the template for different enum values or
  • use your switch and look at the assembler output of your compiler to check if the compiler optimized like you want it or
  • use C++17 and if constexpr
Werner Henze
  • 16,404
  • 12
  • 44
  • 69
0

I would pass the functor (do_something or do_something_else) as a template argument.

Thus, your code of set_gpio becomes clearer and you are sure to have a compile time deduction which function to take.

In this post you can see how this is done: Function passed as template argument

schorsch312
  • 5,553
  • 5
  • 28
  • 57