All I'm trying to do is implement the equal algorithm. However, when I test with a few strings, I get an ambiguity error. I think the compiler cannot differentiate between the A and the B. Why is this?
template <class A, class B> bool equal(A beg, A end, B out)
{
while(beg != end) {
if(*beg == *out) {
++beg;
++out;
}
else return false;
}
return true;
}
MAIN
std::string a("This is a string");
std::string b("This is a string");
std::string c("String c");
std::cout << "a and b are " << equal(a.begin(), a.end(), b.begin()) << std::endl;
std::cout << "a and c are " << equal(a.begin(), a.end(), c.begin()) << std::endl;
ERROR MESSAGE
procedures_main.cpp:17:35: error: call to 'equal' is ambiguous
std::cout << "a and b is " << equal(a.begin(), a.end(), b.begin()) << std::endl;
^~~~~
/Applications/Xcode.app/Contents/Developer/Toolchains/XcodeDefault.xctoolchain/usr/bin/../lib/c++/v1/algorithm:1105:1: note:
candidate function [with _InputIterator1 = std::__1::__wrap_iter<char *>, _InputIterator2 =
std::__1::__wrap_iter<char *>]
equal(_InputIterator1 __first1, _InputIterator1 __last1, _InputIterator2 __first2)
^
./procedures.hpp:73:34: note: candidate function [with A = std::__1::__wrap_iter<char *>, B = std::__1::__wrap_iter<char
*>]
template <class A, class B> bool equal(A beg, A end, B out)
The problem is that the arguments (the iterators from std::string
) are in the namespace std
and in this namespace, there is another algorithm called equal
which is a candidate due to argument dependent lookup (ADL). You need to explicitly qualify your algorithm:
std::cout << "a and b are " << ::equal(a.begin(), a.end(), b.begin()) << std::endl;
// ^^ here
Note that the C++ standard does not require the iterators to be a type in std
, but is allows it and you compiler/standard library decided to use this option.
This is the result of the so-called Argument-Dependent Name Lookup. There is standard algorithm std::equal in C++. The compiler sees that arguments of your function call belong to namespace std. So it also takes into consideration any function with name equal in namespace std. As the result it finds two functions: the one that is defined by you and the other that is declared in namespace std. To escape the error use fully qualified name of your function that is ::equal. By the way you use your function incorrectly and such a usage has undefined behaviour. The second range must have at least the same size as the first range. In your example wnen you use strings a and c the size of c is less than size of a.
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.