Search code examples
c#wpfclassdispose

Dispose the Class


There is a class in my project called DataParse. I am making multiple connections with Ethernet. Every time a new connection is opened I create a new class as follows. Also, there is one timer in this class.

public Dictionary<string, DataParse> classDictionary = new Dictionary<string, DataParse>();

Connect Code

string IpAddress = Ip.Text;
int Port = Convert.ToInt32(PortName.Text);
var IpPort = IpAddress + ":" + Port;
classDictionary.Add(IpPort, new DataParse());
classDictionary[IpPort].DataParseRun(IpPort);

I want to destroy the created class when the connection is closed. I want to destroy the timer with the class.

I implemented a method like this to destroy the class and I failed. He goes into the timer again.

Disconnected Code

private void Events_Disconnected(object sender, ClientDisconnectedEventArgs e)
{
    classDictionary[e.IpPort].Dispose();
    classDictionary.Remove(e.IpPort);
}

DataParse Code

public class  DataParse : IDisposable
    {

    private bool _disposed = false;
    private SafeHandle _safeHandle = new SafeFileHandle(IntPtr.Zero, true);
    public void Dispose()
    {
        Dispose(true);
        GC.SuppressFinalize(this);
    }

    protected virtual void Dispose(bool disposing)
    {
        if (_disposed)
        {
            return;
        }

        if (disposing)
        {
            // Dispose managed state (managed objects).
            _safeHandle?.Dispose();
        }

        _disposed = true;
    }
    
    Timer timer;
    byte[] moduleBuffer;
    int writePtr;
    string key;



    public void DataParseRun(string IpPort)
    {
        moduleBuffer = new byte[50000];
        writePtr = 0;
        timer = new Timer(new TimerCallback(ParseTimer), null, TimeSpan.FromMilliseconds(1000), TimeSpan.FromMilliseconds(200));
        key = IpPort;

    }
     
    void ParseTimer(object state)
    {
        var abc = key;    
    }

   
}

How can I destroy the class.


Solution

  • Try manually disposing the timer in the Dispose method. As far as I see the timer is never disposed.

    timer.Dispose();
    

    EDIT: Cant comment yet so Ill edit the answer. As far as I am aware you cant manually just remove your instance from memory.

    It will be collected via Garbage Collector once all references to the instance are lost or unreachable - thus once you, as Trix in his answer advises, remove the instance from the Dictionary and dispose of the Timer and SafeHandle there should be nothing stopping the GC from collecting it. However when exactly this happens isn't up to you.

    EDIT2: I would say so. You can try to test it by reading some huge file to String to take up 100MB and watch if the memory is let go once you dispose of everything. Apparently there is also a direct call you can make to the GC: GC.Collect() - if you call it from class I don't think it will collect that class but for testing you can call it after you dispose from the dictionary.