I was reading about the template name resolution here. Just to get the feel of the things I replicated the code like this:
void f (char c)
{
std::cout<<"f(char)\n";
}
template <class T>
void g(T t)
{
f(1);
f(T(1));
f(t);
d++;
}
double d;
void f(int n)
{
std::cout<<"f(int)\n";
}
void test()
{
std::cout<<"First call\n";
g(1);
std::cout<<"Second call\n";
g('a');
}
int main()
{
test();
return 0;
}
According to the article linked I should have a compiler error for the d++ statement. Also for the first call of g(1), I should have one call of f(char) followed by two calls of f(int) and for the second call I should get three calls of f(char). However, when I compiled this using Vs2008, it compiled fine without any errors. Also, the output was:
First call
f(int)
f(int)
f(int)
Second call
f(int)
f(char)
f(char)
I am now wondering which one is correct? The article I am linking to or the VS2008 output? Any clue which is correct?
This is not the expected result with a Standard compliant compiler. Since both time you call it with a fundamental type, you will not get name lookup at the instantiation context for the function call.
Name lookup at instantiation context only happens for argument dependent lookup (called lookup using associated namespaces). Both of
intandchardo not have argument dependent lookup, an thus all the function calls you do will callf(char)after you removed thed++line.Since i understand you won’t possibly just believe me, here is the Standard quote, out of
14.6.4.2:Note that the article uses a defective example of the Standard (at
14.6/9) (and note that examples are non-normative: They can’t change or state rules. Their purpose entirely is illustrative). The defect has been fixed and is incorporated into the upcoming Standard. See this defect report.As you see, you will have to change from
int/charto some user defined type (enums or classes) too see the effect of lookup in instantiation context. Read this answer Order affects visibility for more information.