Is-a
A tudásreprezentációban, objektumorientált programozásban és tervezésben (lásd objektumorientált program architektúra ), az-egy (is_a vagy az-egy) egy absztrakciók közötti alárendelt kapcsolat (pl típusok, osztályok ), ahol az egyik osztály, A, egy másik osztály, B, alosztálya (és így B superclass-a az A-nak). Más szavakkal, az A típus a B típus altípusa, amikor A specifikációja magában foglalja B specifikációját. Vagyis bármely olyan objektum (vagy osztály), amely megfelel az A specifikációjának, szintén megfelel a B specifikációnak, mert B specifikációja gyengébb.[1]
Az az-egy kapcsolat ellentétben áll a van-egy ( has_a vagy a ) kapcsolattal a típusok (osztályok) között; összekeverni a van-egy és az-egy kapcsolatokat gyakori hiba, amikor modellt szerkesztünk (pl számítógépes program ) az objektum és az alárendelt valós kapcsolatáról. Az az-egy viszony ellentétben állhat az objektumok (példányok) és a típusok (osztályok) közötti instance-of kapcsolattal is: lásd " típus-token megkülönböztetés " és " típus-token kapcsolatok ".[2]
Összegezve a kapcsolatokat, van
- hiperonim - hyponym ( szupertípus – altípus) kapcsolatok a típusok (osztályok) között, meghatározva egy taxonómiai hierarchiát, ahol
- szubupupciós viszony esetén: a hiponím (altípus, alosztály) type-of ( az-egy ) összefüggésben van hiperonimájával (szupertípus, szuperosztály);
- holonym - meronym (teljes / entitás / konténer-rész / alkotóelem / tag) típusok (osztályok) közötti kapcsolatok, amelyek egy birtokló hierarchiát határoznak meg, ahol
- összesítő (vagyis tulajdonjog nélküli) kapcsolat esetén:
- egy (teljes) holonymnak van-egy kapcsolata van a meronimával (részleges),
- összetétel (azaz tulajdonosi) kapcsolat esetén:
- egy meronima (alkotóelem) part-of kapcsolata vana a holonimjával (entitásával),
- az elszigetelés [3] kapcsolatához:
- egy meronym (tag) van egy member-of kapcsolata van a holonimjával ( konténer );
- összesítő (vagyis tulajdonjog nélküli) kapcsolat esetén:
- concept-object (típus-token) kapcsolat van a típusok (osztályok) és az objektumok (példányok) között, ha
- egy tokennek (objektumnak) egy instance-of kapcsolata van a típusával (osztályával).
Példák az altípusokra
[szerkesztés]A subtyping lehetővé teszi, hogy egy adott típust váltson egy másik típus vagy absztrakció. A subtyping létrehoz egy az-egy kapcsolatot az altípus és néhány meglévő absztrakció között, vagy explicit vagy implicit módon,nyelvi támogatástól függően.A kapcsolatot ki lehet fejezni örökléssel, azon nyelvek esetén, amik támogatják azt, mint subtyping mechanism.
C ++
[szerkesztés]Az alábbi C ++ kód létrehoz egy kifejezett öröklés kapcsolatot a B és A osztályok között, amelyben B jelentése egyaránt egy alosztálya, és egy altípusa A-nak, és fel lehet használni, mint egy A-t, ahol egy B van megadva (egy referenciával, egy mutatóval vagy objectként ).
class A
{ public:
void DoSomethingALike() const {}
};
class B : public A
{ public:
void DoSomethingBLike() const {}
};
void UseAnA(A const& some_A)
{
some_A.DoSomethingALike();
}
void SomeFunc()
{
B b;
UseAnA(b); // b can be substituted for an A.
}
Python
[szerkesztés]A következő python kódot hoz létre explicit öröklés közötti kapcsolat osztályok B és A B ahol egyszerre alosztály és altípusa A és fel lehet használni, mint egy A ahol a B van szükség.
class A:
def do_something_a_like(self):
pass
class B(A):
def do_something_b_like(self):
pass
def use_an_a(some_a):
some_a.do_something_a_like()
def some_func():
b = B()
use_an_a(b) # b can be substituted for an A.
A következő példa szerint a type(a) "normál", és az type(type(a)) egy metatípus. Míg eloszlatva az összes típusnak azonos metatípusa van ( PyType_Type, amely szintén a saját metatípusa), ez nem követelmény. A klasszikus osztályok típusa, az úgynevezett types. ClassType különálló metatípusnak is tekinthető.[5]
>>> a = 0
>>> type(a)
<type 'int'>
>>> type(type(a))
<type 'type'>
>>> type(type(type(a)))
<type 'type'>
>>> type(type(type(type(a))))
<type 'type'>
Java
[szerkesztés]Java-ban az az-egy kapcsolat egy osztály vagy interfész típusparamétereinek és egy másik típusparamétereinek kapcsolatát a kiterjesztések és az implementációs záradékok határozzák meg.
A Gyűjtemény osztályok használatával az ArrayList <E> megvalósítja az List<E>-t , és az <E> Lista kiterjeszti a Collection<E>-t . Tehát az ArrayList <String> a <String> lista altípusa, amely a Collection<String> altípusa. Az altípus-kapcsolat automatikusan megmarad a típusok között. Amikor meghatározunk egy interfészt, a PayloadList-t, amely egyesíti a P típusú általános opcionális értéket az egyes elemekkel, akkor annak deklarálása a következőképpen nézhet ki:
interface PayloadList<E, P> extends List<E> {
void setPayload(int index, P val);
...
}
A PayloadList következő paraméterei a List<String> altípusai:
PayloadList<String, String>
PayloadList<String, Integer>
PayloadList<String, Exception>
Liskov-helyettesítési elv
[szerkesztés]A Liskov-helyettesítési elv magyarázatot ad egy tulajdonságra: "Ha minden S típusú o1 objektumhoz van egy T típusú o2 objektum, oly módon, hogy a T-vel definiált valamennyi P programnál P viselkedése nem változik, ha o1 helyett o2 van, akkor S "a T altípusa" .[6] A következő példa az LSP megsértését mutatja.
void DrawShape(const Shape& s)
{
if (typeid(s) == typeid(Square))
DrawSquare(static_cast<Square&>(s));
else if (typeid(s) == typeid(Circle))
DrawCircle(static_cast<Circle&>(s));
}
Nyilvánvaló, hogy a DrawShape funkció rosszul formázva van. A Shape osztály minden derivatív osztályáról tudnia kell. Ezenkívül meg kell változtatni, amikor a Shape új alosztálya jön létre. Objektumorientált tervezésben ezt a struktúrát tekintjük anatémának. Íme egy finomabb példa az LSP megsértésére:
class Rectangle
{
public:
void SetWidth(double w) { itsWidth = w; }
void SetHeight(double h) { itsHeight = h; }
double GetHeight() const { return itsHeight; }
double GetWidth() const { return itsWidth; }
private:
double itsWidth;
double itsHeight;
};
Ez jól működik, de a négyzet osztálynál, amely a Téglalap osztályt örököli, megsérti az LSP-t, annak ellenére, hogy fennáll az az-egy kapcsolat a Téglalap és a Négyzet között. Mert a négyzet téglalap alakú. A következő példa felülírja a probléma megoldásához két funkciót, a Setwidth és a SetHeight funkciókat. A kód javítása azonban azt jelenti, hogy a tervezés hibás.
public class Square : Rectangle
{
public:
virtual void SetWidth(double w);
virtual void SetHeight(double h);
};
void Square::SetWidth(double w)
{
Rectangle::SetWidth(w);
Rectangle::SetHeight(w);
}
void Square::SetHeight(double h)
{
Rectangle::SetHeight(h);
Rectangle::SetWidth(h);
}
A következő példa szerint a g függvény csak a téglalap osztályra működik, de a négyzetre nem, és így megsértették a nyitott-zárt alapelvet.
void g(Rectangle& r)
{
r.SetWidth(5);
r.SetHeight(4);
assert(r.GetWidth() * r.GetHeight()) == 20);
}
Kapcsolódó szócikkek
[szerkesztés]Megjegyzések
[szerkesztés]- ↑ Subtypes and Subclasses. MIT OCW. (Hozzáférés: 2012. október 2.)
- ↑ Type–token relations
- ↑ See also Containment (computer programming).
- ↑ Mitchell, John. 10 "Concepts in object-oriented languages", Concepts in programming language. Cambridge, UK: Cambridge University Press, 287. o. (2002). ISBN 0-521-78098-5
- ↑ Guido van Rossum: Subtyping Built-in Types. (Hozzáférés: 2012. október 2.)
- ↑ Liskov, Barbara. Data Abstraction and Hierarchy. SIGPLAN Notices (1988. május 1.)
Irodalom
[szerkesztés]- Ronald J. Brachman ; Mi az AZ-EGY és mi nem. A szemantikai hálózatok taxonómiai kapcsolatának elemzése . IEEE Computer, 16 (10); 1983. október
- Jean-Luc Hainaut, Jean-Marc Hick, Vincent Englebert, Jean Henrard, Didier Roland: Az AZ-EGY kapcsolatok végrehajtásának megértése . ER 1996: 42-57