Из техничких разлога садржај читалишта можете пратити искључиво на латиници.

Kako da razmišljate kao programer? (3.)

Jedna od najvećih grešaka koju stalno susrećem u svetu tehnologije je problem kratkoročne koristi nasuprot dugoročnih rešenja. Previše često programer koristi prečice: ono što je najlakše, uzima alatke koje već ima, ili tehnologije koje su trenutno popularne. Te vrste kompromisa dovode do sistema koji su sklepani, postaju zastareli kôd koji je skoro nemoguć za održavanje, neefikasan i spor.

 

Nedavno smo na sajtu TechRepublic imali veliku diskusiju o tome da li programer treba da proba da predvidi buduće potrebe svojih korisnika. Deo te diskusije se vrteo oko pitanja do koje mere bi kôd trebalo da bude generički, što se svodi na kompromis između trajanja početnog razvijanja i fleksibilnosti na duže staze. Na primer, u nekom objektno orijentisanom jeziku, programer može svaki deo koda da primeni kao klasu i zanemari verovatnoću da se u budućnosti pokaže da je bilo bolje da je ta klasa bila interfejs. S druge strane, pisati sve kao interfejs koji će da koristi samo jedna klasa značilo bi uložiti neverovatnu količinu vremena u proces razvoja. Granica je zaista uska.

Jedno mesto gde kompromisi nisu dozvoljeni je oblast čitljivosti koda. Bez obzira na tesne rokove završetka, ne postoji nikakvo opravdanje da se promenljive zovu “a”, “b” i “c”. Ti dodatni bajtovi neće probiti budžet. U stvari, svakom polovinom sekunde koju uštedite kod pisanja koda, vi verovatno dodajete tri minuta na vreme traženja grešaka.

Još jedna prečica koja kasnije stvara velike probleme je neefikasno korišćenje biblioteka. Toliko je primamljivo da se učita milion biblioteka samo zbog jedne funkcije koja bi lako mogla da se kopira. Konačni rezultat je aplikacija koja je loša za skaliranje. Uzmite onu malu aplikaciju za Veb koju ste napisali, onu sa milion zavisnosti, pa pogledajte koliko memorije koristi. “Ali, ona koristi svega nekoliko stotina kilobajta!” kažete vi. Pomnožite to sa onim što se dešava ako vaša aplikacija iznenada postane jako popularna, ili se upotrebljava u okruženju velike korporacije. Pomnožite “koristi svega nekoliko stotina kilobajta” sa 70.000 istovremenih korisnika, i iznenada sistemski administrator lupa na vaša vrata i viče “preraditi kôd”. Ako učitavate celu biblioteku samo zbog jednog ili dva mala pozivanja, upitajte se da li vam to zaista treba i da li biste mogli isto da napišete u okviru svog postojećeg koda. To je jedna dobra osobina otvorenog izvora, možete da uzmete ono što vam treba a sve drugo da ostavite.

XML (i slične tehnologije) predstavljaju još jednu zamku. Znam da sam već dosadan sa tim gunđanjem o XML-u, ali moram da ponavljam kad ga izgleda svi toliko vole. XML se lako koristi, u većini glavnih jezika sada ima mnogo biblioteka i ugrađenih funkcija za rad sa njim. Ali on je besmisleno neefikasan, i kao transportni mehanizam, i u pogledu korišćenja sistemskih resursa. XML uspeva da sastavi najgoru kombinaciju; on troši zilion više bajtova na graničnike od standardnog ravnog fajla, a koristi strukturu stabla koja kod raščlanjivanja teško opterećuje procesor (u najmanju ruku). Ako ste za tabelarne podatke posegnuli za XML šemom, razmislite još malo. Uzmite dvadeset minuta potrebnih da se napiše i testira stvaralačka procedura za podatke razdvojene zarezima (CSV creator) na strani podataka i jedan raščlanjivač (CSV parser) na klijentskoj strani. Ne samo da ćete uštedeti nekoristan teret tih XML funkcija, nego će i veličina podataka biti znatno manja, a raščlanjivanje će biti eksponencijalno brže. Što je još bolje, ako imate isti jezik na oba kraja, serijalizujte svoje strukture podataka i dodajte ih svima. Podaci bi mogli da budu veći od ravnog fajla, ali će još manje opterećivati procesor. Microsoft je naučio ovu lekciju u aplikacijama Live; prešli su sa XML-a na JSON i brzina se drastično povećala.

Po mom iskustvu, na traženje grešaka i testiranje često se utroši najmanje 25% procesa programiranja, a često se dođe i do 50%. Pisanje koda je relativno trivijalan posao ako krećete od solidnog poznavanja jezika, poslovnih ciljeva i od kvalitetnog pseudo koda (koji bi i inače morali da napišete da biste proverili da li program zadovoljava potrebe klijenta). Ako se uloži nešto dodatnog vremena na uklanjanje nepotrebnih redova koda, proveru konzistentnog imenovanja promenljivih, davanje promenljivima odgovarajućih imena, izostavljanje implicitnih operatora osim tamo gde je očigledno da se oni koriste i tako dalje, postiže se mnogo više u korist što lakšeg traženja grešaka i revizije koda. Šta vredi uštedeti dvadeset minuta kodiranja ako produžavate traženje grešaka i održavanje za 10%?

Isto tako, utvrdite kako vaš interpreter ili kompajler tretira uslovne naredbe i petlje. Lako će se desiti da iz lenjosti ili neznanja pišete te naredbe na način zbog kojeg se vaša aplikacija izvršava mnogo sporije nego što je potrebno. Na primer, ako jezik koji koristite izračunava uslove s desna u levo, postavite na desnu stranu one uslove koji će najpre da dovedu do odluke. Zašto da se razmatraju uslovi koji najverovatnije neće uticati na odluku? Isto važi i za petlje. Naravno, lakše je da se napiše nešto kao: for (intRowCounter = 0; intRowCounter < tableDataSet.Rows.Count - 1; intRowCounter++), ali vaši korisnici će biti mnogo, mnogo zadovoljniji ako umesto toga nekoj promenljivoj dodelite tableDataSet.Rows.Count - 1 a onda ispitate tu promenljivu. Na ovaj način softver neće morati stalno da se spušta niz objektno stablo po objekat brojača redova, a onda da oduzima od njega. Takve male stvari se brzo nakupe, pogotovo u bloku koda koji se često koristi.

Programiranje uz ovu vrstu razmišljanja zahteva veliki pomak od kratkoročnog, ka dugoročnom razmišljanju. Ovde sam naveo samo nekoliko nagoveštaja, ali mislim da shvatate u čemu je stvar. Ignorisanjem dugoročnih posledica vašeg kodiranja radi kratkoročne koristi, postižete rastrojen i spor kôd za koji ćete zažaliti što ste ga napisali, a vaši korisnici će poželeti da ga nikad i niste.