c++ - linguisticos - codigos universales de comunicacion
¿Por qué el código es aceptado por clang pero rechazado por vc++? (1)
clang 3.4 acepta el siguiente código; mientras que vc ++ NOV 2013 CTP lo rechaza con un error:
error C2668: ''AreEqual'' : ambiguous call to overloaded function
template<class headT, class... tailTypes>
constexpr headT&& __GetFirst__(headT&& value, tailTypes&&...)
{
return static_cast<headT&&>(value);
};
template<class T>
constexpr bool AreEqual(const T& a, const T& b)
{
return a == b;
}
template<class headT, class... tailTypes>
constexpr bool AreEqual(const headT& head_value, const tailTypes&... tail_values)
{
return AreEqual(head_value, __GetFirst__(tail_values...))
&& AreEqual(tail_values...);
}
int main()
{
AreEqual(1, 1, 2, 1);
}
¿Qué compilador es correcto según el estándar C ++ 14?
Actualización: el mensaje de error completo:
error C2668: ''AreEqual'' : ambiguous call to overloaded function
1> d:/projects/ktl/test/main.cpp(20): could be ''bool AreEqual<headT,int>(const headT &,const int &)''
1> with
1> [
1> headT=int
1> ]
1> d:/projects/ktl/test/main.cpp(8): or ''bool AreEqual<headT>(const T &,const T &)''
1> with
1> [
1> headT=int
1> , T=int
1> ]
1> while trying to match the argument list ''(const int, const int)''
1>
1>Build FAILED.
El comportamiento de Clang (y GCC) es correcto. Puede leer §14.8.2.4 [temp.deduct.partial] del estándar sobre cómo se realiza el ordenamiento parcial de las plantillas de funciones, pero el ejemplo dado en p8 de esa subcláusula cubre directamente esta situación:
template<class... Args> void f(Args... args); // #1
template<class T1, class... Args> void f(T1 a1, Args... args); // #2
template<class T1, class T2> void f(T1 a1, T2 a2); // #3
f(); // calls #1
f(1, 2, 3); // calls #2
f(1, 2); // calls #3; non-variadic template #3 is more
// specialized than the variadic templates #1 and #2