Доступ к определениям типов предыдущих параметров шаблона в списке параметров шаблона? - PullRequest
1 голос
/ 13 сентября 2011

Мне интересно, возможно ли получить доступ к определениям типов, которые даны в качестве параметров предыдущего шаблона в более поздних параметрах шаблона в списке параметров шаблона, например:

#include <iostream>

template<typename V>
struct TypeHolder {
    typedef V value_type;
};

template<typename T, T::value_type v>
struct ValueHolder {
    const static typename T::value_type value = v;
};

int main() {
    typedef TypeHolder<int> IntTypeHolder;
    typedef ValueHolder<IntTypeHolder,5> Five;

    std::cout << Five::value << std::endl;

    return 0;
}

Когда я компилирую вышеуказанноеНапример, я получаю следующую ошибку:

damian @ damian-HP-EliteBook-8440p: ~ $ g ++ -o cpptest test.cpp
test.cpp: 8: 25: ошибка: 'T:: value_type 'не является типом

Это из-за неправильного синтаксиса или то, что я пытаюсь сделать, просто невозможно в c ++?

Ответы [ 4 ]

4 голосов
/ 13 сентября 2011

Это возможно .Вам не хватает ключевого слова typename.

 template<typename T, typename T::value_type v>
 struct ValueHolder { ^^^^^^^^
   ...

Вы должны сообщить компилятору, что T::value_type является типом. Демо .

1 голос
/ 13 сентября 2011

Попробуйте следующее:

template<typename T, typename T::value_type v>
struct ValueHolder {
    const static typename T::value_type value = v;
};

Вы должны добавить префикс "typename" к вашему T:value_type ... к сожалению, только потому, что value_type является typedef членом T, это не так.означает, что синтаксический анализатор C ++ может сказать.Это может быть фактический член статических данных, статический метод и т. Д. Поэтому при доступе к полностью определенным типам в других пространствах имен / классах их необходимо ставить с префиксом typename.

1 голос
/ 13 сентября 2011

Если вы префикс typename к параметру шаблона, он компилируется:

template<typename T, typename T::value_type v>
struct ValueHolder {
    const static typename T::value_type value = v;
}

Использование typename помогает компилятору понять, что в этом случае идентификатор value_type, на который ссылается пространство имен T::, является типом, а не функцией-членом или переменной.

0 голосов
/ 13 сентября 2011

Это из-за неправильного синтаксиса, что вы пытаетесь сделать с T::value_type v, чтобы получить правильное значение?

Тогда лучше использовать что-то вроде этого:

template<typename T>
struct ValueHolder {
    const static typename T::value_type value;
    ValueHolder(typename T::value_type v)
    {
        ValueHolder::value = v;
    }
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...