Предварительное объявление класса, вложенного в шаблон класса, это законно? - PullRequest
0 голосов
/ 17 февраля 2019

Является ли этот код допустимым для C++14/17?

template <class T1, class T2 >
class Foo
{
public:
    class sentry;
};

template <class T1,class T2 = int>
class Foo<T1,T2>::sentry
{
public:
    ~sentry() { }
};

Он компилируется с GCC 4.9.3 , но не работает с GCC 5.3 . Демонстрационная версия

Как это исправить для GCC 5.3 ?

1 Ответ

0 голосов
/ 17 февраля 2019

Это неправильно сформировано в соответствии с [temp.param] / 9 (выделено мной):

Аргумент шаблона по умолчанию является аргументом шаблона ([temp.arg]) указывается после = в шаблоне-параметре.Шаблонный аргумент по умолчанию может быть указан для любого типа параметра шаблона (тип, не тип, шаблон), который не является пакетом параметров шаблона ([temp.variadic]).Шаблонный аргумент по умолчанию может быть указан в объявлении шаблона. Параметр шаблона по умолчанию не должен указываться в списках параметров шаблона определения члена шаблона класса, который появляется за пределами класса члена. Параметр шаблона по умолчанию не должен указываться вобъявление шаблона класса друга.Если в объявлении шаблона функции-друга указан шаблон-аргумент по умолчанию, это объявление должно быть определением и должно быть единственным объявлением шаблона функции в модуле перевода.

sentry - член класса из Foo.Вы определили его вне класса, и поэтому он не может указывать аргумент по умолчанию для параметров Foo.Как правило, аргументы по умолчанию должны появляться только в объявлении основного шаблона.

Это правило также показывает, как ваш код может быть fixed :

template <class T1, class T2 = int>
class Foo
{
public:
    class sentry;
};

template <class T1,class T2>
class Foo<T1,T2>::sentry
{
public:
    ~sentry() { }
};
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...