C ++ 11 Удалить метод переопределенияC++

Программы на C++. Форум разработчиков
Ответить
Anonymous
 C ++ 11 Удалить метод переопределения

Сообщение Anonymous »

Предисловие: < /b> < /p>

Это вопрос о передовых практиках, касающихся нового значения оператора удаления, представленного с C ++ 11, при применении к детскому классу, переопределяющемуся на основе унаследованного родителя. Случай цитируется, чтобы явно запретить вызова функции для определенных типов, где конверсии в противном случае были бы неявными, такими как пример из §8.4.3 из последнего стандартного проекта C ++ 11: < /p>

struct sometype {
sometype() = delete; // OK, but redundant
some_type(std::intmax_t) = delete;
some_type(double);
};
< /code>

Приведенный выше пример является ясным и целенаправленным. Тем не менее, следующий пример, в котором новый оператор переопределен и не позволил быть вызванным путем определения его как удаленного, заставил меня думать о других сценариях, которые я позже идентифицирует в разделе вопросов (пример ниже, из §8.4.3 стандартного черновика C ++ 11): < /p>

§ 8.4.3 из стандартного черновика C ++ 11): < /p>

struct sometype {
void *operator new(std::size_t) = delete;
void *operator new[](std::size_t) = delete;
};
sometype *p = new sometype; // error, deleted class operator new
sometype *q = new sometype[3]; // error, deleted class operator new[]
< /code>

Вопрос: < /b> < /p>

Посредством этой мысли о наследстве мне любопытно относительно мыслей других относительно того, является ли следующим примером использования явным и действительным использованием или если это неясное злоупотребление недавно добавленным функцией. Пожалуйста, предоставьте оправдание для вашего ответа (пример, который дает наиболее убедительные рассуждения, будет принято). В следующем примере, дизайн пытается сохранить две версии библиотеки (библиотека должна быть создана), имея вторую версию библиотеки наследства с первой. Идея состоит в том, чтобы позволить исправлениям ошибок или изменения, внесенные в первую версию библиотеки автоматически распространяться во вторую версию библиотеки, позволяя второй версии библиотеки сосредоточиться только на его отличиях от первой версии. Чтобы установить функцию во второй версии библиотеки, оператор Delete используется для запрета вызова для переопределенной функции: < /p>

class LibraryVersion1 {
public:
virtual void doSomething1() { /* does something */ }
// many other library methods
virtual void doSomethingN() { /* does something else */ }
};

class LibraryVersion2 : public LibraryVersion1 {
public:
// Deprecate the doSomething1 method by disallowing it from being called
virtual void doSomething1() override = delete;

// Add new method definitions
virtual void doSomethingElse() { /* does something else */ }
};
< /code>

Хотя я могу видеть много преимуществ для такого подхода, я думаю, что я больше склоняюсь к мысли, что это злоупотребление этой функцией. Основная ловушка, которую я вижу в приведенном выше примере, заключается в том, что классическая связь «is-a» наследства нарушается. Я прочитал много статей, которые настоятельно рекомендуют против любого использования наследования, чтобы выразить отношения «своего рода-is-a» и вместо этого использовать композицию с функциями обертки, чтобы четко определить отношения классов. Хотя следующий пример, часто вкратце, требуется больше усилий для реализации и обслуживания (относительно количества строк, записанных для этого фрагмента кода, поскольку каждая унаследованная функция, которая должна быть доступна, должна быть явно вызвана в качестве наследственного класса), использование удаления, как изображенное выше, очень похоже во многих отношениях: < /p>

.class LibraryVersion1 {
public:
virtual void doSomething1() { /* does something */ }
virtual void doSomething2() { /* does something */ }
// many other library methods
virtual void doSomethingN() { /* does something */ }
};

class LibraryVersion2 : private LibraryVersion1 {
// doSomething1 is inherited privately so other classes cannot call it
public:
// Explicitly state which functions have not been deprecated
using LibraryVersion1::doSomething2();
// ... using (many other library methods)
using LibraryVersion1::doSomethingN();

// Add new method definitions
virtual void doSomethingElse() { /* does something else */ }
};
< /code>

Заранее спасибо за ваши ответы и дальнейшее понимание этого потенциального использования удаления. < /p>

Подробнее здесь: https://stackoverflow.com/questions/143 ... den-method
Ответить

Быстрый ответ

Изменение регистра текста: 
Смайлики
:) :( :oops: :roll: :wink: :muza: :clever: :sorry: :angel: :read: *x)
Ещё смайлики…
   
К этому ответу прикреплено по крайней мере одно вложение.

Если вы не хотите добавлять вложения, оставьте поля пустыми.

Максимально разрешённый размер вложения: 15 МБ.

Вернуться в «C++»