elpazarolt byte-ok és órajelciklusok

                                                  

vegyünk mondjuk egy egyszerű példát: hello world. természetesen nem egy gigászi bonyolultságú dologról van szó, de kezelni kell benne a belépést, kilépést, a képernyőt, konstans is van benne, szóval azért van mód elhibázni. dos alatt ez ha jól rémlik 20 byte körül van, amennyiben .com programot készít az ember. exe esetén ez akár 1kilobyte is lehet. volt pár éve randim valamelyik ingyenes delphi cuccal. igaz ugyan hogy azt igérte hogy crossplatform lesz a kódom, de 12 megát akkor is sokaltam érte. még akkor is, amikor azt mondjuk hogy nagyon olcsó a vinyó és a ram kapacitás.
de nem csak erről beszélek. térjünk csak vissza a dos-os részhez. első nekifutásra remélem mindenki aki felmérte és megértette a feladatot, és tudomásul vette, hogy a feladat ennyi és nem igényel fejlesztést a későbbiek során, sem supportot, az valahogy így fogalmazhatta meg a feladatot: string címének betöltése, operációs rendszer kiíró funkciójának meghívása, kilépés. azért van ott az a sok feltétel, mert mindig ezekre hivatkozik mindenki. két dologról szeretnék írni: oop és java.

oop. nagyon jól hangzik, és helyenként még működik is - hiszen bármilyen nyelven bármit le lehet kódolni - annyira egyszerű feladatokra használjuk. de azt azért nem árt tudni, hogy a végeredmény így vagy úgy de asm kód lesz. ahogy azt sem szabad figyelmen kívül hagyni hogy a egy utasitás címét nagyságrendekkel gyorsabban lehet felhasználni ha az már jóelőre (fordítási időben) ismert, mintsem különféle táblázatokból összeszedni. ahogy arról is jó tudni, hogy szép dolog az egyszerű forráskód, és a későbbi fejlesztést megkönnyítheti egy leszármazott osztály, de akár meg is nehezítheti, ha az öröklési fában nem tudjuk, hogy hol keressük az adott viselkedést kiváltó kódot. és végül, de nem utolsó sorban, az öröklési fa sokszor egyben hívási fa is. ki ne látott volna már stacktrace-t hosszú sorokon át ecsetelve hogy mi mindenen ment keresztül a dolog amig elhalálozott. minden egyes call (mert végülis ez lesz a hívásból, de a jmp is ilyen) utasítás meglehetősen költséges. egy távoli ugrás például pentium processzoron ~20 utasításnyi mikrokódot eredményez. nem lesz gyors a dolog. plusz ezen kívül az sem elhanyagolható, hogy ehhez jön még az esetleges privilégium ellenőrzés. mindezt azért cserébe hogy olvashatóbb (megkérdőjelezhető, inkább csak megszokás kérdése) legyen a forráskód? elpazarolt órajelciklusok.
java. értem én hogy cross-platform. meg azt is hogy gc. de könyörgöm, nem lehetne natív kódot fordítani? tehát azért, hogy egy hello-world fusson, csillagháborús készültségben kell állnia a jvm-nek, és elzabálnia a rendszererőforrások jelentős részét. én valahogy úgy képzelném, hogy adott a forráskód, és a fordítás során megmondom, hogy milyen rendszerre forduljon. de végülis senki jobbat tanácsolt. forduljon csak le egy bytekódra, álljon elő egy prebuild. majd az adott rendszeren már legyen rendszerspecifikus install folyamat, ami a prebuild részből előállítja a tényleges rendszerre optimalizált változatot. ekkor nem kell erőművet alátenni, csak azért hogy fusson esetleg majd egyszer egy kisalkalmazás.
sokan sokszor emlegetik, hogy az oop-ben írt kód már majdnem olyan gyors mint a natív társa, ahogy egy java-ban írt kód is majdnem olyan gyors (sőt,néha olyat is mondanak, hogy gyorsabb) mint a c-ben írt natív társa. hogy ennek az urban legendnek a végére járjunk, pár dolgot ismét nem árt, ha tudunk. egy virtuális gép, mint a jvm, tud futás időben optimalizálni a futó kódon. maradjunk annyiban, hoyg a lehetősége megvan, és bizonyos programmintákat felismer. tehát ha mondjuk van egy ciklus ami egymilliószor végrehajtódik, de az utasítástörzs nem képes kihatással lenni a ciklusmagon kívüli részre semmilyen formában, akkor ez a ciklus nemes egyszerűséggel ki is hagyható. például itt buknak meg azok akik arról zengenek ódákat, hogy a managelt nyelvek gyorsabbak, és mérnöki hozzáállásról tanúskodva mellékelnek egy ilyen hello world appot ami 1-10-100 millió végrehajtás alatt gyorsabb lesz mint a natív társa. a probléma az, hogy ilyen programszerkezetek - hacsaknem kifejezetten rossz programozó készítette - valós problémákat megoldó kódokban nemigen vannak. tehát ha van egy egymilliós ciklus, az azért van ott, hogy csináljon is valamit, és nem lehet úgy optimalizálni, hogy kihagyjuk :) ellenpéldaként ott a c nyelven megírt kód, ami pontosan azt csinálja amit beleírunk. nem hagy ki részeket időnként. és végül csak még egy apróság: ha tényleg olyan nagyon gyors, sőt néha gyorsabb is, akkor teljesítménykritikus részekhez miért használnak mai napig natív c-ben írt kódrészeket? :)
elpazarolt byte-ok vannak a merevlemezen, és elpazarolt órajelciklusok vannak a processzorban. mai napig ámulok és bámulok milyen szédületes teljesítményű gépek vannak, és mégis-mégis, alig gyorsabbak az alkalmazások. szerintem csak nem elég tökös a programozógárda, plusz igény sincs rá. tévedés: az egyszeri felhasználó, a megrendelő, bárki aki a kódot futtatni fogja, csak boldogabb lenne ha nem kéne új vasat vennie, vagy netalántán még egy vasat beüzemelnie, hogy azt a szédületes terhelést kibírja. régebben hallottam, hogy a google használ 386-os gépeket. biztos nem jávát futtatnak rajta, és nem is virtuális metódustáblákat kezelnek...