6

Mit GCC 4.8.4 mit g++ --std=c++11 main.cpp gibt die folgende errorTypabzug fehlgeschlagen für Auto StdMaxInt = Std :: Max <int>;

error: unable to deduce ‘auto’ from ‘max<int>’ 
auto stdMaxInt = std::max<int>; 

für diesen Code

#include <algorithm> 

template<class T> 
const T& myMax(const T& a, const T& b) 
{ 
    return (a < b) ? b : a; 
} 

int main() 
{ 
    auto myMaxInt = myMax<int>; 
    myMaxInt(1, 2); 

    auto stdMaxInt = std::max<int>; 
    stdMaxInt(1, 2); 
} 

Warum es mit myMax aber nicht mit std::max funktioniert? Und können wir es mit std::max arbeiten lassen?

+0

Ich kenne die genaue Antwort auf Ihre Frage nicht, aber ich denke, es hat damit zu tun, dass std :: max als const-Ausdruck überladen wird, wenn sich die Operanden qualifizieren. Ihre Version hat keine solchen Überlastungen und daher gibt es keine Mehrdeutigkeit. Der einfachste Weg, dieses Problem zu lösen, ohne sich in die Details zu vertiefen, könnte darin bestehen, einfach 'myMax' (oder ein Lambda, z.B.) für diese Art von Benutzungsszenario zu verwenden, aber einfach' std :: max' in seiner Implementierung aufzurufen. –

+0

@Ike 'std :: max' ist mit einer anderen Signatur überladen, um einen dritten Parameter, ein Vergleichsobjekt, zu übernehmen. Der Compiler weiß nicht, welche Überladung beabsichtigt ist. –

+0

'decltype (auto) stdMaxInt = ...' mit C++ 14 zeigt klare Info – billz

Antwort

5

Es ist, weil std::max eine überladene Funktion ist, also weiß es nicht, welche Überladung Sie einen Zeiger zu erstellen möchten. Sie können static_cast verwenden, um die gewünschte Überladung auszuwählen.

auto stdMaxInt = static_cast<const int&(*)(const int&, const int&)>(std::max<int>); 
2

Die static_cast Antwort von @JamesRoot funktioniert, aber für meinen Geschmack, würde ich einen Lambda bevorzugen:

auto stdMaxInt = [](int const& L, int const& R) -> int const& { return std::max(L, R); }; 

Dies könnte den Vorteil einer besseren Inline-Fähigkeit haben, wenn sie an Algorithmen übergeben (ungetestet).