Здравствуйте, VoidEx, Вы писали:
VE>Но вот у Страуструпа точно есть про то, что окружность не надо наследовать от эллипса.
Ага, вот оно:
... in mathematics a circle is a kind
of an ellipse, but in most programs a circle should not be derived from an ellipse or an ellipse
derived from a circle. The oftenheard
arguments ‘‘because that’s the way it is in mathematics’’
and ‘‘because the representation of a circle is a subset of that of an ellipse’’ are not conclusive and
most often wrong. This is because for most programs, the key property of a circle is that it has a
center and a fixed distance to its perimeter. All behavior of a circle (all operations) must maintain
this property (invariant; §24.3.7.1).
Ну а если наши эллипс и круг (или прямоугольник и квадрат) неизменны, проблема поддержания инвариантов неизменными решается автоматически.
Здравствуйте, anton_t, Вы писали:
_>Воовбще-то множество кнопок шире, чем множество кнопок с с текстом.
Кнопок Button. Они не включают в себя ButtonWithText. Вы к понятию "кнопка" приписываете все кнопки, т.е. и всех ее наследников. Я имею ввиду именно сам базовый.
Button b (...); ни при каких условиях не будет ButtonWithText, так как у нее нету текста, а вот Rectangle rect(2, 2) не то, чтобы является Square(2), так еще и с избытком.
Я просто к тому, что квадрат — это частный случай прямоугольника, он ничего нового не вносит, он вносит только ограничения. А делается это наследованием видимо потому, что нормального способа это указать нет. Было бы неплохо что-то в таком виде:
Наследование здесь неествесственно, но используется в силу того, что нормальнее ничего нет.
Здравствуйте, FDSC, Вы писали:
FDS>Т.е. вы предлагаете наследовать прямоугольник от квадрата???
Нет, тут оно вообще неуместно, ни так, ни эдак. Ибо кроме extends надо еще и is, а прямоугольник квадратом в общем случае не является.
Здравствуйте, igna, Вы писали:
I>Ну а если наши эллипс и круг (или прямоугольник и квадрат) неизменны, проблема поддержания инвариантов неизменными решается автоматически.
Здравствуйте, VoidEx, Вы писали:
VE>Я просто к тому, что квадрат — это частный случай прямоугольника, он ничего нового не вносит, он вносит только ограничения.
Зато квадратная матрица с одной стороны ограничивая прямоугольную равенством количества строк и столбцов, с другой стороны добавляет возможность вычисления детерминанта. Можно наследовать? То есть, что на самом деле важно, расширение или "не сужение"?
Здравствуйте, VoidEx, Вы писали:
VE>Здравствуйте, anton_t, Вы писали:
_>>Воовбще-то множество кнопок шире, чем множество кнопок с с текстом. VE>Кнопок Button. Они не включают в себя ButtonWithText. Вы к понятию "кнопка" приписываете все кнопки, т.е. и всех ее наследников. Я имею ввиду именно сам базовый. VE>Button b (...); ни при каких условиях не будет ButtonWithText, так как у нее нету текста, а вот Rectangle rect(2, 2) не то, чтобы является Square(2), так еще и с избытком. VE>Я просто к тому, что квадрат — это частный случай прямоугольника, он ничего нового не вносит, он вносит только ограничения. А делается это наследованием видимо потому, что нормального способа это указать нет. Было бы неплохо что-то в таком виде:
VE>
Здравствуйте, igna, Вы писали:
I>Все-таки математика права, квадрат это прямоугольник, и в приведенном ниже коде (на Java) нет ничего неприличного:
Ох уж мне эти java-developer'ы... Ясное дело, Мейерса вы не читали. А между прочим, в книге "Эффективное использование C++" есть целый раздел, посвящённый тому, почему (в рамках философии C++) квадрат нельзя наследовать от прямоугольника. Коротко говоря, для него не выполняется LSP. Очень советую ознакомится. Если лень читать всю книжку, то подскажу: см. правило №35.
Здравствуйте, Tilir, Вы писали:
T>Здравствуйте, igna, Вы писали:
I>>Все-таки математика права, квадрат это прямоугольник, и в приведенном ниже коде (на Java) нет ничего неприличного:
T>Ох уж мне эти java-developer'ы... Ясное дело, Мейерса вы не читали. А между прочим, в книге "Эффективное использование C++" есть целый раздел, посвящённый тому, почему (в рамках философии C++) квадрат нельзя наследовать от прямоугольника. Коротко говоря, для него не выполняется LSP. Очень советую ознакомится. Если лень читать всю книжку, то подскажу: см. правило №35.
Вы бы лучше сказали, где взять книгу в электронном виде...
Здравствуйте, VoidEx, Вы писали:
VE>Здравствуйте, anton_t, Вы писали:
_>>Воовбще-то множество кнопок шире, чем множество кнопок с с текстом. VE>Кнопок Button. Они не включают в себя ButtonWithText. Вы к понятию "кнопка" приписываете все кнопки, т.е. и всех ее наследников. Я имею ввиду именно сам базовый. VE>Button b (...); ни при каких условиях не будет ButtonWithText, так как у нее нету текста, а вот Rectangle rect(2, 2) не то, чтобы является Square(2), так еще и с избытком.
FDS>>Т.е. вы предлагаете наследовать прямоугольник от квадрата??? VE>Нет, тут оно вообще неуместно, ни так, ни эдак. Ибо кроме extends надо еще и is, а прямоугольник квадратом в общем случае не является.
Следуя вашей логике, мы должны сказать, что кнопка с текстом ведь тоже не является кнопкой без текста, однако наследование у вас в данном случае возможно.
Здравствуйте, Tilir, Вы писали:
T>Ох уж мне эти java-developer'ы... Ясное дело, Мейерса вы не читали. А между прочим, в книге "Эффективное использование C++" есть целый раздел, посвящённый тому, почему (в рамках философии C++) квадрат нельзя наследовать от прямоугольника. Коротко говоря, для него не выполняется LSP. Очень советую ознакомится. Если лень читать всю книжку, то подскажу: см. правило №35.
Читал, читал. Вот кое-кому неплохо бы дочитать до конца сообщение, на которое он ответил, там всего-то несколько строк текста.
Речь о том, что нехорошие вещи при наследовании квадрата от прямоугольника происходят только, если эти квадрат и прямоугольник изменяемы. Именно этот случай чаще всего встречается в практике и рассматривается у Страуструпа, Мейерса и других. Но в случае неизменности квадрата и прямоугольника можно наследовать квадрат от прямоугольника, и никаких неприятностей я (пока?) не знаю. Независимо от полезности неизменных квадрата и прямоугольника в программировании, это наблюдение может оказаться полезным для объяснения того факта, что в математике квадрат является прямоугольником, а в программировании обычно нет.
P.S. Про Java. Это наверное была первая программа на Java, которую я показал на RSDN. Я вообще-то на C++ пишу, и в последнее время немного на C#. Независимо от того, некрасиво вот так вот о всех, кто программирует на Java. Сорри за нотации.
Здравствуйте, igna, Вы писали:
I>Речь о том, что нехорошие вещи при наследовании квадрата от прямоугольника происходят только, если эти квадрат и прямоугольник изменяемы. Именно этот случай чаще всего встречается в практике и рассматривается у Страуструпа, Мейерса и других. Но в случае неизменности квадрата и прямоугольника можно наследовать квадрат от прямоугольника, и никаких неприятностей я (пока?) не знаю.
Насколько я понимаю, главная проблема в том, что изменение величины сторон может привести к превращению квадрата в прямоугольник и наоборот. Выхода здесь два — или запретить менять стороны, или разрешить менять тип объекта "на лету", то есть использовать динамическую классификацию объектов.
Здравствуйте, AndreiF, Вы писали:
I>>Речь о том, что нехорошие вещи при наследовании квадрата от прямоугольника происходят только, если эти квадрат и прямоугольник изменяемы. Именно этот случай чаще всего встречается в практике и рассматривается у Страуструпа, Мейерса и других. Но в случае неизменности квадрата и прямоугольника можно наследовать квадрат от прямоугольника, и никаких неприятностей я (пока?) не знаю.
AF>Насколько я понимаю, главная проблема в том, что изменение величины сторон может привести к превращению квадрата в прямоугольник и наоборот. Выхода здесь два — или запретить менять стороны, или разрешить менять тип объекта "на лету", то есть использовать динамическую классификацию объектов.
Здравствуйте, igna, Вы писали:
I>Речь о том, что нехорошие вещи при наследовании квадрата от прямоугольника происходят только, если эти квадрат и прямоугольник изменяемы. Именно этот случай чаще всего встречается в практике и рассматривается у Страуструпа, Мейерса и других. Но в случае неизменности квадрата и прямоугольника можно наследовать квадрат от прямоугольника, и никаких неприятностей я (пока?) не знаю. Независимо от полезности неизменных квадрата и прямоугольника в программировании, это наблюдение может оказаться полезным для объяснения того факта, что в математике квадрат является прямоугольником, а в программировании обычно нет.
Ещё раз. Давайте сформулируем LSP:
Let q(x) be a property provable about objects x of type T. Then q(y) should be true for objects y of type S where S is a subtype of T.
Можем ли мы придумать для квадрата такое свойство, которого нет у прямоугольника? Да, можем — у квадрата все стороны равны. Для него это provable property Равенство сторон("Квадрат") = true. Очевидно, что существует такой прямоугольник (например со сторонами длиной 2 и 1) для которого Равенство сторон("Прямоугольник") = false => LSP не выполнен и тип "Квадрат" не является подтипом типа "Прямоугольник", что и требовалось доказать. Так называемый "здравый смысл" и "математическая интуиция" здесь ни при чём, это ООП.
I>P.S. Про Java. Это наверное была первая программа на Java, которую я показал на RSDN. Я вообще-то на C++ пишу, и в последнее время немного на C#. Независимо от того, некрасиво вот так вот о всех, кто программирует на Java. Сорри за нотации.
Формально я не сказал ничего плохого о Java-developer'ах, мы все их очень любим и уважаем. Поэтому я даже не буду извиняться перед вами, что сгоряча вас к ним причислил, хотя конечно следовало бы.
T>Let q(x) be a property provable about objects x of type T. Then q(y) should be true for objects y of type S where S is a subtype of T.
T>Можем ли мы придумать для квадрата такое свойство, которого нет у прямоугольника? Да, можем — у квадрата все стороны равны. Для него это provable property Равенство сторон("Квадрат") = true. Очевидно, что существует такой прямоугольник (например со сторонами длиной 2 и 1) для которого Равенство сторон("Прямоугольник") = false => LSP не выполнен и тип "Квадрат" не является подтипом типа "Прямоугольник", что и требовалось доказать.
Если в выделенном поменять "Квадрат" и "Прямоугольник" местами, то будет верно. Я серьезно, проверь свое доказательство.
T>Так называемый "здравый смысл" и "математическая интуиция" здесь ни при чём, это ООП.
Я говорю о неизменных фигурах, в объектах, которые их представляют нет никаких методов для их изменения, а ты: "изменение величины сторон может привести к превращению квадрата в прямоугольник". Эта возможность отсутствует в классах, которые я определил, посмотри первое сообщение.
Здравствуйте, Tilir, Вы писали:
T>Здравствуйте, igna, Вы писали:
I>>Речь о том, что нехорошие вещи при наследовании квадрата от прямоугольника происходят только, если эти квадрат и прямоугольник изменяемы. Именно этот случай чаще всего встречается в практике и рассматривается у Страуструпа, Мейерса и других. Но в случае неизменности квадрата и прямоугольника можно наследовать квадрат от прямоугольника, и никаких неприятностей я (пока?) не знаю. Независимо от полезности неизменных квадрата и прямоугольника в программировании, это наблюдение может оказаться полезным для объяснения того факта, что в математике квадрат является прямоугольником, а в программировании обычно нет.
T>Ещё раз. Давайте сформулируем LSP:
T>
T>Let q(x) be a property provable about objects x of type T. Then q(y) should be true for objects y of type S where S is a subtype of T.
А теперь то же самое на русском. По моему ты напутал с применением этого принципа в теореме
T>Формально я не сказал ничего плохого о Java-developer'ах, мы все их очень любим и уважаем. Поэтому я даже не буду извиняться перед вами, что сгоряча вас к ним причислил, хотя конечно следовало бы.
Следовало бы причислить или следовало бы извинится???
Формально, но вы же не в суде...
I>Все-таки математика права, квадрат это прямоугольник, и в приведенном ниже коде (на Java) I>нет ничего неприличного:
Объект характеризуется данными/состоянием и поведением. Причем, поведение можно поставить на первое место, так как данные по-хорошему, сокрыты. Таким образом, вопрос квадрат является прямоугольником или наоборот, зависит от контекста задачи.
В каких задачах квадраты отличаются поведением от прямоугольника? Если речь о графических или геометрических приложениям — то, вероятно, ни в каких (попробуйте привести контр-пример):
Отрисовываются они одинаково, заливаются одинаково, вращаются, масштабируются одинаково,
даже площадь вычисляется одинаково.
Скорее всего, нет никаких квадратов и прямоугольников, а есть выпуклые многоугольники, например.
Здравствуйте, igna, Вы писали:
I>Я говорю о неизменных фигурах, в объектах, которые их представляют нет никаких методов для их изменения, а ты: "изменение величины сторон может привести к превращению квадрата в прямоугольник". Эта возможность отсутствует в классах, которые я определил, посмотри первое сообщение.
А я говорил о возможных альтернативах решению делать объекты неизменяемыми