.net中对象占用资源的回收

简介:     一,使用Finalizer析构器                1,使用了Finalizer析构器的对象如何被回收?                           在类中定义了析构器的对象将会被移动到一个专门的队列中,这个队列将作为它的应用程序根,而使队列中的对象存活的更久一点,在对象上面调用完析构函数后,对象才会从队列中清理掉。




    一,使用Finalizer析构器


               1,使用了Finalizer析构器的对象如何被回收?


                          在类中定义了析构器的对象将会被移动到一个专门的队列中,这个队列将作为它的应用程序根,而使队列中的对象存活的更久一点,在对象上面调用完析构函数后,对象才会从队列中清理掉。


               2,使用示例

                         

<span style="font-family:Microsoft YaHei;"> class Program
    {
        static void Main(string[] args)
        {
            Cup cup = new Cup() { 
            
                CupName="lhc的小杯子~~~~"
            };

        }
    }

    public class Cup {
        public string CupName { get; set; }

        ~Cup() { 
           //此处放置析构代码:对比C++的析构函数,感觉意思是一样的

                //这里放置释放资源的代码
            Console.WriteLine("小杯子已被打碎~~~~么么哒~~~~~");       
        }
    
    }</span>

            

                感觉从语法上很像C++,嘿嘿~



            3,使用析构器该注意哪些问题?

                    

               1,开发这无法确切的得知析构函数何时会被调用

              2,析构函数会延长对象的存活时间

              3,不要在析构函数中编写阻塞方法或耗时的方法,析构函数应该是迅速释放完资源并结束的

              4,如果程序运行期间一直没有进行垃圾回收,那么程序退出时会执行一次垃圾回收,并调用析构函数



  二,实现IDisposable接口

                

Finalizer的执行时间是不确定的,有时候,我们期望客户端对象使用完毕后立即释放资源,此时可以实现Idispose接口。


试用了下这个接口在dispose的时候都会发生啥,感觉还是雷同C++,写个栗子自己观察下析构的时候会发生啥吧。


使用示例:


<span style="font-family:Microsoft YaHei;"> static void Main(string[] args)
        {
            #region 构造器使用
            //Cup cup = new Cup() { 

            //    CupName="lhc的小杯子~~~~"
            //}; 
            #endregion


            #region dispose的使用
                BigCup bigCup = new BigCup()
                    {

                        CupName = "lhc的小杯子"
                    };

                //try
                //{
                //    bigCup.CupName = "此处模拟对象的使用过程";
                //}
                //finally
                //{

                //    IDisposable dis = bigCup as IDisposable;
                //    if (dis != null)
                //    {
                //        dis.Dispose();
                //    }
                //}

                using (bigCup as IDisposable)
                {
                    bigCup.CupName = "此处模拟对象的使用过程";
                }


            #endregion


        }
    }


    public class BigCup : IDisposable
    {
        public string CupName { get; set; }

        void IDisposable.Dispose()
        {

            Console.WriteLine("销毁了~~~~");
        }

    }

</span>



三,结合析构函数和Dispose()

        

       析构函数的主要问题在于:它不是立即被调用,而是在以后某个不确定的时间,执行垃圾回收时被调用。Dispose()方法也有自己的问题,就是客户端不一定会调用它。因此,最好的方法就是将这两者结合起来:

如果客户端调用了Dispose()方法,那么就不要让CLR去执行析构函数;

如果客户端没有调用,此时再进行析构。


       结合使用Demo:

      

<span style="font-family:Microsoft YaHei;">  public class TestFatherFinalizerAndDispose :IDisposable{

        private bool _dispose = false;

        ~TestFatherFinalizerAndDispose() {
            Console.WriteLine("调用析构函数~~~~");
        }

        public void IDisposable.Dispose() {

            if (!_dispose)
            {
                _dispose = true;
                CleanUp();
                GC.SuppressFinalize(this);//指示垃圾回收期,无视该对象的析构函数。
            }

        }

        //子类可重写该释放资源方法
        public virtual void CleanUp() { 
        
            //此处放置清理资源代码
            Console.WriteLine("垃圾清理完毕~");
        }
    }
    public class TestSonFinalizerAndDispose : TestFatherFinalizerAndDispose {

        public override void CleanUp()
        {
            try
            {
                Console.WriteLine("此处填写释放子类型资源的方法");
            }
            finally {
                base.CleanUp();  //调用父类的方法释放父类的资源
            }
            
        }
    
    }

</span>

     

       完美解决~~~继续准备运筹学考试,话说复习好无聊的,中间写个代码解解闷儿~~








                         

目录
相关文章
|
8月前
|
容器
.NET Core-作用域与对象释放行为详解
.NET Core-作用域与对象释放行为详解
|
4月前
|
C#
.NET开发中合理使用对象映射库,简化和提高工作效率
.NET开发中合理使用对象映射库,简化和提高工作效率
|
8月前
|
JSON 数据格式
.NET Core - 配置绑定:使用强类型对象承载配置数据
.NET Core - 配置绑定:使用强类型对象承载配置数据
|
8月前
|
容器
.NET Core作用域与对象释放行为详解
上节,我们提到,容器中有3种不同生命周期,分别是Singleton、Scoped和Transient。那么,你知道这3种类型的对象的释放时机和坑吗?
|
10月前
|
SQL 存储 缓存
SQl Server——ADO.NET五大对象
在某些编程中总是会需要用到数据库,那如何让应用程序和数据库之间建立联系呢?ADO.NET就提供了应用程序连接数据库的桥梁
|
XML 编解码 C#
.NET MAUI 安卓 UI 资源设置
本文主要介绍使用 MAUI 开发安卓应用时,如何更换和处理 UI 资源:应用名称,图标,主题配色,状态栏,闪屏。
443 0
.NET MAUI 安卓 UI 资源设置
|
机器学习/深度学习 人工智能 计算机视觉
YOLOv7 在 ML.NET 中使用 ONNX 检测对象
本文介绍如何在 ML.NET 中使用 YOLOv7 的 ONNX 模型来检测图像中的对象。
286 0
YOLOv7 在 ML.NET 中使用 ONNX 检测对象
|
开发框架 移动开发 前端开发
ASP.NET MVC中使用jQuery Ajax通过FormData对象异步提交图片文件到服务端保存并返回保存的图片路径
ASP.NET MVC中使用jQuery Ajax通过FormData对象异步提交图片文件到服务端保存并返回保存的图片路径
251 0
|
移动开发 小程序 JavaScript
微信小程序开发之多图片上传+.NET WebAPI后端服务保存图片资源
微信小程序开发之多图片上传+.NET WebAPI后端服务保存图片资源
546 0
微信小程序开发之多图片上传+.NET WebAPI后端服务保存图片资源
C#编程-64:ADO.NET对象模型复习笔记
C#编程-64:ADO.NET对象模型复习笔记
C#编程-64:ADO.NET对象模型复习笔记