A CCC objektumrendszerében többszörös öröklődés van. Érdekelne, ki mit gondol, miért van az újabb nyelvekben (Jáva, C#, D) egyszeres öröklődés?
- 7423 megtekintés
Hozzászólások
egyrészt a diamond inheritance kiküszöbölése miatt
- A hozzászóláshoz be kell jelentkezni
Ez mi, "gyémánt öröklődés", vagy elírás? Egyébként kifejthetnéd részletesebben.
--
CCC3
- A hozzászóláshoz be kell jelentkezni
class a(object)
method hopp {||qout("hopp")}
class b(a)
class c(a)
class d(b,c)
function main()
dNew():hopp
Ez egy működő program, kiírja, hogy "hopp". A liststruct metódus kiírná, hogy a d osztály hopp metódusa az a osztályból öröklődik. Ha ez nem felel meg, egyszerűen felül lehet definiálni. Emiatt miért kéne lemondani a többszörös öröklődésről?
--
CCC3
- A hozzászóláshoz be kell jelentkezni
class a(object)
method hopp {||? "a.hopp"}
class b(a)
method hopp {||? "b.hopp"}
class c(a)
method hopp {||? "c.hopp"}
class d(b,c)
function main()
local d:=dNew()
d:hopp()
return NIL
eredménye: b.hopp
De ha: class d(c,b), akkor c.hopp az eredménye neki.
Hát, nemtom, jó ez vajon? Én még a büdös életbe' nem használtam többszörös öröklést CCC-ben, sose volt rá szükségem. Szerintem az mrev által találóan "tudálékos"-nak nevezett nyelvek sajátja az, hogy minden mindig mindenhol legyen objektum, sőt még objektumabb, és ezért jönnek elő ilyen gondok. Én általában csak azt teszem objektummá, ami "kéri", hogy azzá tegyem, így meg nem jön elő a kérdés. De szerintem mesterségesen megszüntetni az egyébként működő többszörös öröklést CCC-ben nem érdemes.
w
- A hozzászóláshoz be kell jelentkezni
Az igaz, hogy nem túl gyakori, de van példa a többszörös öröklésre. A GTK csatolóban pl. kiváló szolgálatot tesz. Eszem ágában sincs megszüntetni.
A téma szándékosan provokatív. Szerintem tudálékos emberek rosszul terveznek meg nyelveket, amit aztán programozók ezrei sínylenek. Egyébként van olyan nézet is, hogy a Jáva és a C++ szándékosan van elkúrva, nehogy a programozók kifogyjanak a munkából. Persze, ha levágom a lábamat, akkor nem lesz lúdtalpam. Ha megszüntetem a számtípusokat, akkor nem lesz nullával osztás, meg hasonlók. Kb. ennyi értelmét látom a "diamond inheritance"-tól való félelemnek. Más nézet?
--
CCC3
- A hozzászóláshoz be kell jelentkezni
Engem erdekelne valami technikai magyarazat is a diamond inheritancen kivul, konkretan vajon ez hol okozhat problemakat a gyakorlatban?
Azt azert ketlem, hogy barmit is direkt rosszul terveztek a C# es Java nyelveken. (Mar csak azert is, mert egy nyelv tervezese az nem annyibol all, hogy valami okostojas hasara ut es azt mondja, "na igy kb. jo lesz"..)
Nem lehet hogy inkabb a nehezebben felfoghato orokles helyett inkabb a tartalmazasra akarjak rabirni a fejlesztoket? Szerintem a Java-nak inkabb az a filozofiaja, hogy egy osztaly egy dologgal foglalkozzon. Ha pedig kombinalt tudasra van szukseg a feladatahoz, akkor implementalja a szukseges interfeszt, es az ala bedolgozo osztalyokat meg tartalmazza.
Gyakran az oroklesbe latunk bele olyan dolgokat, amikor a tartalmazas is tokeletesen jo, raadasul konnyebben emesztheto.
Egy nyelv elterjetseget nem csak az hatarozza meg szerintem, hogy mennyire expressziv, hanem az is, hogy mennyire konnyu hasznalni, mekkora a hibalehetoseg a hasznalat soran, mennyire konnyu hibat keresni, milyen a fejlesztokornyezet, stb.
Pl. vannak olyan meta-nyelvek, amiben konnyu szerrel lehet magat az osztaly,objektum, oroklodes, adatrejtes, stb. fogalmat definialni es onnantol kezdve az is egy objektumorientalt nyelv lesz, meg se elterjedt ez a tipusu megkozelites.. Talan pont azert, mert van egy hatar, amit egy atlagos fejleszto "ep esszel fel tud fogni" es szerintem a Java es C# bonyolultsaga ezt az optimumot celozza meg, nem pedig a maximalis expresszivitast.
- A hozzászóláshoz be kell jelentkezni
Python-ban is többszörös öröklődés van - ráadásul futásidőben változtatható (mint minden :) ) - MixIn osztályoknál (is) hasznos!
- A hozzászóláshoz be kell jelentkezni
1. Sokkal nehezebb forditot irni hozza. JIT compilerek idejen kulonosen fontos szempont.
Pl. ne feledd, hogy tobbszoros oroklodesnel az objektumban ket, elkulonitett helyet kell hagyni a ket kulonbozo osztalybol jovo adattagoknak (az atfedeseket elkerulendo). Igen am, de ez azt jelenti, hogy nem fix memoriacimen kezdodnek az adattagok, tehat kell egy kulon pointer-tabla a kulonbozo osokbol szarmazo adatteruletek cimzesehez. Es ha aztan az objektumot at-castolod egyik osere, akkor tudni kell, hogy melyik adattag-blokkot kell cimezni, tipustol fuggoen, ugye. Aztan ha = operatorral erteket adsz, kulon ugyelni kell a masolasnal. Es akkor meg csak az adattagokrol beszeltem, fuggvenyekrol nem.
Nem veletlen, hogy c++ forditokban meg ma is gyakori a hiba, mig a c forditok mar evtizedek ota stabilak.
Ha bovebben erdekel a tema, szerezz be egy jobb c++ konyvet (a strosoup-fele jo kezdet, vagy magyarul is van egy par, amelyik elmagyarazza, hogy milyen feature-t hogyan valosit meg a c++ fordito (stack/memoria-muveletek szintjen), na abbol meg fogod erteni, mennyire bonyi is a dolog.
2. Kezdo programozokat (akik minden programnyelv derekhadat adjak) megzavarja/nem ertik/stb, marpedig mindenki kezdokent indul egy uj nyelvvel. Ez egyebkent a hivatalos magyarazata a JAVA eseten a mindenfele c++ feature elhagyasanak.
3. Igazabol nagyon ritkan van ra szukseg. Tipikusan egyszerubb is megerteni/attekinteni az objektum-hierarchiat, ha hanyagolod a kerdest.
- A hozzászóláshoz be kell jelentkezni
"de ez azt jelenti, hogy nem fix memoriacimen kezdodnek az adattagok"
Emiatt van a GObject-ben is csak egyszeres öröklődés. De erre azt lehet mondani, hogy a készítő lusta volt rendesen megírni a többszörös öröklődést, ezért az eredmény funkcionálisan hiányos. Éppen a GTK-ban (GObject alkalmazás) bőven volna helye a többszörös öröklődésnek. Helyette interfészeket kényszerül használni.
Szerintem a C++-nak nem a többszörös öröklődés a baja, hanem az agyonbonyolított szabvány, amiben éppen Stroustrup a bűnös. Ez az ember 1000 oldalas C++ könyvet írt, ahelyett, hogy olyan nyelvet talált volna ki, amit 100 oldalon is le lehet írni.
Lehet, hogy egyes nyelvekben a többszörös öröklődés elbonyolítja a fordítót. A Python és a CCC nem ilyenek. A CCC fordítója 20 sorral sem volna rövidebb többszörös öröklődés nélkül. Tény, hogy fellépnek többértelműségek. Ezekre kell valamilyen egyszerű feloldási szabály. A Pythonban/CCC-ben depth first searching van, a Python az utolsónak talált definíciót tartja meg, a CCC az elsőt (mindegy). Minden olyan esetben, amikor ez a default feloldás nem felel meg, felüldefiniálással kell orvosolni a gondot.
--
CCC3
- A hozzászóláshoz be kell jelentkezni
Az szokták mondani, az interfészek részben pótolják a többszörös öröklődést. Csakhogy interfészek esetén ugyanúgy lehetnek ütköző metódusnevek, mint a többszörös öröklődésnél. Nem olyan ez, mint bicikli elől villamos elé ugrani?
--
CCC3
- A hozzászóláshoz be kell jelentkezni
Teljesen mas a java interfesz implementacioja. Ott ugye minden fugggveny virtualis. Tehat van egy objektumod, amirol tudod, hogy milyen interfeszeket valosit meg. Ha meghivjak vmelyiket, egyszeruen nev szerint kikeresi a virtualis fgv tablabol (strcmp+hash-el), es odaugrik. Azert ez a megoldas nem hasonlithato a c++-fele tobbszoros oroklodeshez. :)
- A hozzászóláshoz be kell jelentkezni
Van két interfészed. Akik kitalálták őket, nem tudtak egymásról és rólad. Véletlenül ütköző metódusnevek vannak bennük. Nem tudsz olyan osztályt írni, amelyik értelmesen implementálja mindkét interfészt. Tehát nincs elkerülve a többszörös öröklődés problémája.
--
CCC3
- A hozzászóláshoz be kell jelentkezni
Van ket osztalyod. Akik irtak oket, nem tudtak egymasrol es ugyanugy neveztek el oket. Akkor most dobjuk ki az egesz osztaly koncepciot?
No offence :)
- A hozzászóláshoz be kell jelentkezni
A dolgok legyenek minél egyszerűbbek. Egy egyszerűnek megtartott többszörös öröklődés, egyszerűbb, mint az egyszeres öröklődés plusz interfészek. A többszörös öröklődésnek kétségtelenül vannak problémái, ezt azonban nem lehet interfészekkel kikerülni, mert azoknál ugyanolyan ellentmondások lépnek fel.
A CCC-ben minden metódus public, minden öröklődés virtuális (C++ terminológiával), a többszörösen örökölt adattagok nem többszöröződnek. Amikor ezek a hibák nem javíthatók ki felüldefiniálással, akkor nem alkalmazható a többszörös öröklődés, hanem mást kell csinálni, pl. beágyazást. És akkor még mindig nem állunk rosszabbul, mint egy egyszeres öröklődésű nyelv, amiben ez a kiindulás. Szerintem ez egy praktikus álláspont.
A CCC-ben az objektum-metódus párosítás futásidőben történik, emiatt az interfész technika magától működik, anélkül, hogy ezért bármit tenni kéne. Az már igaz, hogy ezt a fordító nem képes előre ellenőrizni.
--
CCC3
- A hozzászóláshoz be kell jelentkezni
hory: koszonom, pont ilyen technikai ervekre kerdeztem ra fentebb! Jo latni, hogy valaki veszi a faradsagot es megprobalja leirni mik is az ervek pro es kontra.
- A hozzászóláshoz be kell jelentkezni
C++ nincs elszurva, egyszeruen mas szempontok alapjan terveztek.. a c az elodje, amit ugy terveztek, hogy amellett, hogy kenyelmes (az akkori nyelvekhez hasonlitva), eszmeletlen hatekony forditokat lehet hozza csinalni, ha valaki esszel kodol..
A c++ is ilyen: nem minden alapbol virtual, de ha valamihez az a jo, ele lehet irni..
Nem kenyszeriti ra senkire az alapelveit, nem kotelezo STL-t, template-eket, funktorokat, egyaltalan objektumokat hasznalni.. mindenki eldontheti, hogy meddig akar elmenni..
Hasznalhat akar fuggvenyre mutato pointert is, ha azt szeretne inkabb.. lehet tobbszorosen orokoltetni, de megvalosithato az interface megfeleloje.. mellesleg pont ez teszi bonyolultta, hogy a kenyelmi szintet es a hatekonysagot az ember maganak barmilyen szintre beloheti..
A Java-ban mindent az alapelvei ele helyeztek (peldaul ez a "minden ojjektum" hulyeseg).. kitalaltak egy nyelvet, irtak hozza forditot, futtato kornyezetet, meg mindent.. a tobbszoros orokles valoszinu meghaladta volna a kepessegeiket, ezert inkabb utolag kitalaltak egy ideologiat, hogy miert is nem kell..
kicsit olyan, mint amikor az egyik ovodas magyarazza a masiknak, hogy o direkt hasra akart esni, mert....
---------------------
"Monumentalis gondolataim manifesztacioi - melyek mondatok formajaban realizalodnak - limitalt mentalis kepessegeid szamara nem mind akceptabilisak. Dialogusunk kontinuitasa igy megszakad. Nem jon letre az argumentumok szintezise."
- A hozzászóláshoz be kell jelentkezni
hehe :)
en is C/C++ fan vagyok, de azert elismerem a java fejlesztoi elott, es nem hiszem,
h meghaladna a kepessegeiket implementalni a kivant featuret.
hm, jokis petproject lenne irni egy JIT compilert ;))
- A hozzászóláshoz be kell jelentkezni
ez az amit a fenti hozzaszolasomban probaltam elmagyarazni. Ez nem jo erv, hogy hat a Java-soknak meghaladja a kepessegeit, meg hogy ok nem gondoltak ra (biztos hulyek szegenyek..)
Ennyi erovel azt is mondhatnam, hogy a C a "legjobb nyelv". Hiszen C-ben is leimplementalhatok egy komplett osztaly-objektum-oroklodes stb. semat es ugyanazt (vagy akar meg tobbet is) meg tudok benne csinalni mint C++-ban.
A C es C++ nyelv semmivel sem erosebb, nem lehet nagyob kifejezo ereju kodot irni az egyikben mint a masikban..
Lehet hogy valaki C++ alatt kodol (es mivel eppen zseni programozo), ezert ki tudja hasznalni a C++ adta nehany extra lehetoseget es tenyleg jobb es szebb lesz mint Java-ban. Ellenben mondjuk egy atlagos tehetsegu programozo, lehet hogy jobban teszi ha C#-ban kodol, mert kevesebb hibalehetoseget hagy maganak, konnyebb a hibakereses, stb.
Azt az allitast, hogy egy atlagos tehetsegu programozo Java/C#-ban jobb kodot ir mint C++-ban, azt hiszem minden nyitott szemmel jaro fejleszto meg fogja erositeni.
Az egesz dolog arra emlekeztet, mint amikor meglat valaki egy suzukit az utcan es kijelenti, hogy hat igen, szegeny suzuki-nak csak olyan mernokei vannak, akik csak ezt tudtak csinalni, ennyi tellett a kepessegeikbol..
- A hozzászóláshoz be kell jelentkezni
de. a c++ nyelv annyival nagyobb kifejező erejű a c nyelvnél, hogy írhatsz benne olyan programot, ami fordítási időben fut, ld. template metaprogramozás. legjobb dolog.
- A hozzászóláshoz be kell jelentkezni