浅谈c#垃圾回收机制(GC)

写了一个window服务,循环更新sqlite记录,内存一点点稳步增长。三天后,内存溢出。于是,我从自己的代码入手,查找到底哪儿占用内存释放不掉,最终明确是调用servicestack.ormlite更新sqlite数据库造成的。至于是不是框架问题,可能性不大,因为本地模拟执行的代码没有任何问题。我觉得应该是orm在执行数据库更新后,对象还在被引用造成的。这里,我贴出一个伪代码:

640?wx_fmt=png

我的猜测到底对不对呢?现在还不知道。不过在探寻答案的时候,对GC的相关机制详细地了解了一遍。

640?wx_fmt=png

一、什么是GC?

官网中有这么一句话:

The garbage collector is a common language runtime component that controls the allocation and release of managed memory。

原来GC是CLR的一个组件,它控制内存的分配与释放。

二、托管堆和CLR堆管理器

我们知道c#中的引用类型,分配在堆上。所谓的堆,就是一大块连续的内存地址。CLR堆管理器负责内存的分配、释放。堆又分为小对象堆和大对象堆。它的内存分配流程如下:

640?wx_fmt=png

                                                  图片来源《.NET高级调试》pdf

CLR加载时,就会分配堆。

 三、GC的工作机制

 GC有三个假设:

1、如果没有特别声明,所有的对象都是垃圾(通过引用追踪对象是否为垃圾)

2、假设托管堆上所有的对象的活跃时间都是短暂的(相对于长久活跃的对象来说,GC将更频繁地收集短暂活跃的对象)

3、通过代跟踪对象的持续时间

以下是官方文档给出的和这三个假设一致

The garbage collector in the common language runtime supports object aging using generations

Objects created more recently are part of newer generations, and have lower generation numbers than objects created earlier in the application life cycle. 

Objects in the most recent generation are in generation 0. This implementation of the garbage collector supports three generations of objects, generations 0, 1, and 2

每代都有自己的堆,假如0代的堆满了,就会触发GC,然后把依然有引用的对象升级,放到1代对象。最后压缩堆,把剩余的堆空间合并到一块。1代对象也是如此操作。但到了2代,就处理不同了。2代的堆可能是大对象堆,它的压缩代价过于高昂,所以只是合并相邻的空间。

640?wx_fmt=png

                                                    图片来源博客园c#技术漫谈之垃圾回收(GC)

Garbage collection happens automatically when a request for memory cannot be satisfied using available free memory

 GC发生的时机,就是相应的堆达到了阈值,因为堆也有大小限制,并不是无限的。尽管2代堆或者大对象堆满的时候,通过增加新的内存段来满足内存分配,如果没有可用的内存,这时就会报内存溢出。

四、GC不能释放非托管资源

有两种情况,第一种:托管代码引用了非托管资源,比如文件操作、数据库连接、网络连接等。这时候必须手动释放,或实现 dispose模式,或实现对象终结

When a type uses unmanaged resources that must be released before instances of the type are reclaimed, the type can implement a finalizer.

In most cases, finalizers are implemented by overriding the Object.Finalize method; however, types written in C# or C++ implement destructors, which compilers turn into an override of Object.Finalize 

必须注意的一点是,实现对象终结器,GC会在释放对象之前自动调用。其实这是一个代价非常高昂的备用机制。所以能自己释放非托管资源的,就自己释放。

如果一个对象中包含有终结器,那么在new的时候放入到终结者队列。当GC会把这个对象标为垃圾时,放入到另一个队列F-Reachable中。这个队列包含了所有带有终结器并且将被作为垃圾收集的对象,这些对象的终结器都将被执行。在垃圾收集的过程总并不会执行终结器代码。而是由.NET 进程的终结线程调用。因此,此时的垃圾回收滞后一段时间,目的在于等待终结器代码执行的完成。

五、dispose模式

640?wx_fmt=png

640?wx_fmt=png

这是基类和子类的dispose模式,来源于官网。

原文地址:https://www.cnblogs.com/wangqiang3311/p/10280000.html


.NET社区新闻,深度好文,欢迎访问公众号文章汇总 http://www.csharpkit.com

640?wx_fmt=jpeg

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/317729.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

洛谷P2497:基站建设(splay、斜率优化)

所谓splay斜率优化dp,就是利用splay和斜率对dp进行优化 (逃) 解析 在斜优的时候,有时我们会发现我们插入的点的横坐标并不单调 这个时候我们就无法利用单调队列维护凸包了 这时,我们就要请出今天的主角:s…

MediatR 知多少

引言首先不用查字典了,词典查无此词。猜测是作者笔误将Mediator写成MediatR了。废话少说,转入正题。先来简单了解下这个开源项目MediatR(作者Jimmy Bogard,也是开源项目AutoMapper的创建者,在此表示膜拜)&a…

网络分析(带权并查集)

网络分析 题意: 有n个节点,一开始彼此独立,有两个操作,第一个操作时是连接两个节点,第二个操作是对一个节点x,(在进行第二个操作时,与该点相连的点也会x) 问每个节点的…

良心发现,时隔一年再回首莫比乌斯反演(公式性质证明+题目练习)

文章目录莫比乌斯反演引入公式性质模板公式证明莫比乌斯函数前缀和题目练习完全平方数[HAOI2011]ProblembYY的GCD[SDOI2014]数表[国家集训队]Crash的数字表格/JZPTAB[SDOI2015]约数个数和寒假疫情期间跟着lmm学了一遍,完全是懵逼到底状态,以至于后面考到…

平面切分

平面切分 问题描述 题解: 我对这种题极其非常不擅长。。。 另外吐槽为什么acwing的数据卡的这么死,蓝桥杯官网数据那么水 其实题目很简单,如果只有一个直线,那么就是两部分,如果是两个直线,这两个直线不相…

新起点!新征程!微软技术俱乐部(苏州)成立大会暨微软技术交流会

2019年1月19日,苏州微软将举办苏州史上最盛大的开发者聚会,微软技术俱乐部成立大会暨微软技术交流会。超越苹果,登顶世界市值第一!云与AI两大技术支柱支撑起的微软帝国,正向万亿美元俱乐部挺进!微软的改变我…

跨平台、跨语言应用开发工具,Elements 介绍

目录1,Elements 介绍2,Elements 版本3,Elements 能干嘛4,Elements IDES5,Elements 工具1,Elements 介绍RemObjects Elements,是多平台移动项目开发工具,是一款可以帮助开发人员在 不…

后缀自动机(SAM)构造实现过程演示+习题集锦

文章目录后缀自动机算法实现过程模板习题洛谷后缀自动机模板题品酒大会[HEOI2015]最短不公共子串字符串蒟蒻写这篇blogblogblog主要是存一下,后缀自动机的详细搭建过程,方便以后复习 具体的某些证明,为什么这么做,正确性劈里啪啦一…

使用logdashboard进行可视化的日志追踪

本文源码在Github可以找到下载LogDashboard如果你还不了解LogDashboard请看这里。 LogDashboard 1.1版本支持请求追踪,虽然目前版本还没有发布。不过这个功能可以先睹为快效果图下载项目首先我们可以在 https://github.com/liangshiw/LogDashboard/tree/master/samples/Request…

ML.NET 0.9特性简介

ML.NET 0.9已于上周发布,距离上次0.8版本的发布只有一个多月,此次增加的新特性主要包括特征贡献计算,模型可解释性增强,ONNX转换对GPU的支持,Visual Studio ML.NET项目模板预览,以及API改进。特征贡献计算特…

[学习笔记] 初次见面,请多关照 (公式推导+题集)——杜教筛

筛积性函数的前缀和常见积性函数公式推导狄利克雷卷积杜教筛实现常见卷积习题集Sum神犇和蒟蒻简单的数学题常见积性函数 μ\muμφφφd(n)d(n)d(n):nnn的约数个数σ(n)σ(n)σ(n):nnn的约数和ϵ(n)ϵ(n)ϵ(n):单位元函数,e(n)[n1…

AOP 还在配置吗改用打标签模式吧!

为什么我喜欢打标签来配置AOP1. 配置多很混乱,代码里面很难分辨出来哪些是AOP容器(比如属性注入)2. 对于代码生成器生成的代码里面还需要手动加到配置里面3. 连java spring现在都是清一色的注解来代替xml,这个就是趋势所在我基于Autofac开发了一个基于标…

DZY Loves Math IV(杜教筛)

文章目录titlesolutioncodetitle solution 这道题是多么的妙啊,完全不是我能推出来的式子呢! 观察数据范围,有点奇怪欸,在暗示我?? 考虑暴力枚举nnn S(n,m)∑i1mφ(ni)S(n,m)\sum_{i1}^mφ(n\times i)S…

codeforces:CF1604 总结

前言 solve:4 rank:48!!!!!!!!!! 这排名我不理解了 solve4真真不算多啊… 而且前四题感觉也不算太难… 仔细看了看榜 哦… 因为这次…

IdentityServer4直播

大家好,很久没有更新公众号,让各位久等了,主要是最近出除了工作之外,一直私下在学习和研究IdentityServer4,后续会腾出一部分时间陆续更新公众号。对于IdentityServer4(简称IDS),网上的资料少之可怜&#x…

.NET Core 3.0:System.Data的变化

System.Data虽然不引人关注,但在.NET中,System.Data对于各种关系数据库的连接是非常重要的。System.Data也被称为ADO.NET,其前身是ActiveX Data Objects。System.Data提供了通过的框架,在她的基础上.NET数据驱动应用可以被构建。这…

蓝桥杯国赛 皮亚诺曲线距离

参考博客 题意: 题解: 这个很恶魔 本质好说就是找规律,但是贼难写。。 找了篇题解,做法就是大化小,将大阶化为成小阶,计算出离远点的距离。。。我感觉我是写不出来。。 挺秒的,要推公式估计要…

将 Visual Studio 的代码片段导出到 VS Code

导语和原文作者一样,水弟我现在也是使用 VS Code 和 Rider 作为主力开发工具,尤其是 VS Code 可以跨平台,又有丰富的插件支持和多种编程语言支持。当我从 VS 转移到以 VS Code 的开发过程中,遇到的最大问题就是代码提示的不完善&a…

如何基于 Kubernetes 构建完整的 DevOps 流水线

前言关于 DevOps 是一个很大的话题,它可能既涉及到公司的技术文化构建,也包括开发者技术能力的支持,这次技术干货分享主要是侧重于技术方面,就是如何用 Kubernetes 来服务好 DevOps 的流水线。本文从 4 个方面介绍:什么…

[SNOI2017]遗失的答案 (FWT)

description 小皮球在计算出答案之后,买了一堆皮肤,他心里很开心,但是一不小心,就忘记自己买了哪些皮肤了。 ||| 万幸的是,他还记得他把所有皮肤按照 1∼N 来编号,他买来的那些皮肤的编号(他至…