Luento 7. T-106.1240 Ohjelmoinnin jatkokurssi T1 & T-106.1243 Ohjelmoinnin jatkokurssi L1. Luennoitsija: Otto Seppälä



Samankaltaiset tiedostot
Algoritmit 1. Luento 2 Ke Timo Männikkö

Algoritmit 1. Luento 3 Ti Timo Männikkö

Algoritmit 2. Luento 14 Ke Timo Männikkö

Sisältö. 22. Taulukot. Yleistä. Yleistä

Algoritmit 1. Demot Timo Männikkö

Algoritmit 1. Luento 1 Ti Timo Männikkö

Sisältö. 2. Taulukot. Yleistä. Yleistä

Tietorakenteet ja algoritmit - syksy

Lohkot. if (ehto1) { if (ehto2) { lause 1;... lause n; } } else { lause 1;... lause m; } 16.3

Yleistä. Nyt käsitellään vain taulukko (array), joka on saman tyyppisten muuttujien eli alkioiden (element) kokoelma.

Tietorakenteet ja algoritmit Johdanto Lauri Malmi / Ari Korhonen

f(n) = Ω(g(n)) jos ja vain jos g(n) = O(f(n))

Sisällys. 15. Lohkot. Lohkot. Lohkot

Algoritmit 1. Demot Timo Männikkö

Lohkot. if (ehto1) { if (ehto2) { lause 1;... lause n; } } else { lause 1;... lause m; } 15.3

Algoritmit 2. Luento 8 To Timo Männikkö

Algoritmit 2. Luento 1 Ti Timo Männikkö

A TIETORAKENTEET JA ALGORITMIT

11/20: Konepelti auki

Olion elinikä. Olion luominen. Olion tuhoutuminen. Olion tuhoutuminen. Kissa rontti = null; rontti = new Kissa();

16. Ohjelmoinnin tekniikkaa 16.1

Sisällys. 17. Ohjelmoinnin tekniikkaa. Aritmetiikkaa toisin merkiten. for-lause lyhemmin

58131 Tietorakenteet ja algoritmit (syksy 2015)

Ohjelmointiharjoituksia Arduino-ympäristössä

Sisällys. 16. Ohjelmoinnin tekniikkaa. Aritmetiikkaa toisin merkiten. Aritmetiikkaa toisin merkiten

16. Ohjelmoinnin tekniikkaa 16.1

ITKP102 Ohjelmointi 1 (6 op)

Sisällys. 16. Lohkot. Lohkot. Lohkot

ALGORITMIT 1 DEMOVASTAUKSET KEVÄT 2012

Sisällys. 7. Oliot ja viitteet. Olion luominen. Olio Java-kielessä

TIE448 Kääntäjätekniikka, syksy Antti-Juhani Kaijanaho. 7. joulukuuta 2009

Taulukot. Jukka Harju, Jukka Juslin

811312A Tietorakenteet ja algoritmit Kertausta kurssin alkuosasta

Luento 1 Tietokonejärjestelmän rakenne

Luento 1 Tietokonejärjestelmän rakenne

Luento 1 Tietokonejärjestelmän rakenne. Järjestelmän eri tasot Laitteiston nopeus

Luento 1 Tietokonejärjestelmän rakenne. Järjestelmän eri tasot Laitteiston nopeus

TIEA241 Automaatit ja kieliopit, syksy Antti-Juhani Kaijanaho. 5. marraskuuta 2015

2. Lisää Java-ohjelmoinnin alkeita. Muuttuja ja viittausmuuttuja (1/4) Muuttuja ja viittausmuuttuja (2/4)

ITKP102 Ohjelmointi 1 (6 op)

811312A Tietorakenteet ja algoritmit Kertausta kurssin alkuosasta

Sisällys. 11. Javan toistorakenteet. Laskurimuuttujat. Yleistä

Tietorakenteet (syksy 2013)

Taulukot. Taulukon käsittely. Tämän osan sisältö. Esimerkki. Taulukon esittely ja luonti. Taulukon alustaminen. Taulukon koko

Ohjelmointitaito (ict1td002, 12 op) Kevät Java-ohjelmoinnin alkeita. Tietokoneohjelma. Raine Kauppinen

Java kahdessa tunnissa. Jyry Suvilehto

11. Javan toistorakenteet 11.1

Tietorakenteet ja algoritmit syksy Laskuharjoitus 1

TAMPEREEN TEKNILLINEN YLIOPISTO Digitaali- ja tietokonetekniikan laitos. Harjoitustyö 4: Cache, osa 2

ITKP102 Ohjelmointi 1 (6 op), arvosteluraportti

Ohjelmoinnin perusteet, syksy 2006

811312A Tietorakenteet ja algoritmit I Johdanto

1. (a) Seuraava algoritmi tutkii, onko jokin luku taulukossa monta kertaa:

Ohjelmoinnin perusteet Y Python

7. Oliot ja viitteet 7.1

Alkuarvot ja tyyppimuunnokset (1/5) Alkuarvot ja tyyppimuunnokset (2/5) Alkuarvot ja tyyppimuunnokset (3/5)

Ehto- ja toistolauseet

Ohjelmointi 1 / 2009 syksy Tentti / 18.12

SEPA REFAKTOROINTI Antti Ahvenlampi, 57408L Erik Hakala, 57509T

Java-kielen perusteet

TIEA241 Automaatit ja kieliopit, kevät Antti-Juhani Kaijanaho. 12. tammikuuta 2012

1 Tehtävän kuvaus ja analysointi

Tietorakenteet, laskuharjoitus 2,

Operaattoreiden ylikuormitus. Operaattoreiden kuormitus. Operaattoreiden kuormitus. Operaattoreista. Kuormituksesta

Ohjelmoinnin jatkokurssi, kurssikoe

Java-kielen perusteita

4 Tehokkuus ja algoritmien suunnittelu

4. Algoritmien tehokkuus

811120P Diskreetit rakenteet

Ohjelmassa henkilön etunimi ja sukunimi luetaan kahteen muuttujaan seuraavasti:

Ohjelmoinnin perusteet Y Python

Concurrency - Rinnakkaisuus. Group: 9 Joni Laine Juho Vähätalo

Käyttöjärjestelmät: poissulkeminen ja synkronointi

15. Ohjelmoinnin tekniikkaa 15.1

Ohjelmoinnin peruskurssien laaja oppimäärä

Ohjelmoinnin peruskurssien laaja oppimäärä

2 Konekieli, aliohjelmat, keskeytykset

Ohjelmoinnin peruskurssien laaja oppimäärä

Opintojakso TT00AA11 Ohjelmoinnin jatko (Java): 3 op Taulukot & Periytyminen

Algoritmit 1. Luento 10 Ke Timo Männikkö

Oliosuunnitteluesimerkki: Yrityksen palkanlaskentajärjestelmä

P e d a c o d e ohjelmointikoulutus verkossa

1. Mitä tehdään ensiksi?

12. Javan toistorakenteet 12.1

4. Lausekielinen ohjelmointi 4.1

2. Olio-ohjelmoinista lyhyesti 2.1

Luento 1 (verkkoluento 1) Ohjelman sijainti Ohjelman esitysmuoto Laitteiston nopeus

ITKP102 Ohjelmointi 1 (6 op)

(p j b (i, j) + p i b (j, i)) (p j b (i, j) + p i (1 b (i, j)) p i. tähän. Palaamme sanakirjaongelmaan vielä tasoitetun analyysin yhteydessä.

12. Javan toistorakenteet 12.1

Sisällys. Yleistä attribuuteista. Näkyvyys luokan sisällä ja ulkopuolelta. Attribuuttien arvojen käsittely aksessoreilla. 4.2

Nopea kertolasku, Karatsuban algoritmi

Ohjelmoinnin peruskurssi Y1

811120P Diskreetit rakenteet

Tutkimusmenetelmät-kurssi, s-2004

ITKP102 Ohjelmointi 1 (6 op)

Java-kielen perusteet

Luento 1 (verkkoluento 1) Tietokonejärjestelmä

Ohjelmassa muuttujalla on nimi ja arvo. Kääntäjä ja linkkeri varaavat muistilohkon, jonne muuttujan arvo talletetaan.

Chapel. TIE Ryhmä 91. Joonas Eloranta Lari Valtonen

Transkriptio:

Luento 7 T-106.1240 Ohjelmoinnin jatkokurssi T1 & T-106.1243 Ohjelmoinnin jatkokurssi L1 Luennoitsija: Otto Seppälä Kurssin WWW: http://www.cs.hut.fi/opinnot/t-106.1240/s2007

Suunnitelmista Yleistaso oli tänä vuonna alustavien tietojen perusteella varsin hyvä. Monesta suunnitelmapalautuksesta oli unohtunut kuvat. Omatkin algoritmit ovat toki algoritmeja Ohjelmani ei käytä algoritmeja tai tietorakenteita Lähdeluettelo kannattaa tehdä viimeistään dokumenttiin kunnolla Hyvää harjoitusta diplomi- ja kandityötä varten Erilaisia lähdeviittausoppaita löytyy webistä: lib.hut.fi/opetus/informatiikka/tietoiskut/lahde-tietoisku.html Google: Reference guide IEEE Style Google: Reference guide Harvard style

CVS-demo CVS:n käyttöä demottiin kurssisivuston ohjeita noudattaen

Tehokkuusnäkökohtia

Ohjelmien tehokkuus Millainen on tehokas ohjelma Nopeus Muistinkäyttö Vasteaika (reagoi aina nopeasti käyttäjän toimiin) Kuinka näitä voidaan mitata? Profilointi Koodin ja algoritmien analyysi notaatiot : Iso-O, iso-theta, iso-omega Kuinka niihin voidaan vaikuttaa? Hyvät algoritmit ja tietorakenteet Koodin optimointi

Optimoi vasta lopuksi Donald Knuth: Premature optimization is the root of all evil Optimointi monimutkaistaa koodia Luo ehkä uusia virheitä Vaikeuttaa koodin ylläpidettävyyttä Vaikeuttaa jatkokehitystä / perintää Kaikki optimoinnit eivät ole optimaalisia Hyvä kääntäjä osaa tehdä joitakin optimointeja paremmin kuin ohjelmoija: esim. pipelining Aina ei kannata optimoida Jos voitot ovat pieniä, ylläpidettävyys on tärkeämpää Tee ensin toimiva ohjelma; vasta sitten optimointi

Suunnittelu Ohjelman jako metodeihin, luokkiin ja moduuleihin Osa ohjelman pullonkauloista syntyy jo tässä vaiheessa Suunnittele hyvin Kuinka tieto siirtyy moduleiden välillä? Esim tehtävän 2.1 käyttämä BreakIterator palauttaa tavutuskohdat, ei pilkottuja String-olioita Pilkotut String-oliot pitäisi monesti koota takaisin sopivan levyisiksi riveiksi joka aiheuttaisi vain turhaa lisätyötä Tavutuskohdista voidaan laskea kohdat joista rivi voidaan katkaista ja jakaa merkkijono osiin vain näistä kohdista.

Tietorakenteet ja algoritmit Oikeiden tietorakenteiden ja algoritmien valinta on äärimmäisen tärkeää Suurilla tietomäärillä eri algoritmien nopeuserot voivat olla valtavia Helposti yli tuhatkertaisia nopeuseroja

Koodi Erilaisilla koodirakenteilla ja käskyillä on nopeuseroja Riippuvat monesti ajoympäristöstä Koodin optimointi kannattaa keskittää vain keskeisiin osiin koodista Pienillä nopeuseduilla on merkitystä vain jos tehostunutta kohtaa käytetään usein 90/10 sääntö : 90% suoritusajasta kuluu 10%:ssa koodia.

Järjestelmä Laitteiston vaikutus Eri laitteiden ominaisuudet vaikuttavat siihen minkätyyppiset ongelmat ratkeavat parhaiten Optimoiva kääntäjä Hyvä kääntäjä tekee tietyt optimoinnit puolestasi Nopeuserot parhaimmillaan kymmenkertaisia Mutta käytännössä harvoin

Nopeuden mittaus ja arviointi

Profilointi Ohjelman suoritusta voidaan tutkia profilointityökaluilla Ohjelmien muistinkäyttö Tehdyt aliohjelmakutsut (metodikutsut) Metodeissa käytetty aika Java SDK:ssa kaksi profilointityökalua java -X:prof java -X:runhprof Eclipse IDE:en on olemassa TPTP-niminen lisäosa Todella kätevä (mutta haastava asentaa toimivasti) laskee myös koodikattavuudet jne.

F:\tehokkuus\code>java -Xprof:help Matrix Flat profile of 10.70 secs (1063 total ticks): main Interpreted + native Method 0.3% 0 + 3 java.io.winntfilesystem.getbooleanattributes 0.1% 1 + 0 Matrix.kerroMatriisitJIK_NonOp... 0.1% 0 + 1 java.io.fileinputstream.close0 1.8% 11 + 8 Total interpreted Compiled + native Method 11.0% 117 + 0 Matrix.kerroMatriisitJKI_NonOp 10.9% 116 + 0 Matrix.kerroMatriisitKJI_NonOp... 4.2% 45 + 0 Matrix.kerroMatriisitKIJ 0.2% 0 + 2 Matrix.doIt 97.6% 1035 + 3 Total compiled Thread-local ticks: 0.3% 3 Class loader 0.3% 3 Compilation Flat profile of 0.00 secs (1 total ticks): DestroyJavaVM Thread-local ticks: 100.0% 1 Blocked (of total) Global summary of 11.18 seconds: 100.0% 1117 Received ticks 0.4% 4 Received GC ticks 0.3% 3 Compilation 0.1% 1 Other VM operations 0.3% 3 Class loader

Koodin analysointi Koodin voidaan nähdä koostuvan kolmesta rakenteesta Sekvenssi koodilauseiden sarja, jotka suoritetaan peräkkäin ei sisällä haarautumista (ehtolauseet) muiden metodien kutsut käsitellään osana sekvenssiä ehtolauseet if-else switch silmukat for, while, do-while

Koodin analysointi Suoritusaika ilmoitetaan yleensä syötteen funktiona syötteen määrää merkitään muuttujalla N Lasketaan suoritettuja operaatioita perusoperaatiot : =, +, -, taulu[i], jne. Sekvenssissä lasketaan sen sisältämien lauseiden sisältämien operaatioiden määrät yhteen Silmukassa sen sisältämä sekvenssi voidaan suorittaa useita kertoja (mahdollisesti eri N:n arvoilla)

Esimerkki public int laskeyhteen(int[] taulu){ int summa = 0; for (int i=0; i<taulu.length; i++){ summa += taulu[i]; return summa;

Esimerkki public int laskeyhteen(int[] taulu){ int summa = 0; for (int i=0; i<taulu.length; i++){ summa += taulu[i]; return summa; 1 kerta N kertaa N+1 kertaa 1 + 1 + (N+1) + 3*N + 1 = 4N + 4 -> O(N) N f(n) 1 8 10 44 100 404 1000 4004

Asymptoottinen kompleksisuus Mikä osa funktiosta on olennaista kun N kasvaa? pienempien termien merkitys vähenee Myöskään N:n edessä olevalla kertoimella ei ole merkitystä eri lauseet vievät eri ajan (sijoitus, return, yhteenlasku, vertailu) kertoimia ei siis voisi kuitenkaan vertailla Olennaista on siis vain kertaluokka Asymptoottinen kompleksisuus Otetaan vain suurimmat vaikuttavat termit Poistetaan termin vakiokerroin

Asymptoottinen kompleksisuus Kun algoritmien tehokkutta toisiinsa verrataan suuremmalla syötekoolla ei esimerkkimme kaavan 4N+4 kaikilla termeillä ja kertoimilla ole suurta merkitystä Suurilla N:n arvoilla termi 4N dominoi tulosta. Käytännössä tämä olisi kuitenkin jo jäänyt kakkoseksi 4.01N:lle. Verrattaessa minkä tahansa muun kertaluvun funktioon (esim 15N 2 ) myöskään kertoimella 4.01 ei olisi ollut väliä. Vaikka lauseke olisi ollut 15000N niin jo tuhannen paikkeilla 15N 2 olisi ohittanut sen. Tuntuisi siis riittävältä huomata että suurilla arvoilla lausekkeen dominoiva termi on k*n jossa k on vain jokin vakio (yksinkertaistus)

Asymptoottinen kompleksisuus Formaalimmin voidaan sanoa että lausekkeelle voidaan määritellä asymptoottinen yläraja M g(n) joka on aina suurempi kuin meitä kiinnostava funktio f, kunhan vain N on riittävän suuri (yli n 0 ). f(n) O(g(n)) M on jokin vakio n 0 on jokin piste jota suuremmilla arvoilla aina pätee M > 0, n 0 >0 s.e. f(n) M(g(n)), n>n 0 Esimerkiksi kaavalle 4N+4 arvot olisivat voineet olla M=5 ja n 0 = 10 kun g(n) = N Tällöin voitaisiin Iso-O notaatiolla merkitä (4N + 4) O(N)

Asymptoottinen kompleksisuus M*g(n) f(n) f(n) = O(g(n)) n 0

Analyysi Iso-O notaatiolla Koodiesimerkki

public int dosomething(int[] taulu){ int muuttuja = 0; for (int i=0; i<taulu.length; i++) for (int j=i; j<taulu.length; j++){ muuttuja += taulu[i]*taulu[j]; for (int i=0; i<5; i++){ muuttuja -= apumetodi(taulu, i); return muuttuja; public int apumetodi(int[] summattavat, int kerroin){ int summa = 0; for (int i=0; i<summattavat.length; i++) summa+=summattavat[i]*kerroin; return summa;

public int dosomething(int[] taulu){ int muuttuja = 0; for (int i=0; i<taulu.length; i++) for (int j=i; j<taulu.length; j++){ muuttuja += taulu[i]*taulu[j]; for (int i=0; i<5; i++){ muuttuja -= apumetodi(taulu, i); return muuttuja; public int apumetodi(int[] summattavat, int kerroin){ int summa = 0; for (int i=0; i<summattavat.length; i++) summa+=summattavat[i]*kerroin; return summa;

public int dosomething(int[] taulu){ int muuttuja = 0; for (int i=0; i<taulu.length; i++) for (int j=i; j<taulu.length; j++){ muuttuja += taulu[i]*taulu[j]; for (int i=0; i<5; i++){ muuttuja -= apumetodi(taulu, i); return muuttuja; O(N) public int apumetodi(int[] summattavat, int kerroin){ int summa = 0; for (int i=0; i<summattavat.length; i++) summa+=summattavat[i]*kerroin; O(N) return summa;

public int dosomething(int[] taulu){ int muuttuja = 0; for (int i=0; i<taulu.length; i++) for (int j=i; j<taulu.length; j++){ muuttuja += taulu[i]*taulu[j]; for (int i=0; i<5; i++){ muuttuja -= apumetodi(taulu, i); return muuttuja; O(N) O(N) O(N 2 ) public int apumetodi(int[] summattavat, int kerroin){ int summa = 0; for (int i=0; i<summattavat.length; i++) summa+=summattavat[i]*kerroin; O(N) return summa; O(N)

public int dosomething(int[] taulu){ int muuttuja = 0; for (int i=0; i<taulu.length; i++) for (int j=i; j<taulu.length; j++){ muuttuja += taulu[i]*taulu[j]; for (int i=0; i<5; i++){ muuttuja -= apumetodi(taulu, i); return muuttuja; O(N) O(N) O(N 2 ) O(N) public int apumetodi(int[] summattavat, int kerroin){ int summa = 0; for (int i=0; i<summattavat.length; i++) summa+=summattavat[i]*kerroin; O(N) return summa; O(N)

public int dosomething(int[] taulu){ int muuttuja = 0; O(N 2 ) for (int i=0; i<taulu.length; i++) for (int j=i; j<taulu.length; j++){ muuttuja += taulu[i]*taulu[j]; for (int i=0; i<5; i++){ muuttuja -= apumetodi(taulu, i); return muuttuja; O(N 2 ) O(N) public int apumetodi(int[] summattavat, int kerroin){ int summa = 0; for (int i=0; i<summattavat.length; i++) summa+=summattavat[i]*kerroin; O(N) return summa; O(N)

Laitteiston vaikutus

Laitteiston vaikutus Laitteiston tuntemuksesta on hyötyä, jos halutaan kirjoittaa tehokasta koodia Monesti kääntäjä suorittaa nämä optimoinnit Tällöin on olennaista, ettei koodin rakenne estä kääntäjän toimintaa Javan tapauksessa virtuaalikone on pyritty optimoimaan käytettävälle alustalle.

Välimuisti Välimuisti toimii selvästi tavallista muistia nopeammin Välimuistissa säilytetään usein käytettyjä / juuri käytettyjä muistialkioita Usein käytettyjä alkioita ei tarvitse aina hakea tavallisesta muistista Välimuistin tehokkuuteen vaikuttaa useampi tekijä Kuinka hajallaan käytetyt muistialueet ovat? Käyttävätkö algoritmit peräkkäisiä muistipaikkoja? Kuinka suurta määrää muuttujia ohjelma käyttää kerrallaan? Mahtuvatko usein käytetyt muuttujat välimuistiin?

Muisti pullonkaulana Prosessori toimii huomattavasti muistia nopeammin Rekisterit toimivat prosessorin nopeudella Välimuistit toimivat muistia nopeammin Välimuistin koko on kuitenkin rajallinen Lisäksi ohjelmat käyttävät virtuaalimuistia Sopeuttamalla ohjelman ja eri muistien toiminta yhteen voidaan saavuttaa tehokkuusetuja

Virtuaalimuisti Ohjelmille voidaan virtuaalimuistin avulla tarjota paljon todellista enemmän muistia Muistin laajennus toteutetaan käyttämällä kiintolevyä muistin säilytykseen Harvemmin käytetyt muistisivut tallennetaan levylle Usein käytetyt muistisivut pysyvät muistissa Kun jotakin levyllä olevaa sivua tarvitaan, se tuodaan muistiin

Muistinkäytöstä Erilaiset muistinkäyttöstrategiat voivat vaikuttaa paljon ohjelman suorituskykyyn Suuresta datamäärästä kannattaa käsitellä yhtenäisiä osia pidempiä aikoja kerrallaan eikä yksittäisiä alkioita sieltä täältä jotta välimuisti ja virtuaalimuisti toimisivat tehokkaasti

Blocking Kun ohjelma käyttää jotakin I/O-laitetta, voi metodikutsu joutua odottamaan laitteen vastausta Kyseessä on ns. blokkaava metodikutsu Blokkaava säie ei voi jatkaa suoritusta ennen kuin I/Olaite on valmis Yleensä tämä on etu lukeva säie ei kuluta resursseja odottaessaan ja jatkaa automaattisesti työtään kun dataa on taas tarjolla. Web-serverissä tämä voisi olla myös ongelma, kun jokaista asiakasta kohden pitäisi olla oma säie odottamassa Javassa on myös ei-blokkaava I/O-kirjasto

Iteraatio ja rekursio Rekursiossa tehdään paljon metodikutsuja Metodikutsun yhteydessä suorituspinosta varataan kehys paikallisia muuttujia jne. varten Kehyksen varaaminen ja metodikutsusta palaaminen käyttävät prosessoriaikaa ja muistia Rekursio on tämän vuoksi usein tehottomampi ratkaisu kuin iteraatio Riippuu myös koneen arkkitehtuurista ja käytetystä kääntäjästä...sekä tietysti ohjelmointikielestä Usein rekursiivisen ratkaisun selkeys voi olla olennaisempaa kuin saavutettu tehoetu

Kääntäjän optimointeja Loop unrolling Method inlining Software pipelining Reordering Häntärekursion poisto jne.. (Ylläolevat ovat yleisiä esimerkkejä ja lista sisältää myös ei java-spesifejä esimerkkejä. Tarjolla olevan optimoinnin taso vaihtelee ohjelmointikielen ja käytetyn kääntäjän mukaan)

Ohjelmoijan optimointeja (esim.) Olioiden kierrätys Monimutkaisten olioiden luonti on raskasta Käytöstä poistettujen olioiden tallennus ja uudelleen käyttöönotto nopeuttaa (factory pattern) StringBuffer vs. String Runsaasti merkkijonojen yhteenliittämisiä sisältävässä ohjelmassa StringBuffer voi vähentää väliaikaisten merkkijonojen luomista. Nopeuserot suurilla merkkijonoilla parhaimmillaan valtavia. StringBuilder on vielä parempi. (kunhan kaikki kirjoitus tehdään yhdessä säikeessä) final-määreen käyttö final-määreellä metodien korvaaminen aliluokissa estetään. Tällöin kääntäjä voi korvata metodikutsun sijoittamalla metodin koodin suoraan kutsun tilalle. (tätä ei nykyisin enää suositella) Vakioarvot vs muuttujat Kääntäjä voi sijoittaa vakioiksi (final public static) määritetyt muuttujat vakioina lopulliseen konekoodiin

Ohjelmoijan optimointeja (esim.) Välitulosten uudelleenkäyttö Dynamic programming Ei lasketa uudelleen välituloksia jos ne lasketaan joskus aiemmin algoritmissa jotain toista arvoa varten Hakualgoritmeissa karsinta Jos tiedetään että jokin haku tai ratkaisualgoritmi ei voi löytää haluttua tulosta tällä hetkellä työn alla olevaa reittiä, lopetetaan etsintä tätä kautta ajoissa ja kokeillaan jotakin muuta. Tietovirtojen puskurointi Kovalevyn yms. I/O laitteiden luku/kirjoitusoperaatioiden kannattaa mieluummin kirjoittaa kerralla paljon kuin usein vähän. BufferedWriter, BufferedReader, BufferedInputStream BufferedOutputStream.

Ohjelmoijan optimointeja private-määreen käyttö Myös private-määre mahdollistaa kääntäjän optimoinnin Koska muuttujiin / metodeihin ei pääse ulkoa, voidaan koodia käsitellä voimakkaammin method inlining jne. Ja paljon, paljon muuta...

Yhteenveto Ohjelmien tehokkuuteen vaikuttavia tekijöitä on monia Tehokkuuteen eniten vaikuttavat päätökset tehdään usein jo suunnitelmatasolla Tietorakenteiden ja algoritmien valinta on erittäin tärkeää Vasta näiden jälkeen kannattaa ajatella optimointia Algoritmien nopeutta kuvataan Iso-O, Iso-Θ, Iso-Ω ja pieni-o notaatioilla Kääntäjä osaa optimoida koodia usein riittävän hyvin Vain kriittinen koodi on syytä optimoida käsin Koodia tutkimalla tai profiloimalla voidaan löytää mahdolliset pullonkaulat Käsin optimointi voi haitata ylläpidettävyyttä tai jopa hidastaa ohjelmaa jos ei tiedä mitä tekee Laitteiston ja kääntäjän tuntemuksesta on apua