문제

수동으로 정리해야 하는 리소스는 무엇입니까? 씨# 그렇게 하지 않으면 어떤 결과가 발생합니까?

예를 들어 다음 코드가 있다고 가정해 보겠습니다.

myBrush = new System.Drawing.SolidBrush(System.Drawing.Color.Black);
// Use Brush

dispose 메서드를 사용하여 브러시를 정리하지 않으면 가비지 수집기가 프로그램 종료 시 사용된 메모리를 해제한다고 가정합니까?이 올바른지?

수동으로 정리하려면 어떤 다른 리소스가 필요합니까?

도움이 되었습니까?

해결책

기술적으로 IDisposable에서 상속된 모든 항목은 사전에 삭제되어야 합니다.'using' 문을 사용하면 작업을 더 쉽게 할 수 있습니다.

http://msdn.microsoft.com/en-us/library/yh598w02.aspx

때로는 문서 샘플 코드와 도구에서 생성된 코드(예:비주얼 스튜디오).

IDisposable의 좋은 점은 다음과 같은 기능을 제공한다는 것입니다. 적극적으로 기본 관리되지 않는 리소스를 해제합니다.때로는 정말로 이 작업을 수행하고 싶을 때가 있습니다. 예를 들어 네트워크 연결 및 파일 리소스를 생각해 보세요.

다른 팁

무언가를 폐기하지 않으면 가비지 수집기가 코드에 해당 항목에 대한 참조가 더 이상 없다는 것을 알게 되면 정리됩니다. 이는 일정 시간이 걸릴 수 있습니다.그러한 경우에는 실제로 중요하지 않지만 열린 파일의 경우 아마도 그럴 것입니다.

일반적으로 Dispose 메서드가 있는 경우 작업이 끝나면 이를 호출해야 합니다. 또는 가능하면 Dispose 메서드로 마무리해야 합니다. using 성명:

using (SolidBrush myBrush = new System.Drawing.SolidBrush(System.Drawing.Color.Black))
{
    // use myBrush
}
  • 내부 Windows 데이터 구조를 처리합니다.
  • 데이터베이스 연결.
  • 파일 핸들.
  • 네트워크 연결.
  • COM/OLE 참조.

목록은 계속됩니다.

전화하는 것이 중요합니다. Dispose 또는 더 나은 방법은 다음을 사용하는 것입니다. using 무늬.

using (SolidBrush myBrush = new System.Drawing.SolidBrush(System.Drawing.Color.Black))
{
    // use myBrush
}

무언가를 폐기하지 않으면 가비지 수집기가 해당 항목에 대한 참조가 더 이상 없음을 확인하면 일정 시간이 지나면 정리됩니다.

의 경우 System.Drawing.Brush, Windows는 모든 프로그램이 핸들을 해제할 때까지 메모리에 로드된 브러시에 대한 내부 창 구조를 유지합니다.

IDisposable을 삭제하지 않을 경우 발생하는 결과는 미미한 성능 저하부터 앱 충돌까지 다양할 수 있습니다.

귀하의 예에서 Brush 개체는 원할 때 GC에 의해 정리됩니다.그러나 귀하의 프로그램은 이전에 정리하여 얻을 수 있었던 추가 메모리의 이점을 얻지 못했을 것입니다.Brush 개체를 많이 사용하는 경우 이는 중요해질 수 있습니다.GC는 또한 세대별 가비지 수집기이기 때문에 개체가 오래 사용되지 않은 경우 개체를 정리하는 데 더 효율적입니다.

반면에 데이터베이스 연결 개체를 삭제하지 않으면 풀링된 데이터베이스 연결이 매우 빠르게 부족해져 앱이 중단될 수 있습니다.

사용하거나

using (new DisposableThing...
{
    ...
}

또는 개체의 수명 동안 IDisposable에 대한 참조를 유지해야 하는 경우 개체에 IDisposable을 구현하고 IDisposable의 Dispose 메서드를 호출합니다.

class MyClass : IDisposable
{
    private IDisposable disposableThing;

    public void DoStuffThatRequiresHavingAReferenceToDisposableThing() { ... }

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

    protected virtual void Dispose(bool disposing)
    //etc... (see IDisposable on msdn)

}

일반적으로 IDisposable을 구현하는 모든 항목은 사용 중인 리소스를 일시 중지하고 조사하게 만듭니다.

GC는 메모리 부족이 있을 때만 발생하므로 시기를 예측할 수 없습니다.AppDomain을 언로드하면 확실히 트리거됩니다.

다른 사람들이 말했듯이 사용하는 것이 당신의 친구입니다.나는 썼다 이 블로그 항목 가장 중요한 부분을 제외하여 오류가 발생하기 쉬운 매우 간단한 방법으로 IDisposable을 구현하는 방법에 대해 설명합니다.

특정 개체가 일회용 리소스인지 기억나지 않을 때 사용하는 방법은 Intellisense가 나를 확인하도록 선언 뒤에 ".Dispose"(최대!)를 입력하는 것입니다.

MemoryStream ms = new MemoryStream().Dispose

그런 다음 .Dispose를 삭제하고 using() 지시문을 사용합니다.

using(MemoryStream ms = new MemoryStream())
{
  ...
}

글쎄, 리소스의 관리형 버전을 사용하고 Windows API를 직접 호출하지 않는 한 괜찮습니다."창 핸들"(및 기타 많은 것)은 개체가 아니라 .NET에 알려져 있으므로 얻은 것이 IntPtr인 경우에만 리소스를 삭제/파괴해야 하는 것에 대해 걱정하십시오.

그런데 리소스(다른 .NET 개체와 마찬가지로)는 현재 컨텍스트를 떠나자마자 수집을 위해 플래그가 지정되므로 메서드 내에서 Brush를 생성하는 경우 이를 종료할 때 플래그가 지정됩니다.

관리되는 경우(예:프레임워크의 일부) 걱정할 필요가 없습니다.IDisposable을 구현하는 경우에는 using 차단하다.

관리되지 않는 리소스를 사용하려면 종료자에 대해 읽어보고 IDisposable을 직접 구현해야 합니다.

아래에 더 자세한 내용이 있습니다 이 질문

먼저 프로그램 종료 시 프로세스에서 사용하는 메모리가 프로세스 자체와 함께 제거된다고 가정할 수 있습니다.

in.net에서 dispose 또는 소멸자를 사용하는 동안 GC에서 dispose 함수가 호출되는 시간은 비결정적이라는 점을 이해해야 합니다.그렇기 때문에 명시적으로 dispose를 사용하거나 호출하는 것이 권장됩니다.

파일과 같은 리소스를 사용하는 경우 .net의 관리되는 세계 외부에 있는 세마포 및 리소스와 같은 메모리 개체를 해제해야 합니다.

예를 들어 SolidBrush는 GDI 개체이고 .net 세계 외부에 있기 때문에 폐기해야 합니다.

가비지 수집기는 프로그램 종료 시에만 해제되지 않으며, 그렇지 않으면 실제로 유용하지 않습니다(어쨌거나 괜찮은/최근 OS에서는 프로세스가 종료될 때 모든 메모리가 OS에 의해 자동으로 정리됩니다).

C/C++에 비해 C#의 가장 큰 장점 중 하나는 할당된 개체를 해제하는 데 신경 쓸 필요가 없다는 것입니다(적어도 대부분의 경우).gc는 런타임이 결정할 때 이를 수행합니다(다양한 전략 시기/방법).

많은 리소스가 GC에서 처리되지 않습니다.파일, 스레드 관련 자원(잠금), 네트워크 연결 등...

주의해야 할 곳 중 하나는 개체입니다. 바라보다 GC에 비해 작지만...예를 들어 SharePoint API에서 SPWeb 개체는 GC에 관한 한 작은 공간을 차지하므로 수집 우선 순위가 낮지만 실제로는 GC가 차지하지 않는 많은 메모리(힙에서)를 차지했습니다. 에 대해 모른다.예를 들어, 이러한 것들을 모두 처리하는 경우 몇 가지 재미있는 메모리 문제에 직면하게 될 것입니다. 항상 using 또는 dispose를 사용하는 것을 기억하세요!

개체를 해제해야 하는 리소스를 "보유"하는 것으로 생각하기보다는 개체가 개체보다 오래 지속될 무언가(아마도 컴퓨터 외부!)를 변경한 것으로 생각하는 것이 더 낫습니다. 실행 취소되거나 "정리"되지는 않지만 객체만 정리할 수 있습니다.이러한 변경은 일반적으로 "사용 중"으로 표시된 풀의 구체적인 개체 형태를 취하지만 정확한 형태는 중요하지 않습니다.중요한 것은 변경 사항을 취소해야 하며 개체가 이를 수행하는 데 필요한 정보를 보유하고 있다는 것입니다.

가비지 수집기는 관리되는 모든 리소스를 처리합니다.귀하의 예에서는 가비지 수집기가 결정하면 브러시가 정리되며, 이는 브러시에 대한 마지막 참조가 더 이상 유효하지 않은 후 얼마 후에 발생합니다.

수동으로 정리해야 하는 특정 사항이 있지만 이는 DLL 호출과 같이 관리되지 않는 소스에서 검색된 포인터이므로 .NET Framework 내에서는 이 처리가 필요하지 않습니다.

라이센스 : CC-BY-SA ~와 함께 속성
제휴하지 않습니다 StackOverflow
scroll top