c# ( generic, 박싱, 언박싱)

JHO·2024년 7월 24일
0

c#스터디

목록 보기
9/9
post-thumbnail

1. obejct

1-1 object, 박싱, 언박싱

  • 참조 타입
int a = 5;
object b = a;
  • object는 참조 타입이기 때문에, a의 데이터를 복사해 힙 메모리에 할당.
    -> 값 타입에서 참조 타입으로 변환하는 과정이 박싱!
int c = (int)b;
  • b의 데이터를 복사해 스택 메모리에 할당.
    -> 참조 타입에서 값 타입으로 변환하는 과정이 언박싱!

1-2. object 주의할 점

int a = 5;
object b = a;
float c = (int)b;
  • int 타입으로 선언되었던 타입이 object타입으로 변화하고 나서(박싱)float 타입과 같은 다른 타입으로 변화하면 런타임 에러 발생!
  • 박싱과 언박싱이 발생하는 상황은 프로그램 성능 상 좋지는 않지만, 그렇다고 아예 사용을 안할수는 없으니 상황을 정확히 이해하고 최소한으로 사용해야함.

2. generic


2-1. generic

  • 다양항 형식을 적용하기 위해 사용.
  • 제네릭은 박싱/언박싱 단계를 거치지 않고 형식을 조정하므로 성능이 향상되고, 컴파일 단계에서 올바른 데이터 형식이 적용되므로 형식 안정성이 보장.
    -> 제네릭은 컴파일 시점에 데이터 형식이 결정되고, 런타임 시점에 인스턴스화된 제네릭 형식에 대한 정보가 유지.
  • 또한, object 형식을 사용할때보다 간결하고, 직관적인 코드 작성이 가능.
public static void Swap<T>(ref T a, ref T b)
{
   T temp = a;
   a = b;
   b = temp;
}
  • 위와 같은 식으로 사용하기 가능.

2-2. where T

  • where T를 사용해 원하는 형식만 적용 가능.
public static void Swap<T>(ref T a, ref T b) where T:struct
{
   T temp = a;
   a = b;
   b = temp;
}
  • 위의 경우 구조체형, 즉 값 타입만 적용 가능.
  • where T: class 로 사용하는 경우 참조 타입만 적용 가능.
public class MyClass<T, U> where T : class where U : struct
{
    private T _first;
    private U _second;
}
static void Main(string[] args)
{
    MyClass<a, b> myClass = new MyClass<a, b>();
}
  • 이런식으로도 사용 가능

2-3. c++ Templete과의 차이점

#include <iostream>
// 템플릿 함수 정의
template <typename T>
T add(T a, T b) {
    return a + b;
}
int main() {
    int result1 = add<int>(3, 5); // int형 템플릿 함수 사용
    double result2 = add<double>(1.5, 2.5); // double형 템플릿 함수 사용
    std::cout << "Result 1: " << result1 << std::endl;
    std::cout << "Result 2: " << result2 << std::endl;
    return 0;
}
public class Example<T>
{
    public T GetValue(T input)
    {
        // 구체적인 처리 로직
        return input;
    }
}
class Program
{
    static void Main()
    {
        Example<int> intExample = new Example<int>();
        int result1 = intExample.GetValue(123);
        Example<string> stringExample = new Example<string>();
        string result2 = stringExample.GetValue("Hello");
        // Example<double> doubleExample = new Example<double>();
        // double result3 = doubleExample.GetValue("Not a double"); // 컴파일 에러: 타입 불일치
        Console.WriteLine("Result 1: " + result1);
        Console.WriteLine("Result 2: " + result2);
    }
}
  • Templete은 원하는 타입의 함수를 그때그때 만들어야하지만, Generic은 모든 타입을 받는 함수를 만든다.
  • C++의 Templete과의 차이점의 경우,
  • 타입 결정 시점은 템플릿은 컴파일 타임에, 제네릭은 런타임에 결정.
  • 타입 안전성의 경우, 둘다 컴파일 타임에 타입 검사가 이루어지지만, 제네릭의 경우 where T를 사용해 미리 타입 검증이 가능하여 런타임 전에 안전성을 보장해준다.
profile
개발노트

0개의 댓글