Domanda

Alcune persone hanno sostenuto che la funzione di C # 4.0 ha introdotto la parola dynamic è lo stesso del "tutto è un oggetto" caratteristica di VB. Tuttavia, qualsiasi chiamata su una variabile dinamica viene tradotto in un delegato volta e da allora in poi, il delegato sarà chiamato. In VB, quando si utilizza Object, nessuna cache è applicato e ogni chiamata su un metodo non tipizzato comporta tutta una serie di sotto-il-cofano riflessione, talvolta pari un enorme 400 volte nei termini di prestazioni.

Avere il tipo delegato-ottimizzazione dinamica e caching state aggiunte anche le VB chiamate di metodo non tipizzati, o è oggetto senza tipo di VB ancora così lento?

È stato utile?

Soluzione

Soluzione

Alcune ricerche e una migliore lettura del in precedenza di cui all'articolo menzionato da Hans Passant, provoca la seguente conclusione:

  • VB.NET 2010 supporta la DLR;
  • È possibile implementare IDynamicMetaObjectProvider se si vuole sostenere esplicitamente la dinamica, il compilatore VB.NET viene aggiornato per riconoscere che;
  • Object VB utilizzerà solo il DLR e il metodo di caching se gli strumenti oggetto IDynamicMetaObjectProvider;
  • tipi
  • BCL e il quadro non implementano IDynamicMetaObjectProvider, utilizzando Object su tali tipi o i propri tipi invocherà la classica, non in cache VB.NET tardo-legante.

Sfondo: elaborare sul perché late-binding caching potrebbe aiutare VB prestazioni codice

Alcune persone (tra i quali Hans Passant, vedere la sua risposta) può chiedere perché la cache o non-caching in late-binding potrebbe eventualmente materia. In realtà, fa una grande differenza, sia in VB ed in altre tecnologie late-binding (ricordate IQueryInterface con COM?).

Dopo vincolante si riduce ad un semplice principio: dato un nome e il parametro-dichiarazioni, scorrere tutti i metodi di questa classe e le classi madri mediante metodi disponibili se l'interfaccia Type (e in VB, un metodo , una proprietà e un campo possono aspetto lo stesso, rendendo questo processo ancora più lento). Se si considera che le tabelle di metodo non sono ordinati, allora questo è facilmente molto più costoso di un unico diretta (vale a dire, digitato) chiamata di metodo.

Se tu fossi in grado di guardare in alto del metodo, una volta, e poi memorizzare il metodo puntatore in una tabella di ricerca, questo sarebbe notevolmente accelerare questo processo. Metodo cache vincolante nel DLR fa un passo futher e sostituisce il metodo di guardia con un puntatore al metodo effettivo, se possibile. Dopo la prima chiamata, questo diventa un ordine di grandezza più veloce per ogni chiamata successiva (si pensi 200x a 800x volte più veloce).

Per fare un esempio di quando questo importa, ecco qualche codice che illustra questo problema. Nel caso in cui ogni classe ha una proprietà di stringa .Name, ma le classi non condividono un antenato o di un'interfaccia comune, si può ingenuamente ordinare elenchi di uno qualsiasi di questi tipi in questo modo:

' in the body of some method '
List<Customers> listCustomers = GetListCustomers()
List<Companies> listCompanies = GetListCompanies()

listCustomers.Sort(MySort.SortByName)
listCompanies.Sort(MySort.SortByName)

' sorting function '
Public Shared Function SortByName(Object obj1, Object obj2) As Integer
    ' for clarity, check for equality and for nothingness removed '    
    return String.Compare(obj1.Name, obj2.Name)    
End Function

Questo codice (simile almeno) in realtà ha fatto in produzione con uno dei miei clienti ed è stato utilizzato in un spesso chiamato callback AJAX. Senza la memorizzazione nella cache manualmente le proprietà .Name, già nelle liste di medie dimensioni di meno di mezzo milione di oggetti, il codice late-binding è diventato un fardello notevole che alla fine ha portato l'intero sito verso il basso. Si è rivelato difficile da rintracciare questo problema, ma questa è una storia per un'altra volta. Dopo aver sistemato questo, il sito riacquistato il 95% delle sue resouces CPU.

Quindi, la risposta alla domanda di Hans "non si hanno grossi problemi di cui preoccuparsi" è semplice: questo è un grosso problema (o può essere), esp. per i programmatori VB che hanno ottenuto troppo distratto sull'utilizzo di late-binding.

In questo caso particolare, e molti come loro, VB.NET 2010 è a quanto pare non è stato aggiornato per introdurre late-binding, e come tale, Object rimane male per l'ignaro e non deve essere confrontato con dynamic.

PS:. Late-binding problemi di prestazioni sono molto difficili da rintracciare, a meno che non si dispone di un profiler prestazioni buone e sapere come late-binding è implementato internamente dal compilatore

Altri suggerimenti

cosa c'è di nuovo articolo :

  

Visual Basic 2010 è stato aggiornato alla   sostenere pienamente il DLR nella sua   latebinder

Non è possibile ottenere più esplicito di quello. E 'il DLR che implementa la memorizzazione nella cache.

Buona domanda. Sto indovinando la risposta è "no", perché questo articolo in MSDN rivista dice VB.Net è stato modificato per supportare il Dynamic Language runtime, e descrive brevemente le modifiche al runtime, ma non menziona la memorizzazione nella cache.

Qualcuno sa meglio?

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top