pure cuteness
pure cuteness

Reputation: 1645

Overload resolution, order of defined functions and templates

Consider the following code snippet:

template<class T>
std::enable_if_t<std::is_integral<T>::value, bool> func(T value) {
    std::cout << "T\n";
    return func(static_cast<int64_t>(value));
}

bool func(int64_t value) {
    std::cout << "int64_t\n";
    return true;
}

int main() {
    func(1);
}

It causes infinite recursion. However, swapping the definition order of these two functions (if bool func(int64_t value) defined before template one) helps to avoid this issue.

Why is that? Does order of function overloads matter?

Upvotes: 8

Views: 797

Answers (3)

songyuanyao
songyuanyao

Reputation: 172894

Does order of function overloads matter?

It doesn't change the result of overload resolution, but the result of name lookup; which happens before overload resolution.

(emphasis mine)

For a name used in global (top-level namespace) scope, outside of any function, class, or user-declared namespace, the global scope before the use of the name is examined:

That means for the invocation of func inside the templated func, only itself could be found (and be added to the overload set), the non-template version won't be considered at all.

As you have seen, if you change their declaration order, both func would be found and considered at the following overload resolution, and the non-template func is selected (as expected).

Upvotes: 7

Some programmer dude
Some programmer dude

Reputation: 409166

When the compiler is parsing the first function (the template) it doesn't know anything about the second overload of func. Parsing is done top-to-bottom of the source file.

That's the reason you need to have declarations of symbols before you use them. That also means just having a declaration of bool func(int64_t); at the top would solve your problem.

Upvotes: 3

eerorika
eerorika

Reputation: 238311

Does order of function overloads matter?

The order of overloads does matter in the sense that if the overload set is called before a potential overload is declared, that not-yet declared function doesn't take part in the overload resolution.

The order of overloads declared before the function call does not matter.

Upvotes: 1

Related Questions