어떤 조건에 따라 컴파일 타임에 두 개의 타입 중 하나를 선택 가능하게 해주는 도구다.
C++ 표준에서는 std::conditional 으로 제공된다. (C++11 이상)
template <bool, typename, typename B> struct IF { using type = B; };
template <typename A, typename B> struct IF<true, A, B> { using type = A; };
template <bool Condition, typename A, typename B>
using IF = typename IF<Condition, A, B>::type;
위와 같이 템플릿 부분 특수화를 사용하여 구현된다. 동작 기준은 템플릿 인자 Condition이 결정한다.
템플릿 인자 Condition의 값이 true이면 A 타입이 선택되고, false이면 B 타입이 선택된다.
template <bool, typename, typename B> struct IF { using type = B; };
template <typename A, typename B> struct IF<true, A, B> { using type = A; };
template <bool Condition, typename A, typename B>
using IF = typename IF<Condition, A, B>::type;
int main() {
IF< true, int, float> val1;
IF<false, int, float> val2;
cout << typeid(val1).name() << endl;
cout << typeid(val2).name() << endl;
return 0;
}
위의 코드는 사용 예시로 실제 구현해보면 val1은 int형, val2는 float형을 출력한다.
사용시 주의할 점은 템플릿 인수 Condition는 컴파일 타임에 계산될 수 있어야 한다는 점이다.
Type Selection의 응용으로는 다음과 같이 static array 구현을 예로 들 수 있다.
template <typename T, unsigned int N>
class Array {
using sizeType = IF<(N <= 0xFF),
unsigned char, // if (N <= 255) -> uchar
IF<(N <= 0xFFFF),
unsigned short, // else if (N <= 65535) -> ushort
unsigned int // else -> uint
>
>;
public:
...
private:
T mData[N]{ };
sizeType mSize{ };
};
int main() {
Array<double, 25> arr1;
Array<float, 654> arr2;
Array<int, 88888> arr3;
return 0;
}
위 예시에서 Array 클래스 템플릿에 템플릿 인자로 데이터형 T, 크기 N으로 지정해주었다.
N의 크기에 따라서 멤버 변수 mSize의 형식을 최적화하여 사용되므로 사용되는 메모리를 조금이나마 더 줄일 수 있다.
동작은 만약 N <= 255 인 경우 unsigned char를, 256 <= N <= 65535 인 경우 unsigned short를,
그 외의 경우 (N > 65535) 에는 unsigned int형으로 mSize의 형식을 결정한다.
위 코드에서 중요하게 볼 점은 IF를 여러번 사용할 수 있다는 점이다.
실제로 위 예제를 구현하여 mSize의 형식을 살펴보면 의도한대로 잘 동작한다는 것을 알 수 있다.
Reference
'Programming > C++ Template' 카테고리의 다른 글
CRTP (Curiously Recurring Template Pattern) (0) | 2024.05.11 |
---|---|
Thin Template 기법 (0) | 2024.04.28 |