Hello all,
After executing the following piece of code, the object remains in memory... the garbage collector won't collect the memory:
Dim tempObj as new MyExampleClass()
tempObj.Dispose( )
tempObj = Nothing
System.GC.Collect( )
System.GC.WaitingForPendingFinalizers( )
It seems to be due to "Handles SelectedValueChanged" because if i remove it, the object gets properly disposed and the memory collected.
Ways i found to "fix" this:
So i'm asking the CSLA Experts... what would be the proper way to unbind the combobox so that it's not linked to the NVList in any way?
Thanks,
-Flat
PS: I'm using CSLA 2.1.
_____________________________
<Serializable()> _
Public
Class MyNameValueListInherits NameValueListBase(Of Integer, String)
Private Shared _list As MyNameValueList
Public Shared Function GetMyNameValueList() As MyNameValueList
If CanReadObject() = False Then
Throw New AccessViolationException("You are not permitted to view Securitization Programs.")
End If
If _list Is Nothing Then
_list = DataPortal.Fetch(Of MyNameValueList)(GetType(MyNameValueList))
End If
Return _list
End Function
Public Shared Sub InvalidateCache()_list = Nothing
End Sub
.......
End Class
_______________________________________________________________________
Partial Class MyControl
Friend WithEvents myComboBox As System.Windows.Forms.ComboBox
Sub New()
myComboBox.DisplayMember = "Value"
myComboBox.ValueMember = "Key"
myComboBox.DataSource = MyNameValueList.GetMyNameValueList()
myComboBox.DataBindings.Add("SelectedValue", _obj, "MyID", True, DataSourceUpdateMode.OnPropertyChanged)End Sub
Private Sub myComboBox_SelectedValueChanged(ByVal sender As Object, ByVal e As System.EventArgs) Handles myComboBox.SelectedValueChanged
End Sub
End Class
ajj3085:What problem exactly are you trying to solve? The best way to work with the garbage collector is to not worry about it at all.
My problem... an avg of ~2MB memory leak each time i'm trying to dispose of 1 instance of the MyExampleClass. It doesn't show here, but my real class is *much* more complex than that. Each instance of that class takes ~2MB in memory and we have multiple instances of that class in memory at once. So each time we close our form (which contains anywhere from 1 to 13 instances of that control), we have a ~2-26MB memory leak and overtime and we end up receiving a OutOfMemoryError exception message.
richardb:I think the recommendation is to unbind anything that you DataBindings.Add'ed in the first place as the form closes down.
I forgot to add the following line in a Form_Closing method in my above example class: myComboBox.DataBindings.Clear( )
But i already had this line in my real class and made sure it was called properly we the control is being closed.
Thanks for your replies,
-Flat
We had similar issues with a .Net 1.1 project - out Winform app never seemed to garbage collect during the day and although that wasn't necessarily a problem, some users complained when they switched to another application the PC was "a bit slow". Out winform exe was slowly using all the lovely memory available.
A combination of doing some manual GC calls and unbinding all controls (and sub controls) helped.
Private Sub ClearBindings(ByVal c As Control)
Dim bindings(c.DataBindings.Count) As Binding
c.DataBindings.CopyTo(bindings, 0)
c.DataBindings.Clear()
For Each bind As Binding In bindings
System.ComponentModel.TypeDescriptor.Refresh(bind.DataSource)
Next
For Each cc As Control In c.Controls
ClearBindings(cc)
Next
End Sub
Thanks for trying to help Richard!
I gave your piece of code a try but in my case, it didn't work. Somehow, the Shared member from MyNameValueList and my instances of MyExampleClass still seem to be linked via an event even after running your code.
Thanks again
Flatulus:My problem... an avg of ~2MB memory leak each time i'm trying to dispose of 1 instance of the MyExampleClass. It doesn't show here, but my real class is *much* more complex than that. Each instance of that class takes ~2MB in memory and we have multiple instances of that class in memory at once. So each time we close our form (which contains anywhere from 1 to 13 instances of that control), we have a ~2-26MB memory leak and overtime and we end up receiving a OutOfMemoryError exception message.
richardb:I think the recommendation is to unbind anything that you DataBindings.Add'ed in the first place as the form closes down.I forgot to add the following line in a Form_Closing method in my above example class: myComboBox.DataBindings.Clear( )
But i already had this line in my real class and made sure it was called properly we the control is being closed.
Well, I think that clears databindings of the control, such as Value or Text to your business object... I don't think it will clear the combobox's DataSource, which I recommened you try above.
26MB is for 1 form that contains 13 instances of the MyExampleClass control. So if during the day the user opens and closes that form 10 times, that a nice 260MB leak. Also, we use the same technic throughout our code... the leak probably occurs elsewhere.
I tried your "DataSource = typeof" thing... and i receive the following error:
Complex DataBindings accept as data source either an IList or IListSource.
And now i'm trying to assign a "Type" object. I don't know what this was supposed to achieve...
Thanks again for the reply!
NOTE: We are *not* using any System.GC call in our real code. I simply added the 2 System.GC lines above to show you that after i got rid of the MyExampleClass object there was a mem leak at that point.
Flatulus:26MB is for 1 form that contains 13 instances of the MyExampleClass control. So if during the day the user opens and closes that form 10 times, that a nice 260MB leak. Also, we use the same technic throughout our code... the leak probably occurs elsewhere.
Flatulus:And now i'm trying to assign a "Type" object. I don't know what this was supposed to achieve...
Flatulus:NOTE: We are *not* using any System.GC call in our real code. I simply added the 2 System.GC lines above to show you that after i got rid of the MyExampleClass object there was a mem leak at that point.
ajj3085:Well, if your control is no longer referenced anywhere, it should "go away" automatically. I have tons of dropdowns bound to NVL subclasses all over my application without problem. Do you have any static events on your forms, controls or what-have-you? I think they can cause references to hang around longer if you don't unhook static event handlers properly.
Private Sub myComboBox_SelectedValueChanged(ByVal sender As Object, ByVal e As System.EventArgs) Handles myComboBox.SelectedValueChanged
End Sub
Then my objects' memory is getting properly collected after disposal.
Found another way to fix that problem which i think is the one we're going to use in the future:
<In New()>
Dim myBS As New BindingSource
myBS.DataSource = MyNameValueList.GetMyNameValueList()
myComboxBox.DataSource = myBS
<In Dispose()>
DirectCast(myComboxBox.DataSource, BindingSource).DataSource = Nothing
The leak seems gone if i bind/unbind using that method.
Thanks all for your replies
I think the recommendation is to unbind anything that you DataBindings.Add'ed in the first place as the form closes down.
Copyright (c) Marimer LLC