2016-07-11 8 views
3

Ich frage mich, wie Anrufe für diese beiden Überlastungen von std::make_optional aufgelöst werden:Funktion Vorlage Überlastungen Auflösung Verwirrung

template< class T > 
constexpr std::optional<std::decay_t<T>> make_optional(T&& value); 

template< class T, class... Args > 
constexpr std::optional<T> make_optional(Args&&... args); 

Ich weiß Aufruf ohne explizites Template-Argument wie make_optional(123) die ersten nennen, aber wie wäre es make_optional<int>(123)? Welche Überladung wird ausgewählt und nach welchen Regeln?

UPDATE: Und wenn ich make_optional<string>("hello world") schreiben sagen, werde ich die zweite Überlastung Aufruf (auch wenn der String kann implizit in ein string umgewandelt werden), richtig?

+1

wo Bibliothek (und Namespace) deklarieren? ['std :: experimental'] (http://en.cppreference.com/w/cpp/header/experimental/optional) scheint nur den ersten zu definieren. – Nawaz

+0

@Nawaz: Die zweite Überladung von 'make_optional' kommt von [P0032 (PDF)] (http://wg21.link/P0032), welches [LWG vor Oulu weitergeleitet wurde] (https://issues.isocpp.org) /show_bug.cgi?id=100), anscheinend. Obwohl P0091 es möglicherweise veraltet macht, haben sie es möglicherweise nicht übernommen. Zurzeit ist Nawaz richtig: Die zweite Überladung existiert nicht. –

+0

@ NicolBolas [Es existiert] (https://github.com/cplusplus/draft/commit/1882aa320a101fcfdb7a6d4de40197982209ce30). –

Antwort

2

Die Überladungsauflösung beginnt mit der Bestimmung der brauchbaren Kandidaten, der Auswahl desjenigen mit der besten Konvertierungssequenz und der anschließenden Durchsicht der Tiebreaker.


make_optional(123) hat nur ein brauchbarer Kandidat, da T ist ein nicht-abgeleitete Kontext in der zweiten Überlastung. Somit ist es trivialerweise der beste mögliche Kandidat.


make_optional<int>(123) gibt uns zwei geeignete Kandidaten:

  • make_optional(int&&) mit [T=int]
  • make_optional<int>(int&&) mit [T=int, Args={int}]

Die Funktion identische Argumente (int&&), so dass sie trivialerweise gleich lebensfähig mit identischen Umwandlungssequenzen. Die erste Überladung ist eine speziellere Funktionsvorlage als die zweite Überladung (da sie ein einzelnes Argument anstelle eines variadischen Pakets benötigt), also ist es die bevorzugte Variante.


make_optional<string>("hello world") gibt uns zwei geeignete Kandidaten:

  • make_optional(string&&) mit [T=string]
  • make_optional<string>(const char(&)[12]) mit [T=string, Args={const char (&)[12]}]

Hier sind die beiden Funktionen übernehmen nicht die gleiche Argument - die erste Nimmt eine string&& (die eine benutzerdefinierte Konvertierung aus dem Zeichenfolgenliteral erfordern würde) und th Die Sekunde dauert eine const char(&)[12] (was eine genaue Übereinstimmung ist). Daher hat die zweite Überladung die bessere Umwandlungssequenz und ist bevorzugt.