1

using for class templates works like a charm

 template<class T,int N>
 struct VecNT{ T arr[N]; };

 using Vec5d = VecNT<double,5>;     // doing great job!

but it seems it does not work for functions at all

 template<class T,int N>
 T sumNT(T* xs){ T sum=0; for(int i=0;i<N;i++){sum+=xs[i];}; return sum; };

 using sum5d = sumNT<double,5>;  
    // ERROR: sumNT<double,5> does not name a type

 using sum5d(double* xs) = sumNT<double,5>(T* xs);
    // ERROR: expected nest-name-specifier before 'sum5d'

So how to make sum5d as an specialized/instantiated alias for sumNT<double,5> ?

Prokop Hapala
  • 2,424
  • 2
  • 30
  • 59
  • Have you tried e.g. `auto sum5d = &sumNT;`? This should make a function pointer which can be used then like a function ID. (Or `double (*sum5d)(double*) = &sumNT;`?) – Scheff's Cat Aug 29 '19 at 07:08

1 Answers1

2

You can just declare a function pointer for your alias:

template<class T,int N>
T sumNT(T* xs){ T sum=0; for(int i=0;i<N;i++){sum+=xs[i];}; return sum; };

constexpr auto sum5d = &sumNT<double,5>;  

int main()
{
    double d[5];
    sum5d(d);
}

GCC and Clang manage to optimise away the function pointer and call the original function directly, MSVC doesn't: https://godbolt.org/z/1_fs83

Alan Birtles
  • 32,622
  • 4
  • 31
  • 60
  • thanks. Just for curiosity what `constexpr` exactly does here? Does it help the optimization (like to bake the constant template parameters, and optimize out the function pointer? – Prokop Hapala Aug 29 '19 at 07:26
  • `constexpr` is for a constant that the compiler can generate at compile time. Ofent (and in this case) compilers will generate the same code with just `const`, the main difference is that if you mark something as `constexpr` which the compiler can't generate at compile time it will fail to compile. see https://stackoverflow.com/questions/14116003/difference-between-constexpr-and-const and https://stackoverflow.com/questions/42107744/what-is-constexpr-in-c – Alan Birtles Aug 29 '19 at 08:28