|
Как нарушить принцип подстановки Лисков не привлекая внимания санитаров+
#40141012
![]() Ссылка:
Ссылка на сообщение:
Ссылка с названием темы:
Ссылка на профиль пользователя:
Ссылка на вложение:
|
||||||||||||||||
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
#18+
или 'арифметические вычисления и небезопасность универсального полифорфизма' проект arithmetic -- классы для для симплекс метода побочный эффект - разный результат в вычислениях (3 * 5) / 2 из-за разного округления в классе целых. Очередной пример нарушения принципа, который сводит к нулю пользу от универсального полиморфизма в обеих формах. Как от полиморфизма включения, так и от полиморфизма шаблонов. Есть две версии полиморфной функции: одна написана в терминах базового класса (каталог v2/PrgFunc.cs) Код: C# 1. 2. 3. 4.
Код: C# 1. 2. 3. 4. 5.
(int) out1; Но в классе целых деление переопределено так, что используется банковское округление и 15 : 2 дает 8 в результате обе версии полиморфной функции возвращают разные значения то ли 7, то ли 8 в зависимости от реального класса объектов. Это результат (надеюсь) всем известных проблем с условиями контра- и ко- вариантностью функционального типа метода. Эти условия всем разжевали Б.Мейер и Л.Карделли. для методов (функций) у которых множество объектов класса появляется с левой и с правой стороны функциональнй стрелки: f: domen(class) >< X -> domen(class) >< Y (для любых множеств X и Y) /* Стало понятно после формального анализа примера Мартина с наследованием квадратов и прямоугольников в статье Об отличиях между понятиями типа и класса https://www.researchgate.net/publication/344177979 , что условия в родительском классе можно задавать таким образом, что область определения и множество значений метода не будет меняться. Но к нарушению принципа подстановки будет приводить. */ В такую группу методов попадают все алгебраические операции: domen(class) >< domen(class) -> domen(class) То есть, функции для вычисления чего либо, скорее всего, нельзя писать полиморфные. /* в Переопределении сложения: небезопасное наследование в группе целых (https://www.researchgate.net/publication/366867037) приводился пример с проблемой на операциях вычитания, переход от полугруппы натуральных к группе целых) */ В частности, в этом примере, проблема заключается в операциях деления (переход от кольца целых к полю вещественных) Код: C# 1. 2. 3. 4.
Код: C# 1. 2. 3. 4.
в текущем примере полиморфные функции (function) не выбрасывает эксепшен, а тихонько начинает нарушать начальное требования -- для округления использовать отбрасывание дробной части. Это еще хуже, чем эксепшн. Классы integer и real были отлажены, что бы показать как плохо станет работать полиморфный симплекс метод. В текущем примере результат сем-восем еще такое дело, а неправильная оптимизация в симплекс методе явно будет нарушать начальную спецификацию при попытке использовать универсальный полиморфизм. Виды округления в Си Шапре согласно IEEE 754 -2019 Округление к ближайшему или четному (Банковское округление) Math.Round(v, MidpointRounding.ToEven) Округление к ближайшему или большему по модулю Math.Round(v, MidpointRounding.AwayFromZero) выбирается ближайшее целое число, а если их два - то, в первом случае -- четное, во втором -- большее по модулю. Округление отбрасыванием дробной части (int) v или Math.Truncate(v) Округление к положительной бесконечности из двух целых чисел выбирается большее: Math.Ceiling(v) или Math.Round(value, MidpointRounding.ToPositivetiveInfinity) Округление к отрицательной бесконечности из двух целых чисел выбирается меньшее: Math.Floor(v ) или Math.Round(value, MidpointRounding.ToNegativetiveInfinity) ... |
||||||||||||||||
:
Изменено: 26.06.2025, 19:24 - tchingiz
Нравится:
Не нравится:
|
||||||||||||||||
26.06.2025, 19:17 |
|
Как нарушить принцип подстановки Лисков не привлекая внимания санитаров+
|
|||
---|---|---|---|
#18+
В кольце целых не выполняется требование о наличии обратного элемента для каждого числа по делению. В отличие от поля, кольцо по делению полугруппа. Ссылка на раздел 6.1 Степанов А.А. От математики к обобщенному программированию. Текст из Степанова переписан на языке RAISE specification language scheme group = class
type
T
value
e : T -- identity element
,op : T >< T -> T -- group operation
,inverse : T -> T -- inverse operation
axiom
[associativity]
all x,y,z : T :- op (x, op(y,z)) is op (op(x,y), z)
,[identity]
all x : T :- (op (x, e) is x ) /\ (op (e, x) is x)
,[cancellation]
all x : T :- op (x, inverse(x)) is e
end В качестве тренировки.На практике условия из аксиом надо использовать для кодирования тестовых вариантов, как это делалось на примере аксиом метрического пространства https://resql.ru/forum/topic.php?fid=71&tid=2187231 ... |
|||
:
Нравится:
Не нравится:
|
|||
11.07.2025, 11:28 |
|
Как нарушить принцип подстановки Лисков не привлекая внимания санитаров+
#40141139
![]() Ссылка:
Ссылка на сообщение:
Ссылка с названием темы:
Ссылка на профиль пользователя:
Ссылка на вложение:
|
||||||||||||||||
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
#18+
Получилось хорошо. Как и ожидалось, обобщенная версия симплекс метода плохо находит максимум при целых числах. То есть, нарушает принцип подстановки. Не обобщенная версия на double лежит тут https://resql.ru/forum/topic.php?fid=71&tid=2187253. Надо вручную пересчитать. Пришлось использовать фабрику, вместо конструкторов с параметром вещественное число. Код: C# 1. 2. 3. 4. 5. 6. 7. 8. 9. 10. 11. 12. 13. 14. 15. 16. 17. 18. 19. 20. 21. 22. 23. 24. 25. 26. 27.
... |
||||||||||||||||
:
Изменено: Вчера, 16:51 - tchingiz
Нравится:
Не нравится:
|
||||||||||||||||
Вчера, 16:35 |
|
|
start [/forum/topic.php?fid=71&msg=40141139&tid=2187270]: |
0ms |
get settings: |
9ms |
get forum list: |
12ms |
check forum access: |
3ms |
check topic access: |
3ms |
track hit: |
60ms |
get topic data: |
14ms |
get forum data: |
4ms |
get page messages: |
45ms |
get tp. blocked users: |
2ms |
others: | 14ms |
total: | 166ms |
0 / 0 |