come si possono passare i valori l a std :: make_pair

Aug 16 2020

In std::make_pair c'è solo un'implementazione C ++ 14 in poi

template <class T1, class T2> constexpr std :: pair <V1, V2> make_pair (T1 && t, T2 && u);

Entrambi i parametri sono riferimenti di valore R e in base a questo

I riferimenti ai valori R non possono essere inizializzati con valori l.

    int i = 1;
    char ch = 'a';
    std::unordered_map<int, char> mp;
    mp.insert(make_pair<int,char>(i, ch));

Quindi, quando provo a usare make_pair come nel codice sopra, genera correttamente un errore error: cannot bind rvalue reference of type 'int&&' to lvalue of type 'int'.

Tuttavia funziona perfettamente per il codice sopra, se cambio, rilascia gli argomenti del modello e lo chiamo come

mp.insert(make_pair(i, ch));

Sono confuso come funziona, come ie chentrambi sono L-valori. La risoluzione dell'argomento del modello converte i valori L in valori R o come funziona?

Risposte

3 songyuanyao Aug 16 2020 at 08:06

I parametri di make_pairnon vengono dichiarati come riferimento-valore, ma riferimento di inoltro .

I riferimenti di inoltro sono un tipo speciale di riferimenti che preservano la categoria di valore di un argomento della funzione, rendendo possibile l'inoltro tramite std :: forward. I riferimenti di inoltro sono:

  1. parametro di funzione di un modello di funzione dichiarato come riferimento rvalue al parametro di modello di tipo cv-unqualified dello stesso modello di funzione:

Il riferimento di inoltro funziona sia con lvalues ​​che con rvalues, con l'aiuto della deduzione dell'argomento del modello . Quando viene passato un lvalue, il parametro template viene dedotto come lvalue-riferimento, dopo il collasso del riferimento, anche il parametro della funzione è lvalue-reference. Quando si passa un rvalue, il parametro del modello viene dedotto come non riferimento, il parametro della funzione è rvalue-riferimento.

D'altra parte, se si specifica esplicitamente l'argomento del modello make_pair<int,char>(...), il parametro della funzione diventa di conseguenza rvalue-riferimento.

1 JaMiT Aug 16 2020 at 11:01

La risposta di songyuanyao spiega già la maggior parte di quello che sta succedendo. Tuttavia, vorrei contribuire a come farlo funzionare con argomenti espliciti del modello. Eri quasi tutto lì, ma non hai fatto l'ultimo passo.

Sono confuso come funziona, come ie chentrambi sono L-valori.

Esattamente. Vuoi valori l, che è qualcosa che puoi specificare negli argomenti del modello:

std::make_pair<int &, char &>(i, ch)

o un modulo che funziona in più casi:

std::make_pair<const int &, const char &>(i, ch)

Un po 'di scrittura extra, ma necessaria se la deduzione dell'argomento fallisce per qualche motivo.