наследование от шаблона класса с аргументом по умолчанию

Я создал класс, похожий на этот. Ключ в том, что у него есть основной аргумент шаблона плюс базовый класс шаблона со значением по умолчанию. Существует также конструктор шаблонных копий …

struct default_base{};

template <typename T, typename TBase=default_base>
class some_class : public TBase{
public:
some_class(){}
template <typename U, typename UBase>
some_class(const some_class<U,UBase>& u){
T t(U());
}
};int main(){
some_class<int> a;
return 0;
}

Я получаю эту досадно расплывчатую ошибку компилятора и не смог обнаружить мою ошибку … поэтому мой вопрос — что на самом деле не так? Я использую GCC 4.8.1.

g++ -O0 -g3 -Wall -c -fmessage-length=0 -o "src\\stuff.o" "..\\src\\stuff.cpp"..\src\stuff.cpp: In constructor 'some_class<T, TBase>::some_class(const some_class<U,     UBase>&)':
..\src\stuff.cpp:87:10: error: default argument for template parameter for class     enclosing 'T t(U (*)())'
T t(U());
^
..\src\stuff.cpp: In function 'int main()':
..\src\stuff.cpp:104:16: error: wrong number of template arguments (1, should be 2)
some_class<int> a;
^
..\src\stuff.cpp:82:7: error: provided for 'template<class T, class TBase> class   some_class'
class some_class : public TBase{
^
..\src\stuff.cpp:104:19: error: invalid type in declaration before ';' token
some_class<int> a;

Edit: Spot на ответы, ура 🙂 Даже если я все еще думаю, что это должно скомпилировать … это компилируется …

template <typename T>
struct some_other_class{
some_other_class(){}
template <typename U>
some_other_class(){
T t(U());
}
};

1

Решение

T t(U());

Это так называемый «самый неприятный анализ». Это объявление функции, которое возвращает T и принимает нулевую функцию, которая возвращает U в качестве параметра. Представить:

typedef U nullary_function_return_U();
T t(nullary_function_return_U /*param_name*/)
{
return T;
}

Вы можете обойти это, добавив скобки:

T t( (U()) );

Или в C ++ 11 вы можете использовать единый синтаксис инициализации:

T t{U{}};

Самое неприятное на самом деле. Сообщение об ошибке действительно ужасно и независимо от самого неприятного разбора, оно должно действительно скомпилироваться, не так ли?

Я проверил на GCC 4.8.1 — Ошибка, Clang 3.4 — ОК, MSVC2010 — ОК. Я сократил это до наименьшего случая, который вызывает ошибку на НКУ:

template <typename = int>
struct Foo
{
Foo()
{
int t(int()); // Error
}
};

int main()
{
int t(int()); // OK
Foo<> a; // Error
}

Это похоже на ошибку GCC. Я сделал отчет GCC Bugzilla.


редактировать:

Паоло Карлини 2014-07-07 14:11:14 UTC
Это уже фиксированная магистраль и 4.9.1. Я добавляю тестовый пример и закрываю ошибку.

7

Другие решения

Вы действительно хотите объявить функцию с именем t, взяв функцию возврата U в качестве аргумента и возвращения T? При устранении неоднозначности объявления объявлять переменную t используя, например,

T t{U()};

Кажется, GCC доволен декарацией.

1

По вопросам рекламы [email protected]