12.11.2026. ·
5 min

Programeri godinama koriste pogrešno pravilo za nasleđivanje klasa

HelloWorld
0
Programeri godinama koriste pogrešno pravilo za nasleđivanje klasa

Nasleđivanje klasa jedan je od osnovnih koncepata objektno orijentisanog programiranja, ali način na koji programeri odlučuju kada da ga koriste mogao bi da bude jedan od uzroka loše arhitekture softvera. Prema analizi objavljenoj 5. novembra, poznato pravilo da klasa treba da nasledi drugu klasu kada između njih postoji odnos „A je B“ često dovodi do pogrešnih odluka, jer zanemaruje najvažnije pitanje: da li nova klasa zaista može da ispuni sva obećanja koja daje osnovna klasa?

Ovaj pristup godinama se predaje na kursevima objektno orijentisanog programiranja. Ideja je jednostavna: ako je kvadrat pravougaonik, klasa Square treba da nasledi klasu Rectangle. Ako jedan objekat nešto poseduje, a nije to nešto, onda je primerenije koristiti kompoziciju.

Međutim, upravo takvo pojednostavljivanje može da napravi ozbiljne probleme u dizajnu softvera.

Problem sa pravilom „A je B“

Kritike nasleđivanja nisu nove. Autori knjige Design Patterns, poznati kao Gang of Four, još 1994. godine preporučili su da se prednost daje kompoziciji objekata u odnosu na nasleđivanje klasa. Sličan stav izneo je i Šon Parent u predavanju iz 2013. godine pod naslovom „Inheritance Is the Base Class of Evil“.

Uprkos tome, nasleđivanje je i dalje veoma zastupljeno, uključujući i novije projekte. Rezultat su često duboke hijerarhije klasa koje je teško održavati, osnovne klase koje programeri izbegavaju da menjaju i izvedene klase koje ne mogu da ispune očekivanja postavljena njihovim roditeljskim klasama.

Autor analize smatra da deo problema potiče upravo od poistovećivanja nasleđivanja sa prirodnim jezičkim odnosom „jeste“. Takva provera jeste jednostavna i intuitivna, ali činjenica da nešto pripada određenoj kategoriji ne znači da je dobra osnova za organizaciju programskog koda.

Jedan od najpoznatijih primera je odnos kvadrata i pravougaonika. U geometriji je kvadrat nesumnjivo posebna vrsta pravougaonika. Međutim, ako klasa Rectangle omogućava nezavisno menjanje širine i visine, klasa Square ne može da nasledi njeno ponašanje bez kršenja očekivanja.

Kada se promeni širina kvadrata, mora da se promeni i njegova visina. Isto važi i u obrnutom smeru. Zbog toga funkcija koja očekuje pravougaonik, menja mu širinu i visinu nezavisno i potom proverava površinu, neće raditi kako je očekivano ako dobije kvadrat.

Drugim rečima, geometrijska klasifikacija je tačna, ali programski odnos nasleđivanja nije.

Sličan problem postoji kod jediničnih vektora. Oni su posebna vrsta vektora čija je dužina uvek jedan. Ako klasa UnitVector3 nasledi klasu Vector3, automatski može da dobije operacije poput menjanja koordinata ili množenja, koje mogu da naruše to svojstvo. Izvedena klasa tada mora da blokira, menja ili drugačije obrađuje operacije koje bi korisnik osnovne klase očekivao da rade.

Tu je i primer pingvina. Biološki gledano, pingvin jeste ptica, ali ne može da leti. Ako osnovna klasa Bird sadrži funkciju fly(), klasa pingvina moraće da je implementira tako da prijavi grešku ili ne uradi ništa. Ni jedno ni drugo nije ponašanje koje bi korisnik takve funkcije očekivao.

Pokušaj rešavanja ovog problema može da dovede do dodatnih međuklasa i interfejsa, poput FlyingBird ili FlyingAnimal, čime se jednostavna hijerarhija pretvara u komplikovanu kombinaciju različitih sposobnosti.

Liskov princip supstitucije kao bolji kriterijum

Postoji precizniji način da se proceni da li jedna klasa treba da nasledi drugu. Reč je o Liskov principu supstitucije (Liskov Substitution Principle, LSP), jednom od osnovnih principa objektno orijentisanog dizajna.

Njegova suština je da objekat izvedene klase mora moći da zameni objekat osnovne klase, a da pritom ne naruši očekivano ponašanje programa.

U praksi to znači da izvedena klasa ne sme da postavlja strože preduslove za izvršavanje operacija, da oslabi njihove rezultate ili da naruši nepromenljiva svojstva koja garantuje osnovna klasa.

Ovaj princip omogućava da se problem kvadrata i pravougaonika sagleda kroz konkretno ponašanje njihovih funkcija, umesto kroz geometrijsku definiciju. Isto važi i za jedinične vektore i pingvine.

Zanimljivo je da ni nasleđivanje isključivo interfejsa, bez preuzimanja postojeće implementacije, ne rešava automatski problem. Autor kao primer navodi Java biblioteku, u kojoj metoda Collections.unmodifiableList vraća listu koja ne dozvoljava izmene, iako interfejs List sadrži metodu add(). Pozivanje te metode u ovom slučaju izaziva izuzetak UnsupportedOperationException.

Takav dizajn pokazuje da problem nije samo u deljenju implementacije između klasa. Čak i kada se nasleđuju samo interfejsi, pogrešno postavljena očekivanja o tome šta određeni tip može da radi mogu da dovedu do nepraktičnih rešenja.

Nasleđivanje nije loše, ali mora da ima opravdanje

To, međutim, ne znači da nasleđivanje treba izbegavati po svaku cenu. Ono stvara snažnu povezanost između klasa, što može biti korisno kada je opravdano očekivati da će se one razvijati zajedno i deliti iste ugovore i ograničenja.

Problem nastaje kada su povezani koncepti u stvarnom svetu automatski predstavljeni kao povezane klase u programu. Menadžer jeste zaposleni, zaposleni je osoba, a osoba je pravno lice. Međutim, takve klasifikacije same po sebi ne predstavljaju dobar razlog za formiranje duboke hijerarhije nasleđivanja.

Pre nego što jednu klasu povežu sa drugom putem nasleđivanja, programeri bi zato trebalo da provere da li izvedena klasa može da ispuni sva obećanja osnovne, da li osnovna klasa može da zadrži svoje postojeće ugovore i da li je opravdano da se te dve klase menjaju zajedno.

Ako su odgovori potvrdni, nasleđivanje može biti sasvim dobro rešenje, uključujući i preuzimanje postojeće implementacije.

Ključna poruka analize je da pitanje „Da li je A B?“ nije dovoljno dobar kriterijum za donošenje tehničke odluke. Mnogo je važnije proveriti kako se klase ponašaju, koje ugovore garantuju i da li jedna zaista može da zameni drugu bez iznenađenja za ostatak programa.

Oceni tekst

0

0 komentara

Iz ove kategorije

Svi članci sa Bloga

Slični poslovi

Povezane kompanije po tagovima