C#의 리플렉션은 런타임에 타입의 메타데이터를 검사할 수 있는 강력한 기능입니다. 이는 컴파일 시점에 클래스의 구조를 알지 못하더라도 속성, 메서드, 이벤트 및 기타 멤버를 조사할 수 있음을 의미합니다. 리플렉션을 이해하는 것은 플러그인 아키텍처나 사용자 정의 타입과 상호작용해야 하는 프레임워크와 같은 동적 동작이 필요한 시나리오에서 매우 중요합니다.
리플렉션의 주요 개념
메타데이터
- 메타데이터는 프로그램의 타입에 대한 데이터를 설명합니다. 클래스 이름, 메서드 시그니처, 속성 타입 및 속성 등의 정보를 포함합니다.
- 코드를 컴파일할 때, 이 메타데이터는 컴파일러가 생성한 어셈블리(DLL 또는 EXE 파일)에 저장됩니다.
타입
- C#에서는 모든 것이
System.Object에서 파생된 객체입니다. 리플렉션을 통해 이러한 객체를 동적으로 다룰 수 있습니다. - 리플렉션을 사용하여 타입의 인스턴스를 생성하고, 메서드를 호출하며, 필드나 속성에 직접 접근할 수 있습니다.
어셈블리
- 어셈블리는 배포 및 버전 관리를 위해 사용되는 컴파일된 코드 라이브러리입니다.
- 리플렉션을 통해
Assembly클래스가 제공하는 메서드를 사용하여 어셈블리를 동적으로 로드할 수 있습니다.
실용적인 예제
1. 타입 검사
리플렉션을 사용하여 타입에 대한 정보를 얻을 수 있습니다:
using System;
using System.Reflection;
public class SampleClass
{
public int MyProperty { get; set; }
public void MyMethod()
{
Console.WriteLine("Hello from MyMethod!");
}
}
class Program
{
static void Main(string[] args)
{
Type sampleType = typeof(SampleClass);
// 속성 가져오기
PropertyInfo[] properties = sampleType.GetProperties();
foreach (var prop in properties)
{
Console.WriteLine($"Property: {prop.Name}, Type: {prop.PropertyType}");
}
// 메서드 가져오기
MethodInfo[] methods = sampleType.GetMethods();
foreach (var method in methods)
{
Console.WriteLine($"Method: {method.Name}");
}
}
}
이 예제에서는 SampleClass라는 간단한 클래스를 정의하고, 하나의 속성과 하나의 메서드를 포함합니다. 리플렉션(typeof(SampleClass))을 사용하여 런타임에 속성과 메서드를 동적으로 검색합니다.
2. 동적 인스턴스 생성
리플렉션은 타입을 사전에 알지 못하더라도 클래스의 인스턴스를 생성할 수 있게 해줍니다:
public class AnotherSampleClass
{
public string Message { get; set; }
public AnotherSampleClass(string message)
{
Message = message;
}
public void ShowMessage()
{
Console.WriteLine(Message);
}
}
class Program
{
static void Main(string[] args)
{
Type anotherSampleType = typeof(AnotherSampleClass);
object instance = Activator.CreateInstance(anotherSampleType,
new object[] { "Hello from AnotherSample!" });
MethodInfo showMessageMethod = anotherSampleType.GetMethod("ShowMessage");
showMessageMethod.Invoke(instance,null); // 생성된 인스턴스에서 ShowMessage 메서드 호출.
}
}
이 예제에서는 AnotherSampleClass의 인스턴스를 Activator.CreateInstance를 사용하여 동적으로 생성합니다. 그런 다음 리플렉션을 사용하여 메서드를 호출합니다.
3. 속성과 함께 작업하기
속성은 클래스나 멤버에 대한 추가 메타데이터를 제공하며, 리플렉션을 통해 접근할 수 있습니다:
[AttributeUsage(AttributeTargets.Class)]
public class CustomAttribute : Attribute
{
public string Description { get; }
public CustomAttribute(string description) => Description = description;
}
[Custom("This is a custom attribute.")]
public class YetAnotherExample {}
class Program
{
static void Main(string[] args)
{
Type yetAnotherExampleType = typeof(YetAnotherExample);
var attributes = yetAnotherExampleType.GetCustomAttributes(false);
foreach (var attr in attributes)
{
if(attr is CustomAttribute customAttr)
{
Console.WriteLine($"Description: {customAttr.Description}");
}
}
}
}
여기서 CustomAttribute라는 사용자 정의 속성을 정의합니다. 이 속성은 YetAnotherExample 클래스에 적용됩니다. 리플렉션(GetCustomAttributes())을 사용하여 런타임에 설명을 검색하고 표시합니다.
결론
리플렉션은 C#에서 타입을 다룰 때 상당한 유연성을 제공합니다. 동적 타입 생성 및 실행 중 멤버 세부 정보 검사와 같은 많은 가능성을 열어주지만, 직접 코딩 방식에 비해 잠재적인 성능 영향을 고려하여 신중하게 사용해야 합니다. 리플렉션의 작동 방식을 이해하면 다양한 시나리오를 효과적으로 처리할 수 있는 더 적응력 있는 코드를 작성할 수 있습니다!
'프로그래밍 > C#' 카테고리의 다른 글
| C# 사용자 정의 속성: 코드에 메타데이터를 추가하는 강력한 도구 (0) | 2025.09.07 |
|---|---|
| C#의 사전 정의된 속성: 코드에 메타데이터를 추가하는 강력한 도구 (0) | 2025.09.06 |
| C# 리플렉션: 동적 프로그래밍의 강력한 도구 (1) | 2025.09.05 |
| C# 리플렉션: 동적 프로그래밍의 강력한 도구 (0) | 2025.09.05 |
| C# 비동기 프로그래밍에서 취소 토큰의 중요성과 활용법 (0) | 2025.09.04 |