È oggetto di compensazione / array deallocation veramente necessaria in VB6 / VBA (pro / contro?)

StackOverflow https://stackoverflow.com/questions/1525772

  •  20-09-2019
  •  | 
  •  

Domanda

Un sacco di quello che ho imparato a conoscere VB ho imparato da utilizzare Static analisi del codice (in particolare del Aivosto Project Analyzer). E uno una delle cose che controlla per è se non è stata deselezionata tutti gli oggetti e gli array. Ho usato per fare proprio questo alla cieca perchè PA ha detto così. Ma ora che so un po 'di più sul modo in cui VB rilascia le risorse, mi sembra che queste cose dovrebbe accadere automaticamente. Si tratta di una caratteristica eredità pre VB6, o c'è un motivo per cui si dovrebbe impostare in modo esplicito gli oggetti di nuovo a nulla e usare Erase su array?

È stato utile?

Soluzione

Il problema, a quanto mi risulta, ha a che fare con il fatto che VB6 (e dai suoi predecessori) ha le sue radici in COM, e il suo sistema di conteggio dei riferimenti garbage collection.

Immaginate, per esempio, che si dichiara una refernece a un oggetto da una libreria 3rd party. Quell'oggetto ha un conteggio di riferimenti COM che viene utilizzato sia per mantenere in vita e determinare quando dovrebbe essere distrutto. Esso non viene distrutta quando si imposta su Nothing, ma quando conteggio dei riferimenti dell'oggetto raggiunge lo zero.

Ora, non tutti i componenti COM sono stati scritti in Visual Basic. Alcuni sono stati scritti in C o C ++. gestione delle eccezioni strutturata non esisteva in tutte le lingue. Quindi, in caso di errore, il conteggio dei riferimenti sul oggetto non è stato garantito per essere adeguatamente ridotta, e gli oggetti COM erano noti per rimanere in giro più a lungo di quanto non erano destinate a. Questo non è stato un problema con Visual Basic, di per sé. E 'stato un problema COM. (E che, si potrebbe notare, è per questo .NET non usa il conteggio dei riferimenti.)

È per questo che gli sviluppatori Visual Basic è diventato ossessivo di rilasciare i riferimenti a oggetti prima di uscire routine. Semplicemente non sai cosa un componente si sta assegnando sta creando sotto il cofano. Ma quando si rilascia il riferimento ad esso, si sta almeno rilasciando il valore del riferimento ad esso. E 'diventato quasi un mantra religioso. Dichiarare, utilizzazione, il rilascio. Era il modo COM di fare le cose.

Certo, Visual Basic potrebbe essere migliore o più veloce a dereferenziazione variabili ho dichiarato in pila. Ma, dannazione, io voglio che sia chiaro che tali oggetti sono stati rilasciati. Un po 'di garanzia va un lungo cammino quando si sta cercando di rintracciare una perdita di memoria.

Altri suggerimenti

Matt Curland, autore di avanzata Visual Basic 6 , che sa di più su visual Basic maggior parte di noi farà mai, pensa che sia fatica sprecata. Considerate questa citazione (p110) su DAO, la libreria di accesso ai dati COM che si rivolge in primo luogo il motore di database di Access:

  

Un altro esempio di cattiva codice teardown.   DAO ha Chiudere i metodi che devono essere   chiamato nell'ordine corretto, e   oggetti devono essere rilasciati nel   ordine corretta così (Recordset   prima di database, ad esempio). Questo   singolo povero comportamento oggetto modello ha   condotto all'idea sbagliata che le perdite VB   la memoria a meno che non esplicitamente impostato tutto   le variabili locali per niente al   Dopo una funzione. Questo è un   completamente falsa nozione in un   ben progettato modello di oggetti. VB lattina   cancellare le variabili più veloce alla fine   riga Sub di quanto si possa dal codice, e   controlla le variabili, anche se si   rilasciare in modo esplicito i tuoi riferimenti.   Qualsiasi sforzo che fate viene duplicato.

Hai letto questo Aivosto pagina web (dai creatori di Project Analyzer)?

  

Se si utilizza variabili statiche,   è importante recuperare la memoria   hanno occupato quando non è necessario il   le variabili più. con dinamica   memoria delle variabili non è tanto di un   problema, perché sono distrutti   quando la procedura si conclude.

In altre parole, non è necessario preoccuparsi di compensazione ordinarie, non statici, variabili locali.

lo faccio sempre per una buona pratica, non si sa mai quello che un'eccezione potrebbe fare se si cade in uno e gli oggetti non vengono deallocate. Si dovrebbe relase in finally e assicurarsi che non si utilizza la memoria altrimenti si può incorrere in una perdita di memoria.

Ho avuto un problema interno di un semplice sistema di inseguitore di tempo libero in cui il server continuava a schiantarsi in modo casuale, ci sono volute settimane per stabilire che era una perdita di memoria di un oggetto che avrebbe dovuto autodistruzione da solo. Il mio codice era stato gettato in un'eccezione e mai ripulita dopo essersi causando il server (il sito web non è reale l'intero server) per andare verso il basso.

Sì, impostare tutti gli oggetti a nulla e ripulire il più possibile. VB6 è noto per avere perdite di memoria quando non è ripulire la tua roba. raccolta dei rifiuti era scadente in VB6 / VBA.

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