Вопрос по pointers, c++, templates, types – @Martin: ОК, спасибо!

7

могу определить шаблонный класс, который предоставляет целочисленную константу, представляющую «глубину» (указателя) типа, предоставленного в качестве входного аргумента шаблона? Например, если класс был названDepthследующее будет верно:

Depth<int ***>::value == 3
Depth<int>::value == 0

Ваш Ответ

2   ответа
14
template <typename T> 
struct pointer_depth_impl
{
    enum { value = 0 };
};

template <typename T>
struct pointer_depth_impl<T* const volatile>
{
    enum { value = pointer_depth_impl<T const volatile>::value + 1 };
};

template <typename T>
struct pointer_depth
{
    enum { value = pointer_depth_impl<T const volatile>::value };
};
@ Йоханнес: Хорошо; что избавляет от необходимости<type_traits>, Я не думаю, что это особенно хакерски; по крайней мере, не больше взлома, чем множество других черт типа :-) James McNellis
Спасибо Джеймс, и последнее предложение тоже очень полезно. user2023370
Хитрость в том, чтобы всегда проходитьT const volatile до следующей рекурсии, а затем только матч против<T *const volatile>, Это что-то вроде хака, но это поможет избежать написания специальных const / volatile версий. Johannes Schaub - litb
4

Это может быть сделано с помощью рекурсии.

template<typename T>
struct Depth
{
    enum { value = 0 };
};

template<typename T>
struct Depth<T*>
{
    enum { value = Depth<T>::value + 1 };
};
@ rafak: потому что перечислениям никогда не нужно выделять место для значения. В оригинальной версии @Khaled он использовал статическую переменную int. Хотя компилятор может в большинстве случаев оптимизировать требования к пространству, это не всегда так. Martin York
+1: но предпочитаю использовать enum для этого. Martin York
@Martin: Действительно, отредактировано. Khaled Nassar
@Martin: ОК, спасибо! rafak
@Martin: не могли бы вы объяснить, почему предпочитаете enum? rafak

Похожие вопросы