This is an extension of this question from 2011: Range for loops and ADL
Using Visual Studio 2015, I cannot create a range-based loop for a custom container using search argument-dependent (ADL).
I made a very simple test case below with a custom container:
#include <vector> namespace Foo { template <typename T> class Container { public: std::vector<T> values; }; } template <typename T> typename std::vector<T>::iterator begin(Foo::Container<T>& foo) { return foo.values.begin(); } template <typename T> typename std::vector<T>::iterator end(Foo::Container<T>& foo) { return foo.values.end(); }
Using this container and ADL, the following test compiles fine:
int main(int argc, char* argv[]) { Foo::Container<int> values; for (auto it = begin(values); it != end(values); ++it) { ... } return 0; }
As it should be. I'm not sure that ADL is used even here, but despite this, it makes sense. From the MSDN Documentation :
Keep these facts in mind about the range for:
Automatically recognizes arrays.
Recognizes containers with the names .begin () and .end ().
Uses an argument-dependent search for begin () and end () for anything else.
From what I understand in ADL and the above documentation, you must also compile:
int main(int argc, char* argv[]) { Foo::Container<int> values; for (auto value : values) { ... } return 0; }
But this is not so. Instead, the following errors occur:
error C3312: no callable 'begin' function found for type 'Foo::Container<int>' error C3312: no callable 'end' function found for type 'Foo::Container<int>'
So what is going on here? Is my ADL interpretation incorrect or is it an error with the MSVC 14.0 compiler?