Скопировать оператор присваивания в CRTP - gcc vs clang и msvc - PullRequest
0 голосов
/ 14 октября 2018

Следующий код (см. этот вопрос ) приводит к ошибке при компиляции с gcc 8.2, но принимается clang 7.0.0 и msvc 15.9.0 preview 3:

template<typename T>
struct B
{
    void operator=(const T&) { }
    void foo() { }
};

struct D : public B<D>
{
    using B<D>::operator=;
    using B<D>::foo;       // hidden by D::foo
    void foo() { }
};

int main()
{
    D d1, d2;
    d1 = d2;
    d1.foo();
    return 0;
}

Сообщение об ошибке , сгенерированное gcc :

<source>: In function 'int main()':
<source>:8:8: error: 'constexpr D& D::operator=(const D&)' cannot be overloaded with 'void B<T>::operator=(const T&) [with T = D]'
struct D : public B<D>
       ^
<source>:4:8: note: previous declaration 'void B<T>::operator=(const T&) [with T = D]'
  void operator=(const T&) { }
       ^~~~~~~~

У нас есть два оператора присваивания в D, первый из которых генерируется по умолчанию,второй вводится с using.Они имеют одинаковую подпись, поэтому перегрузка не выполняется.Но почему operator= из базового класса просто не скрыт классом в производном, как это происходит с foo() функцией-членом?

Что здесь происходит?Почему только GCC жалуется?Стоит ли жаловаться?

1 Ответ

0 голосов
/ 15 октября 2018

GCC здесь неверен: это , специально вызванный как ситуация, когда перегрузка не происходит.(Конечно, как и вы сказали, этого не происходит и с другими функциями-членами.)

...