programing

GC는 언제 사용해야 합니까?Finalize()를 억제하시겠습니까?

stoneblock 2023. 5. 9. 22:03

GC는 언제 사용해야 합니까?Finalize()를 억제하시겠습니까?

에서 ?NET에서는 어떤 상황에서 사용해야 합니까?GC.SuppressFinalize()?

이 방법을 사용하면 어떤 이점이 있습니까?

SuppressFinalize파이널라이저가 있는 클래스에서만 호출해야 합니다. Collector에 'Garbage Collector(GC)'를 알려주고 this개체가 완전히 정리되었습니다.

되는 된천IDisposable피니셔가 있는 경우 패턴은 다음과 같습니다.

public class MyClass : IDisposable
{
    private bool disposed = false;

    protected virtual void Dispose(bool disposing)
    {
        if (!disposed)
        {
            if (disposing)
            {
                // called via myClass.Dispose(). 
                // OK to use any private object references
            }
            // Release unmanaged resources.
            // Set large fields to null.                
            disposed = true;
        }
    }

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

    ~MyClass() // the finalizer
    {
        Dispose(false);
    }
}

일반적으로 CLR은 객체가 생성될 때 피니시저로 객체를 탭합니다(생성 비용이 더 많이 듭니다). SuppressFinalizeGC에 개체가 제대로 정리되었으며 Finalizer 큐로 이동할 필요가 없음을 알립니다.그것은 C++ 파괴자처럼 보이지만, 그것처럼 행동하지 않습니다.

SuppressFinalize객체가 피니시저 대기열에서 대기하는 동안 오래 지속될 수 있기 때문에 최적화는 사소한 것이 아닙니다.전화하고 싶지 않습니다.SuppressFinalize다른 물건에 대해서는 주의해 주십시오.그것은 발생을 기다리고 있는 심각한 결함입니다.

설계 가이드라인은 객체가 구현되는 경우 피니시저가 필요하지 않음을 알려줍니다.IDisposable하지만 파이널라이저가 있다면 구현해야 합니다.IDisposable클래스의 결정론적 정리를 허용합니다.

대부분의 시간 동안 당신은 도망칠 수 있어야 합니다.IDisposable자원을 정리하기 위해.개체가 관리되지 않는 리소스를 보유하고 있고 이러한 리소스가 정리되었는지 확인해야 하는 경우에만 피니시저가 필요합니다.

합니다: 코더자고빌신디드버하기위그해추다가니합를피참니저.IDisposable은 자신들의 코가폐었테을스위클한래스기를 처분했습니다.IDisposable적반하장으로 반대하다

public void Dispose() // Implement IDisposable
{
    Dispose(true);
#if DEBUG
    GC.SuppressFinalize(this);
#endif
}

#if DEBUG
~MyClass() // the finalizer
{
    Dispose(false);
}
#endif

SupressFinalize시스템에 피니시저에서 수행되었을 작업이 이미 수행되었으므로 피니시저를 호출할 필요가 없습니다.에서.NET 서문

ID 일회용 인터페이스를 구현하는 개체는 ID 일회용에서 이 메서드를 호출할 수 있습니다.가비지 수집기가 개체를 호출하지 못하도록 하는 방법을 삭제합니다.필요 없는 개체에 대해 완료합니다.

의 임의의 적으로은대, 분부반일.Dispose()는 메드는호수있합니다야어할을 호출할 수 .GC.SupressFinalize()파이널라이저에서 정리될 모든 것을 정리해야 하기 때문입니다.

SupressFinalize는 시스템이 객체를 피니시저 스레드에 큐잉하지 않도록 최적화하는 기능입니다.하게 쓴 것Dispose()/finalizer는 전화가 있든 없든 제대로 작동해야 합니다.GC.SupressFinalize().

Dispose(true);
GC.SuppressFinalize(this);

개체에 finalizer가 있는 경우 .net은 finalizer 큐에 참조를 넣습니다.

전화가 왔으니깐Dispose(true)개체를 삭제하므로 이 작업을 수행하는 데 최종화 대기열이 필요하지 않습니다.

소콜GC.SuppressFinalize(this)최종화 대기열에서 참조를 제거합니다.

클래스 또는 클래스에서 파생된 모든 것이 피니시저를 사용하여 객체에 대한 마지막 라이브 참조를 보유할 수 있다면,GC.SuppressFinalize(this)또는GC.KeepAlive(this)해당 피니시저에 의해 악영향을 받을 수 있는 모든 작업 후에 개체에 대해 호출되어야 하며, 따라서 해당 작업이 완료될 때까지 피니시저가 실행되지 않도록 해야 합니다.

GC.KeepAlive()그리고.GC.SuppressFinalize(this)피니시저가 없는 클래스는 기본적으로 동일하며 피니시저가 있는 클래스는 일반적으로 호출해야 합니다.GC.SuppressFinalize(this)을 그서후자기능마을단지사다용계니의 합니다.Dispose()항상 필요한 것은 아니지만 틀리지는 않을 것입니다.

해당 메서드는 다음에서 호출해야 합니다.DisposeIDisposable가 결승점을 입니다.Dispose방법.

참조: GC.Suppress Finalize(개체) 메서드 - Microsoft Docs

언급URL : https://stackoverflow.com/questions/151051/when-should-i-use-gc-suppressfinalize