在引发对象订阅的异步事件后,是否会自动释放对象

本文关键字:对象 是否 释放 异步 事件 | 更新日期: 2023-09-27 17:57:05

假设我有这个可以从主线程调用多次的函数。每次调用它时,我都会创建一个WebClient对象来异步下载一些数据。

我的问题...这样做安全吗?调用事件后是否释放WebClient对象?如果内存不会自动释放,我不想继续分配内存。

我的应用程序适用于带有Silverlight的WP7。

谢谢!

void DownloadData(string cURL)
{
    WebClient webClient = new WebClient();
    webClient.DownloadStringCompleted +=
       new System.Net.DownloadStringCompletedEventHandler(
            webClient_DownloadStringCompleted);
    webClient.DownloadStringAsync(new Uri(cURL));
}
static void webClient_DownloadStringCompleted(object sender,
                      System.Net.DownloadStringCompletedEventArgs e)
{
    ...
}

在引发对象订阅的异步事件后,是否会自动释放对象

WebClient的 SilverLight 版本没有实现IDisposable。你做对了 - webClient到时候会自动进行垃圾回收。

与其手动处理WebClient,不如将其放在使用块中。

using (WebClient webClient = new WebClient())
{
    // Your business in here...
}

我看到 2 个问题。首先,Web客户端不会在所有可能的情况下都释放,其次,由于您永远不会取消订阅该事件,因此将保留对WebClient的引用。

我认为这很接近它(虽然仍然不完美,但请考虑线程中止):

void DownloadData(string cURL) 
        {
            WebClient webClient = new WebClient();
            try
            {
                webClient.DownloadStringCompleted += new System.Net.DownloadStringCompletedEventHandler(webClient_DownloadStringCompleted);
                webClient.DownloadStringAsync(new Uri(cURL));
            }
            catch
            {
                webClient.Dispose();
                throw;
            }
        }
        static void webClient_DownloadStringCompleted(object sender, System.Net.DownloadStringCompletedEventArgs e)
        {
            WebClient webClient = (WebClient)sender;
            webClient.DownloadStringCompleted -= webClient_DownloadStringCompleted;
            try
            {
            }
            finally
            {
                webClient.Dispose();
            }
        }

WebClient 没有实现 iDisposable 接口,因此不需要做任何特殊的事情来允许正确的垃圾回收。 当 CLR 检测到当前没有对该对象的引用时,将计划该对象进行垃圾回收。 当然,您不知道何时会发生这种情况,因此内存可能会或可能不会(很可能不会)立即释放。