C-ohjelmointi, kevät 2005

Harjoitustyöaiheita

Valitse yksi harjoitustyön aiheista ja toteuta se C-kielellä. Lisäohjeita löydät harjoitustyöohjeesta.

1. RAVINTOLAN SIMULOINTI

Toteuta jonorakenne käyttämällä linkitettyjä listoja. (Vain taulukkoa käyttäviä ratkaisuja ei hyväksytä.) Tee rakenteen avulla ohjelma, joka simuloi ravintolan toimintaa seuraavasti:

Ravintolassa on ruokalista, jolta asiakas voi tilata haluamansa ruuan. Jokaiselle ruualla on oma valmistusaikansa. Ravintolassa on neljä kokkia, joista jokainen voi valmistaa kerrallaan kahta eri ruokalajia.

Kun asiakas tilaa ruuan, hänen tilauksensa sijoitetaan tilausjonon viimeiseksi. Kun joku kokeista vapautuu (hänellä on valmistettavanaan enää yksi tai ei yhtään ruokaa), hän ottaa valmistettavakseen tilausjonon ensimmäisen tilauksen, joka tällöin poistetaan jonosta.

Ohjelman käyttäjä antaa uusia tilauksia ja voi sopivalla käskyllä kasvattaa simulointijärjestelmän kelloa esim. yhdellä minuutilla kerrallaan. Ohjelma kertoo, milloin kukin ruokalaji on valmistunut.

2. SUKUPUU

Tee ohjelma, jonka avulla käyttäjä voi tallentaa sukupuun. Sukupuuhun voi tallettaa tietoja henkilöistä (nimi, syntymäaika, kuolinaika), näiden välisistä suhteista (sekä viralliset avioliitot että epäviralliset suhteet - jälkimmäiset halutaan tallettaa esim. sen vuoksi, että voidaan helposti pitää kirjaa lasten vanhemmista) ja suhteista syntyneistä lapsista. Yksinkertaisuuden vuoksi voit tehdä järjestelmän sellaiseksi, että jokaisella henkilöllä on eri nimi.

Ohjelmasi pitää tarjota ainakin seuraavat toiminnot:

- henkilön lisäys (henkilö voidaan lisätä joko "itsenäisenä" tai joidenkin lapsena)
- henkilön tietojen muutos
- suhteen lisäys 
- annetun henkilön kaikkien jälkeläisten tulostus
- annetun henkilön kaikkien esivanhempien tulostus
- annetun henkilön kaikkien rekisteröityjen suhteiden tulostus.
Ohjelmasi voi luottaa syötettyjen tietojen järkevyyteen. Sen ei tarvitse esim. tarkistaa, että joku ei ole naimisissa kahden henkilön kanssa yhtä aikaa tai että jonkun lapsi ei ole vanhempi kuin henkilö itse.

Ohjelmasi täytyy käyttää dynaamista muistinvarausta - vain taulukoihin perustuvia ratkaisuja ei hyväksytä.

3. POKERI

Tee ohjelma, joka pelaa käyttäjän kanssa pokeria. Pelin aluksi molemmille (ohjelmalle ja käyttäjälle) annetaan sama alkupääoma. Sen jälkeen voidaan pelata varsinaista peliä niin monta kierrosta, kun käyttäjä haluaa, ellei toiselta pelaajista lopu rahat. Alla on selostettu yhden kierroksen kulku.

Ohjelma sekottaa korttipakan. Molemmille pelaajille jaetaan viisi korttia. Sen jälkeen kumpikin pelaajista voi vaihtaa haluamansa määrän kortteja (0-5 kpl). Tämän jälkeen asetetaan panokset:
- ensimmäinen pelaaja asettaa haluamansa suuruisen panoksen (aloittaja vaihtuu joka kierroksella)
- toinen pelaaja asettaa vähintään yhtä suuren panoksen tai luovuttaa
- jos toinen pelaaja korotti panosta, on ensimmäisen pelaajan korotettava panosta vähintään vastaavalla summalla tai luovutettava
- näin jatketaan, kunnes vuorossa oleva pelaaja ei enää tee ylimääräistä korotusta panokseen.
(Oikeassa pokerissa panoksia asetetaan useammassa erässä - tämä on yksinkertaistettu versio harjoitustyötä varten.)

Tämän jälkeen katsotaan kummankin pelaajan kortit ja päätetään, kumpi on voittanut. Voittaja määräytyy käden hyvyyden mukaan. Erilaiset kädet ja niiden arvojärjestys on selitetty esimerkiksi www-sivulla http://cc.kangwon.ac.kr/~kimoon/docs/poker.html.

Ohjelmasi "ei tiedä" vastapelaajan kortteja siinä mielessä, että se valitsee taktiikkansa näistä korteista riippumatta. Sen sijaan ohjelmasi voi käyttää eri käsien todennäköisyyksiä apuna taktiikan valinnassa. Ohjelman pitää jotenkin arvioida sillä olevan käden hyvyys ja valita panos sen mukaan. Lisää kuitenkin mukaan vähän satunnaisuutta, jotta pelaaja ei voisi suoraan ohjelman toiminnasta päätellä, millaiset kortit ohjelmalla on. Myös vaihdettavat kortit pitää valita järkevästi.

Ohjelmasi käyttämän taktiikan ei tarvitse olla todennäköisyyksien mukaan paras mahdollinen, mutta se ei saa myöskään perustua täyteen satunnaisuuteen.

Tämän aiheen palautukseen pitää liittää käyttöohjeen lisäksi lyhyt selostus siitä, millaista taktiikkaa ohjelma käyttää.

4. TAVUTUSALGORITMI

Eräs tavutusalgoritmi on seuraava. Olkoon c seuraava käsiteltävä merkki.

 
         1.c = sanan alkukirjain 
         2.jos c on vokaali, niin jatka kohdasta 4 
         3.jos c on sanan viimeinen kirjain, niin algoritmi on LOPPU, 
           muuten ota seuraava kirjain ja jatka kohdasta 2 
         4.jos c on sanan viimeinen kirjain, niin algoritmi on LOPPU, 
           muuten ota seuraava kirjain 
         5.joc c on konsonantti, niin jatka kohdasta 10 
         6.jos c muodostaa yhdessä edeltävän kirjaimen kanssa jonkin 
           seuraavista pareista: aa ai au ee ei eu ey ie ii iu oi oo 
           ou ui uo uu yi yy yö äi äy ää öi öy öö, niin jatka kohdasta 8 
         7.aseta tavuviiva ennen c:ta ja jatka kohdasta 4 
         8.jos c on viimeinen kirjain, niin algoritmi on LOPPU, muuten 
           ota seuraava kirjain 
         9.jos c on vokaali, niin jatka kohdasta 7 
        10.jos c on viimeinen kirjain, niin algoritmi on LOPPU 
        11.jos c:ta seuraa vokaali, niin aseta tavuviiva ennen c:ta ja 
           ota seuraava kirjain; jatka kohdasta 4. Muuten ota seuraava 
           kirjain ja jatka kohdasta 10 
Huom. Yo. algoritmi on tarkoitettu suuntaa antavaksi eikä itse ohjelman rungoksi.

5. PASIANSSI

Erästä pasianssia pelataan seuraavasti: Tee ohjelma, joka pelaa ko. pasianssia n kertaa, missä n annetaan parametrina komentorivillä. Ohjelma tulostaa lopuksi todennäköisyyden millä pasianssi menee läpi. Ainoa valintakohta pelissä on, kun jokin pinoista vapautuu. Voit itse miettiä periaatteen siihen, mikä muiden pinojen korteista sijoitetaan vapautuneeseen pinoon. Saat todennäköisyyden, kun jaat läpimenneiden pelien määrän kaikkien pelien määrällä. Todennäköisyys on hyvin pieni.

6. MIINAHARAVA

Miinaharava on Windows-ympäristössä oleva tunnettu peli. Siinä kone sijoittaa ruudukolle joukon pommeja, jotka pelaajan pitää pystyä merkitsemään purkamista varten. Pelissä pelaaja valitsee vuorollaan aina yhden ruudun. Jos ruudussa on pommi, pelaaja räjähtää ja peli loppuu pelaajan tappioon. Muuten kone näyttää luvulla montako pommia on valitun ruudun viereisissä ruuduissa. Pelaaja voittaa, jos hän saa merkittyä kaikki pommit oikein ja valittua kaikki muut ruudut.

Kirjoita ohjelma, jonka avulla voit pelata miinaharavaa. Pelissä pitää voida antaa parametreina pommien määrä ja ruudukon koko. Valitse ruudukolle sellainen maksimikoko, että koko ruudukko mahtuu ruudulle. Koko ruudukko tulostetaan jokaisen siirron jälkeen uudestaan. Näin ei tarvita muuta näytönkäsittelyä kuin tavallista rivi kerrallaan tulostusta. Huom! Pelin ei tarvitse osata pelata miinaharavaa, eli mitään tekoälyohjelmaa ei tarvitse tehdä.

7. KOKKAAVAN YSTÄVÄN APU

Ystäväsi on päättänyt ryhtyä mestarikokiksi, mutta hänellä on jatkuvasti ongelmia ruoka-aineiden suhteen. Niinpä sunnuntain lasagne-ateria muuttui tonnikalavoileiviksi, kun kaapissa ei ollutkaan jauhelihaa. Tällaista linjaahan ei kukaan kestä kovin pitkään. Kirjoita siis ohjelma, jonka avulla ystäväsi voi tallettaa reseptejä ja ruoka-aineita, sekä tarkastaa paljonko jotain ruoka-ainetta on jäljellä. Ohjelman käyttöliittymä voi olla rivipohjainen, mitään koko ruudun täyttäviä valikkosysteemiä ei tarvita.

8. GAME OF LIFE

Kirjoita ohjelma, joka toteuttaa "Game of life" -simulaation. Matemaatikko John Conwayn vuonna 1970 kehittämä Game of Lifen simuloi soluruudukon ja yksinkertaisten sääntöjen avulla alkeellista elämää, jossa eliöt vain syntyvät, ovat elossa ja kuolevat.

Aika kulkee sukupolvittain. Seuraavan sukupolven tilanne määräytyy suoraan edellisestä sukupolvesta. Jokaisen yksittäisen solun elämään vaikuttavat sen kahdeksan naapurisolua seuraavasti:

Peli päättyy, kun kaikki ruudukon solut ovat kuolleita tai kun käyty läpi haluttu määrä sukupolvia. Voit myös lopettaa pelin, kun ruudukon tilanne on vakiintunut jatkuvasti toistuviin samanlaisiin tapahtumaketjuihin.

9. TILAAJALUETTELON YLLÄPITO

Kirjoita ohjelma, joka ylläpitää pienen kustantajan lehtien tilaajaluetteloa. Ohjelma osaa ainakin

10. KAHDEKSAN KUNINGATTAREN ONGELMA

Tee ohjelma, joka selvittää kaikki ne eri tavat, joilla kahdeksan kuningatarta voidaan asettaa shakkilaudalle siten, että ne eivät voi hyökätä toistensa kimppuun.