c++templatesoptimizationspecializationpartial-specialization

Specialize function by argument values known at compile time in C++


I have some function with 2 arguments: distance and radius

float expensive_function(float distance, float radius) {
    return distance + radius;
}

The whole project only uses 2 different radiuses and they both are known at compile time (1.2f and 3.4f). Is there a way to specialize this function knowing that? I would like something like that, but it doesn't compile:

template <float RADIUS>
float expensive_function(float distance) {
    return distance + RADIUS;
}

expensive_function<1.2f>(run_time_distance);
expensive_function<3.4f>(run_time_distance);

Compiler says: Candidate template ignored: invalid explicitly-specified argument for template parameter 'RADIUS' and No matching function for call to 'expensive_function'

I'm not very familiar with C++ template programming, so I didn't expect it to work. I don't know if what I'm looking for even possible. I just want to make sure compiler will generate the most performant code for either cases, plus it's better semantically in my opinion.


Solution

  • before C++20 you cannot make a float or double Non-type template paramter.

    you need to use int and some table to lookup to get it to compile

    #include <iostream>
    
    constexpr float floats[] = {1.2,3.4};
    template <int index>
    void foo()
    {
        constexpr float value = floats[index];
        std::cout << value << '\n';
    }
    
    int main()
    {
        foo<0>();
    }
    

    Demo

    you can use an enum to make it easier to read

    enum class float_values
    {
        f1_2,
        f3_4
    };
    
    template <float_values index>
    void foo()
    {
        constexpr float value = floats[static_cast<int>(index)];
        std::cout << value << '\n';
    }