How does ADL affect this piece of C++ code?
In this case, normal name lookup finds N2::foo
, and N1::foo
is found by ADL, they're both added to the overload set, then overload resolution is performed and the calling is ambiguous.
BTW: Without using N2::foo;
in main()
, ::foo
will be found by normal name lookup, and N1::foo
is found by ADL too; as the result the calling is still ambiguous.
Updated:
So, the question here is why
::foo
can not be called by "foo(N1::S{});
" in themain
function?
Because with the usage of using N2::foo;
, the name N2::foo
is introduced in the main
function. When calling foo
the name N2::foo
will be found at the scope of main
, then name lookup stops, the further scope (the global namespace) won't be examined, so ::foo
won't be found and added to overload set at all. As the result N2::foo
is called for both cases.
name lookup examines the scopes as described below, until it finds at least one declaration of any kind, at which time the lookup stops and no further scopes are examined.
BTW: If you put using N2::foo;
in global namespace before main
, foo(N1::S{});
would call ::foo
. Both N2::foo
and ::foo
are found by name lookup and ::foo
wins in overload resolution.