Mis on virtuaalne pärand?

Virtuaalne pärand on pärimise tüüp, mille puhul ülemklassi rakendamine on puudulik ja objekti täielikuks määratlemiseks on vaja alamklassi. Seda tüüpi pärandit saab kasutada koos nii üksik- kui ka mitmekordse pärandiga, kuid kõige sagedamini kasutatakse seda mitme pärandi korral. Iga klass, mis pärib virtuaalsest baasklassist, muutub selle baasklassi otseseks alamklassiks. Virtuaalne baasklass võib kõigi oma meetodite rakendamisel tugineda alamklassile, kuid see ei ole nõue.

C++ on enimtuntud arvutikeel, mis kasutab virtuaalset pärandit. Virtuaalse pärandi deklareerimiseks C++ keeles kasutatakse märksõna “virtuaalne”. Nii ülemklass kui ka alamklass peavad deklareerima virtuaalsed meetodid märksõnaga “virtuaalne”. See annab C++ kompilaatorile teada, et ülemklass on mittetäielik ja selle lõpetamiseks peab ta hankima teavet alamklassist. Alamklassi kasutamine ülemklassi täitmiseks ei tähenda, et alamklassid kirjutaksid üksteist üle, kui neil on sama põhiklass, ja selle asemel hoolitseb C++ kompilaator selle eest, millised tükid iga objekti juurde kuuluvad.

Kuna virtuaalse pärimise jaoks on vaja virtuaalset baasklassi, ei saa C++ globaalseid funktsioone virtuaalseks deklareerida. Seda pärimistüüpi saab kasutada ainult objektorienteeritud programmeerimise (OOP) põhimõtete järgimisel. Selle põhjuseks on asjaolu, et globaalsed funktsioonid ei ole seotud kindla klassiga ja on seetõttu tavaliselt iseseisvad. Ilma ülem- ja alamklassita ei saa toimuda pärimist, seega välistavad globaalsed funktsioonid ja virtuaalne pärand üksteist. Globaalseid funktsioone saab teoreetiliselt kasutada virtuaalsete funktsioonide sees, kuid vastupidine ei pruugi alati toimida.

Virtuaalset pärandit kasutatakse paljude programmeerimisprobleemide lahendamiseks ja üks kõige kasulikumaid on mitmetähenduslikkuse lahendamine. Mitme pärimise korral võib olla põhiklass A, millel on kaks alamklassi, B ja C, ning seejärel klass D, mis pärineb mõlemast klassist B ja C. Seda mustrit nimetatakse tavaliselt “surmateemandiks”, sest kui klassid A, B-l ja C-l on sama meetodi juurutused, klassi D ei saa määrata, millist rakendust ta peaks kasutama. Virtuaalne pärimine lahendab selle probleemi, kuna iga klassi teostus jääb eraldiseisvaks ja seetõttu üheselt mõistetavaks. Seda eristamist haldavad spetsiaalsed sisemised objektid, mida nimetatakse virtuaalseteks tabeliteks (vtables), mis jälgivad iga objektitüüpi, kuid programmeerija ei pea neid tabeleid selgesõnaliselt manipuleerima, kuna need on keelde sisse ehitatud.