Разработка Сообщества разработчиков ПО с открытым исходным кодом.
Как вы узнали, перед T :: size_type необходимо указать префикс typename. Почему?
Из "Шаблоны C ++: Полное руководство"
Определение языка решает эту проблему, указывая, что в общем случае зависимое полное имя не обозначает тип, если это имя не с префиксом ключевого слова typename.
... Префикс typename для имени является обязательным , когда имя
- появляется в шаблоне
- квалифицировано
- не используется в качестве списка спецификаций базового класса или в списке инициализаций членов, вводящих определение конструктора
- Зависит от параметра шаблона
Кроме того, префикс typename не разрешен , если не выполняются по крайней мере первые три предыдущих условия.
Вам нужно добавить typename.
То есть
template <typename T>
T invertible(T const& container, typename T::size_type startIndex, typename T::size_type endIndex);
Не имея никакой информации о вашем типе T, компилятор должен знать, что T :: size_type обозначает тип.
From стандарт, раздел 14.6.2:
Предполагается, что имя, используемое в объявлении или определении шаблона и зависящее от параметра-шаблона, не именует тип, если только применимый поиск по имени не обнаружит имя типа или имя уточнено по ключевому слову
typename
.
Поскольку во время синтаксического анализа объявления шаблона значение T неизвестно. Таким образом, компилятор не знает, существует ли вообще T :: size_type. Например, он может относиться к статической переменной. Когда вы позже используете шаблон, T, конечно, известен, но ошибка возникает раньше. И, пожалуйста, используйте что-нибудь менее древнее, чем gcc 4.0.1; -)
Изменить: если вы скомпилируете его с -fpermissive, компилятор, вероятно, проглотит ваш код, но он выдаст предупреждение.
Оказалось, что мне нужно указать, что T :: size_type - это имя типа. Почему?
template <typename T>
T invertible(T const& container, typename T::size_type startIndex, typename T::size_type endIndex);