Reputation: 15277
I am trying to understand the difference between a "Function Type" and a "Function Pointer" as template parameter and when to apply what. Or, what's the difference?
Simple example:
template <int Function(int)>
struct S1 {
//....
};
template <int (*Function)(int)>
struct S2 {
//....
};
int always42(int) {
return 42;
}
int main() {
S1<always42> s1;
S2<always42> s2;
//....
return 0;
}
Or will the "function type" decay to a "function pointer"?
Can somebody please shed some light on this?
Upvotes: 3
Views: 68
Reputation: 24738
Both template parameters are int (*)(int)
as there is type decay for int(int)
. That is, the type of a non-type template parameter specified as int(int)
decays into int(*)(int)
.
You can see that both template parameters correspond to the same type by using the incomplete type_shower
class template below:
template<typename> struct type_shower;
template <int Function(int)>
struct S1 {
type_shower<decltype(Function)> _;
};
template <int (*Function)(int)>
struct S2 {
type_shower<decltype(Function)> _;
};
For both, the compiler issues the same error message, which shows the type of Function
:
error: implicit instantiation of undefined template
'type_shower<int (*)(int)>'
type_shower<decltype(Function)> _;
Note that no type decay occurs if the template parameter is specified as a reference to a function, i.e., int(&)(int)
:
template <int (&Function)(int)>
struct S3 {
type_shower<decltype(Function)> _;
};
error: implicit instantiation of undefined template
'type_shower<int (&)(int)>'
type_shower<decltype(Function)> _;
Upvotes: 2
Reputation: 172924
Yes, function type is adjusted to function pointer for non-type template parameter.
Array and function types may be written in a template declaration, but they are automatically replaced by pointer to object and pointer to function as appropriate.
A non-type template-parameter of type “array of T” or of function type T is adjusted to be of type “pointer to T”.
Upvotes: 2