2015-03-06 24 views
6

Da .NET 4 in poi, Lazy<T> può essere utilizzato per inizializzare gli oggetti con pigrizia. Intuitivamente, l'inizializzazione pigra può essere eseguita anche nel depuratore della proprietà pubblica per fornire la stessa funzionalità al chiamante. Mi chiedo se lo Lazy<T> offra alcun vantaggio intrinseco rispetto a quest'ultimo e dovrebbe quindi essere preferito?Si deve preferire Lazy <T> all'inizializzazione pigra in un getter?

Personalmente, ritengo che Lazy<> possa ridurre rapidamente la leggibilità del codice, ma forse l'ho appena visto utilizzato in modo improprio. Da un lato positivo, garantisce la sicurezza del thread, ma ci sono molti costrutti di sincronizzazione .NET che - forse ho torto - rendono abbastanza facile ottenere lo stesso all'interno di un getter.

Quali sono alcune considerazioni da tenere presente quando si sceglie l'approccio migliore?

+1

Fornire un esempio di inizializzazione lazy ottenuta senza 'Lazy '. Non è così facile come sembri pensare. –

+1

possibile duplicato di [Proprietà cache vs Lazy ] (http://stackoverflow.com/questions/5134786/cached-property-vs-lazyt) – Default

+1

Impostazione predefinita: mancato, grazie. Questo può essere contrassegnato come duplicato. @Ben Voigt: simile a ciò che Patrick Hofman descrive nella sua risposta. Inoltre, chiedo gentilmente alle persone di fare il downvoting per fornire commenti su come questa domanda possa essere migliorata (posso dire che sono un po 'deluso da quanto aggressivo sia diventato questo sito). – w128

risposta

7

Lazy<> può essere utile poiché include anche il supporto per il multithreading, qualcosa che devi creare da solo quando crei il tuo 'pigro'.

Per il codice che non ha bisogno di multi-threading, questo sarebbe il codice più performante e leggibile secondo me (usando l'operatore null-coalescing).

return variable ?? (variable = new ClassName()); 

notare che dal momento che questo codice non è thread-safe, si potrebbe finire per chiamare new ClassName() più volte.

È necessario introdurre lock e quindi la risoluzione diminuirà. Se è solo per la leggibilità, Lazy<> potrebbe non essere così male in quel caso.

Inoltre, Lazy<> impedisce di utilizzare il campo di supporto nel caso di proprietà memorizzate nella cache.

+0

Sì, questo è esattamente il modo in cui normalmente procedere al caricamento lazy in un getter, utilizzando l'operatore null coalescente e un certo tipo di blocco. Per me non sembra meno leggibile che introdurre un mucchio di espressioni lambda ecc., Ma ovviamente è soggettivo e può variare caso per caso. Altrimenti, questo ha perfettamente senso - grazie! – w128

+2

@ w128 Non userei mai "alcun tipo di blocco" invece di usare 'Lazy ', poiché 'Lazy ' fa già tutto ciò per te. –

+0

@MatthewWatson: Anche questo era il mio argomento :) –