温故而知新之 构造函数、析构函数

构造函数

作用:初始化对象、数据

特点:默认是有一个无参构造方法,可以有多个并重载

析构函数

作用:释放对象,回收非托管资源(系统级的资源GC管不到,例如数据库连接、字体、文件、图像、Socket等)。

功能:是用来释放一个对象的。在对象删除前,用它来做一些清理工作,它与构造函数的功能正好相反。

谁在使用:GC垃圾回收器在调用

代码示例

    class Program
    {
        static void Main(string[] args)
        {
                Man man = new Man();
                Console.ReadLine();
                //---让GC通过析构函数自动调用回收
                //man = null;
                //GC.Collect();
                //---手动调用回收
                man.Dispose();
        }
    }
    class Man: IDisposable
    {
        private readonly IntPtr unmanageResource;
        private readonly SafeHandle manageResource;
        Man() {//构造函数,对象初始化时调用
            unmanageResource = Marshal.AllocHGlobal(sizeof(int));
            manageResource = new SafeFileHandle(new IntPtr(), true);
        }

        ~Man() {//析构函数,对象结束时调用
            Dispose();
            GC.SuppressFinalize(this);//让GC忽略掉
        }

        public void Dispose()
        {
            Dispose(true);
            GC.SuppressFinalize(this);
        }

        public virtual void Dispose(bool disposing)
        {
            ReleaseUnmanagedResourse(unmanageResource);//处理非托管资源
            if (disposing)
                ReleaseManagedResourse(manageResource);//处理托管资源
        }
        private void ReleaseManagedResourse(SafeHandle safeHandle)
        {
            safeHandle?.Dispose();
        }
        private void ReleaseUnmanagedResourse(IntPtr intPtr)
        {
            Marshal.FreeHGlobal(intPtr);
        }
    }

示例代码说明

你能通过调用GC.Collect方法强制垃圾搜集器来清理内存,但在大多数情况下,这应该避免因为它会导致性能问题。在上面的程序中,可以清晰的看到 托管资源和非托管资源 回收机制的联合使用

一般我们不手动写回收,针对这种需要手动调用 Dispose 的对象,我们也有一种好的使用方法

using (Man man = new Man())
{
    //使用 using 括号,再using作用域结束时对象也随之释放
}
posted @ 2021-08-26 15:09  顽皮大叔  阅读(131)  评论(0编辑  收藏  举报