CA1816: GC.SuppressFinalize를 올바르게 호출하십시오.
속성 | 값 |
---|---|
규칙 ID | CA1816 |
제목 | GC.SuppressFinalize를 올바르게 호출하세요. |
범주 | 사용 현황 |
수정 사항이 주요 변경인지 여부 | 주요 변경 아님 |
.NET 9에서 기본적으로 사용 | 제안 사항 |
원인
이 규칙의 위반은 다음 항목에 의해 발생할 수 있습니다.
봉인되지 않은 클래스에서는 구현 IDisposable.Dispose 이며 호출 GC.SuppressFinalize하지 않는 메서드입니다.
구현 IDisposable.Dispose 되지 않고 호출 GC.SuppressFinalize하는 메서드입니다.
GC.SuppressFinalize를 호출하고 this(C#) 또는 Me(Visual Basic)가 아닌 다른 항목을 전달하는 메서드.
규칙 설명
IDisposable.Dispose 메서드를 사용하면 가비지 수집에 개체를 사용할 수 있게 되기 전에 언제든지 사용자가 리소스를 해제할 수 있습니다. IDisposable.Dispose 메서드가 호출되면 개체의 리소스를 해제합니다. 따라서 종료하지 않아도 됩니다. IDisposable.Dispose는 GC.SuppressFinalize를 호출하므로 가비지 수집기에서 개체의 종료자를 호출하지 않습니다.
종료자를 사용하는 파생 형식에서 IDisposable을 다시 구현하고 호출하지 않도록 하려면 종료자를 사용하지 않는 봉인되지 않은 형식에서 GC.SuppressFinalize를 호출해야 합니다.
위반 문제를 해결하는 방법
이 규칙의 위반 문제를 해결하려면
메서드가 Dispose의 구현인 경우 GC.SuppressFinalize에 호출을 추가합니다.
메서드가 Dispose의 구현이 아닌 경우 GC.SuppressFinalize에 대한 호출을 제거하거나 형식의 Dispose 구현으로 이동합니다.
this(C#) 또는 Me(Visual Basic)를 전달하도록 GC.SuppressFinalize에 대한 모든 호출을 변경합니다.
형식을 재정의할 수 없는 경우 다음으로
sealed
표시합니다.
경고를 표시하지 않는 경우
다른 개체의 수명을 제어하기 위해 의도적으로 사용하는 GC.SuppressFinalize 경우에만 이 규칙의 경고를 표시하지 않습니다. Dispose의 구현이 GC.SuppressFinalize를 호출하지 않는 경우 이 규칙의 경고를 표시해야 합니다. 이 경우 종료를 표시하지 않는 데 실패하면 성능이 저하되고 장점이 없습니다.
경고 표시 안 함
단일 위반만 표시하지 않으려면 원본 파일에 전처리기 지시문을 추가하여 규칙을 사용하지 않도록 설정한 후 다시 사용하도록 설정합니다.
#pragma warning disable CA1816
// The code that's violating the rule is on this line.
#pragma warning restore CA1816
파일, 폴더 또는 프로젝트에 대한 규칙을 사용하지 않도록 설정하려면 구성 파일에서 심각도를 none
으로 설정합니다.
[*.{cs,vb}]
dotnet_diagnostic.CA1816.severity = none
자세한 내용은 방법: 코드 분석 경고 표시 안 함을 참조하세요.
CA1816을 위반하는 예제
이 코드는 GC.SuppressFinalize를 호출하지만 this(C#) 또는 Me(Visual Basic)를 전달하지 않는 메서드를 보여 줍니다. 결과적으로 이 코드는 규칙 CA1816을 위반합니다.
Public Class DatabaseConnector
Implements IDisposable
Private _Connection As New SqlConnection
Public Sub Dispose() Implements IDisposable.Dispose
Dispose(True)
' Violates rules
GC.SuppressFinalize(True)
End Sub
Protected Overridable Sub Dispose(ByVal disposing As Boolean)
If disposing Then
If _Connection IsNot Nothing Then
_Connection.Dispose()
_Connection = Nothing
End If
End If
End Sub
End Class
public class DatabaseConnector : IDisposable
{
private SqlConnection? _Connection = new SqlConnection();
public void Dispose()
{
Dispose(true);
GC.SuppressFinalize(true); // Violates rule
}
protected virtual void Dispose(bool disposing)
{
if (disposing)
{
if (_Connection != null)
{
_Connection.Dispose();
_Connection = null;
}
}
}
}
CA1816을 충족하는 예제
이 예제에서는 this(C#) 또는 Me(Visual Basic)를 전달하여 GC.SuppressFinalize를 올바르게 호출하는 메서드를 보여 줍니다.
Public Class DatabaseConnector
Implements IDisposable
Private _Connection As New SqlConnection
Public Sub Dispose() Implements IDisposable.Dispose
Dispose(True)
GC.SuppressFinalize(Me)
End Sub
Protected Overridable Sub Dispose(ByVal disposing As Boolean)
If disposing Then
If _Connection IsNot Nothing Then
_Connection.Dispose()
_Connection = Nothing
End If
End If
End Sub
End Class
public class DatabaseConnector : IDisposable
{
private SqlConnection? _Connection = new SqlConnection();
public void Dispose()
{
Dispose(true);
GC.SuppressFinalize(this);
}
protected virtual void Dispose(bool disposing)
{
if (disposing)
{
if (_Connection != null)
{
_Connection.Dispose();
_Connection = null;
}
}
}
}
관련 규칙
참고 항목
.NET