vibz vibz - 3 years ago 131
C++ Question

C++ template meta programming using template functions

I have been lately been learning template meta programming in C++.
After checking calculating factorials example, was wondering if the same thing could be done only with template functions rather than template classes.
My first attempt is shown below

#include <stdio.h>
#include <iostream>

using namespace std;

template <int t>
int multiply(t)
{
return (multiply(t-1) * t);
}

template <>
int multiply(1)
{
return 1;
}

int main () {
cout << multiply(5) << endl;
return 0;

}


But I get the following compiler errors

temp.cpp:7: error: template declaration of 'int multiply'
temp.cpp:14: error: expected ';' before '{' token
temp.cpp: In function 'int main()':
temp.cpp:19: error: 'multiply' was not declared in this scope


Can I do such template metaprogramming using template functions? Is this allowed ?

Answer Source

As stated by tobi303 in the comments, using just (t) as a parameter list of a function, where t is not a type name, makes no sense.

Since int t is a template parameter, not a regular parameter, it should only be present in the template parameters list (between the < and > angle brackets), and not in the function parameters list (between the ( and ) parenthesis). Template parameters must also be passed as such, i.e. multiply<5>() instead of multiply(5) in your code.

You could use something like:

#include <iostream>

using namespace std;

template <int t>
constexpr int multiply() {
    return multiply<t - 1>() * t;
}

template <>
constexpr int multiply<1>() {
    return 1;
}

int main () {
    cout << multiply<5>() << endl;
    return 0;
}

Note also that I've added constexpr (C++11 and later) to always be able to evaluate these functions at compile-time. However, the compiler is not forced to evaluate these at compile-time instead of run-time, and you might still end up with the run-time overhead.

Recommended from our users: Dynamic Network Monitoring from WhatsUp Gold from IPSwitch. Free Download