首页
学习
活动
专区
工具
TVP
发布
精选内容/技术社群/优惠产品,尽在小程序
立即前往

是否应该在没有终结器的对象上调用GC.SuppressFinalize?

在没有终结器的对象上调用 GC.SuppressFinalize 是没有必要的,因为没有终结器的对象不会被垃圾回收器调用终结器。

GC.SuppressFinalize 的作用是取消垃圾回收器对指定对象的终结器的调用。如果一个对象有终结器,那么在垃圾回收器回收该对象时,它会调用该对象的终结器。但是,如果一个对象没有终结器,那么垃圾回收器就不会调用该对象的终结器。因此,在没有终结器的对象上调用 GC.SuppressFinalize 是没有必要的。

如果一个对象有终结器,并且需要在对象被回收之前执行一些特殊的操作,那么可以在该对象的终结器中调用 GC.SuppressFinalize 来取消垃圾回收器对该对象的终结器的调用。这样可以避免重复调用终结器,并避免出现死锁等问题。

总之,在没有终结器的对象上调用 GC.SuppressFinalize 是没有必要的,因为没有终结器的对象不会被垃圾回收器调用终结器。

相关搜索:在 .net 对象的终结器中调用 glDeleteTextures 的正确方法有没有办法模拟本地对象上的方法调用如何检查Mock对象上是否调用了特定的属性setter?我的ajax没有调用控制器上的方法我是否应该在服务器上的WEB API中使用异步/等待?CaseComment对象上的触发器没有覆盖范围调用模板函数问题“调用没有匹配的函数”参数:迭代器,对象函数我是否应该在ASP.NET中验证服务器上的用户权限如何测试在要测试的方法内创建的对象上是否调用了方法是否存在没有JSON限制的JavaScript对象文字的解析器/编码器?将服务注入控制器时,“无法调用空对象上的方法”SignalR服务器(C#.net)中的全局变量是否应该在调用不同函数后保留它们的值?" using“in C# -从using语句中调用的帮助器函数是否使用包含的IDisposable对象?在调用executor服务的可运行实例的submit时获得的Future对象上是否有使用get的用例垃圾收集器是否在.NET中的异步调用期间销毁暂时未引用的对象?没有调用子状态的控制器和模板。已从子对象的父状态的同级状态转换Android:当屏幕上的键盘出现或消失时,是否有任何自动调用的监听器?NS MediaFilePicker -类构造函数可观察对象在类型上没有“new”和“on”属性的情况下无法调用snapshotChanges()上的take(1):angular firestore是否在第二次调用时从服务器获取数据,即使数据没有更改?在websphere上更改对象的值属性后,是否需要重新启动dmgr管理器?
相关搜索:
页面内容是否对你有帮助?
有帮助
没帮助

相关·内容

C# IDispose

这意味着该对象会从析构队列中移除。 对象成为垃圾:当没有任何引用指向该对象时,该对象将变成垃圾。即使是在调用 Dispose() 后,只要仍然有对对象有效引用,垃圾收集就无法回收它。...在.NET中,垃圾收集负责回收不再使用内存。垃圾收集会自动调用对象析构函数(如果定义了的话),以清理非托管资源。然而,在已经手动释放了非托管资源情况下,再次调用析构函数就没有必要了。...当创建一个包含终结(即析构函数)对象时,这个对象引用会被放到析构队列中。垃圾收集在进行垃圾回收时,会检查这个队列,找出那些不再被应用程序代码引用对象。...然后,GC 会把这些对象从析构队列移动到另一个队列,即待处理队列(FReachable queue)。此时,不再执行任何内存回收操作,而是启动一个单独终结线程来运行所有待处理队列中对象终结。...一旦这些对象终结执行完毕,它们就会在下一次垃圾回收当中被彻底清理。 调用 GC.SuppressFinalize() 方法后,对象就会从析构队列中移除,因此其终结不会被执行。

18920

.NET Core.NET 5.0 析构函数依然有效?

,将调用尚未被垃圾回收所有对象析构函数。...析构函数本质是终结,如果对象已被释放,在合适时机将自动调用Finalize方法,除非我们手动通过GC来抑制调用终结GC.SuppressFinalize),但不建议手动调用Finalize方法 通过资源释放标准例子...(调用终结方法),除非进行手动抑制,但在.NET Core并不能完全保证此行为。...(针对可到达或不可到达对象),根据建议,并不能保证所有可终结对象在关闭之前都将被终结。...由于上述链接原因存在,所以在ECMAC#5.0规范削弱了这一要求,因此.Net Core并不会违反此版本规范 总结 在应用程序关闭前,.NET Framework会尽一切合理努力调用析构函数即终结进行资源清理

31420
  • C#规范整理·资源管理和序列化

    提供终结意义在于:我们不能奢望类型调用者肯定会主动调用Dispose方法,基于终结会被垃圾回收调用这个特点,它被用作资源释放补救措。...对于没有继承IDisposable接口类型对象,垃圾回收则会直接释放对象所占用内存;而对于实现了Dispose模式类型,在每次创建对象时候,CLR都会将该对象一个指针放到终结列表中,垃圾回收在回收该对象内存前...同时,CLR还会分配专门线程读取freachable队列,并调用对象终结,只有到这个时候,对象才会真正被标识为垃圾,并且在下一次进行垃圾回收时释放对象占用内存。...注意2 如果调用者已经调用Dispose方法进行了显式地资源释放,那么,隐式释放资源(也就是终结)就没有必要再运行了。...当检查到方法内“根”时,如果发现没有任何一个地方引用了局部变量,则不管是否已经显式将其赋值为null,都意味着该“根”已经被停止。然后,垃圾回收会发现该根引用为空,同时标记该根可被释放。

    25020

    .NET面试题系列 - 垃圾回收:概念与策略

    在标记阶段,GC沿着线程栈开始遍历,检查每个根是否为null。对于那些有引用对象根,则不认为它们是垃圾。...在创建这个对象时,会在Finalization Queue(终结列表,由垃圾回收控制一个内部数据结构)为其加入一个指针。拥有Finalize方法对象被称为可终结。...Finalize方法又被称为终结。复写Finalize方法称为实现终结。只有你需要释放非托管资源时才需要这么做。 复写Finalize方法唯一方法是实现一个解构函数。...因为终结会导致续命,所以请留心,记得呼叫Dispose,并呼叫GC.SuppressFinalize(this),这可以让终结没有机会上场,对象就被销毁了。 4.6 什么是解构函数?...类中没有非托管资源,且有对象实现IDisposible: 特别注意这些对象,确保调用了它们Dispose方法(显式或者隐式)。

    90110

    从C#垃圾回收(GC)机制中挖掘性能优化方案

    Garbage Collector(垃圾收集,在不至于混淆情况下也成为GC)以应用程序root为基础,遍历应用程序在Heap动态分配所有对象[2],通过识别它们是否被引用来确定哪些对象是已经死亡...下面,来介绍一下GC中用到几个函数:   GC.SuppressFinalize(this); //请求公共语言运行时不要调用指定对象终结。   ...GC.GetTotalMemory(false); //检索当前认为要分配字节数。 一个参数,指示此方法是否可以等待较短间隔再返回,以便系统回收垃圾和终结对象。   ...我们调用完Dispose方法后,还有调用GC.SuppressFinalize(this) 方法来告诉GC,不需要在调用这些对象Finalize()方法了。   ...您还应该注意不要将调用GC.Collect 代码放置在程序中用户可以经常调用。这可能会削弱垃圾回收中优化引擎作用,而垃圾回收可以确定运行垃圾回收最佳时间。

    1.7K30

    编程小知识之 Dispose 模式

    ,这些资源可以分成两类: 托管资源 : 受 CLR 管理(分配和释放)资源,譬如 new 出某个类型对象 非托管资源 : 不受 CLR 管理(分配和释放)资源,譬如某个 native 文件句柄...,如果外部代码没有调用 DisposePattern Dispose 方法,那么 DisposePattern 持有的非托管资源(m_handle)便泄露了....我们需要借助 C# 中析构函数(或者叫终结) 这里我们暂时不去关注 C# 中析构函数各个细节,只要知道析构函数可以在类型被回收之前执行就行了,新示例代码如下: // dispose pattern...(this); 便是用来"屏蔽"析构函数执行(定义了析构函数类型可以通过调用 GC.SuppressFinalize 来抑制析构函数执行)....情况下更不能安全进行,综上,你不应该在析构函数中释放托管资源)

    1K20

    .NET GC 精要(三)

    ,引用类型等) 进阶 .NET 为了处理非托管资源(unmanaged resource)释放问题,引入了终结(Finalization)机制,相关代码实现也并不复杂,仅需要在类型中定义...你可能会认为答案非常简单:在对象被清理时候调用执行即可.这种方式的确是可行,但是会降低 GC 性能:在自定义"终结"函数中,代码可能会执行数据库关闭等耗时操作,如果我们在 GC 流程中直接同步调用这些...所以实际, .NET 使用了与 GC 完全独立一个线程来处理终结机制,这个"终结"线程会定期执行被清理对象"终结"函数,细节实现则主要涉及两个队列: Finalization Queue...首先,如果一个对象定义了"终结"函数,那么在创建该对象时,该对象引用会被额外添加到 Finalization Queue 中,之后如果 GC 流程发现该对象已经没有被引用,正常情况下该对象就会被清理,...(注意观察图中 Object Z(实现了"终结"函数) 引用变化) 可以看到,终结器使对象存在周期变长了,很多时候我们并不希望这种情况发生,缓解该问题一个方法就是我们主动调用对象"终结"函数,关于此有一个被称为

    34600

    熟悉而陌生新朋友——IAsyncDisposable

    (该部分内容本文将不做过多介绍) 虽然析构函数方法在某些需要进行清理情况下是有效,但它有下面两个严重缺点: 只有在GC检测到某个对象可以被回收时才会调用对象终结方法,这发生在不再需要资源之后某个不确定时间...当CLR需要调用终结方法时,它必须把回收对象内存工作推迟到垃圾收集下一轮(终结方法会在两轮垃圾收集之间运行)。这意味着对象内存会在很长一段时间内得不到释放。...disposedValue) { if (disposing) { // TODO: 释放托管状态(托管对象) } // TODO: 释放未托管资源(未托管对象)并重写终结 // TODO: 将大型字段设置为...null disposedValue = true; } } // // TODO: 仅当“Dispose(bool disposing)”拥有用于释放未托管资源代码时才替代终结 // ~ExampleClass...而IServiceScope默认实现在异步释放时会进行判断:如果注入实例为IAsyncDisposable则调用DisposeAsync(),否则判断是否为IDisposable。

    72210

    谈谈.net对象生命周期

    如果有足够空间,会调用这个类型构造函数,构造函数会返回一个指向内存中这个新对象引用,这个新对象地址刚好就是下一个对象指针一次所指向位置。   ...(5) 指向等待被终结(finalized)对象 (6) 任何一个指向对象CPU寄存   在一次垃圾回收过程中,运行环境会检查托管堆上面的对象是否仍然是从应用程序根可到达。...Finalize()调用将(最终)发生在一次"自然"垃圾回收或用程序通过GC.Collect()强制回收过程中,所以这样看来,终结方法就是让类对象释放内部非托管资源地方。...GC.SuppressFinalize(this); } } 可以看到,这个类中即有终结方法重写也有Dispose()方法,这样就能保证:程序员若忘记调用Dispose...()方法释放非托管资源,那么对象就会在垃圾回收过程中调用终结方法来释放非托管资源;若程序员调用了Dispose()方法,那么 GC.SuppressFinalize(this) 会保证在垃圾回收过程中不再会调用对象终结方法

    1.3K10

    GC前世与今生

    Garbage Collector(垃圾收集,在不至于混淆情况下也成为GC)以应用程序root为基础,遍历应用程序在Heap动态分配所有对象[2],通过识别它们是否被引用来确定哪些对象是已经死亡...,应该调用GC.SuppressFinalize。...如果对象正在终结队列(finalization queue), GC.SuppressFinalize会阻止GC调用Finalize方法。因为Finalize方法调用会牺牲部分性能。...private Component Components; // 跟踪是否调用.Dispose方法,标识位,控制垃圾收集行为 privatebool disposed =false;...托管和非托管代码都能被释放 // 如果disposing 等于false, 方法已经被终结 finalizer 从内部调用过, //你就不能在引用其他对象,只有非托管资源可以被释放。

    61230

    C#垃圾回收机制(GC)

    Garbage Collector(垃圾收集,在不至于混淆情况下也成为GC)以应用程序root为基础,遍历应用程序在Heap动态分配所有对象[2],通过识别它们是否被引用来确定哪些对象是已经死亡哪些仍需要被使用...,应该调用GC.SuppressFinalize。...如果对象正在终结队列(finalization queue),GC.SuppressFinalize会阻止GC调用Finalize方法。因为Finalize方法调用会牺牲部分性能。...private Component Components; // 跟踪是否调用.Dispose方法,标识位,控制垃圾收集行为 private bool disposed = false...托管和非托管代码都能被释放 // 如果disposing 等于false, 方法已经被终结 finalizer 从内部调用过, //你就不能在引用其他对象,只有非托管资源可以被释放。

    78210

    编写代码良好习惯——C#

    十五、利用using和try/finally语句来清理资源   在IDisposable接口Dispose()方法中用GC.SuppressFinalize()可通知垃圾收集不再执行终结操作。   ...十八、实现标准Dispose模式   1、使用非内存资源,它必须有一个终结,垃圾收集在完成没有终结内存对象后会将实现了终结对象添加到终结队列中,然后垃圾收集会启动一个新线程来运行这些对象终结...()方法需要做四个方面的工作:释放所有的非托管资源;释放所有的托管资源;设置一个状态标记来表示是否已经执行了Dispose();调用GC.SuppressFinalize(this)取消对象终结操作;...二十一、使用委托表达回调   1、委托对象本身不提供任何异常捕获,所以任何多播委托调用都会结束整个调用链;   2、通过显示调用委托链每个委托目标可以避免多播委托仅返回最后一个委托输出。   ...三十五、重写优于事件处理   1、一个事件处理抛出异常,则事件链其他处理将不会被调用,而重写虚方法则不会出现这种情况;   2、重写要比关联事件处理高效得多,事件处理需要迭代整个请求列表

    72131

    改善C#程序建议4:C#中标准Dispose模式实现

    (析构GC.SuppressFinalize(this); } /// /// 不是必要,提供一个Close...提供终结全部意义在于:我们不能奢望类型调用者肯定会主动调用Dispose方法,基于终结会被垃圾回收调用这个特点,终结被用做资源释放补救措施。...在供垃圾回收调用隐式清理资源终结中,调用参数是false: ~SampleClass() { //必须为false Dispose...理解了这一点,我们就理解了为什么Dispose方法中,虚方法传入参数是true,而终结中,虚方法传入参数是false。...注意:我们提到了需要及时释放资源,却并没有进一步细说是否需要及时让引用等于null这一点。有一些人认为等于null可以帮助垃圾回收机制早点发现并标识对象是垃圾。其他人则认为这没有任何帮助。

    66420

    框架设计原则和规范(完)

    每次继承,父类字段都被继承,这样,继承树低端对象不可避免膨胀。 大多数字段并没有被修改,一直保持着构造时默认值,可否把这些字段从对象中剥离开来,减少对象体积。...不要显式在代码中设置依赖属性默认值,应该在元数据中设置默认值 F. 不要在属性访问中添加额外代码,而应该使用标准代码来访问静态字段 G.不要依赖书香来保存保密数据。...2) 如果类型持有需要开发人员显式释放类型,而且其本事没有终结方法,要为其实现基本Dispose模式并提供终结方法 3) 如果类本身并不持有非托管资源或可处置对象,但是它子类型却可能会持有,那么考虑为此基类实现基本...(this); } //此方法被IDisposable.Dispose方法所调用时disposing 为 true,所以应该检查资源是否还可用 //此方法被终结(垃圾回收机制)调用时 disposing...要先调用Dispose(true),然后再调用GC.SuppressFinalize(this) C.

    97740

    C#种Dispose和Close有什么不同

    以 SreamReader 为例,我们用 Reflector 来查看该类中 Close 方法,会发现它其实就是调用 Dispose 方法,并传入参数值 true ,因此如果我们不使用 Using 语句清理资源的话...(Using 语句块使用 Dispose 方法清理资源),手动调用 Close 方法效果基本和 Dispose 方法是一样。...这里有一点要提一下,使用 using 语句来调用 Dispose 方法,那么资源一定能被释放,如果希望在资源用完后马上释放的话,就必须手动调用 Close 方法。...其实我们去看 Dispose 方法和 Close 方法源码会发现, Dispose 比 Close 多了行 GC.SuppressFinalize(this) 代码,这行代码意思是通知 GC 当发现...SreamReader 无引用根时不要将它放入队列中,这样就避免了终结线程再次对它处理,这也减轻了终结线程负担。

    1.5K30

    C#.NET 中推荐 Dispose 模式实现

    不过前人准备了 Dispose 模式 供我们参考,最大程度避免这样坑。 ---- C#程序中 Dispose 方法,一旦被调用了该方法对象,虽然还没有垃圾回收,但实际已经不能再使用了。...简单说来,C# 中每一个类型都代表一种资源,而资源又分为两类: 托管资源:由 CLR 管理分配和释放资源,即由 CLR 里 new 出来对象; 非托管资源:不受 CLR 管理对象,Windows...内核对象,如文件、数据库连接、套接字、COM 对象等; 毫无例外地,如果我们类型使用到了非托管资源,或者需要显式释放托管资源,那么,就需要让类型继承接口 IDisposable。...这相当于是告诉调用者,该类型是需要显式释放资源,你需要调用 Dispose 方法。 不过,这一切并不这么简单,一个标准继承了 IDisposable 接口类型应该像下面这样去实现。.../// public void Close() { Dispose(); } /// /// 由终结调用以释放资源

    54810

    C++程序员转向C#时十大陷阱

    实际,C#中没有显式析构。 如果你在处理一个未受管制资源,当你用完时,你需要显式地释放那些资源。...资源隐式控制可通过提供一个Finalize方法(称为终结),当对象被销毁时,它将被垃圾收集调用终结只应该释放对象携带未受管制资源,而且也不应该引用别的对象。...因为使用终结要付出代价,所以,你只应该在需要方法实现(也就是说,在使用代价昂贵、未受管制资源方法实现)。...永远不要直接调用Finalize方法(除了在你自己类Finalize里调用基类Finalize方法外),垃圾收集会帮你调用它。 C#析构在句法酷似C++析构,但它们本质不同。...为了做到这一点,你应该调用静态方法GC.Suppressfinalize,并传入对象this指针,你Finalize方法就能够调用Dispose方法。

    2.1K10

    利用using与tryfinally来清理资源

    拥有非托管资源那些类型都实现了IDisposable接口,此外,还提供了finalizer(终结/终止化),以防用户忘记释放该资源。...你可以在用完这两个对象之后自己去调用它们Dispose方法,以修复此问题: 这么写在一般情况下是没有问题,但如果SQL命令在执行过程中抛出了异常,那么Dispose()就不会得到调用。...如果你拿不准某个对象是否应该放在using里面,那么可以采用稳妥一些写法,也就是假设该对象有可能会实现IDisposable接口,并将其包裹在刚才演示那种using结构中。...Dispose方法会调用GC.SuppressFinalize()以屏蔽finalizer,但Close方法通常不会调用,从而导致那些根本就不需要执行finalizer对象依然排在等待执行队列中。...从某种意义上说,C#程序资源管理起来要比C++困难,因为并没有一套确切finalization(终结/终止化)流程供开发者释放程序中每一份资源。

    71710
    领券