deniok: (Default)
[personal profile] deniok
LSP гласит:
 
Пусть q(t) некоторое свойство, выполняющееся для всех t типа T. Тогда, если S подтип T, то q(s) должно выполняться для всех s типа S.
 
Смысл в том, что при выполнении LSP мы можем подставлять (substitute) объект типа S вместо объекта типа T, при этом никакие свойства программы не будут нарушены, то есть программа останется корректной.
 
Что здесь понимается под свойствами? ИМХО, исключительно инварианты публичного интерфейса. То есть что-то типа
 
Для любых t типа StackOfX и x типа X последовательность операций
t.push(x);
t.pop();
возвращает t в исходное состояние.
 
А вот sizeof(T)=16 – это не свойство в том смысле, в котором оно вводится в LSP. Оно апеллирует к внешним по отношению к публичному интерфейсу вещам. То есть sizeof(S) может быть равно 24. Это к LSP не относится. Тут, вроде, говорят, что sizeof ковариантна по возвращаемому значению.
 
Свойства в LSP-ном смысле на традиционных ООП языках не задаются, а подразумеваются, синтаксиса не хватает. А в Хаскелле (GHC) они могут использоваться для оптимизаций, через rewrite rules
{-# RULES
        "myRule"   forall t x. pop (push t x) = t
 #-}
 
И кто теперь более ООП? :-)

ЗЫ: Вроде нигде не наврал.

Date: 2007-07-08 04:42 pm (UTC)
From: [identity profile] ivan-gandhi.livejournal.com
sizeof(T)=16 - это может быть частное наблюдаемое свойство Т, а может оказаться и частью декларируемого интерфейса.

Но в целом идея хороша. А то у меня были проблемы с этим "принципом".

Date: 2007-07-08 05:14 pm (UTC)
From: [identity profile] deni-ok.livejournal.com
> sizeof(T)=16 - это может быть частное наблюдаемое свойство Т, а может оказаться и частью декларируемого интерфейса.

Вот в том-то и дело, что частью интерфейса - вроде как не может. То есть, что такое 16 - в этой науке неведомо. Поинт в том, что для всех параметров функций интерфейса мы должны выставить квантор общности и написать некоторый закон, который для этого интерфейса (и только для него!) выполняется. То есть скажем для

interface INum {
INum INum::plus(INum a);
INum INum::minus(INum a);
}

есть закон

forall x y : x.plus(y).minus(y) == x

Нельзя при формулировании закона подразумевать существование чего-то кроме самого этого интерфейса. (Ну может быть какие-то другие интерфейсы - в эту сторону не думал).

Хотя возможно это мои домыслы. Посмотрим, что умные люди скажут.

Date: 2007-07-09 07:27 am (UTC)
From: [identity profile] deni-ok.livejournal.com
Просмотрел оригинальную статью http://citeseer.ist.psu.edu/liskov94family.html.
Похоже, что я погорячился насчёт

> То есть, что такое 16 - в этой науке неведомо

Тем не менее, если в T объявлено в качестве инварианта, что

forall t : t.someMethod() == 16

то в субтипе S этот инвариант тоже должен сохраняться s.someMethod() должен быть равен 16 и ничему другому.



Date: 2007-07-09 07:14 am (UTC)
From: [identity profile] rvp74.livejournal.com
{-# RULES
"myRule" forall t x. pop (push t x) = t
#-}

Ого! А ведь у меня была похожая идея для оптимизатора. Опередели! :)

Date: 2007-07-09 07:31 am (UTC)
From: [identity profile] deni-ok.livejournal.com
Используй на здоровье - это же публичный домен.
Могу дать полную и неограниченную лицензию :))
Копирайт можешь не писать (тем более, как я подозреваю, он не мой - слишком уж напрашивающаяся мысль)

Profile

deniok: (Default)
deniok

February 2022

S M T W T F S
  12345
6789101112
13141516171819
20212223 242526
2728     

Most Popular Tags

Style Credit

Expand Cut Tags

No cut tags
Page generated Jul. 29th, 2025 02:58 pm
Powered by Dreamwidth Studios