C# 垃圾回收机制(GC) 的概述 资源清理 内存管理

简介: C# 垃圾回收机制(GC) 的概述 资源清理 内存管理

什么是垃圾回收

在编写程序时,会产生很多的数据 比如:int string 变量,这些数据都存储在内存里,如果不合理的管理他们,就会内存溢出导致程序崩溃

C#内置了自动垃圾回收GC,在编写代码时可以不需要担心内存溢出的问题 变量失去引用后 GC会帮我们自动回收,但不包括数据流,和一些数据库的连接,这就需要我们手动的释放资源

总结:让内存利用率更高


什么样子的对象才会给回收?

GC只会回收 的内存 ,而 值类型在 中的使用完后马上就会给释放,并不需要 GC 进行处理,堆中的没有被引用或者null的对象才会被回收,静态的变量也不会被回收

上面说到他并不会回收一些数据流

比如: Stream StreamReader StreamWrite HttpWebResponse 网络端口 等还有一些数据库的连接

这些对象需要调用 Close() 或者 Dispose() 方法进行 手动回收

总结:没有被引用的对象 或为 null的


什么时候进行垃圾回收?

什么时候回收这些都由操作系统决定,一般不需要进行理会全由系统调用,如有特殊情况,明确的需要进行释放 也可以强制的垃圾回收

GC.Collect()

正常情况下 非常不建议使用这方法,这会让程序暂停但时间很短,会影响执行效率

需要注意的是 给释放后的内存是无法在找回的

总结:由操作系统决定 但也可以强制释放 正常情况不需要理会内存问题


效率问题(重要)

除非马上需要进行非常消耗内存的操作 其他情况尽量不要调用GC.Collect();

测试:

for (int i = 0; i < 90000; i++)           
string str = i.ToString();
//假装我是一个方法哈

测试时间:20毫秒

假如每次使用完方法后强制垃圾回收

for (int i = 0; i < 90000; i++)
            {
string str = i.ToString();
 //假装我是一个方法哈
  GC.Collect();          
            }

测试时间:4793毫秒

性能相差200倍


“代”的机制

使用代的机制进行垃圾回收 可以大大的提示垃圾回收的性能

垃圾回收共分3代

索引 【0】【1】 【2】共3个

每次创建对象的时候 都是在第0代 分配内存 并且每一代都配有初始内存空间



假设现在程序已经跑了一段时间了 而第0代分配的2MB的空间已满了



这时候就会进行 垃圾回收 把失去引用的对象释放 此时未使用完的对象将进入到第1代



垃圾回收后 第0代就已经空了 后面创建的对象就会重新放入第0代


以此类推 0代满后 又会重新垃圾回收 还在使用的对象又会放入第1代

此后运行一段时间 1代也已经满了 而0代还在使用的对象也会移动到1代 这时候已经不够放了 又会进行垃圾回收 1代的将移动到2代 0代的将移动到1代



以此类推

假如我代数都满了 但对象我都还在使用 并没有回收多少 这时GC就会自动的把初始内存给扩大 比如原来2MB 扩大到4MB 还不够使用的情况下就会抛出异常

int n  =GC.MaxGeneration;
//获取系统支持最大的代数

结果:2

GC.Collect(1); 
   //指定回收第2代内存   注意从0开始

析构函数

该函数是在类使用完成后调用的,一些非托管资源 Sream 可以在此处调用Dispose()方法进行释放内存,一个类只有一个析构函数而且无法继承他

~Class1()
        {
            Console.WriteLine("我给调用了");
        }

但有时候该函数并不会调用,无法控制何时调用析构函数,因为这是由垃圾回收器决定的,在垃圾回收时先运行析构函数在回收其他对象。

public void A()
        {
            Console.WriteLine("xxxx");
        }
        ~Class1()
        {
            Console.WriteLine("我给调用了");
        }

可以看到 析构函数 并没有给使用,假如你写的是一些释放资源的方法,那也不会执行该函数


相关文章
|
1月前
|
JavaScript 前端开发 Java
垃圾回收机制会导致内存泄漏吗?
【10月更文挑战第29天】虽然JavaScript的垃圾回收机制本身是为了有效地管理内存,但开发者在编写代码时需要注意上述这些可能导致内存泄漏的情况,遵循良好的编程习惯,及时释放不再使用的资源,以确保程序能够高效地利用内存资源,避免出现内存泄漏问题。
|
16天前
|
缓存 监控 算法
Python内存管理:掌握对象的生命周期与垃圾回收机制####
本文深入探讨了Python中的内存管理机制,特别是对象的生命周期和垃圾回收过程。通过理解引用计数、标记-清除及分代收集等核心概念,帮助开发者优化程序性能,避免内存泄漏。 ####
28 3
|
22天前
|
算法 Java 开发者
Java内存管理与垃圾回收机制深度剖析####
本文深入探讨了Java虚拟机(JVM)的内存管理机制,特别是其垃圾回收机制的工作原理、算法及实践优化策略。不同于传统的摘要概述,本文将以一个虚拟的“城市环卫系统”为比喻,生动形象地揭示Java内存管理的奥秘,旨在帮助开发者更好地理解并调优Java应用的性能。 ####
|
1月前
|
缓存 算法 Java
本文聚焦于Java内存管理与调优,介绍Java内存模型、内存泄漏检测与预防、高效字符串拼接、数据结构优化及垃圾回收机制
在现代软件开发中,性能优化至关重要。本文聚焦于Java内存管理与调优,介绍Java内存模型、内存泄漏检测与预防、高效字符串拼接、数据结构优化及垃圾回收机制。通过调整垃圾回收器参数、优化堆大小与布局、使用对象池和缓存技术,开发者可显著提升应用性能和稳定性。
48 6
|
14天前
|
存储 监控 算法
Java内存管理的艺术:深入理解垃圾回收机制####
本文将引领读者探索Java虚拟机(JVM)中垃圾回收的奥秘,解析其背后的算法原理,通过实例揭示调优策略,旨在提升Java开发者对内存管理能力的认知,优化应用程序性能。 ####
29 0
|
2月前
|
缓存 算法 Java
JVM知识体系学习六:JVM垃圾是什么、GC常用垃圾清除算法、堆内存逻辑分区、栈上分配、对象何时进入老年代、有关老年代新生代的两个问题、常见的垃圾回收器、CMS
这篇文章详细介绍了Java虚拟机(JVM)中的垃圾回收机制,包括垃圾的定义、垃圾回收算法、堆内存的逻辑分区、对象的内存分配和回收过程,以及不同垃圾回收器的工作原理和参数设置。
77 4
JVM知识体系学习六:JVM垃圾是什么、GC常用垃圾清除算法、堆内存逻辑分区、栈上分配、对象何时进入老年代、有关老年代新生代的两个问题、常见的垃圾回收器、CMS
|
2月前
|
存储 监控 算法
Java中的内存管理与垃圾回收机制解析
本文深入探讨了Java编程语言中的内存管理方式,特别是垃圾回收机制。我们将了解Java的自动内存管理是如何工作的,它如何帮助开发者避免常见的内存泄漏问题。通过分析不同垃圾回收算法(如标记-清除、复制和标记-整理)以及JVM如何选择合适的垃圾回收策略,本文旨在帮助Java开发者更好地理解和优化应用程序的性能。
|
2月前
|
监控 算法 Java
Java中的内存管理:理解垃圾回收机制
【10月更文挑战第2天】 在本文中,我们将深入探讨Java编程语言中的内存管理机制,特别是垃圾回收机制。我们将从基本原理、垃圾回收算法到实际应用场景全面解析,帮助你更好地理解和优化Java应用的内存使用。无论你是初学者还是有经验的开发者,这篇文章都能带给你新的启发和思考。
37 2
|
3月前
|
存储 算法 Java
深入解析 Java 虚拟机:内存区域、类加载与垃圾回收机制
本文介绍了 JVM 的内存区域划分、类加载过程及垃圾回收机制。内存区域包括程序计数器、堆、栈和元数据区,每个区域存储不同类型的数据。类加载过程涉及加载、验证、准备、解析和初始化五个步骤。垃圾回收机制主要在堆内存进行,通过可达性分析识别垃圾对象,并采用标记-清除、复制和标记-整理等算法进行回收。此外,还介绍了 CMS 和 G1 等垃圾回收器的特点。
124 0
深入解析 Java 虚拟机:内存区域、类加载与垃圾回收机制
|
2月前
|
存储 监控 算法
深入理解Java内存模型与垃圾回收机制
【10月更文挑战第10天】深入理解Java内存模型与垃圾回收机制
22 0