Wie können L-Werte an std :: make_pair übergeben werden?
In std::make_pair
gibt es nur eine Implementierung ab C ++ 14
Vorlage <Klasse T1, Klasse T2> constexpr std :: pair <V1, V2> make_pair (T1 && t, T2 && u);
Beide Parameter sind R-Wert Referenzen und gemäß dieser
R-Wert-Referenzen können nicht mit L-Werten initialisiert werden.
int i = 1;
char ch = 'a';
std::unordered_map<int, char> mp;
mp.insert(make_pair<int,char>(i, ch));
Wenn ich also versuche, make_pair wie im obigen Code zu verwenden, wird ein Fehler korrekt ausgegeben error: cannot bind rvalue reference of type 'int&&' to lvalue of type 'int'
.
Es funktioniert jedoch perfekt für den obigen Code, wenn ich die Vorlagenargumente ablege und als aufrufe
mp.insert(make_pair(i, ch));
Ich bin verwirrt, wie das funktioniert i
und ch
beide sind L-Werte. Konvertiert die Auflösung von Vorlagenargumenten L-Werte in R-Werte oder wie funktioniert das?
Antworten
Die Parameter von make_pair
werden nicht als rWertreferenz deklariert, sondern als Weiterleitungsreferenz .
Weiterleitungsreferenzen sind eine spezielle Art von Referenzen, die die Wertekategorie eines Funktionsarguments beibehalten und es ermöglichen, es mit std :: forward weiterzuleiten. Weiterleitungsreferenzen sind entweder:
- Funktionsparameter einer Funktionsvorlage, die als rWertreferenz für den cv-unqualifizierten Typvorlagenparameter derselben Funktionsvorlage deklariert wurde:
Die Weiterleitungsreferenz funktioniert sowohl mit l-Werten als auch mit r-Werten mithilfe der Ableitung von Vorlagenargumenten . Wenn ein l-Wert übergeben wird, wird der Vorlagenparameter als l-Wert-Referenz abgeleitet. Nach dem Reduzieren der Referenz ist der Funktionsparameter ebenfalls l-Wert-Referenz. Wenn ein r-Wert übergeben wird, wird der Vorlagenparameter als Nichtreferenz abgeleitet, der Funktionsparameter ist rWertreferenz.
Wenn Sie andererseits das Vorlagenargument explizit wie angegeben angeben make_pair<int,char>(...)
, wird der Funktionsparameter entsprechend zur Wertreferenz.
Die Antwort von songyuanyao erklärt bereits das meiste, was vor sich geht. Ich möchte jedoch dazu beitragen, dass dies mit expliziten Vorlagenargumenten funktioniert. Sie waren den größten Teil des Weges dorthin, haben aber nicht den letzten Schritt getan.
Ich bin verwirrt, wie das funktioniert
i
undch
beide sind L-Werte.
Genau. Sie möchten l-Werte, die Sie in den Vorlagenargumenten angeben können:
std::make_pair<int &, char &>(i, ch)
oder ein Formular, das in mehreren Fällen funktioniert:
std::make_pair<const int &, const char &>(i, ch)
Ein bisschen zusätzliches Schreiben, aber erforderlich, wenn der Argumentabzug aus irgendeinem Grund fehlschlägt.