2012-02-05 8 views
21

Quali vantaggi ha utilizzando std::reference_wrapper come parametro modello di contenitori anziché puntatori grezzi? Questo è std::vector<std::reference_wrapper<MyClass> > vs. std::vector<MyClass*>Vantaggi dell'utilizzo di reference_wrapper anziché del puntatore raw nei contenitori?

mi piace dimenticando i valori nulli e non dover usare la sintassi del puntatore, ma la verbosità dei tipi (cioè vector<reference_wrapper<MyClass> >) più avere lo std chiamata utilizzo del sito :: ref per avvolgere il riferimento effettivo mi fa penso che non ne valga la pena.

Mi riferisco ai casi in cui l'utilizzo di std :: shared_ptr o di qualsiasi altro puntatore intelligente non è un'opzione.

Ci sono altri vantaggi dell'utilizzo di reference_wrapper o di altri fattori che attualmente non prendo in considerazione? (Penso che la mia domanda si applichi sia a reference_wrapper di C++ 11 sia a boost)

+5

IMO, la non nullità di riferimento è un grande vantaggio, che spesso supera la verbosità. Ma questa è solo un'opinione di un odio ossessionato. – kkm

+0

@kkm mantiene questo argomento ancora con [not_null] (https://github.com/isocpp/CppCoreGuidelines/blob/master/CppCoreGuidelines.md#i12-declare-a-pointer-that-must-not-be-null -as-not_null) puntatori? – Woofas

+0

@Woofas: Forse no. Non ho molta familiarità con le ultime proposte linguistiche. Questo è stato fuori per 3 giorni! :) – kkm

risposta

18

Non credo ci sia una differenza tecnica. Il wrapper di riferimento fornisce funzionalità di puntatore di base, inclusa la possibilità di modificare dinamicamente la destinazione.

Un vantaggio è che dimostra l'intento. Indica a chi legge il codice che "chiunque abbia la variabile" non sta effettivamente controllando la sua durata. L'utente non ha dimenticato di cancellare o qualcosa di nuovo, che alcune persone possono iniziare a cercare quando vedono la semantica dei puntatori.

+1

Corollario - i riferimenti/ref_wrappers non impediscono problemi di durata dell'oggetto, anche se la loro sintassi è migliore dei puntatori. – mskfisher

+0

Sì, è tutto incentrato sull'intento. Vorrei aggiungere che i riferimenti sono puntatori non nulli. 'std :: vector ' potrebbe avere un nullptr in esso, mentre durante l'iterazione su un vettore di riferimenti, sai che tutti dovrebbero essere validi. –

0

I riferimenti C sono davvero problematici mentre si lavora con i modelli. Se siete "fortunati" abbastanza per compilare il codice con riferimento come parametro modello che si potrebbe avere problemi con il codice che avrebbe funzionato (per qualche ragione) come segue:

template<class T> f(T x) { g(x); } 
template<class T> g(T x) { x++; } 

Quindi, anche se si chiama f<int&>(x) chiamerà g<int> . Ma reference_wrapper funziona bene con i modelli.

Come accennato in precedenza, si avranno problemi con la compilazione di cose come vector<int&>, ma vector<reference_wrapper<int>> funziona correttamente.

+0

"Quindi anche se si chiama' f (x) 'chiamerà' g '." Sì, penso che questo sia perché non hai preso l'argomento per 'f()' come riferimento di inoltro e poi 'std :: inoltralo a' g() '. Penso che se lo facessi, potresti farlo funzionare. Se è così, manca un passaggio quando la codifica non rende il linguaggio "davvero problematico". ;-) –

Problemi correlati