코드 개발 시 클래스 내에 특정 멤버 변수가 있는지 확인해야 하는 경우가 많습니다. 이 정보는 멤버 이름이 서로 다른 다양한 클래스에서 작동하는 일반 알고리즘 템플릿 함수를 만드는 데 특히 유용합니다.
클래스가 템플릿 인수로 주어지면 목표는 클래스가 클래스인지 확인하는 것입니다. "x" 또는 "X"(또는 해당 대문자)로 표시되는 특정 멤버 변수를 보유합니다. 이 기능은 MFC의 CPoint 또는 GDI의 PointF 클래스와 같은 다양한 좌표계를 처리하는 일반 알고리즘의 생성을 용이하게 합니다.
이 문제를 해결하기 위해 다음과 같은 템플릿을 구현할 수 있습니다. 클래스를 템플릿 인수로 받아들이고 원하는 멤버 변수가 있는지 확인합니다. 연산자의 크기와 유형 특성을 활용하면 "x"와 "X" 멤버 변수의 존재를 구별할 수 있습니다.
다음은 구현 예입니다.
template<int> struct TT { typedef int type; }; template<class P> bool Check_x(P p, typename TT<sizeof(&P::x)>::type b = 0) { return true; } template<class P> bool Check_x(P p, typename TT<sizeof(&P::X)>::type b = 0) { return false; }
이 템플릿은 작동합니다. &P::x와 &P::X의 크기를 비교하여 어떤 멤버 변수가 존재하는지 확인합니다. &P::x가 존재하는 경우 템플릿은 true를 반환합니다. 그렇지 않으면 false를 반환합니다.
제안된 솔루션은 Visual Studio 및 GNU C와 모두 호환됩니다. 그러나 보다 보편적인 접근 방식을 위해 C 11 유형 특성을 사용하는 솔루션을 사용할 수 있습니다.
#include <type_traits> template <typename T, typename = int> struct HasX : std::false_type { }; template <typename T> struct HasX<T, decltype((void) T::x, 0)> : std::true_type { };
이 솔루션은 decltype 및 std::false_type 유형 특성을 활용하여 지정된 클래스에서 x의 존재를 감지합니다. . T에 x 멤버 변수가 있는 경우 HasX
HasX 템플릿의 사용을 보여주기 위해:
struct A { int x; }; struct B { int y; }; int main() { std::cout << std::boolalpha << HasX<A>::value << std::endl; // true std::cout << std::boolalpha << HasX<B>::value << std::endl; // false return 0; }