2010-11-16 33 views
2

J'essaie de comprendre la durée de vie du tmpTabPages dans le bit de code suivant. Supposons que le formulaire a un TabControl vide nommé MyTabControl, qu'il existe une collection de chaînes appelée NameCollection.Durée de vie des objets dans une collection dans VB.Net

Private Sub Form1_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load 
    For Each itm In NameCollection 
     Dim tmpTabPage as New TabPage(itm.toString) 

     'Add Controls to tmpTabPage 

     MyTabControl.TabPages.Add(tmpTabPage) 
    Next 
End Sub 

Depuis la portée de la tmpTabPage est le Pour/bloc suivant, généralement il est la vie serait jusqu'à la fin du droit de bloc? Mais puisqu'il est ajouté à une collection qui a une portée en dehors du bloc, a-t-il la même durée de vie que la collection, ou dans ce cas le MyTabControl? Enfin, si j'appelle MyTabControl.TabPages.Clear, les tmpTabPages de la collection seront-ils détruits ou vont-ils simplement s'asseoir pour prendre de la mémoire?

Répondre

5

Le gros problème concernant les classes dérivées de Control (y compris TabPage) est la méthode Dispose(). Ils sont à l'abri de la collecte automatique des garbage, Winforms conserve une table interne qui mappe le handle d'un contrôle à la référence de contrôle. C'est pourquoi, disons, votre formulaire principal ne reçoit pas soudainement les ordures collectées, même si votre programme ne garde pas de référence. L'ajout de TabPage à la collection de TabControl prend en charge l'élimination automatique. La même chose s'applique pour le TabControl, il serait ajouté à la collection Controls du formulaire. La chaîne normale des événements est que votre programme ou l'utilisateur ferme le formulaire. La classe Form itère ses contrôles enfants et appelle leur méthode Dispose(). TabControl fait la même chose dans sa méthode Dispose(), en éliminant les pages à onglet.La fenêtre Windows est détruite au cours du processus, en supprimant le handle de cette table de mappage et en autorisant maintenant le garbage collector à collecter le wrapper géré pour les contrôles.

Il ya un piège méchant qui dérange beaucoup de programmeurs Winforms. Si vous supprimez un contrôle de la collection de ses parents, vous avez la responsabilité de l'éliminer vous-même. Le retirer pas le met automatiquement au rebut. Winforms maintient la fenêtre native en vie en re-parenting temporaire du contrôle à une fenêtre cachée appelée la "fenêtre de stationnement". Nice feature, il vous permet de déplacer un contrôle d'un parent à l'autre sans avoir à détruire et recréer le contrôle.

Mais le mot-clé est "temporairement". Ce n'est que temporairement si vous repartez ensuite le contrôle. Il est donc déplacé de la fenêtre de stationnement au nouveau parent. Si vous ne le repartez pas, il restera toujours vivant sur la fenêtre du parking. Gobber les ressources jusqu'à la fin du programme. Ceci est autrement connu comme une fuite. Il peut planter votre programme lorsque Windows refuse de créer une autre fenêtre lorsque vous en avez déjà créé 10 000.

La méthode ControlCollection.Clear() est particulièrement nocive ici. Ce n'est pas et non que les contrôles, ils sont tous déplacés vers cette fenêtre de stationnement. Si ce n'est pas prévu, c'est rarement le cas, vous devrez appeler Dispose() sur vous-même.

3

Les objets dans .NET deviennent éligibles pour la collecte des ordures lorsqu'il n'y a aucun moyen de les atteindre. Dans ce cas, sera un moyen d'atteindre le TabPage via la collection TabPages, jusqu'à ce qu'il soit supprimé de la collection ou que le contrôle de tabulation lui-même devienne éligible pour la collecte. Maintenant, quand un objet devient éligible pour la collecte des ordures, cela ne signifie pas qu'il est collecté immédiatement - le garbage collection fonctionne à plusieurs reprises selon des heuristiques assez complexes, et il y a aussi des "générations" de mémoire qui font les choses sont plus difficiles à prévoir.

Mais au fond:

  • Vous n'avez pas besoin de vous inquiéter qu'un objet qui a été ajouté à une collection sera mystérieusement recueillie et causer des problèmes
  • Vous ne généralement pas besoin de vous inquiéter que les objets seront mémoire de fuite pour toujours. Il y a certainement des situations dans lesquelles vous devez prendre des mesures actives pour vous assurer qu'un objet est admissible à la collecte lorsque vous ne l'utilisez plus, mais il est rare que ce soit . (Typiquement, ils sont liés à des variables statiques et/ou des événements, dans mon expérience.)
0

parce que quelque chose a une référence aux contrôles dont ils ne seront pas éliminés.

oui la durée de vie serait jusqu'à la fin de la procédure si vous ne leur avez pas ajouté une référence à la colelction.

clair supprimera les objets de la collection et ils auront des déchets collectés à condition qu'il n'y a pas d'autres références à eux (qui y shuoldnt dans la situation que vous décrivez)

0

Vous ajoutez seulement une référence de TabPage objet à la collection pas l'objet TmpTabPage. L'objet tmpTabPage dans ce cas vous l'utilisez uniquement pour allouer de la mémoire.