I have a question regarding the standard ADL resolution in C++.
Here is a sample code explaining my enquiry:
#include <string>
// The mechanism:
namespace A {
template< class C >
::std::string scope(const C*)
{ return "A"; }
namespace B {
template< class C >
::std::string scope(const C *foo)
{ return A::scope(foo)+"::B"; }
} // namespace B
} // namespace A
::std::string scope(...)
{ return ""; }
// The test classes
struct foo {};
namespace A {
struct foo {};
namespace B {
struct foo {};
}
}
// The usage
int main()
{
foo *Foo=0;
A::foo *FooA=0;
A::B::foo *FooB=0;
scope(Foo); // OK, returns ""
scope(FooA); // OK, returns "A"
scope(FooB); // On one compiler, OK returns "A::B" ; On another, compiler error "Ambiguous call" between A::scope() and A::B::scope()
}
So, my question is what is the standard regarding ADL? Should all the functions from parent namespaces of the argument be found, or only the functions available in the (nested) namespace of the argument + the global functions?
This program has been tested on MSVC 2008 (and compiles with SP but not without...)
According to the standard, ADL works (modulo a couple of special rules)
"as if" the function name were preceded by the namespace; in your last
line, lookup should precede as if you'd written A::B::scope
. Which
does not look in the surrounding namespaces.
Note that even within namespace A::B
, there would be no ambiguity; in
A::B
, A::B::scope
hides A::scope
. Unqualified name lookup stops
in the scope where it first finds the name.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With