Helsingin yliopisto / Tietojenkäsittelytieteen laitos / 582309 Ohjelmointitekniikka (Java)
© 2006 Arto Wikla. Tämän oppimateriaalin käyttö on sallittu vain yksityishenkilöille opiskelutarkoituksissa. Materiaalin käyttö muihin tarkoituksiin, kuten kaupallisilla tai muilla kursseilla, on kielletty.

Ohjelmointitekniikka (Java): Harjoituksia jaksolle 3, 13.2.-24.2.

(Viimeisin päivitys 16.2.2006)

  1. Selitä lyhyesti seuraavat käsitteet: timeslicing, co-operative, preemptive, critical section, mutual exclusion, busy waiting, deadlock. Anna valaisevia esimerkkejä. Mikä on kunkin vallitseva suomennos? Keksitkö kuvaavampia suomennoksia? Mitkä näistä liittyvät jollakin tavoin Java-kielisiin ohjelmiin? Miten?

  2. Laadi peli Maalivahti, jossa pelaaja yrittää estää ruudun ylälaidasta saapuvaa palloa pääsemästä ruudun alalaitaan siirtelemällä nuolinäppäimin "mailaa" vasemmalle ja oikealle. Pallon lähtöpaikka ja tulokulma arvotaan. Maila on pelkkä jana. Tehtävän voi tehdä hyvin yksinkertaisena: pallon ei tarvitse kimmota seinistä tai mailasta, pallon nopeutta tai mailan leveyttä ei tarvitse voida säätää, jne. Riittää vain laskea pisteet: torjuttuja/palloja. Toisaalta jos haluaa ja intoa riittää, pelin voi laajentaa vaikka yhden tai kahden pelaajan tennikseksi, jossa pallo kimmahtelee jne. Lähtökohtana ja mallina voi käyttää esimerkkiohjelmaa BounceThread.java.

    [Aivan vapaaehtoisia muunnelmia tehtävän teemasta:

    ]

  3. Muokkaa ja kokeile ohjelmaa SynchBankTest2.java siten kuin sivulla Ohjelmointitekniikka (Java): rinnakkaisuudesta kohdassa Synkronoinnin tarve, synchronized pohditaan: Aiheuta lukkiuma (deadlock) kolmella erilaisella tavalla: tilisiirron määrää kasvattamalla, tilisiirron suuntaa vaihtamalla ja notify-muutoksella. Selitä tarkasti lukkiutumisen syyt. Kuka Java-ohjelmassa vastaa lukkiumien estämisestä? Miten?

  4. Maailma muodostuu n*n-ruudukosta. Ruutu voi olla tyhjä tai siinä voi olla joko kasvi tai eläin. Eläimiä on kahdenlaisia: kasvissyöjiä ja petoja. Kasvit eivät liiku, eläimet osaavat liikkua naapuriruutuun. Jos kasvissyöjä osuu kasviruutuun, se syö kasvin. Jos kasvissyöjä osuu petoruutuun, peto syö kasvissyöjän. Samoin käy myös, kun peto osuu kasvissyöjäruutuun. Peto ei mene koskaan kasviruutuun.

    Jos kaksi kasvissyöjää tai kaksi petoa osuu samaan ruutuun, johonkin arvottuun tyhjään ruutuun syntyy uusi eläin - kasvissyöjien kohdatessa uusi kasvissyöjä, petojen kohdatessa uusi peto. Lapsen synnyttyä tulija palaa samantien ruutuun josta se tuli kohtaamaan kumppaninsa.

    Eläimet liikkuvat arvottuun suuntaan yhden ruudun verran. Kaikki suunnat ovat keskenään yhtä todennäköisiä. Kun eläin on siirtynyt, se nukkuu. Kasvissyöjä nukkuu t millisekuntia, peto u millisekuntia.

    Jos kasvissyöjä on kulkenut p ruutua saamatta ruokaa, se kuolee. Jos peto on kulkenut q ruutua saamatta ruokaa, se kuolee. Jos jossakin ruudussa on käynyt s eläintä, siihen syntyy uusi kasvi s:nnen kulkijan poistuttua.

    Simuloi tätä maailmaa Java-ohjelmana siten, että eläimet mallinnetaan omina säikeinään. Kasvien ja eläinten paikat sekä parametrit n, p, q, s, t ja u asetetaan ohjelman alussa. Löydätko sellaisia parametrien arvoja, joilla "luonto on tasapainossa", so. maailma ei täyty tai tyhjene (myös eläimiä sisältävää maailmaa!).

    Jotkut pitävät tällaista säikeiden käyttämistä huonona ohjelmointityylinä. Yksi perustelu voisi olla, että koko n*n-ruudukko joudutaan varaamaan yhden eläimen siirymisoperaation ajaksi; aitoa rinnakkaisuutta ei siis oikeastaan synny. Skeduloija vain "arpoo" seuraavaksi valittavan eläimen, mikä voitaisiin toki ohjelmoida itsekin. Toisaalta jotkut ovat sitä mieltä, että tällainen ratkaisu on luonteva simuloinnissa. Mitä mieltä olet? Millainen ratkaisu olisi "paras"?
    (Yksi klassinen tapa toteuttaa ajassa tapahtuvien asioiden simulointia perustuu ns. prioriteettijonon käyttämiseen, ks. vaikkapa kevään 2003 Tietorakenteet-kurssin esimerkkiä. (laitoksen intranetissä))

    Jos maailma toteuttaisiin matriisin sijaan linkitettynä verkkorakenteena, voisivatko operaatiot varata koko maailman sijaan vain pienen osan maailmasta? Esimerkiksi vain muutaman ruudun? Auttaisiko tämä yllä mainittuun ongelmaan?

  5. Java-Tutorialin sivulla Synchronizing Threads on esimerkki, jossa tuottaja (Producer) tuottaa kokonaislukuja ja kuluttaja (Consumer) kuluttaa niitä. Laajenna esimerkkiä siten, että tuottajia on n kappaletta, kuluttajia m kappaletta. Suunnittele ohjelmalle havainnollinen tulostus ja kokeile sitä erilaisin n:n ja m:n arvoin.

  6. Tekninen essee: Selitä sovellusohjelmoijalle lyhyesti (n. 2-3 A4-sivua) mutta käytännönläheisesti Javan säieturvallisisten kokoelmien idea. Esimerkkeinä voit käyttää pakkauksen java.util.concurrent luokkia ConcurrentLinkedQueue<E> ja ConcurrentHashMap<K,V>. Kirjoituksen ajateltu lukija on tietojenkäsittelytieteen aineopintojen loppupuolella oleva opiskelija.

  7. Tekninen essee: Kirjoita Java-ohjelmoijalle käytännönläheinen ja lyhyt (n. 2-3 A4-sivua) tekninen ohje GUI-ohjelmoinnin rinnakkaisuuteen liittyviä perustekniikoista. Tärkeitä käsitteitä ovat mm. Single-Thread Rule, event dispatch thread ja worker thread. Säikeiden käyttäminen on käytännössä välttämätöntä animaatioden toteuttamisessa, mutta myös monissa muissa tilanteissa. Miksi ja millaisissa? Millä tavoin tietoa välitetään omien säikeiden ja käyttöliittymäkomponenttien välillä? Anna pieniä, edustavia ja toimivia ohjelmaesimerkkejä. Kirjoituksen ajateltu lukija on tietojenkäsittelytieteen aineopintojen loppupuolella oleva opiskelija.

  8. Vastaa henkilökohtaiseen kurssikyselyyn osoitteessa http://ilmo.cs.helsinki.fi/kurssit/servlet/Valinta. Muista myös lähettää lomake! Lähetysnäppäin on lomakkeen lopussa. Tähän kysymykseen vastataan yksilönä ja anonyymisti. Tehtävä myös rastitetaan opiskelijoittain, ei opintopiireittäin. Ja rastin saa kirjoittaa, jos on todella vastannut kyselyyn! Opiskelijaan luotetaan tässä-(kin) asiassa! Koetta koskeviin kysymyksiin ei tietenkään voi vastata, mutta kysely tehdään kuitenkin jo nyt, jotta saadaan varmistettua hyvä vastausprosentti. Vastauksilla ihan oikeasti on merkitystä laitoksen opetusta kehitettäessä!



[Pääsivulle] Takaisin harjoitusten pääsivulle.