Falsche Überladungsauflösung für Funktionen mit zwei Argumenten

Nehmen wir das folgende Beispielprogramm:

#include <cmath>

namespace half_float
{
    template<typename T> struct half_expr {};

    struct half : half_expr<half>
    {
        operator float() const;
    };

    template<typename T> half sin(const half_expr<T>&);
    template<typename T> half atan2(const half_expr<T>&, const half_expr<T>&);
}

using namespace std;
using half_float::half;

int main()
{
    half a, b;
    half s = sin(a);
    half t = atan2(a, b);
}

ImVS 2010 Dies kompiliert einwandfrei (ignorieren Sie die offensichtlichen Linker-Fehler für jetzt). Aber inVS 2012 das gibt mir:

Fehler C2440: 'Konvertierung': Konvertierung von 'float' nach 'half_float :: half' nicht möglich

Es scheint also, dass die Überladungsauflösung die Version nicht aus dem Namespace auswählthalf_float (was ADL leisten sollte), aber das vonstd mit der impliziten Konvertierung nachfloat. Aber das Seltsame ist, dass dies nur für die passiertatan2 anrufen und nicht diesin Anruf.

In dem größeren Projekt, in dem dieser Fehler tatsächlich zum ersten Mal bei mir aufgetreten ist, tritt er auch bei anderen 2-Argument-Funktionen (oder besser gesagt bei solchen mit 2) aufhalf Argumente), wiefmod, aber nicht für eine 1-Argument-Funktion. Ebenso funktioniert es im größeren Projekt auch gut fürgcc 4.6 / 4.7 undclang 3.1 ohne Fehler, obwohl ich diese SSCCE-Version dort nicht explizit getestet habe.

Meine Frage ist also, liegt dieses fehlerhafte Verhalten vorVS 2012Seite (vorausgesetzt, es passiert nur für2012 und nur für die 2-Argument-Funktion), oder habe ich einige Feinheiten in den Überladungsauflösungsregeln übersehen (was in der Tat ein bisschen schwierig werden kann, denke ich)?

BEARBEITEN: Es passiert auch, wenn ich direkt binusing namespace half_float Oder setzen Sie das Ganze direkt in den globalen Namespace. Ebenso passiert es auch, wenn ich nicht binusing namespace stdDies ist jedoch eher die VS-Implementierung, die die mathematischen Funktionen in einen globalen Namespace versetzt.

BEARBEITEN: Es passiert beides mit dem OriginalVC 2012 Compiler sowie dieNovember 2012 CTP davon.

BEARBEITEN: Obwohl ich mir nicht ganz sicher bin, ob es sich wirklich um einen Verstoß gegen die Norm im engeren Sinne handelt, habe ich eineFehler denn es stützt sich auf die Ergebnisse meiner Antwort, da es zumindest der Definition der 1-Argument-Funktionen widerspricht und eine weitere Untersuchung durch dieVS-Mannschaft.

Antworten auf die Frage(3)

Ihre Antwort auf die Frage