A desalocação de compensação/matriz de objetos é realmente necessária em VB6/VBA (Prós/Contras?)

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

  •  20-09-2019
  •  | 
  •  

Pergunta

Muito do que aprendi sobre VB, aprendi usando a análise estática de código (particularmente o Project Analyzer da Aivosto).E uma das coisas que ele verifica é se você limpou ou não todos os objetos e matrizes.Eu costumava fazer isso cegamente porque PA disse.Mas agora que sei um pouco mais sobre a forma como o VB libera recursos, me parece que essas coisas deveriam acontecer automaticamente.Este é um recurso legado do pré-VB6 ou há uma razão pela qual você deve definir explicitamente os objetos como nada e usar Erase em arrays?

Foi útil?

Solução

O problema, pelo que entendi, tem a ver com o fato de que o VB6 (e seus antecessores) tem suas raízes no COM e em seu sistema de coleta de lixo de contagem de referências.

Imagine, por exemplo, que você declara uma referência a um objeto de uma biblioteca de terceiros.Esse objeto possui uma contagem de referência COM que é usada para mantê-lo ativo e para determinar quando deve ser destruído.Ele não é destruído quando você o define como Nothing, mas quando a contagem de referência do objeto chega a zero.

Agora, nem todos os componentes COM foram escritos em Visual Basic.Alguns foram escritos em C ou C++.O tratamento estruturado de exceções não existia em todas as linguagens.Portanto, se ocorresse um erro, não era garantido que a contagem de referências no objeto fosse reduzida adequadamente e os objetos COM eram conhecidos por permanecerem por mais tempo do que deveriam.Isso não foi um problema com o Visual Basic, por si só.Foi um problema de COM.(E é por isso, você pode notar, que o .NET não usa contagem de referência.)

É por isso que os desenvolvedores do Visual Basic ficaram obsessivos em liberar referências de objetos antes de sair das rotinas.Você simplesmente não sabe qual componente que está alocando está criando nos bastidores.Mas quando você libera sua referência a ele, você está pelo menos liberando sua contagem de referências a ele.Tornou-se quase um mantra religioso.Declare, use, libere.Era a maneira da COM fazer as coisas.

Claro, o Visual Basic pode ser melhor ou mais rápido em desreferenciar variáveis ​​que declarei na pilha.Mas, caramba, quero que fique ÓBVIO que esses objetos foram liberados.Um pouco de segurança ajuda muito quando você está tentando rastrear um vazamento de memória.

Outras dicas

Matt Curland, autor de Visual Básico Avançado 6, que sabe mais sobre Visual Basic do que a maioria de nós jamais saberá, acha que é um esforço desperdiçado.Considere esta citação (p110) sobre DAO, a biblioteca de acesso a dados COM que visa principalmente o Mecanismo de Banco de Dados do Access:

outro exemplo de código de desmontagem ruim.O DAO possui métodos próximos que devem ser chamados na ordem correta, e os objetos também devem ser liberados na ordem correta (registro antes do banco de dados, por exemplo).Esse único comportamento de modelo de objeto ruim levou ao equívoco de que o VB vaza memória, a menos que você defina explicitamente todas as variáveis ​​locais para nada no final de uma função.Esta é uma noção completamente falsa em um modelo de objeto bem projetado.O VB pode limpar as variáveis ​​mais rapidamente na sub -linha final do que você pode do código e verifica as variáveis, mesmo que você solte explicitamente suas referências.Qualquer esforço que você fizer será duplicado.

Você leu isso Página web de Aivosto (dos criadores do Project Analyzer)?

Se você estiver usando variáveis ​​estáticas, é importante recuperar a memória que eles ocupam quando você não precisa mais das variáveis.Com variáveis ​​dinâmicas, a memória não é um problema, porque são destruídas quando o procedimento termina.

Em outras palavras, você não precisa se preocupar em limpar variáveis ​​locais comuns e não estáticas.

Eu sempre faço isso para uma boa prática, você nunca sabe o que uma exceção pode fazer se cair em um e seus objetos não são desalocados. Você deve relacioná -los finalmente em declarações e garantir que eles não estejam usando nenhuma memória, caso contrário, poderá encontrar um vazamento de memória.

Eu tive um problema dentro de um simples sistema de rastreador de tempo, onde o servidor continuava travando aleatoriamente, levou semanas para determinar que era um vazamento de memória de um objeto que deveria se autodestruturar por conta própria. Meu código estava sendo lançado em uma exceção e nunca foi limpo depois de fazer com que o servidor (o site real e não o servidor inteiro) desça.

Sim, defina todos os objetos para nada e limpe o máximo que puder. O VB6 é notório por ter vazamentos de memória ao não limpar suas coisas. A coleta de lixo foi sub-par no VB6/VBA.

Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top