Tietorakenteet ja algoritmit I TRAI /SJ Luentomuistiinpanoja

Koko: px
Aloita esitys sivulta:

Download "Tietorakenteet ja algoritmit I TRAI 31.8.2012/SJ Luentomuistiinpanoja"

Transkriptio

1 Tietorakenteet ja algoritmit I Luentomuistiinpanoja Simo Juvaste Asko Niemeläinen Itä-Suomen yliopisto Tietojenkäsittelytiede

2 Alkusanat Tämä moniste perustuu valtaosaltaan aiemman Tietorakenteet ja algoritmit -kurssin luentomonisteeseen, joka taas perustui valtaosaltaan Askon mainioon tekstiin. Edellisen version kantava ajatus oli käyttää toteuttamaamme tietrakennekirjastoa konkreettistamaan algoritmejamme ja mahdollistamaan esimerkkien ja harjoitusten suorittaminen tietokoneella. Nyt uudessa tutkintorakenteessa kurssi jakautuu kahteen osaan. Tässä ensimmäisessä osassa keskitytään aikavaativuuden analysointiin, perustietorakenteisiin, joihinkin järjestämisalgoritmeihin sekä perustietorakenteiden toteuttamiseen. Toiseen osaan jäävät aiemmin kurssiin kuuluneet verkkoalgoritmit, algoritmistrategiat, ulkoinen muisti sekä mahdollisuuksien mukaan hieman vaativammat algoritmit. Toinen merkittävä uudistus on ohjelmointikielen vaihtuminen proseduraalisista Pascalista ja C:stä oliopohjaiseen Java 1.5:een. Vaikka kieli ja sen kirjastot vaikeammalta tuntuvatkin, tuovat ne myös paljon hyvää tietorakenteiden käyttäjälle ja toteuttajalle. Itse tietorakenteet ja algoritmit ovat kuitenkin muuttumattomia työvälineen vaihtumisesta huolimatta Simo Juvaste Asko Niemeläisen alkuperäiset alkusanat Kokosin nyt käsillä olevat luentomuistiinpanot Joensuun yliopistossa syksyllä 1996 luennoimaani Tietorakenteiden ja algoritmien kurssia varten. Muistiinpanot pohjautuvat vuonna 1993 järjestämäni samannimisen kurssin luentoihin, jotka puolestaan noudattelivat pitkälti Alfred V. Ahon, John E. Hopcroftin ja Jeffrey D. Ullmanin ansiokasta oppikirjaa Data Structures and Algorithms (Addison-Wesley 1983). Kurssin laajuus oli vuonna 1993 vielä 56 luentotuntia, mutta nyttemmin kurssi on supistunut 40 luentotuntia käsittäväksi, minkä vuoksi jouduin karsimaan osan aiemmin järjestämäni kurssin asiasisällöstä. Muutenkaan nämä muistiinpanot eivät enää täysin noudattele mainitsemaani oppikirjaa, sillä käsittelen asiat oppikirjaan nähden eri järjestyksessä, osin eri tavoinkin. Radikaalein muutos aiempaan on se, että pyrin kuvailemaan abstraktit tietotyypit mieluummin käyttäjän kuin toteuttajan näkökulmasta. Lähestymistavan tarkoituksena on johdattaa kurssin kuulijat käyttämään abstrakteja tietotyyppejä liittymän kautta, toisin sanoen toteutusta tuntematta. Toteutuskysymyksiin paneudun vasta kurssin loppupuolella, silloinkin enimmäkseen kuvailevasti. Abstraktien tietotyyppien toteuttamisen ei näet mielestäni pitäisi Ohjelmoinnin peruskurssin jälkeen muodostua ongelmaksi, mikäli tietotyypin käyttäytyminen ja toteutusmallin keskeisimmät ideat ymmärretään. Käyttäjän näkökulman korostaminen on perusteltua myös siksi, että tietorakenne- ja algoritmikirjastojen käytön odotetaan lähivuosina merkittävästi kasvavan. Näiden kirjastojen myötä ohjelmoijat välttyvät samojen rakenteiden toistuvalta uudelleentoteuttamiselta, mutta joutuvat samalla sopeutumaan valmiina tarjolla olevien toteutusten määräämiin rajoituksiin. Tällaisen uuden ohjelmointikulttuurin omaksuminen ei käy hetkessä, vaan siihen on syytä ryhtyä sopeutumaan hyvissä ajoin. Painotan kurssilla algoritmien vaativuusanalyysiä, vaikka hyvin tiedänkin monien tietojenkäsittelytieteen opiskelijoiden aliarvioivan vaativuuden analysoinnin merkitystä. Algoritmiikan tutkimuksessa ei vaativuusanalyysiä voi välttää. Analysointitaitoa on myös helppo hyödyntää jopa hyvin yksinkertaisilta vaikuttavissa ohjelmointitehtävissä. Tahdon lausua kiitokseni kärsivällisille kuulijoilleni, jotka joutuivat keräämään nämä muistiinpanot osa osalta, joskus jopa sivu sivulta, muistiinpanojen valmistumisen myötä. Samoin kiitän perhettäni, joka on muistiinpanojen kirjoittamisen aikana tyytynyt toissijaiseen osaan. Kiitokset myös Tietojenkäsittelytieteen laitoksen kansliahenkilökunnalle sekä Yliopistopainolle tehokkaasta toiminnasta. Erityiset kiitokset ansaitsee vielä muistiinpanot tarkastanut FL Pirkko Voutilainen. Joensuussa 14. elokuuta 1997 Asko Niemeläinen

3 Sisällysluettelo Luku 1: Algoritmiikasta Ongelmasta ohjelmaksi Abstraktit tietotyypit Suorituksen vaativuus Suoritusajan laskeminen käytännössä 18 Luku 2: Abstraktit listatyypit Lista Pino Jono Pakka Rengas Taulukko Yhteenveto 36 Luku 3: Puut Puiden peruskäsitteistö Puu abstraktina tietotyyppinä Binääripuu 46 Luku 4: Joukot Määritelmiä Sanakirja Relaatio ja kuvaus Monilista Prioriteettijono Laukku 58 Luku 5: Verkot 59 Luku 6: Lajittelu eli järjestäminen Sisäinen lajittelu Yksinkertaisia lajittelualgoritmeja Pikalajittelu (Quicksort) Kasalajittelu Lomituslajittelu Kaukalolajittelu 67 Luku 7: Abstraktien tietotyyppien toteuttaminen Kotelointi ja parametrointi Listan toteuttaminen Listan erikoistapaukset Puiden toteuttaminen 83 Luku 8: Joukkojen toteuttaminen Yksinkertaiset joukkomallit Joukkojen erikoistapaukset Etsintäpuut Joukon läpikäynti Verkot 95 Kirjallisuutta 97

4 Luku 1 Algoritmiikasta Annetun ongelman ratkaisevan tietokoneohjelman laatiminen on monivaiheinen prosessi, josta valitettavan usein huomataan ainoastaan lopputulos eli valmis ohjelma. Sana "ohjelmointi" luo helposti mielikuvan yksin ohjelmakoodin kirjoittamisesta jättäen huomiotta koko ohjelmointiprosessin kannalta merkittävämmät työvaiheet. Luonnehditaan tämän luvun aluksi näitä työvaiheita, minkä jälkeen esitellään kurssilla tarvittavat perustyövälineet. 1.1 Ongelmasta ohjelmaksi Ongelman ratkaisemiseksi on välttämätöntä ymmärtää, mikä ongelma onkaan tarkoitus ratkaista. Tehtävänmäärittely on monasti kovin ylimalkainen ja epätäsmällinen, joten aivan aluksi on paikallaan määritellä ongelma riittävän yksityiskohtaisesti, jottei ratkaisulle asetetuista vaatimuksista jää epäselvyyttä. Esimerkiksi päällisin puolin yksinkertaiselta näyttävä tehtävä "Laadi ohjelma, joka laskee lukujen summan" on tarkemmin katsoen kovin puutteellisesti määritelty. Määrittelystä ei käy ilmi, minkä tyyppisiä lukuja on tarkoitus summata, kuinka monta lukuja tulee olemaan, mistä summattavat luvut saadaan ja mitä lasketulle summalle tehdään. Tehtävän täsmällisempi määrittely voisi olla vaikkapa "Laadi ohjelma, joka laskee ja tulostaa näppäimistöltä syötettävien kokonaislukujen summan. Syötteet loppuvat, kun näppäillään luku nolla." Kun ongelma on täsmennetty, voidaan ryhtyä suunnittelemaan ratkaisuperiaatetta eli ratkaisualgoritmia. Algoritmi määritellään eri lähteissä toisiinsa nähden hieman eri tavoin. Tällä kurssilla algoritmi tarkoittaa äärellistä käskyjonoa, jonka jokaisella käskyllä on yksiymmärteinen merkitys ja jonka jokainen käsky voidaan suorittaa äärellisellä työmäärällä äärellisessä ajassa. Lisäksi vaaditaan, että algoritmin suorituksen tulee aina päättyä, toisin sanoen algoritmi ei saa koskaan jäädä ikuiseen suoritukseen, ei edes odottamattomia syötteitä saadessaan. Vaatimus suorituksen päättymisestä rajaa joitakin kelvollisia ohjelmia algoritmien joukon ulkopuolelle. Esimerkiksi seuraava Java-menetelmä ei kelpaa algoritmiksi: public static void infinite() { 1 while (true); 2 } 3 1

5 1. ALGORITMIIKASTA 2 Toisaalta algoritmien joukkokaan ei ole ohjelmien joukon osajoukko, sillä algoritmia ei yleensä esitetä millään ohjelmointikielellä, vaan käytetään enemmän luonnollista kieltä muistuttavaa pseudokieltä. Pseudokielinen algoritmi on yksittäistä ohjelmaa yleisempi, koska pseudokielen yksityiskohdat toteutetaan eri ohjelmointikielillä eri tavoin. Pseudokielen käyttäminen algoritmien esittämisessä on perusteltua siksi, ettei algoritmin suunnitteluvaiheessa välttämättä edes tiedetä, millä kielellä ja millaisessa ympäristössä algoritmi tullaan toteuttamaan. Algoritmin tulisikin aina olla suuremmitta vaikeuksitta toteutettavissa millä tahansa ohjelmointikielellä. Tämä vaatimus on kohtuullinen, sillä rakenteisen ohjelmoinnin perustekniikat peräkkäisyys, toisto ja valinta luontuvat sellaisinaan pseudokieleen ja riittävät minkä tahansa (peräkkäis)algoritmin esittämiseen. Itse asiassa algoritmi edustaa korkeampaa abstraktiotasoa kuin ohjelma. Tällä kurssilla esiteltävien välineiden ja tekniikoiden yhtenä motiivina onkin algoritmien samoin kuin tiedon esittämisen abstraktiotason kohottaminen. Koska esimerkit ja harjoitukset on tarkoitus pystyä myös kääntämään ja suorittamaan, on kuitenkin käytännöllisintä käyttää jotakin ohjelmointikieltä algoritminotaation pohjana. Tällä kurssilla algoritmit esitetään pääosin Java-kielellä, kuitenkin käyttäen abstraktimpaa algoritminotaatiota (pseudokieleltä) apuna selkeyttämään algoritmeja. Ennen kuin algoritmia ryhdytään toteuttamaan eli koodaamaan ohjelmointikielelle, on syytä vakuuttua algoritmin oikeellisuudesta ja tehokkuudesta. Oikeellisuusnäkökohtiin ei tällä kurssilla puututa syvällisesti. Sen sijaan algoritmien tehokkuuden analysointi on yksi tämän kurssin keskeisimmistä aihepiireistä. Jos suunniteltu algoritmi todetaan tehottomaksi, on ratkaistava, kannattaako yrittää löytää tehokkaampi algoritmi, jos sellaista ylipäätään on edes olemassa, vai riittääkö tehotonkin algoritmi ratkaisuksi käsillä olevaan ongelmaan. Algoritmia vastaavaa ohjelmakoodia tuotettaessa täytyy pseudokielen käskyt ja rakenteet muuntaa ohjelmointikieliseen muotoon. Matalan abstraktiotason algoritmin koodaaminen on suoraviivainen tehtävä, mutta mitä korkeammalta abstraktiotasolta lähdetään liikkeelle, sitä monimutkaisempiin kysymyksiin täytyy toteutettaessa löytää vastaukset. Myös tehokkuusnäkökohtia joudutaan usein pohtimaan vielä toteutusvaiheessakin silloin kun tehdään valintoja erilaisten toteutusvaihtoehtojen välillä. Toteutusvaiheessa voidaan soveltaa esimerkiksi asteittaista tarkentamista, jonka avulla ehkä hyvinkin laaja toteutusprosessi kyetään pitämään hallitusti koossa. Algoritmin suunnitteluvaihe on tärkeä myös koodausvaiheen onnistumisen kannalta. Mitä tarkempi algoritmin suunnitelma on, sitä paremmin se ohjaa toteutusta oikeaan suuntaan. Erityisesti tarkan algoritmin pitäisi varmistaa, ettei toteutukseen lipsahda tehottomia osatoteutuksia. Erityisesti käytettäessä valmiita tietorakenne- ja aliohjelmakirjastoja, kuten Java API:a, on vielä varmistuttava niiden operaatioiden toiminnasta ja aikavaativuuksista. Jos valmiiden kirjastojen toteutukset tai operaatiot eivät olekaan aivan yhteensopivia algoritmimme kanssa, voi aikavaativuuteen helposti lipsahtaa kertaluokan lisä. Tälläistä on usein vaikea havaita pienimuotoisessa testauksessa, jolloin tehottomuus voi jäädä ohjelmistoon piileväksi, ja se havaitaan vasta myöhemmin käytettäessä suurempia aineistoja. Tätä ongelmaa pyrimme tällä kurssilla välttämään paneutumalla tarkemmin kirjastojen toteutukseen, sekä jossain määrin kokeellisella aikavaativuuden testaamisella TRA2-kurssilla. Koodauksen valmistuttua on muodostunut ohjelma vielä testattava mahdollisten koodaus- ja muiden virheiden havaitsemiseksi. Jos ongelma on alkujaan määritelty täsmällisesti ja algoritmi todettu oikeelliseksi, ovat mahdolliset virheet syntyneet toteutusai-

6 1. ALGORITMIIKASTA 3 kana ja ne pystytään toivottavasti korjaamaan käymättä koko raskasta prosessia läpi uudelleen. Toki virheet voivat silti olla hankalasti korjattavia, joten huolellisuus on toteutusvaiheessakin välttämätöntä. Selkeän algoritmin selkeä toteutus johtaa selkeään ohjelmaan, johon ehkä myöhemmin tarvittavien muutostenkin tekeminen onnistuu kohtuullisella työmäärällä, mutta sekavan ohjelman vähäinenkin muuttaminen voi osoittautua hankalaksi tehtäväksi. Joskus on jopa järkevämpää aloittaa työ uudelleen alkutekijöistään. Käytännössä muutostarpeita ilmenee varsin usein, joten muutosten mahdollisuuteen on pyrittävä varautumaan jo algoritmin suunnittelu- ja toteutusvaiheissa. Muutostarpeet aiheutuvat esimerkiksi itse ongelman määrittelyn muuttumisesta tai tehokkuuden lisäämisen vaatimuksesta. Näistä jälkimmäiseen puolestaan voidaan yrittää vaikuttaa joko algoritmia tehostamalla tai toteuttamalla algoritmin kriittiset yksityiskohdat entistä tehokkaammalla tavalla. Kaikkiin muutoksiin on luonnollisesti mahdotonta varautua, mutta huolellisesti rakennetun ohjelman osittainen muuttaminen ei aiheuta koko rakennelman romahtamista. Esimerkki 1-1: Tarkastellaan aiheeseen johdattelevana tehtävänä liikennevalojen vaiheistuksen suunnittelevan ohjelman rakentamista. Ohjelman tarkoituksena on ryhmitellä risteyksessä sallitut ajoreitit siten, että samaan ryhmään kuuluvat ajoreitit eivät leikkaa toisiaan toisin sanoen samassa liikennevalojen vaiheessa sääntöjen mukaisia reittejä ajettaessa ei voi sattua yhteentörmäystä ja että ryhmiä on mahdollisimman vähän, jolloin tarvittavien vaiheiden määrä minimoituu. Ohjelma saa syötteenään mahdolliset ajoreitit ja ohjelma tulostaa reittien optimaalisen ryhmittelyn. Havainnollistetaan ongelmaa kuvan 1-1 esittämällä risteyksellä, jossa kadut A ja C ovat yksisuuntaisia, kadut B ja D puolestaan kaksisuuntaisia. Mahdollisia ajoreittejä on kaikkiaan seitsemän erilaista. Niistä vaikkapa reitit AB ja DC voidaan ajaa samanaikaisesti, mutta reittien AC ja DB yhtäaikainen käyttäminen aiheuttaa yhteentörmäyksen vaaran. A A D B D * B C C Kuva 1-1: Katujen risteys Kuvataan ongelma verkkona eli graafina, joka koostuu joukosta solmuja ja joukosta näitä solmuja yhdistäviä kaaria. Verkkojen käsitteistö esitellään tarkemmin luvussa 5 ja TRA2-kurssilla. Esittäkööt solmut ajoreittejä ja olkoon verkossa kaari kahden solmun välillä vain siinä tapauksessa, ettei näitä kahta reittiä voida ajaa samanaikaisesti. Kuvan 1-1 risteystä vastaava verkko nähdään kuvassa 1-2. Taulukko 1-3 esittää saman verkon toisessa muodossa, taulukkona, jossa ykköset ilmaisevat kaaren olemassaolon ja tyhjät alkiot kaaren puuttumisen. Näistä esitysmuodoista kuva 1-1

7 1. ALGORITMIIKASTA 4 AB AC AD BC BD DB DC Kuva 1-2: Yhteentörmäävien reittien verkko. on ilman muuta ihmiselle ymmärrettävin ja taulukko 1-3 puolestaan tietokoneelle ymmärrettävin. Kuvan 1-2 esitys ei ole paras mahdollinen kummallekaan, mutta ongelmaa verkkona tarkasteltaessa se antaa tyhjentävän kuvan tilanteesta. Taulukko 1-3: Verkon matriisiesitys. AB AC AD BC BD DB DC AB 1 1 AC 1 1 AD BC 1 1 BD 1 1 DB 1 1 DC Väritetään nyt verkon solmut niin, ettei minkään kaaren molemmissa päissä käytetä samaa väriä. Alkuperäinen ongelma on ratkaistu, kun löydetään pienin määrä värejä, jolla verkon kaikki solmut saadaan väritetyksi rikkomatta väritysehtoa. Tällöin keskenään samanvärisiä solmuja vastaavat ajoreitit voidaan ajaa yhtaikaa eli ne muodostavat yhden vaiheen. Ohjelman tuloste saadaan suoraan solmujen värien mukaisesta ryhmittelystä. AB AC AD BC BD DB DC Kuva 1-4: Eräs mahdollinen ryhmittely.

8 1. ALGORITMIIKASTA 5 Ratkaisun keskeinen idea on siis muodostaa syötettä vastaava verkko, etsiä verkon optimaalinen väritys ja palauttaa värityksen tulos varsinaisen ongelman ratkaisuksi. Idean toteuttaminen ei valitettavasti ole aivan yksinkertaista. Miten esimerkiksi etsitään yhteentörmäyksen aiheuttavat reittiparit, kun syötteenä annetaan vain sallitut reitit? Tämä osaongelma voidaan onneksi ratkaista kohtuullisella työmäärällä (miten?), mutta väritysongelma osoittautuu erittäin vaikeaksi: kyseessä on niin sanottu NP-täydellinen ongelma, joka ei ratkea polynomisessa ajassa! Tämä algoritmitutkimuksen teoreettinen tulos on nyt hyödyllinen, koska sen ansiosta vältytään tuhlaamasta aikaa tehokkaan algoritmin turhaan etsimiseen tehokasta algoritmiahan ei ole olemassakaan. Minimaalisen värityksen tuottava tehoton algoritmi toki löytyy (millainen?), mutta sen asemesta lienee hyödyllisempää yrittää löytää heuristinen algoritmi, joka tuottaa nopeasti lähes optimaalisen värityksen, muttei välttämättä parasta väritystä. Hyvällä onnella heuristisen algoritmin antama tulos on jopa yhtä hyvä kuin optimaalinen tuloskin, eikä tulos huonommassakaan tapauksessa toivottavasti ole aivan surkea. Varsin kelvollinen heuristiikka verkon väritysongelmaan on aloittaa värittämällä yhdellä värillä niin monta solmua kuin väritysehtoa rikkomatta on mahdollista, jatkaa värittämällä toisella värillä jäljelle jääneistä solmuista niin monta kuin väritysehtoa rikkomatta on mahdollista ja niin edelleen, kunnes kaikki solmut on väritetty. Tässä on kyseessä niin sanottu ahne menetelmä, joka ei ota huomioon väritettävän verkon erityispiirteitä, vaan käsittelee verkosta kerrallaan niin suuren osan kuin suinkin pystyy. Verkon rakenteen lisäksi ahneen menetelmän antamaan tulokseen voi vaikuttaa se, mistä solmusta värittäminen aloitetaan, sekä se, missä järjestyksessä vielä värittämättömät solmut käydään läpi. Onkin helppo nähdä, ettei ahneen algoritmin tuottama tulos aina ole optimaalinen edes yksinkertaisen verkon tapauksessa. Eräs ahneen menetelmän tuottama kuvan 1-2 verkon väritys nähdään taulukossa 1-5 (joka vastaa kuvan 1-4 väritystä). Kyseinen verkko värittyy kolmella värillä, kun tarkastelu aloitetaan solmusta AB ja solmut käydään läpi kuvan 1-2 mukaisessa järjestyksessä vasemmalta oikealle ja ylhäältä alas. Voidaan jopa osoittaa, ettei tämän verkon värittäminen onnistu ainakaan vähemmällä kuin kolmella värillä: solmut AB, BC, DB, AC ja BD muodostavat niin sanotun kehän eli nämä solmut yhdistyvät kaarten välityksellä yksinkertaiseksi renkaaksi, ja koska tässä renkaassa on solmuja pariton määrä, tarvitaan sen värittämiseen kolme väriä. Koska kolmivärinen ratkaisu löytyi, on ongelma ratkennut optimaalisesti: kuvan 1-1 liikennevaloihin tarvitaan kolme vaihetta, yksi kutakin taulukossa 1-5 samalla värillä väritettyä reittijoukkoa kohden. Muitakin vaiheiden määrään nähden yhtä hyviä ratkaisuja on olemassa. Taulukko 1-5: Eräs mahdollinen ryhmittely. Väri sininen punainen vihreä Reitit AB, AC, AD, DC BC, BD DB

9 1. ALGORITMIIKASTA 6 Edellisessä esimerkissä nähtiin algoritmien suunnittelussa usein käytetty lähestymistapa, jossa ongelma muunnetaan toiseksi ongelmaksi, jonka ratkaisumenetelmä tunnetaan. Näin saatu ratkaisu on lopuksi osattava palauttaa alkuperäisen ongelman ratkaisuksi. Kyse on siis reaalimaailman ongelman abstrahoimisesta algoritmisesti käsiteltäväksi ongelmaksi, algoritmisen ongelman ratkaisusta ja ratkaisun muuntamisesta takaisin reaalimaaliman käsitteisiin. Jatketaan äskeisen ahneen menetelmän tarkastelua pseudokielen tasolla. Pseudokielen käskyiltä ja rakenteilta ei vaadita täsmällistä muotoa, vaan asiat ilmaistaan kulloinkin tarkoituksenmukaisella tarkkuudella. Liiallista ohjelmointikieleen tai tiettyyn toteutukseen johdattelevaa tarkkuutta on vältettävä, koska liiallisessa tarkkuudessa vaanii vaara abstraktion katoamisesta, mikä puolestaan voi estää hyvän lopputuloksen muotoutumisen. Esimerkki 1-2: Olkoon G verkko, jonka solmuista osa on ehkä jo väritetty. Seuraava algoritmi greedycolor värittää uudella värillä sellaiset solmut joiden värittäminen ei riko väritysehtoa. public static void greedycolor(graph G, Color newcolor) { 1 for each uncolored vertex v of G { 2 if (v not adjacent to any vertex with color newcolor) 3 v.setcolor(newcolor); 4 } 5 public static int greedycolorstart(graph G) { 6 mark all vertices non-colored; 7 int numofcolors = 0; 8 while (not all vertices colored) 9 greedycolor(g, ++numofcolors); 10 return numofcolors; 11 } 12 Väritysongelma ratkaistaan suorittamalla greedycolor-algoritmia toistuvasti (yllä greedy- ColorStart, rivit 9-10), kunnes verkon kaikki solmut on väritetty, ja laskemalla samalla algoritmin suorituskertojen lukumäärä. Algoritmin ensimmäinen versio sisältää monia vielä tarkennettavia kohtia, kuten tyyppien Graph ja Vertex määrittelyn, joukkomuuttujan tyhjäksi alustamisen, solmujoukon yli toistamisen ja solmujen välisen naapuruuden tutkimisen. Tarkennetaan näistä rivin 2 toisto käyttämällä Java:n kokoelman yli toistoa sekä ohittamalla jo väritetyt solmut. Tarkennetaan samoin rivin 3 ehtolause käymällä läpi solmun v naapurisolmut ja tutkimalla, onko yksikään niistä jo väritetty nyt käytössä olevalla värillä. Ellei näin ole, voidaan solmu v nyt värittää. Tarkennettuna algoritmi näyttää seuraavanlaiselta: public static void greedycolor(graph G, Color newcolor) { 1 for (Vertex x : G.vertices()) { 2 if (x.getcolor()!= nocolor) 3 continue; 4

10 1. ALGORITMIIKASTA 7 boolean found = false; 5 for (Vertex w : v.neighbors()) { 6 if (w.getcolor() == newcolor) 7 found = true; 8 } 9 if (! found) 10 v.setcolor(newcolor); 11 } 12 } 13 Vastaavasti olisi tarkennettava algoritmin käynnistysaliohjelmaa greedycolorstart. Jotta ratkaisusta saataisiin todella tehokas, on syytä ennen toistojen tarkentamista tarkistaa, miten verkkotyyppi on toteutettu. Se puolestaan edellyttää TRA2 kurssilla nähtävien tietorakenteiden tuntemusta, joten päätetään esimerkin käsittely tähän. 1.2 Abstraktit tietotyypit Esimerkeissä 1-1 ja 1-2 käytetty asteittaisen tarkentamisen idea on tuttu jo aiemmilta ohjelmointikursseilta, mutta verkko- ja joukkotyyppien toteuttamiseen ei muilla kursseilla ole vielä paneuduttu. Kaikkia näitä monimutkaisia tietotyyppejä ei Java-kirjastoon sisälly valmiina. Erityisesti Java-kirjaston kokoelmat ovat jossain määrin rajoittuneempia kuin mitä tällä kurssilla ajatellaan. Algoritmin suunnittelun kannalta olisi hyödyllistä jos esimerkiksi voitaisiin käyttää käsitettä "joukko" sekä tavanomaisia joukko-operaatioita kuten "yhdiste" ja "leikkaus" ikään kuin ne olisivat todella olemassa. Näin johdutaan abstrakteihin tietotyyppeihin, jotka ovat tiedon esittämisen ja käsittelyn malleja. Abstraktin tietotyypin määrittelyssä kuvataan aina kokoelma operaatioita, joilla tietotyypin esittämää tietoa käsitellään. Tämän operaatiokokoelman kuvaus muodostaa abstraktin tietotyypin liittymän. Liittymä yksin määrää sen, miten abstraktia tietotyyppiä saadaan käyttää. ADT voidaan ajatella kokoelmien hallinnan apuvälineenä. Hyötytietoelementit ADT Hyötytieto Kuva 1-6: ADT kokoelman ylläpidon apuvälineenä. "ripustetaan" ADT:n ylläpidettäväksi, jolloin meidän ei tarvitse huolehtia kokoelman ylläpitämisestä, vaan voimme keskittyä itse elementteihin liittyvään tietojenkäsittelytehtävään. Kuva 1-6 esittää ADT:n ja hyötytiedon suhdetta. ADT:n toteutusrakenne (kuvassa neliöt katkoviivan sisällä) on käyttäjän kannalta (lähes) yhdentekevä. Parhaimmillaan Looginen järjestys

11 1. ALGORITMIIKASTA 8 unohdamme koko ADT:n ja käsittelemme hyötytietoa (elementtejä) kuten ne itse osaisivat säilyttää itsensä ja järjestyksensä. Useimmiten tehtävämme elementeillä on jokin looginen järjestys jonka mukaan haluamme niitä käsitellä. Erilaisia järjestystarpeita varten määrittelemme erilaisia ADT:tä. Kuhunkin tarpeeseen on osattava valita oikeanlainen abstrakti tietotyyppi. Esimerkki 1-3: Joukko (abstraktina tietotyyppinä) on kokoelma keskenään samantyyppisiä alkioita, vaikkapa verkon solmuja. Joukkomallille tyypillinen piirre on se, että sama alkio voi sisältyä joukkoon vain yhtenä esiintymänä kerrallaan. Joukkoja käsitellään esimerkiksi muodostamalla kahden joukon yhdiste tai tutkimalla, kuuluuko jokin alkio joukkoon. Joukkotyypin liittymä voi sisältää vaikkapa seuraavankaltaisen osan: // returns union of this Set and Set B 1 public Set<E> union(set<e> B); 2 // returns whether Object x is a member of this Set or not 3 public boolean member(<e> x); 4 Tässä esiintyvä tyyppi <E> on joukon alkioiden tyyppi, joka luonnollisesti on eri ohjelmissa erilainen. Joukon alkiothan voivat itsekin olla joukkoja, kuten on laita esimerkiksi potenssijoukkojen tapauksessa. Liittymä antaa abstraktin tietotyypin käyttäjälle kaiken tarpeellisen tiedon tyypin käyttämiseksi, nimittäin sallitut operaatiot parametreineen ja tulostyyppeineen. Lisäksi liittymässä tulee mainita operaatioiden oikeellista käyttöä mahdollisesti rajoittavat ehdot. Jos käyttäjä noudattaa näitä ehtoja, on hänellä oikeus odottaa operaatioiden toimivan asianmukaisella tavalla. Ehtojen vastainen käyttö puolestaan voi johtaa virhetilanteeseen tai aiheuttaa muuten kummallisen toiminnan. Edelleen liittymän kuvauksen tulisi kertoa kunkin operaation aika- ja tilavaativuus. Java-kirjastojen dokumentaatiossa tämä on useimmiten kerrottu implisiittisesti tai ei lainkaan, mikä onkin niiden ehkä suurin puute. Abstrakti tietotyyppi voitaisiin määritellä aksiomaattisesti, jolloin liittymä ehtoineen saataisiin miltei sellaisenaan tietotyypin määrittelystä. Sivuutetaan tällä kurssilla aksiomaattinen lähestymistapa ja tarkastellaan abstrakteja tietotyyppejä pikemminkin intuitiivisesti. Olkoon tarkastelukulma mikä hyvänsä, on selvää, ettei pelkkä liittymä vielä mahdollista abstraktin tietotyypin konkreettista käyttämistä, vaan käyttämisen edellytyksenä on tietotyypin toteuttaminen. Toteutus voi pohjautua toisiin abstrakteihin tietotyyppeihin, jotka on edelleen toteutettava kukin erikseen. Lopulta toteutus palautuu ohjelmointikielen tarjoamiin valmiisiin välineisiin. Toteutus sisältää ainakin liittymässä kuvattujen operaatioiden ohjelmakoodin sekä abstraktia mallia vastaavan todellisen tietorakenteen määrittelyn. Toteutus on usein operaatioiltaankin liittymässä kuvattua laajempi, koska esimerkiksi todellisen tietorakenteen käsittelemiseksi saatetaan tarvita välineitä, joista käyttäjän ei tarvitse tietää mitään. Käyttäjä ei luonnollisesti näe todellista tietorakennettakaan, vaan käyttäjän mielikuvassa abstrakti tietotyyppi on sellaisenaan olemassa. Vastaavasti toteuttaja ei tiedä, millaisiin sovelluksiin toteutusta tullaan käyttämään, vaan ainoastaan sen, millaisia operaatioita käyttäjät tuntevat. Tällainen abstraktin tietotyypin koteloinnin idea helpottaa sekä käyttäjän että toteuttajan työtä. Käyttäjä näet välttyy toteutuksen yksityiskohtiin tutustumiselta ja voi sen sijaan paneutua tehokkaammin varsinai-

12 1. ALGORITMIIKASTA 9 sen ongelmansa ratkaisuun. Toteuttaja puolestaan voi keskittyä etsimään tehokasta toteutusta liittymän kuvaamalle abstraktille mallille. Kotelointi helpottaa myös tietotyypin toteutuksen muuttamista, jos se on tarpeen. Toteutusta voidaan näet muuttaa miten hyvänsä ilman, että käyttäjän tarvitsee edes tietää muutoksista, kunhan liittymä säilyy ennallaan. Toisaalta saman tietotyypin eri toteutuksia kyetään vaivattomasti vaihtelemaan esimerkiksi empiirisessä tutkimustyössä. Tähän saakka on käytetty tietotyypin ja tietorakenteen käsitteitä esittämättä niiden täsmällistä merkitystä. Määritellään nyt nämä kaksi käsitettä: Määritelmä 1-4: Muuttujan tietotyyppi on kyseisen muuttujan sallittujen arvojen joukko. Esimerkki 1-5: Kokonaislukujen tyyppi sisältää periaatteessa äärettömän monta arvoa: 0, 1, 1, 2, 2, 3, 3, Käytännössä tietokoneen sananpituus rajaa mahdollisten arvojen joukon aina äärelliseksi. Esimerkiksi 32 bitillä voidaan esittää eri lukua. Pascal-kielen tyypin set of 0..9 arvoja ovat joukot { }, {0}, {1}, {2}, {3},, {9}, {0, 1}, {0, 2},, {8, 9}, {0, 1, 2},, {0, 1, 2, 3, 4, 5, 6, 7, 8, 9}. Kaikkiaan näitä arvoja on 2 10 eli 1024 erilaista. Boolen tyypissä erilaisia arvoja on vain kaksi, false ja true. Määritelmä 1-6: Tietorakenne on kokoelma toisiinsa kytkettyjä muuttujia. Kyseessä on siis ohjelmointikielen rakenne josta bitit voidaan periaatteessa piirtää näkyviin. Joskin Javan tapauksessa bittien täsmällinen piirtäminen vaatisi hieman enemmän paneutumista Javan toteutukseen. Pelkkä kielen dokumentaatio ei riitä. Esimerkki 1-7: Java-kielen taulukot, tietueet ja tiedostot ovat tietorakenteita samoin kuin viitteiden avulla toisiinsa kytkettyjen dynaamisten muuttujien muodostamat monimutkaisemmatkin rakenteet. Ääritapauksessa yhtäkin muuttujaa voidaan sanoa tietorakenteeksi tällainen on esimerkiksi yhden kokonaisluvun sisältävä tietue. Abstraktin tietotyypin kuvaaman mallin toteutuksessa määritellään aina jokin todellinen tietorakenne. Käyttäjä ei näe tämän todellisen rakenteen sisältöä, vaan abstraktin mallin mukaisia arvoja, esimerkiksi tyhjän joukon. Toteuttaja puolestaan näkee todellisen rakenteen kaikki osaset, kuten esimerkiksi muuttujien välisten kytkentöjen toteuttamisessa käytettävät osoittimet. Toteuttajan on silti kyettävä hahmottamaan myös se abstraktin mallin mukainen arvo, jota todellinen rakenne kuvaa. Tietorakenteiden ja tietotyyppien käsittelyyn sekä niiden määrittelytapoihin palataan esimerkkien kera luvussa 2. Samalla pohditaan miten abstrakteja rakenteita pitää konkretisoida jotta ne olisi toteutettavissa oikeilla ohjelmointikielillä.

13 1. ALGORITMIIKASTA Suorituksen vaativuus Kun saman ongelman ratkaisemiseksi tunnetaan useita erilaisia algoritmeja, on näistä osattava valita kulloiseenkin sovellukseen tarkoituksenmukaisin. Valinta perustuu usein seuraaviin kahteen kriteeriin: 1) Algoritmin tulee olla helppo ymmärtää ja toteuttaa. 2) Algoritmin tulee olla tietokoneen muistitilan ja ajankäytön suhteen tehokas. Ikävä kyllä nämä kriteerit ovat usein keskenään ristiriidassa, sillä ihmisen ymmärrettäväksi helppo algoritmi saattaa olla kovin hidas, mutta tehokkaan algoritmin toiminnan ymmärtäminen voi tuottaa suuria vaikeuksia, toteuttamisen vaikeuksista puhumattakaan. Jollei sama algoritmi täytä molempia kriteerejä, kannattaa valinta tavallisesti perustaa käyttötarpeeseen. Muutaman kerran käytettävältä ohjelmalta ei ole järkevää vaatia äärimmäistä tehokkuutta, kun taas toistuvasti tarvittavan ohjelman on paras olla tehokas. Samoin odotettavissa oleva syötteen koko vaikuttaa algoritmin valintaan. Jos voidaan esimerkiksi varmasti ja perustellusti olla varmoja, ettei syötteen koko koskaan tule olemaan enempää kuin muutamia satoja, eikä sekunti suoritusaikana ole liikaa, meille riittää hieman hitaampi algoritmi, eikä ole perusteltua tuhlata aikaa tehokkaamman mahdollisen algoritmin toteuttamiseen. Yleisesti kuitenkin meidän voi olla vaikea nähdä kaikkia mahdollisia tulevaisuudessa käytettäviä syötekokoja. Algoritmien tehokkuutta arvioitaessa käytetään erilaisia vaativuuden käsitteitä. Käytännössä useimmin tarkastellaan algoritmin aikavaativuutta eli arvioidaan algoritmin suoritusaikaa. Joskus ollaan kiinnostuneita myös tilavaativuudesta, jolloin arvioidaan algoritmin suorituksen vaatiman aputilan tarvetta. Aputila tarkoittaa tässä algoritmin syötteiden ja tulosteiden tallettamisen lisäksi tarvittavaa muistitilaa. Joskus joudutaan paneutumaan myös laitteistovaativuuteen, kuten esimerkiksi selvitettäessä, kuinka monta ulkoista muistivälinettä algoritmin tehokas toteuttaminen edellyttää tai kuinka nopeasti tietoja on pystyttävä vaihtamaan eri laitteiden kesken. Muisti- ja muut resurssit ovat tosin nykyisin yhä harvemmin tehokkuuden pullonkauloja. Tällä kurssilla arvioidaan lähinnä aikavaativuutta, mutta paikoin tarkastellaan muitakin vaativuuskysymyksiä. Aikavaativuutta arvioitaessa on tärkeä ymmärtää, että vaativuudeltaan erilaistenkin algoritmien todellisten suoritusaikojen erot ovat merkityksettömiä pienten ongelmien käsittelyssä. Vasta kooltaan suuret ongelmat paljastavat algoritmin hitauden. Erot voivat tällöin olla dramaattiset. Ongelman pienuus ja suuruus puolestaan ovat suhteellisia käsitteitä. Esimerkiksi lajitteluongelma on pieni, kun lajiteltavana on kymmeniä alkioita, mutta joillekin verkkoalgoritmeille kymmensolmuinen verkkokin voi olla suuri käsiteltävä. Ohjelman suoritusaikaa voitaisiin mitata kellolla. Tällainen mittaaminen ei kuitenkaan tuottaisi vertailukelpoisia tuloksia, koska kulloiseenkin suoritukseen kuluvan ajan pituuteen vaikuttavat monet sellaiset tekijät, joita on vaikea tai jopa mahdoton kontrolloida. Näitä ovat esimerkiksi käytetty kääntäjä ja laitteisto sekä laitteiston hetkelliset kuormituserot. Absoluuttisen suoritusajan mittaamisen asemesta onkin mielekkäämpää arvioida suhteellista suoritusaikaa, jonka arviointi onnistuu paitsi ohjelmille, myös algoritmeille. Tämä on algoritmin suunnittelijan kannalta merkittävä etu, koska sen ansiosta voidaan keskenään vertailla vielä toteuttamattomiakin algoritmeja ja siten välttää tehottomaksi todetun algoritmin toteuttamisesta aiheutuva turha työ. Suoritusajan yksikkönä

14 1. ALGORITMIIKASTA 11 käytetään joustavaa termiä "askel". Kuva 1-7 havainnollistaa erään tulkinnan, myöhemmin tarkennamme käsitettä edelleen. a = 1; 1 b = 3; 2 for (i = 0; i < 1000; i++) 1 a = a + 1; 2 (n.) kaksi askelta (n.) 1000 askelta Kuva 1-7: Suoritusaskel. Suoritusaika suhteutetaan tavallisesti algoritmin syötteen kokoon. Syöte on tässä ymmärrettävä laajasti: algoritmi voi saada syötteensä suoraan käyttäjältä, tiedostoista tai vaikkapa parametrien välityksellä. Joissakin tapauksissa varsinaista syötettä ei ole lainkaan olemassa. Silloin suorituksen kesto määräytyy esimerkiksi käytettyjen vakioiden arvoista. Satunnaisuuteen perustuvien algoritmien aikavaativuuden arvioinnissa puolestaan sovelletaan todennäköisyyslaskennan menetelmiä (satunnaisalgoritmeja käsitellä lyhyesti TRA2 kurssilla). Syötteestäkään eivät kaikki osat aina ole aikavaativuutta arvioitaessa mielenkiintoisia, kuten seuraavassa esimerkissä todetaan: Esimerkki 1-8: Lukekoon algoritmi ensiksi sata kokonaislukua ja sen jälkeen vielä mielivaltaisen määrän muita syötteitä, joihin kaikkiin sovelletaan jotakin sadan ensimmäisen syötteen määräämää laskentaa. Koska algoritmin jokaisella suorituskerralla luetaan mainitut sata lukua, ei niiden lukeminen vaikuta suhteelliseen suoritusaikaan. Sen sijaan syötteen loppuosan vaikutus on olennainen: viisi syötettä luetaan ja käsitellään varmasti nopeammin kuin miljoona syötettä. Siirräntään kuluvaa aikaa ei vaativuusanalyysissä useinkaan oteta lukuun, koska siirrännän nopeuteen vaikuttavat algoritmista riippumattomat tekijät. Syötteen oletetaankin tavallisesti olevan jollakin tavoin valmiina saatavilla, esimerkiksi lajiteltavien alkioiden taulukossa, josta ne saadaan vaivattomasti esiin. Tällä oletuksella ei yleensä ole merkitystä suoritusaikaa määrättäessä, mutta joskus syötteiden käsittelyyn kuluva aika on erityisesti huomattava ottaa aika-arvioon mukaan. Näin on laita seuraavan esimerkin tapauksessa: Esimerkki 1-9: Algoritmi lukee kokonaislukuja, kunnes syötteenä annetaan sama luku viisi kertaa peräkkäin. Lopuksi algoritmi tulostaa neljännen lukemistaan luvuista. Mikä on algoritmin suoritusaika? Koska algoritmi tulostaa neljännen syötteensä, joka saadaan selville, kun on ensin luettu kolme muuta syötettä, syntyy helposti käsitys, että algoritmin suoritukseen kuluva aika on "4" eli vakio. Tämä käsitys paljastuu asiaa tarkemmin pohdittaessa virheelliseksi: Algoritmin suoritus päättyy vasta sitten, kun kaikki syötteet on saatu luetuksi. Mielivaltaista määrää kokonaislukuja ei mitenkään pystytä lukemaan vakioajassa, vaan aikaa kuluu sitä enemmän, mitä useampia lukuja algoritmille syötetään. Sen vuoksi suoritusajan määrääkin nyt syötteen lukemiseen kuluva aika, toisin sanoen syötteen todellinen koko.

15 1. ALGORITMIIKASTA 12 Syötteen tai sen vastineen suoritusajan arvioimisen kannalta merkityksellisen osan tunnistamista varten ei voida antaa täsmällisiä ohjeita. Taito tähän tunnistamiseen kehittyy harjoituksen myötä. Varsin usein tunnistaminen itse asiassa onkin triviaali tehtävä. Syötteen koko saattaa vaihdella suorituskerrasta toiseen, mutta aikavaativuus tulisi pystyä arvioimaan yleisesti algoritmin mielivaltaiselle suoritukselle. Sen vuoksi suoritusaika esitetään syötteen koon funktiona. Jos syötteen kokoa merkitään n:llä, on luontevaa käyttää suoritusaikafunktiolle merkintää T(n). Näinollen askelten määrä ilmaistaan syötteen funktiona, esimerkiksi: for (i = 0; i < n; i++) 1 a = a + 1; 2 (n.) n askelta Mikäli syöte koostuu useista toisistaan riippumattomista osasista, jotka kaikki ovat aikaarvioiden kannalta merkittäviä, käytetään syötteen koon kuvaamiseen useita muuttujia ja vastaavasti suoritusaikakin ilmaistaan usean muuttujan funktiona. Aina on muistettava varmistaa, että suoritusaikafunktiossa käytettävien tunnusten (esim. n) merkitys on selkeä, eli kertoa mitä syötteen ominaisuutta ne kuvaavat. Vastaavasti, jos annetun ohjelmanosan syötteen kokoa merkitään jollain muulla kirjaimella, myös aikavaativuusfunktio annetaan sitä käyttäen. Jos sitten muuttuja korvataan toisella, muutos on tehtävä myös aikavaativuusfunktioon. Esimerkki 1-10: Suoritusaikafunktio T(n) =cn 2 + b, missä b ja c ovat vakioita, ilmaisee suoritusajan olevan neliöllinen suhteessa syötteen kokoon n. Tämä merkitsee, että syötteen koon kymmenkertaistuessa suoritusaika suurin piirtein satakertaistuu. Esimerkki 1-11: Esimerkiksi merkkijonon etsinnän toisesta merkkijonosta aikavaativuus riippuu sekä etsittävästä avaimesta, että läpikäytävästä kohdetekstistä. Kuvataan avaimen pituutta m:llä ja kohdetekstin pituutta n:llä. Erään yksinkertaisen etsintäalgoritmin suoritusaikafunktio on T(n, m) = cnm, missä c on vakio. Funktion T mittayksikköä ei kiinnitetä. Voidaan ajatella, että lasketaan algoritmin suorittamien käskyjen tai muiden keskeisten perustoimintojen lukumäärä. Taito nähdä, minkä toimintojen lukumäärä kulloinkin on mielekästä laskea, kehittyy harjoituksen myötä samoin kuin syötteen koon tunnistamisen taitokin. Funktion lausekkeessa esiintyvien vakioiden todelliset arvot taas riippuvat käytettävästä kääntäjästä ja laitteistosta, joiden vaikutusta ei voida ennakoida. Sen vuoksi näiden vakioiden merkitykselle ei pidä antaa liian suurta painoa. Tärkeimpiä ovat syötteen kokoa sisältävät termit. Suoritusaika ei aina riipu pelkästään syötteen koosta, vaan myös syötteen laadusta. Kun tämä otetaan huomioon, voidaan tarkastelu eriyttää seuraaviin kolmeen tapaukseen: 1) T(n) tarkoittaa pahimman tapauksen suoritusaikaa eli pisintä mahdollista n:n kokoisen syötteen vaatimaa suoritusaikaa. 2) T avg (n) tarkoittaa keskimääräistä suoritusaikaa eli kaikkien n:n kokoisten syötteiden vaativien suoritusaikojen keskiarvoa. 3) T best (n) tarkoittaa parhaan tapauksen suoritusaikaa eli lyhintä mahdollista n:n kokoisen syötteen vaatimaa suoritusaikaa.

16 1. ALGORITMIIKASTA 13 Kuten jo merkinnöistäkin nähdään, tarkastellaan yleensä aina pahinta tapausta, ellei erityisesti mainita jostakin muusta tapauksesta. Paras tapaus ei useinkaan ole edes mielenkiintoinen. Esimerkiksi lajittelussa paras tapaus voisi olla valmiiksi lajiteltu kokoelma. Tämä tuskin kertoo lajittelualgoritmin hyvyydestä mitään. Keskimääräisen suoritusajan arviointi saattaa puolestaan osoittautua erittäin hankalaksi tehtäväksi, koska kaikki samankokoiset syötteet voidaan vain harvoin olettaa keskenään yhtä todennäköisiksi. Pahimman tapauksen tarkka analysointikin voi tosin joskus olla vaivalloista. Jos esimerkiksi sama syöte ei ole pahin algoritmin kaikille osille, joudutaan ensin etsimään kokonaisvaikutukseltaan pahin syöte. Seuraavassa esitettävä kertaluokkatarkastelu kuitenkin helpottaa analysointia melkoisesti. Kertaluokat Kun algoritmien suoritusajat ilmaistaan syötteen koon funktioina, voidaan aikoja vertailla toisiinsa funktioiden kasvunopeuksia vertailemalla. Vakiokerrointen todellisten arvojen häilyvyyden vuoksi tarkastelua ei viedä äärimmilleen, yksittäisten funktioiden tasolle, vaan tarkastellaan funktioiden kertaluokkia. Kertaluokkatarkastelussa käytetään apumerkintöjä O, Ω, Θ ja o, joiden merkitys määritellään seuraavasti: Määritelmä 1-12: Kertaluokkamerkinnät O, Ω, Θ ja o. 1) T(n) =O(f(n)), jos on olemassa positiiviset vakiot c ja n 0 siten, että T(n) cf(n), kun n n 0. [Lue: T(n) on kertaluokkaa f(n), iso-o, ordo; "rajoittaa ylhäältä"] 2) T(n) =Ω(g(n)), jos on olemassa positiiviset vakiot c ja n 0 siten, että T(n) cg(n), kun n n 0. [omega; "rajoittaa alhaalta"] 3) T(n) =Θ(h(n)), jos T(n) =O(h(n)) ja T(n) =Ω(h(n)). [theta; "rajoittaa ylhäältä ja alhaalta"] 4) T(n) =o(p(n)), jos T(n) =O(p(n)) ja T(n) Θ(p(n)). [pikku-o; "rajoittaa aidosti ylhäältä"] Ensimmäinen määritelmistä antaa suoritusaikafunktion T kasvunopeudelle ylärajan: kyllin suurilla n:n arvoilla funktio T kasvaa enintään yhtä nopeasti kuin vakiolla c kerrottu funktio f. Toinen määritelmä antaa vastaavasti kasvunopeuden alarajan: kyllin suurilla n:n arvoilla funktio T kasvaa vähintään yhtä nopeasti kuin vakiolla c kerrottu funktio g. Kolmas määritelmä sitoo funktion T kasvunopeuden samaksi kuin on funktion h kasvunopeus. Viimeinen määritelmä rajaa funktion T kasvunopeuden aidosti hitaammaksi kuin funktion p kasvunopeus, eli kaikilla vakiolla c on T(n)<cp(n), kun n on kyllin suuri. Määritelmät esitetään joissakin lähteissä hieman eri muotoisina, mutta olennaisesti samaa tarkoittavina. Tällä kurssilla käytetään lähinnä vain ylärajan ilmaisevaa O-merkintää, vaikka usein voitaisiin sen asemesta käyttää täsmällisempää Θ-merkintää. Ylärajaominaisuus on näet transitiivinen, toisin sanoen jos f(n) = O(g(n)) ja g(n) = O(h(n)), niin silloin myös f(n) = O(h(n)). Tämä merkitsee, että ylärajoja on aina useita. Θ-merkinnän määräämä rajafunktio sen sijaan on yksiymmärteinen: mahdollisimman tiukka. Ylärajoistakin pyritään aina löytämään tiukin, jotta kertaluokkavertailut vastaisivat tarkoitustaan.

17 1. ALGORITMIIKASTA 14 Esimerkki 1-13: Olkoon T(n) = 5n+2. Silloin T(n) = O(n), mikä nähdään vaikkapa valitsemalla c = 7 ja n 0 =1: 5n+2 5n+2n = 7n, kun n 1. Ylärajan n rinnalle kelpaisivat myös ylärajat n 2, n 3 ja niin edelleen. Koska T(n) = Ω(n), mikä nähdään esimerkiksi valitsemalla c = 5 ja n 0 = 1, on n myös alaraja, joten n on tiukin yläraja ja itse asiassa T(n)=Θ(n). Määritelmässä 1-12 esiintyvien epäyhtälöiden ei tarvitse päteä arvoilla n < n 0. Usein funktioiden keskinäinen järjestys pienillä n:n arvoilla poikkeaakin siitä järjestyksestä, joka vallitsee tarkasteltaessa suuria n:n arvoja. Esimerkiksi 5n+2 > 6n, kun n = 1, ja vasta kun n 2, on 5n+2 6n. Aikavaativuustarkastelussa pienet n:n arvot ovat merkityksettömiä, koska vasta suuret syötteet paljastavat algoritmien suoritusaikojen kertaluokkien erot. Kertaluokkaa arvioitaessa voidaan määritelmässä 1-12 esiintyvät vakiot c ja n 0 valita vapaasti, kunhan valinta vain toteuttaa määritelmän epäyhtälön. Esimerkin 1-13 yläraja n olisi löytynyt myös valitsemalla c =6 ja n 0 = 12, c =70 ja n 0 = 1 tai jollakin muulla tavoin. Ylärajatarkastelussa negatiiviset termit on helppo pudottaa pois ja positiiviset on siis saatava sulautumaan merkitsevimpään termiin. Esimerkki 1-14: Ylärajatarkastelu: T(n)=2n 2 4n+5. 2n 2 4n+5 2n n 2 +5 n 2 =7n 2, eli 2n 2 4n+5 = O(n 2 ). Alarajatarkastelussa on päinvastoin positiiviset termit helppo pudottaa pois ja negatiiviset termit on saatava sulautumaan merkitsemimpään termiin. Sulauttamisessa on varottava ettei merkitsevin termi mene negatiiviseksi (negatiivisia suoritusaikoja ei vielä ole keksitty!). Esimerkki 1-15: Alarajatarkastelu: T(n) =2n 2 4n+5. 2n 2 4n+5 2n 2 4n 2n 2 4n 2n 2 1 4n -- n [pitää paikkansa kun n 4] = 1n 2, eli 2n 2 4n+5 = Ω(n 2 ). 4 1 Alarajatarkastelussa voidaan lisätä kerroin -- n negatiiviseen termiin, sillä kun n 4 4 (siis n 0 = 4), niin negatiivinen termi on entistä suurempi ja siten pienentää kokonaisuutta. Esimerkiksi kerroin n olisi sensijaan tehnyt koko funktion negatiiviseksi ja siten mahdottomaksi. Esimerkki 1-16: Esimerkkien 1-14 ja 1-15 nojalla 2n 2 4n+5 = Θ(n 2 ). Ellei epäyhtälön toteuttavia vakioita laisinkaan löydy, on kertaluokkayrite tarkasteltavaan funktioon nähden väärä. Näytettäessä ettei funktio f(n) ole kertaluokkaa g(n) on toisin sanoen osoitettava, ettei ole olemassa sellaisia positiivisia vakioita c ja n 0, että epäyhtälö f(n) cg(n) pätisi kaikilla arvoilla n n 0. Esimerkki 1-17: Näytetään, ettei funktio T(n) = 5n+2 ole kertaluokkaa 1 eli vakio: Jos olisi T(n) = O(1), niin määritelmän 1-12 nojalla olisi olemassa positiiviset vakiot c ja n 0 siten, että 5n+2 c, kun n n 0. Epäyhtälöt 5n+2 c ja n (c 2)/5 ovat yhtäpitävät. Koska c on vakio, on myös (c 2)/5 vakio. Tämä merkitsee, ettei epäyhtälö 5n+2 c toteudu ainakaan silloin, kun n > max{n 0,(c 2) /5}, mikä on vastoin oletusta. Ristiriita, eli väite on väärä.

18 1. ALGORITMIIKASTA 15 Kertaluokkatarkastelussa ei suoritusaikafunktioiden lausekkeissa esiintyvillä vakiokertoimilla ja vakiotermeillä ole merkitystä. Esimerkiksi funktiot 2n ja n ovat molemmat O(n), mikä nähdään esimerkiksi valitsemalla c = ja n 0 = 1. Näiden funktioiden arvot toki poikkeavat toisistaan huomattavasti, mutta ne kasvavat samaa vauhtia. Sen sijaan esimerkiksi kertaluokat n ja n 2 ovat olennaisesti erilaiset: kun n kasvaa, kasvaa n 2 yhä vauhdikkaammin. Kahdesta eri kertaluokkaa olevasta algoritmista kertaluokaltaan pienempi on yleensä myös tehokkaampi. Pienillä syötteillä tilanne tosin voi kääntyä päinvastaiseksi, mutta pienillä syötteillä suoritusajalla ei yleensä ole merkitystä. Suoritusaika (T(n)) n 3 2 n logn n Syötteen koko (n) n 2 nlog 2 n n n nlogn 3n n+10 Kuva 1-8: Eri funktioiden kasvunopeuksia. Huomaa, että suurinkin kuvassa näkyvä n on varsin pieni, 30. Suuremmilla n:n arvoilla jotkin funktiot vielä vaihtavat järjestystä. Esimerkki 1-18: Kuva 1-8 esittää kymmenen aikavaativuudeltaan eri kertaluokkaa ole- 400 van ohjelman suoritusajat syötteen koon funktioina. Ajat on mitattu millisekunteina ja kaikki mittaukset on tehty samalla laitteistokokoonpanolla. Graafisesti eri funktioiden kasvunopeutta on vaikea tarkastella, varsinkaan suuremmilla n:n arvoilla. Esimerkiksi kuvasta on vaikea uskoa, että nlog 2 n = o( n n). Sensijaan taulukosta 1-9 näemme saman asian paremmin numeerisessa muodossa. Taulukossa on esitetty kymmenen eri ohjelman aikavaativuuksien vaikutus käsiteltävissä olevaan syötteeseen. Oletamme, että yhden operaation viemä aika on yksi millisekunti. Kullekkin ohjelmalle on laskettu se syötteen koko, jonka ne ehtivät käsitellä yhdessä sekunnissa, minuutissa, jne. Esimerkiksi aikavaativuudeltaan n oleva ohjelma ehtii minuutissa käsittelemään syötteen, jossa on alkiota. Näemme, että logaritmista aikavaativuutta oleva ohjelma ehtii varmasti käsitellä sekunnissa kaiken tarvittavan tiedon. (Tosin logaritmista aikavaativuuttahan ei peräkkäisalgoritmeissa

19 1. ALGORITMIIKASTA 16 Taulukko 1-9: Aikavaativuuserot numeroina. Aikavaativuus T(n), ms Ohjelman käsittelemän syötteen koko n annetussa ajassa: Sekun nissa Minuutissa Tunnissa Päivässä Vuodessa logn n n n nlogn nlog 2 n n n n n n voi koko algoritmilla ollakaan. Algoritmin osa, kuten binäärihaku, voi olla logaritminen aikavaativuudeltaan). Aikavaativuudeltaan O(n) ja O(nlogn) olevat ohjelmat hyötyvät lisääntyneestä ajasta edelleen hyvin. Sensijaan O(n 2 )jao(n 3 ) hyötyvät jo huomattavasti vähemmän. Eksponentiaalinen O(2 n ) ohjelma ei kykene käsittelemään suuria tietomääriä, vaikka sitä suoritettaisiin vuosia. Samanlaisia tuloksia voitaisiin havaita vaikka yksi operaatio kestäisi millisekunnin sijasta nanosekunnin. Aikavaativuuksien luokittelu Käytännössä aikavaativuusfunktioiden vertailu on melko helppoa. Tärkeintä on havaita suoritusaikafunktiosta merkittävin tekijä, käytännössä siis nopeimmin kasvava osa. Perusmuotoisen funktion lisäksi aikavaativuudessa voi olla jokin osa peruslaskutoimituksella (, /, +, ) mukaan liitettynä. Tällöin sen aiheuttama muutos on tietysti otettava huomioon. Nopeimmin kasvavia funktioita ovat eksponenttifunktiot, kuten, esimerkiksi 2 n, 3 n,2 n /n. Näissä syötteen koko on siis ykköstä suuremman luvun eksponenttina. Käytännössä useimmat aikavaativuudet ovat polynomisia, esimerkiksi n, n 2, n 5, n 12345, n3 n. Mitä suurempi eksponentti, sitä suurempi aikavaativuus. Polynomisiin kuuluvat myös aikavaativuudet muotoa n c, missä 0<c<1 on. Nämä ovat alilineaariasia, ts. o(n). Näitäkin hitaammin kasvavia ovat logaritmiset aikavaativuudet, kuten logn, loglogn, (logn) 2. Vakiofunktiot (O(1)) eivät kasva lainkaan. Eri kertaluokkafunktioiden keskinäisen järjestyksen selvittäminen voi joskus olla pulmallista. Tämäntyyppinen ongelma ratkeaa lähes aina niin sanottua L'Hôspitalin sääntöä soveltaen (derivoimalla osamäärän molemmat puolet): jos lim n f(n)= ja lim n g(n) =, niin (1-1) lim n (f(n)/g(n)) = lim n (f'(n)/g'(n)). Sääntöä sovelletaan toistuvasti, kunnes raja-arvo saadaan selville. Jos raja-arvo on

20 1. ALGORITMIIKASTA 17 0, on f(n)=o(g(n)) (1-2) c 0,on f(n)=θ(g(n)), on g(n) =o(f(n)). Ellei raja-arvo ole yksiymmärteinen, ei kertaluokkia voida asettaa järjestykseen. Esimerkki 1-19: nlogn vs. n 1,5 f(n) = nlogn g(n) = n 1,5 (1-3) f (n) = logn g (n) = --n ln2 2 (1-4) 1 3 f (n)= g (n) = nln2 4 n (1-5) nln2 4 n lim = lim = 3 n 3nln n n 4 lim ln2 n n (1-6) f ( n) = ogn ( ( )), ts. nlogn = o(n 1,5 ) (1-7) Sama voidaan todeta epämuodollisemmin päättelemällä: nlogn?? n 3/2 :n (1-8) logn?? n 1/2 ( ) 2 (1-9) log 2 n?? n (1-10) Kun muistetaan, että log k n=o(n), niin voimme todeta, että n 3/2 kasvaa nopeammin. Usein kertaluokkien järjestys voidaan päätellä yksinkertaisemminkin kuin laskemalla derivaattoja ja raja-arvoja. Esimerkiksi n k = o(n k+1 ) kaikilla vakioilla k. Edellisen tarkastelun perusteella voidaan todeta, että laitteiston tehokkuuden lisäyksen asemesta olisikin tuottoisampaa pyrkiä nopeuttamaan ohjelmia, toisin sanoen tulisi pyrkiä suunnittelemaan entistä tehokkaampia algoritmeja. Tämä on haasteellinen tehtävä, sillä moniin usein esiintyviin ongelmiin tunnetaan toistaiseksi vain tehottomia ratkaisuja, vaikka tehokkaitakin ratkaisuja saattaa olla olemassa. Joillekin ongelmille taas on osattu todistaa vaativuuden alaraja eli on näytetty, ettei ongelmaa voida ratkaista alarajaa nopeammin. Yksi näistä ongelmista on yleinen lajitteluongelma, jonka aikavaativuus on O(nlogn). Tämä alaraja on jo saavutettu, mutta jotkin muut todistetut alarajat ovat vielä teoreettisia. On myös olemassa joukko ongelmia, joita ei lainkaan voida ratkaista algoritmisesti, kuten esimerkiksi pysähtymisongelma. Algoritmiikan piirissä onkin vielä runsaasti tutkittavaa ja tässä tutkimustyössä vaativuusanalyysin rooli on keskeinen. Vaativuusanalyysiä tarvitaan jopa yksittäistä algoritmia tehostettaessakin, sillä algoritmin tehottomat osat täytyy löytää ennen kuin tehostamisyrityksiä kannattaa edes aloittaa. Johtopäätöksenä voitaisiin sanoa, että prosessorin kellotaajuuden kymmenkertaistamisen hyöty on aika pieni verrattuna algorimin kehittämiseen vaikkapa O(n 2 ):sta O(nlogn):een.

Tietorakenteet ja algoritmit I TRAI 29.8.2011/SJ Luentomuistiinpanoja

Tietorakenteet ja algoritmit I TRAI 29.8.2011/SJ Luentomuistiinpanoja Tietorakenteet ja algoritmit I Luentomuistiinpanoja Simo Juvaste Asko Niemeläinen Itä-Suomen yliopisto Tietojenkäsittelytiede Alkusanat Tämä moniste perustuu valtaosaltaan aiemman Tietorakenteet ja algoritmit

Lisätiedot

Tietorakenteet ja algoritmit - syksy 2015 1

Tietorakenteet ja algoritmit - syksy 2015 1 Tietorakenteet ja algoritmit - syksy 2015 1 Tietorakenteet ja algoritmit - syksy 2015 2 Tietorakenteet ja algoritmit Johdanto Ari Korhonen Tietorakenteet ja algoritmit - syksy 2015 1. JOHDANTO 1.1 Määritelmiä

Lisätiedot

Algoritmit 1. Luento 2 Ke Timo Männikkö

Algoritmit 1. Luento 2 Ke Timo Männikkö Algoritmit 1 Luento 2 Ke 11.1.2017 Timo Männikkö Luento 2 Algoritmin esitys Algoritmien analysointi Suoritusaika Asymptoottinen kertaluokka Peruskertaluokkia NP-täydelliset ongelmat Algoritmit 1 Kevät

Lisätiedot

Tietorakenteet ja algoritmit Johdanto Lauri Malmi / Ari Korhonen

Tietorakenteet ja algoritmit Johdanto Lauri Malmi / Ari Korhonen Tietorakenteet ja algoritmit Johdanto Lauri Malmi / Ari 1 1. JOHDANTO 1.1 Määritelmiä 1.2 Tietorakenteen ja algoritmin valinta 1.3 Algoritmit ja tiedon määrä 1.4 Tietorakenteet ja toiminnot 1.5 Esimerkki:

Lisätiedot

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

f(n) = Ω(g(n)) jos ja vain jos g(n) = O(f(n)) Määritelmä: on O(g(n)), jos on olemassa vakioarvot n 0 > 0 ja c > 0 siten, että c g(n) kun n > n 0 O eli iso-o tai ordo ilmaisee asymptoottisen ylärajan resurssivaatimusten kasvun suuruusluokalle Samankaltaisia

Lisätiedot

Algoritmit 1. Luento 3 Ti Timo Männikkö

Algoritmit 1. Luento 3 Ti Timo Männikkö Algoritmit 1 Luento 3 Ti 17.1.2017 Timo Männikkö Luento 3 Algoritmin analysointi Rekursio Lomituslajittelu Aikavaativuus Tietorakenteet Pino Algoritmit 1 Kevät 2017 Luento 3 Ti 17.1.2017 2/27 Algoritmien

Lisätiedot

Algoritmit 2. Luento 1 Ti Timo Männikkö

Algoritmit 2. Luento 1 Ti Timo Männikkö Algoritmit 2 Luento 1 Ti 14.3.2017 Timo Männikkö Luento 1 Algoritmi Algoritmin valinta Algoritmin analysointi Algoritmin suoritusaika Peruskertaluokkia Kertaluokkamerkinnät Kertaluokkien ominaisuuksia

Lisätiedot

3. Laskennan vaativuusteoriaa

3. Laskennan vaativuusteoriaa 3. Laskennan vaativuusteoriaa tähän asti puhuttu siitä, mitä on mahdollista laskea äärellisessä ajassa siirrytään tarkastelemaan laskemista kohtuullisessa ajassa vaihtoehtoisesti voidaan laskenta-ajan

Lisätiedot

Algoritmit 1. Luento 10 Ke Timo Männikkö

Algoritmit 1. Luento 10 Ke Timo Männikkö Algoritmit 1 Luento 10 Ke 14.2.2018 Timo Männikkö Luento 10 Algoritminen ongelmanratkaisu Suunnittelumenetelmät Raaka voima Järjestäminen eli lajittelu Kuplalajittelu Lisäyslajittelu Valintalajittelu Permutaatiot

Lisätiedot

4 Tehokkuus ja algoritmien suunnittelu

4 Tehokkuus ja algoritmien suunnittelu TIE-20100 Tietorakenteet ja algoritmit 52 4 Tehokkuus ja algoritmien suunnittelu Tässä luvussa pohditaan tehokkuuden käsitettä ja esitellään kurssilla käytetty kertaluokkanotaatio, jolla kuvataan algoritmin

Lisätiedot

Algoritmit 1. Luento 1 Ti Timo Männikkö

Algoritmit 1. Luento 1 Ti Timo Männikkö Algoritmit 1 Luento 1 Ti 10.1.2017 Timo Männikkö Luento 1 Algoritmi Algoritmin toteutus Ongelman ratkaiseminen Algoritmin tehokkuus Algoritmin suoritusaika Algoritmin analysointi Algoritmit 1 Kevät 2017

Lisätiedot

1.4 Funktioiden kertaluokat

1.4 Funktioiden kertaluokat 1.4 Funktioiden kertaluokat f on kertaluokkaa O(g), merk. f = O(g), jos joillain c > 0, m N pätee f(n) cg(n) aina kun n m f on samaa kertaluokkaa kuin g, merk. f = Θ(g), jos joillain a, b > 0, m N pätee

Lisätiedot

A274101 TIETORAKENTEET JA ALGORITMIT

A274101 TIETORAKENTEET JA ALGORITMIT A274101 TIETORAKENTEET JA ALGORITMIT ALGORITMIEN ANALYYSISTÄ 1.ratkaisu Laskentaaika hakkeri - optimoitu ALGORITMIANALYYSIÄ hyvä algoritmi hakkeri -optimoitu hyvä algoritmi Tehtävän koko Kuva mukailtu

Lisätiedot

Algoritmit 2. Luento 14 Ke Timo Männikkö

Algoritmit 2. Luento 14 Ke Timo Männikkö Algoritmit 2 Luento 14 Ke 3.5.2017 Timo Männikkö Luento 14 Ositus ja rekursio Rekursion toteutus Kertaus ja tenttivinkit Algoritmit 2 Kevät 2017 Luento 14 Ke 3.5.2017 2/30 Ositus Tehtävän esiintymä ositetaan

Lisätiedot

58131 Tietorakenteet ja algoritmit (kevät 2014) Uusinta- ja erilliskoe, , vastauksia

58131 Tietorakenteet ja algoritmit (kevät 2014) Uusinta- ja erilliskoe, , vastauksia 58131 Tietorakenteet ja algoritmit (kevät 2014) Uusinta- ja erilliskoe, 10..2014, vastauksia 1. [9 pistettä] (a) Todistetaan 2n 2 + n + 5 = O(n 2 ): Kun n 1 on 2n 2 + n + 5 2n 2 + n 2 +5n 2 = 8n 2. Eli

Lisätiedot

Nopea kertolasku, Karatsuban algoritmi

Nopea kertolasku, Karatsuban algoritmi Nopea kertolasku, Karatsuban algoritmi Mikko Männikkö 16.8.2004 Lähde: ((Gathen and Gerhard 1999) luku II.8) Esityksen kulku Algoritmien analysointia (1), (2), (3), (4) Klassinen kertolasku Parempi tapa

Lisätiedot

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

1. (a) Seuraava algoritmi tutkii, onko jokin luku taulukossa monta kertaa: Tietorakenteet, laskuharjoitus 10, ratkaisuja 1. (a) Seuraava algoritmi tutkii, onko jokin luku taulukossa monta kertaa: SamaLuku(T ) 2 for i = 1 to T.length 1 3 if T [i] == T [i + 1] 4 return True 5 return

Lisätiedot

Algoritmit 1. Luento 10 Ke 11.2.2015. Timo Männikkö

Algoritmit 1. Luento 10 Ke 11.2.2015. Timo Männikkö Algoritmit 1 Luento 10 Ke 11.2.2015 Timo Männikkö Luento 10 Algoritminen ongelman ratkaisu Suunnittelumenetelmät Raaka voima Järjestäminen eli lajittelu Kuplalajittelu Väliinsijoituslajittelu Valintalajittelu

Lisätiedot

Luku 6. Dynaaminen ohjelmointi. 6.1 Funktion muisti

Luku 6. Dynaaminen ohjelmointi. 6.1 Funktion muisti Luku 6 Dynaaminen ohjelmointi Dynaamisessa ohjelmoinnissa on ideana jakaa ongelman ratkaisu pienempiin osaongelmiin, jotka voidaan ratkaista toisistaan riippumattomasti. Jokaisen osaongelman ratkaisu tallennetaan

Lisätiedot

Algoritmit 2. Luento 8 To Timo Männikkö

Algoritmit 2. Luento 8 To Timo Männikkö Algoritmit 2 Luento 8 To 4.4.2019 Timo Männikkö Luento 8 Algoritmien analysointi Algoritmien suunnittelu Rekursio Osittaminen Rekursioyhtälöt Rekursioyhtälön ratkaiseminen Master-lause Algoritmit 2 Kevät

Lisätiedot

58131 Tietorakenteet ja algoritmit (kevät 2016) Ensimmäinen välikoe, malliratkaisut

58131 Tietorakenteet ja algoritmit (kevät 2016) Ensimmäinen välikoe, malliratkaisut 58131 Tietorakenteet ja algoritmit (kevät 2016) Ensimmäinen välikoe, malliratkaisut 1. Palautetaan vielä mieleen O-notaation määritelmä. Olkoon f ja g funktioita luonnollisilta luvuilta positiivisille

Lisätiedot

ALGORITMIT 1 DEMOVASTAUKSET KEVÄT 2012

ALGORITMIT 1 DEMOVASTAUKSET KEVÄT 2012 ALGORITMIT 1 DEMOVASTAUKSET KEVÄT 2012 1.1. (a) Jaettava m, jakaja n. Vähennetään luku n luvusta m niin kauan kuin m pysyy ei-negatiivisena. Jos jäljelle jää nolla, jaettava oli tasan jaollinen. int m,

Lisätiedot

Ohjelmoinnin perusteet Y Python

Ohjelmoinnin perusteet Y Python Ohjelmoinnin perusteet Y Python T-106.1208 2.3.2009 T-106.1208 Ohjelmoinnin perusteet Y 2.3.2009 1 / 28 Puhelinluettelo, koodi def lue_puhelinnumerot(): print "Anna lisattavat nimet ja numerot." print

Lisätiedot

811312A Tietorakenteet ja algoritmit Kertausta kurssin alkuosasta

811312A Tietorakenteet ja algoritmit Kertausta kurssin alkuosasta 811312A Tietorakenteet ja algoritmit 2017-2018 Kertausta kurssin alkuosasta II Perustietorakenteet Pino, jono ja listat tunnettava Osattava soveltaa rakenteita algoritmeissa Osattava päätellä operaatioiden

Lisätiedot

Luku 8. Aluekyselyt. 8.1 Summataulukko

Luku 8. Aluekyselyt. 8.1 Summataulukko Luku 8 Aluekyselyt Aluekysely on tiettyä taulukon väliä koskeva kysely. Tyypillisiä aluekyselyitä ovat, mikä on taulukon välin lukujen summa tai pienin luku välillä. Esimerkiksi seuraavassa taulukossa

Lisätiedot

811312A Tietorakenteet ja algoritmit, , Harjoitus 3, Ratkaisu

811312A Tietorakenteet ja algoritmit, , Harjoitus 3, Ratkaisu 811312A Tietorakenteet ja algoritmit, 2018-2019, Harjoitus 3, Ratkaisu Harjoituksessa käsitellään algoritmien aikakompleksisuutta. Tehtävä 3.1 Kuvitteelliset algoritmit A ja B lajittelevat syötteenään

Lisätiedot

Algoritmit 1. Luento 14 Ke 25.2.2015. Timo Männikkö

Algoritmit 1. Luento 14 Ke 25.2.2015. Timo Männikkö Algoritmit 1 Luento 14 Ke 25.2.2015 Timo Männikkö Luento 14 Heuristiset menetelmät Heuristiikkoja kapsäkkiongelmalle Kauppamatkustajan ongelma Lähimmän naapurin menetelmä Kertaus ja tenttivinkit Algoritmit

Lisätiedot

Algoritmit 1. Demot Timo Männikkö

Algoritmit 1. Demot Timo Männikkö Algoritmit 1 Demot 1 25.-26.1.2017 Timo Männikkö Tehtävä 1 (a) Algoritmi, joka laskee kahden kokonaisluvun välisen jakojäännöksen käyttämättä lainkaan jakolaskuja Jaettava m, jakaja n Vähennetään luku

Lisätiedot

Diskreetin matematiikan perusteet Laskuharjoitus 2 / vko 9

Diskreetin matematiikan perusteet Laskuharjoitus 2 / vko 9 Diskreetin matematiikan perusteet Laskuharjoitus 2 / vko 9 Tuntitehtävät 9-10 lasketaan alkuviikon harjoituksissa ja tuntitehtävät 13-14 loppuviikon harjoituksissa. Kotitehtävät 11-12 tarkastetaan loppuviikon

Lisätiedot

Verkon värittämistä hajautetuilla algoritmeilla

Verkon värittämistä hajautetuilla algoritmeilla Verkon värittämistä hajautetuilla algoritmeilla 5 12 30 19 72 34 Jukka Suomela 15 77 18 4 9. tammikuuta 2012 19 2 68 Verkko 2 Verkko solmu 3 Verkko solmu kaari 4 Hajautettu järjestelmä solmu (tietokone)

Lisätiedot

Tietorakenteet, laskuharjoitus 2,

Tietorakenteet, laskuharjoitus 2, Tietorakenteet, laskuharjoitus, 6.-9.1 Muista TRAKLA-tehtävien deadline 31.1. 1. Tarkastellaan ensin tehtävää yleisellä tasolla. Jos funktion T vaativuusluokka on O(f), niin funktio T on muotoa T (n) =

Lisätiedot

A ja B pelaavat sarjan pelejä. Sarjan voittaja on se, joka ensin voittaa n peliä.

A ja B pelaavat sarjan pelejä. Sarjan voittaja on se, joka ensin voittaa n peliä. Esimerkki otteluvoiton todennäköisyys A ja B pelaavat sarjan pelejä. Sarjan voittaja on se, joka ensin voittaa n peliä. Yksittäisessä pelissä A voittaa todennäköisyydellä p ja B todennäköisyydellä q =

Lisätiedot

TKT20001 Tietorakenteet ja algoritmit Erilliskoe , malliratkaisut (Jyrki Kivinen)

TKT20001 Tietorakenteet ja algoritmit Erilliskoe , malliratkaisut (Jyrki Kivinen) TKT0001 Tietorakenteet ja algoritmit Erilliskoe 5.1.01, malliratkaisut (Jyrki Kivinen) 1. [1 pistettä] (a) Esitä algoritmi, joka poistaa kahteen suuntaan linkitetystä järjestämättömästä tunnussolmullisesta

Lisätiedot

12. Javan toistorakenteet 12.1

12. Javan toistorakenteet 12.1 12. Javan toistorakenteet 12.1 Sisällys Yleistä toistorakenteista. Laskurimuuttujat. While-, do-while- ja for-lauseet. Laskuri- ja lippumuuttujat. Tyypillisiä ohjelmointivirheitä. Silmukan rajat asetettu

Lisätiedot

Algoritmit 2. Luento 7 Ti Timo Männikkö

Algoritmit 2. Luento 7 Ti Timo Männikkö Algoritmit 2 Luento 7 Ti 4.4.2017 Timo Männikkö Luento 7 Joukot Joukko-operaatioita Joukkojen esitystapoja Alkiovieraat osajoukot Toteutus puurakenteena Algoritmit 2 Kevät 2017 Luento 7 Ti 4.4.2017 2/26

Lisätiedot

Tutkimusmenetelmät-kurssi, s-2004

Tutkimusmenetelmät-kurssi, s-2004 Algoritmitutkimuksen menetelmistä Tutkimusmenetelmät-kurssi, s-2004 Pekka Kilpeläinen Kuopion yliopisto Tietojenkäsittelytieteen laitos Algoritmitutkimuksen menetelmistä p.1/20 Sisällys Tänään Tietojenkäsittelytiede

Lisätiedot

Tietorakenteet, laskuharjoitus 3, ratkaisuja

Tietorakenteet, laskuharjoitus 3, ratkaisuja Tietorakenteet, laskuharjoitus 3, ratkaisuja 1. (a) Toistolauseen runko-osassa tehdään yksi laskuoperaatio, runko on siis vakioaikainen. Jos syöte on n, suoritetaan runko n kertaa, eli aikavaativuus kokonaisuudessaan

Lisätiedot

58131 Tietorakenteet ja algoritmit Uusinta- ja erilliskoe ratkaisuja (Jyrki Kivinen)

58131 Tietorakenteet ja algoritmit Uusinta- ja erilliskoe ratkaisuja (Jyrki Kivinen) 58131 Tietorakenteet ja algoritmit Uusinta- ja erilliskoe 12.9.2018 ratkaisuja (Jyrki Kivinen) 1. [10 pistettä] Iso-O-merkintä. (a) Pitääkö paikkansa, että n 3 + 5 = O(n 3 )? Ratkaisu: Pitää paikkansa.

Lisätiedot

T Syksy 2004 Logiikka tietotekniikassa: perusteet Laskuharjoitus 7 (opetusmoniste, kappaleet )

T Syksy 2004 Logiikka tietotekniikassa: perusteet Laskuharjoitus 7 (opetusmoniste, kappaleet ) T-79144 Syksy 2004 Logiikka tietotekniikassa: perusteet Laskuharjoitus 7 (opetusmoniste, kappaleet 11-22) 26 29102004 1 Ilmaise seuraavat lauseet predikaattilogiikalla: a) Jokin porteista on viallinen

Lisätiedot

Tietotekniikan valintakoe

Tietotekniikan valintakoe Jyväskylän yliopisto Tietotekniikan laitos Tietotekniikan valintakoe 2..22 Vastaa kahteen seuraavista kolmesta tehtävästä. Kukin tehtävä arvostellaan kokonaislukuasteikolla - 25. Jos vastaat useampaan

Lisätiedot

811312A Tietorakenteet ja algoritmit 2015-2016. I Johdanto

811312A Tietorakenteet ja algoritmit 2015-2016. I Johdanto 811312A Tietorakenteet ja algoritmit 2015-2016 I Johdanto Sisältö 1. Algoritmeista ja tietorakenteista 2. Algoritmien analyysistä 811312A TRA, Johdanto 2 I.1. Algoritmeista ja tietorakenteista I.1.1. Algoritmien

Lisätiedot

Algoritmit 1. Demot Timo Männikkö

Algoritmit 1. Demot Timo Männikkö Algoritmit 1 Demot 1 31.1.-1.2.2018 Timo Männikkö Tehtävä 1 (a) Algoritmi, joka tutkii onko kokonaisluku tasan jaollinen jollain toisella kokonaisluvulla siten, että ei käytetä lainkaan jakolaskuja Jaettava

Lisätiedot

Algoritmit 2. Luento 2 Ke Timo Männikkö

Algoritmit 2. Luento 2 Ke Timo Männikkö Algoritmit 2 Luento 2 Ke 15.3.2017 Timo Männikkö Luento 2 Tietorakenteet Lineaarinen lista, binääripuu Prioriteettijono Kekorakenne Keko-operaatiot Keon toteutus taulukolla Algoritmit 2 Kevät 2017 Luento

Lisätiedot

Algoritmi on periaatteellisella tasolla seuraava:

Algoritmi on periaatteellisella tasolla seuraava: Algoritmi on periaatteellisella tasolla seuraava: Dijkstra(V, E, l, v 0 ): S := { v 0 } D[v 0 ] := 0 for v V S do D[v] := l(v 0, v) end for while S V do valitse v V S jolle D[v] on minimaalinen S := S

Lisätiedot

11. Javan toistorakenteet 11.1

11. Javan toistorakenteet 11.1 11. Javan toistorakenteet 11.1 Sisällys Laskuri- ja lippumuuttujat. Sisäkkäiset silmukat. Tyypillisiä ohjelmointivirheitä: Silmukan rajat asetettu kierroksen verran väärin. Ikuinen silmukka. Silmukoinnin

Lisätiedot

Matematiikan tukikurssi, kurssikerta 3

Matematiikan tukikurssi, kurssikerta 3 Matematiikan tukikurssi, kurssikerta 3 1 Epäyhtälöitä Aivan aluksi lienee syytä esittää luvun itseisarvon määritelmä: { x kun x 0 x = x kun x < 0 Siispä esimerkiksi 10 = 10 ja 10 = 10. Seuraavaksi listaus

Lisätiedot

Karteesinen tulo. Olkoot A = {1, 2, 3, 5} ja B = {a, b, c}. Näiden karteesista tuloa A B voidaan havainnollistaa kuvalla 1 / 21

Karteesinen tulo. Olkoot A = {1, 2, 3, 5} ja B = {a, b, c}. Näiden karteesista tuloa A B voidaan havainnollistaa kuvalla 1 / 21 säilyy Olkoot A = {1, 2, 3, 5} ja B = {a, b, c}. Näiden karteesista tuloa A B voidaan havainnollistaa kuvalla c b a 1 2 3 5 1 / 21 säilyy Esimerkkirelaatio R = {(1, b), (3, a), (5, a), (5, c)} c b a 1

Lisätiedot

Algoritmit 1. Luento 11 Ti Timo Männikkö

Algoritmit 1. Luento 11 Ti Timo Männikkö Algoritmit 1 Luento 11 Ti 14.2.2017 Timo Männikkö Luento 11 Algoritminen ongelmanratkaisu Osittaminen Lomituslajittelu Lomituslajittelun vaativuus Rekursioyhtälöt Pikalajittelu Algoritmit 1 Kevät 2017

Lisätiedot

Tietorakenteet ja algoritmit

Tietorakenteet ja algoritmit Tietorakenteet ja algoritmit Rekursio Rekursion käyttötapauksia Rekursio määritelmissä Rekursio ongelmanratkaisussa ja ohjelmointitekniikkana Esimerkkejä taulukolla Esimerkkejä linkatulla listalla Hanoin

Lisätiedot

Diskreetin matematiikan perusteet Laskuharjoitus 1 / vko 8

Diskreetin matematiikan perusteet Laskuharjoitus 1 / vko 8 Diskreetin matematiikan perusteet Laskuharjoitus 1 / vko 8 Tuntitehtävät 1-2 lasketaan alkuviikon harjoituksissa ja tuntitehtävät 5- loppuviikon harjoituksissa. Kotitehtävät 3-4 tarkastetaan loppuviikon

Lisätiedot

12. Javan toistorakenteet 12.1

12. Javan toistorakenteet 12.1 12. Javan toistorakenteet 12.1 Sisällys Yleistä toistorakenteista. Laskurimuuttujat. While-, do-while- ja for-lauseet. Laskuri- ja lippumuuttujat. Tyypillisiä ohjelmointivirheitä. Silmukan rajat asetettu

Lisätiedot

Esimerkkejä vaativuusluokista

Esimerkkejä vaativuusluokista Esimerkkejä vaativuusluokista Seuraaville kalvoille on poimittu joitain esimerkkejä havainnollistamaan algoritmien aikavaativuusluokkia. Esimerkit on valittu melko mielivaltaisesti laitoksella tehtävään

Lisätiedot

Algoritmit 2. Luento 2 To Timo Männikkö

Algoritmit 2. Luento 2 To Timo Männikkö Algoritmit 2 Luento 2 To 14.3.2019 Timo Männikkö Luento 2 Tietorakenteet Lineaarinen lista, binääripuu Prioriteettijono Kekorakenne Keko-operaatiot Keon toteutus taulukolla Algoritmit 2 Kevät 2019 Luento

Lisätiedot

Yhtälönratkaisusta. Johanna Rämö, Helsingin yliopisto. 22. syyskuuta 2014

Yhtälönratkaisusta. Johanna Rämö, Helsingin yliopisto. 22. syyskuuta 2014 Yhtälönratkaisusta Johanna Rämö, Helsingin yliopisto 22. syyskuuta 2014 Yhtälönratkaisu on koulusta tuttua, mutta usein sitä tehdään mekaanisesti sen kummempia ajattelematta. Jotta pystytään ratkaisemaan

Lisätiedot

Algoritmit 1. Luento 12 Ti Timo Männikkö

Algoritmit 1. Luento 12 Ti Timo Männikkö Algoritmit 1 Luento 12 Ti 19.2.2019 Timo Männikkö Luento 12 Osittamisen tasapainoisuus Pikalajittelun vaativuus Lajittelumenetelmien vaativuus Laskentalajittelu Lokerolajittelu Kantalukulajittelu Algoritmit

Lisätiedot

7.4 Sormenjälkitekniikka

7.4 Sormenjälkitekniikka 7.4 Sormenjälkitekniikka Tarkastellaan ensimmäisenä esimerkkinä pitkien merkkijonojen vertailua. Ongelma: Ajatellaan, että kaksi n-bittistä (n 1) tiedostoa x ja y sijaitsee eri tietokoneilla. Halutaan

Lisätiedot

Algoritmit 1. Luento 13 Ti 23.2.2016. Timo Männikkö

Algoritmit 1. Luento 13 Ti 23.2.2016. Timo Männikkö Algoritmit 1 Luento 13 Ti 23.2.2016 Timo Männikkö Luento 13 Suunnittelumenetelmät Taulukointi Kapsäkkiongelma Ahne menetelmä Verkon lyhimmät polut Dijkstran menetelmä Verkon lyhin virittävä puu Kruskalin

Lisätiedot

811312A Tietorakenteet ja algoritmit Kertausta kurssin alkuosasta

811312A Tietorakenteet ja algoritmit Kertausta kurssin alkuosasta 811312A Tietorakenteet ja algoritmit 2016-2017 Kertausta kurssin alkuosasta II Algoritmien analyysi: oikeellisuus Algoritmin täydellinen oikeellisuus = Algoritmi päättyy ja tuottaa määritellyn tuloksen

Lisätiedot

Algoritmit 2. Luento 13 Ti Timo Männikkö

Algoritmit 2. Luento 13 Ti Timo Männikkö Algoritmit 2 Luento 13 Ti 2.5.2017 Timo Männikkö Luento 13 Merkkijonon sovitus Horspoolin algoritmi Laskennallinen vaativuus Päätösongelmat Epädeterministinen algoritmi Vaativuusluokat NP-täydellisyys

Lisätiedot

Johnson, A Theoretician's Guide to the Experimental Analysis of Algorithms.

Johnson, A Theoretician's Guide to the Experimental Analysis of Algorithms. Kokeellinen algoritmiikka (3 ov) syventäviä opintoja edeltävät opinnot: ainakin Tietorakenteet hyödyllisiä opintoja: ASA, Algoritmiohjelmointi suoritus harjoitustyöllä (ei tenttiä) Kirjallisuutta: Johnson,

Lisätiedot

Tietorakenteet ja algoritmit II

Tietorakenteet ja algoritmit II Tietorakenteet ja algoritmit II Luentomuistiinpanoja Simo Juvaste Asko Niemeläinen Itä-Suomen yliopisto Tietojenkäsittelytiede Alkusanat Tämä uuden TRAII kurssin luentomateriaali on kutakuinkin edellisen

Lisätiedot

1. Osoita, että joukon X osajoukoille A ja B on voimassa toinen ns. de Morganin laki (A B) = A B.

1. Osoita, että joukon X osajoukoille A ja B on voimassa toinen ns. de Morganin laki (A B) = A B. HY / Avoin yliopisto Johdatus yliopistomatematiikkaan, kesä 2015 Harjoitus 3 Ratkaisuehdotuksia Tehtäväsarja I Seuraavissa tehtävissä harjoitellaan muun muassa kahden joukon osoittamista samaksi sekä joukon

Lisätiedot

useampi ns. avain (tai vertailuavain) esim. opiskelijaa kuvaavassa alkiossa vaikkapa opintopistemäärä tai opiskelijanumero

useampi ns. avain (tai vertailuavain) esim. opiskelijaa kuvaavassa alkiossa vaikkapa opintopistemäärä tai opiskelijanumero Alkioiden avaimet Usein tietoalkioille on mielekästä määrittää yksi tai useampi ns. avain (tai vertailuavain) esim. opiskelijaa kuvaavassa alkiossa vaikkapa opintopistemäärä tai opiskelijanumero 80 op

Lisätiedot

58131 Tietorakenteet ja algoritmit (syksy 2015) Toinen välikoe, malliratkaisut

58131 Tietorakenteet ja algoritmit (syksy 2015) Toinen välikoe, malliratkaisut Tietorakenteet ja algoritmit (syksy 0) Toinen välikoe, malliratkaisut. (a) Alussa puu näyttää tältä: Lisätään 4: 4 Tasapaino rikkoutuu solmussa. Tehdään kaksoiskierto ensin oikealle solmusta ja sitten

Lisätiedot

58131 Tietorakenteet ja algoritmit (syksy 2015)

58131 Tietorakenteet ja algoritmit (syksy 2015) 58131 Tietorakenteet ja algoritmit (syksy 2015) Harjoitus 2 (14. 18.9.2015) Huom. Sinun on tehtävä vähintään kaksi tehtävää, jotta voit jatkaa kurssilla. 1. Erään algoritmin suoritus vie 1 ms, kun syötteen

Lisätiedot

Matematiikan tukikurssi, kurssikerta 2

Matematiikan tukikurssi, kurssikerta 2 Matematiikan tukikurssi kurssikerta 1 Relaatioista Oletetaan kaksi alkiota a ja b. Näistä kumpikin kuuluu johonkin tiettyyn joukkoon mahdollisesti ne kuuluvat eri joukkoihin; merkitään a A ja b B. Voidaan

Lisätiedot

Datatähti 2019 loppu

Datatähti 2019 loppu Datatähti 2019 loppu task type time limit memory limit A Summa standard 1.00 s 512 MB B Bittijono standard 1.00 s 512 MB C Auringonlasku standard 1.00 s 512 MB D Binääripuu standard 1.00 s 512 MB E Funktio

Lisätiedot

Tietorakenteet, laskuharjoitus 7, ratkaisuja

Tietorakenteet, laskuharjoitus 7, ratkaisuja Tietorakenteet, laskuharjoitus, ratkaisuja. Seuraava kuvasarja näyttää B + -puun muutokset lisäysten jälkeen. Avaimet ja 5 mahtuvat lehtisolmuihin, joten niiden lisäys ei muuta puun rakennetta. Avain 9

Lisätiedot

Johdatus lukuteoriaan Harjoitus 2 syksy 2008 Eemeli Blåsten. Ratkaisuehdotelma

Johdatus lukuteoriaan Harjoitus 2 syksy 2008 Eemeli Blåsten. Ratkaisuehdotelma Johdatus lukuteoriaan Harjoitus 2 syksy 2008 Eemeli Blåsten Ratkaisuehdotelma Tehtävä 1 1. Etsi lukujen 4655 ja 12075 suurin yhteinen tekijä ja lausu se kyseisten lukujen lineaarikombinaationa ilman laskimen

Lisätiedot

1 Kannat ja kannanvaihto

1 Kannat ja kannanvaihto 1 Kannat ja kannanvaihto 1.1 Koordinaattivektori Oletetaan, että V on K-vektoriavaruus, jolla on kanta S = (v 1, v 2,..., v n ). Avaruuden V vektori v voidaan kirjoittaa kannan vektorien lineaarikombinaationa:

Lisätiedot

Valitaan alkio x 1 A B ja merkitään A 1 = A { x 1 }. Perinnöllisyyden nojalla A 1 I.

Valitaan alkio x 1 A B ja merkitään A 1 = A { x 1 }. Perinnöllisyyden nojalla A 1 I. Vaihto-ominaisuudella on seuraava intuition kannalta keskeinen seuraus: Olkoot A I ja B I samankokoisia riippumattomia joukkoja: A = B = m jollain m > 0. Olkoon vielä n = m A B, jolloin A B = B A = n.

Lisätiedot

Harjoitustyön testaus. Juha Taina

Harjoitustyön testaus. Juha Taina Harjoitustyön testaus Juha Taina 1. Johdanto Ohjelman teko on muutakin kuin koodausta. Oleellinen osa on selvittää, että ohjelma toimii oikein. Tätä sanotaan ohjelman validoinniksi. Eräs keino validoida

Lisätiedot

3.3 Paraabeli toisen asteen polynomifunktion kuvaajana. Toisen asteen epäyhtälö

3.3 Paraabeli toisen asteen polynomifunktion kuvaajana. Toisen asteen epäyhtälö 3.3 Paraabeli toisen asteen polynomifunktion kuvaajana. Toisen asteen epäyhtälö Yhtälön (tai funktion) y = a + b + c, missä a 0, kuvaaja ei ole suora, mutta ei ole yhtälökään ensimmäistä astetta. Funktioiden

Lisätiedot

Määrittelydokumentti

Määrittelydokumentti Määrittelydokumentti Aineopintojen harjoitustyö: Tietorakenteet ja algoritmit (alkukesä) Sami Korhonen 014021868 sami.korhonen@helsinki. Tietojenkäsittelytieteen laitos Helsingin yliopisto 23. kesäkuuta

Lisätiedot

Matematiikan tukikurssi

Matematiikan tukikurssi Matematiikan tukikurssi Kurssikerta 1 Määrittelyjoukoista Tarkastellaan funktiota, jonka määrittelevä yhtälö on f(x) = x. Jos funktion lähtöjoukoksi määrittelee vaikkapa suljetun välin [0, 1], on funktio

Lisätiedot

Ohjelmoinnin perusteet Y Python

Ohjelmoinnin perusteet Y Python Ohjelmoinnin perusteet Y Python T-106.1208 28.2.2011 T-106.1208 Ohjelmoinnin perusteet Y 28.2.2011 1 / 46 Ohjelmointiprojektin vaiheet 1. Määrittely 2. Ohjelman suunnittelu (ohjelman rakenne ja ohjelman

Lisätiedot

Tarkennamme geneeristä painamiskorotusalgoritmia

Tarkennamme geneeristä painamiskorotusalgoritmia Korotus-eteen-algoritmi (relabel-to-front) Tarkennamme geneeristä painamiskorotusalgoritmia kiinnittämällä tarkasti, missä järjestyksessä Push- ja Raise-operaatioita suoritetaan. Algoritmin peruskomponentiksi

Lisätiedot

Rekursiolause. Laskennan teorian opintopiiri. Sebastian Björkqvist. 23. helmikuuta Tiivistelmä

Rekursiolause. Laskennan teorian opintopiiri. Sebastian Björkqvist. 23. helmikuuta Tiivistelmä Rekursiolause Laskennan teorian opintopiiri Sebastian Björkqvist 23. helmikuuta 2014 Tiivistelmä Työssä käydään läpi itsereplikoituvien ohjelmien toimintaa sekä esitetään ja todistetaan rekursiolause,

Lisätiedot

Joukot. Georg Cantor ( )

Joukot. Georg Cantor ( ) Joukot Matematiikassa on pyrkimys määritellä monimutkaiset asiat täsmällisesti yksinkertaisempien asioiden avulla. Tarvitaan jokin lähtökohta, muutama yleisesti hyväksytty ja ymmärretty käsite, joista

Lisätiedot

AVL-puut. eräs tapa tasapainottaa binäärihakupuu siten, että korkeus on O(log n) kun puussa on n avainta

AVL-puut. eräs tapa tasapainottaa binäärihakupuu siten, että korkeus on O(log n) kun puussa on n avainta AVL-puut eräs tapa tasapainottaa binäärihakupuu siten, että korkeus on O(log n) kun puussa on n avainta pohjana jo esitetyt binäärihakupuiden operaatiot tasapainotus vie pahimmillaan lisäajan lisäys- ja

Lisätiedot

Algoritmit 2. Luento 3 Ti Timo Männikkö

Algoritmit 2. Luento 3 Ti Timo Männikkö Algoritmit 2 Luento 3 Ti 21.3.2017 Timo Männikkö Luento 3 Järjestäminen eli lajittelu Kekorakenne Kekolajittelu Hajautus Yhteentörmäysten käsittely Ketjutus Algoritmit 2 Kevät 2017 Luento 3 Ti 21.3.2017

Lisätiedot

Algoritmit 1. Luento 12 Ke Timo Männikkö

Algoritmit 1. Luento 12 Ke Timo Männikkö Algoritmit 1 Luento 12 Ke 15.2.2017 Timo Männikkö Luento 12 Pikalajittelu Pikalajittelun vaativuus Osittamisen tasapainoisuus Lajittelumenetelmien vaativuus Laskentalajittelu Lokerolajittelu Kantalukulajittelu

Lisätiedot

Reaalifunktioista 1 / 17. Reaalifunktioista

Reaalifunktioista 1 / 17. Reaalifunktioista säilyy 1 / 17 säilyy Jos A, B R, niin funktiota f : A B sanotaan (yhden muuttujan) reaalifunktioksi. Tällöin karteesinen tulo A B on (aiempia esimerkkejä luonnollisemmalla tavalla) xy-tason osajoukko,

Lisätiedot

Algoritmit 2. Luento 13 Ti Timo Männikkö

Algoritmit 2. Luento 13 Ti Timo Männikkö Algoritmit 2 Luento 13 Ti 30.4.2019 Timo Männikkö Luento 13 Simuloitu jäähdytys Merkkijonon sovitus Horspoolin algoritmi Ositus ja rekursio Rekursion toteutus Algoritmit 2 Kevät 2019 Luento 13 Ti 30.4.2019

Lisätiedot

Vasen johto S AB ab ab esittää jäsennyspuun kasvattamista vasemmalta alkaen:

Vasen johto S AB ab ab esittää jäsennyspuun kasvattamista vasemmalta alkaen: Vasen johto S AB ab ab esittää jäsennyspuun kasvattamista vasemmalta alkaen: S A S B Samaan jäsennyspuuhun päästään myös johdolla S AB Ab ab: S A S B Yhteen jäsennyspuuhun liittyy aina tasan yksi vasen

Lisätiedot

1.4 Funktion jatkuvuus

1.4 Funktion jatkuvuus 1.4 Funktion jatkuvuus Kun arkikielessä puhutaan jonkin asian jatkuvuudesta, mielletään asiassa olevan jonkinlaista yhtäjaksoisuutta, katkeamattomuutta. Tässä ei kuitenkaan käsitellä työasioita eikä ihmissuhteita,

Lisätiedot

ja λ 2 = 2x 1r 0 x 2 + 2x 1r 0 x 2

ja λ 2 = 2x 1r 0 x 2 + 2x 1r 0 x 2 Johdatus diskreettiin matematiikkaan Harjoitus 4, 7.10.2015 1. Olkoot c 0, c 1 R siten, että polynomilla r 2 c 1 r c 0 on kaksinkertainen juuri. Määritä rekursioyhtälön x n+2 = c 1 x n+1 + c 0 x n, n N,

Lisätiedot

MS-A0402 Diskreetin matematiikan perusteet Esimerkkejä ym., osa I

MS-A0402 Diskreetin matematiikan perusteet Esimerkkejä ym., osa I MS-A040 Diskreetin matematiikan perusteet Esimerkkejä ym., osa I G. Gripenberg Aalto-yliopisto. maaliskuuta 05 G. Gripenberg (Aalto-yliopisto) MS-A040 Diskreetin matematiikan perusteet Esimerkkejä. ym.,

Lisätiedot

Hahmon etsiminen syotteesta (johdatteleva esimerkki)

Hahmon etsiminen syotteesta (johdatteleva esimerkki) Hahmon etsiminen syotteesta (johdatteleva esimerkki) Unix-komennolla grep hahmo [ tiedosto ] voidaan etsia hahmon esiintymia tiedostosta (tai syotevirrasta): $ grep Kisaveikot SM-tulokset.txt $ ps aux

Lisätiedot

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

2. Lisää Java-ohjelmoinnin alkeita. Muuttuja ja viittausmuuttuja (1/4) Muuttuja ja viittausmuuttuja (2/4) 2. Lisää Java-ohjelmoinnin alkeita Muuttuja ja viittausmuuttuja Vakio ja literaalivakio Sijoituslause Syötteen lukeminen ja Scanner-luokka 1 Muuttuja ja viittausmuuttuja (1/4) Edellä mainittiin, että String-tietotyyppi

Lisätiedot

Matematiikan tukikurssi

Matematiikan tukikurssi Matematiikan tukikurssi Kurssikerta 1 1 Matemaattisesta päättelystä Matemaattisen analyysin kurssin (kuten minkä tahansa matematiikan kurssin) seuraamista helpottaa huomattavasti, jos opiskelija ymmärtää

Lisätiedot

Oikeasta tosi-epätosi -väittämästä saa pisteen, ja hyvästä perustelusta toisen.

Oikeasta tosi-epätosi -väittämästä saa pisteen, ja hyvästä perustelusta toisen. Tietorakenteet, kevät 2012 Kurssikoe 2, mallivastaukset 2. (a) Järjestämistä ei voi missään tilanteessa suorittaa nopeammin kuin ajassa Θ(n log n), missä n on järjestettävän taulukon pituus. Epätosi: Yleisessä

Lisätiedot

Algoritmien suunnittelu ja analyysi (kevät 2004) 1. välikoe, ratkaisuja

Algoritmien suunnittelu ja analyysi (kevät 2004) 1. välikoe, ratkaisuja 58053-7 Algoritmien suunnittelu ja analyysi (kevät 2004) 1. välikoe, ratkaisuja Malliratkaisut ja pisteytysohje: Jyrki Kivinen Tentin arvostelu: Jouni Siren (tehtävät 1 ja 2) ja Jyrki Kivinen (tehtävät

Lisätiedot

2.1. Tehtävänä on osoittaa induktiolla, että kaikille n N pätee n = 1 n(n + 1). (1)

2.1. Tehtävänä on osoittaa induktiolla, että kaikille n N pätee n = 1 n(n + 1). (1) Approbatur 3, demo, ratkaisut Sovitaan, että 0 ei ole luonnollinen luku. Tällöin oletusta n 0 ei tarvitse toistaa alla olevissa ratkaisuissa. Se, pidetäänkö nollaa luonnollisena lukuna vai ei, vaihtelee

Lisätiedot

Ohjelmoinnin perusteet Y Python

Ohjelmoinnin perusteet Y Python Ohjelmoinnin perusteet Y Python T-106.1208 2.3.2011 T-106.1208 Ohjelmoinnin perusteet Y 2.3.2011 1 / 39 Kertausta: tiedoston avaaminen Kun ohjelma haluaa lukea tai kirjoittaa tekstitiedostoon, on ohjelmalle

Lisätiedot

2.2 Neliöjuuri ja sitä koskevat laskusäännöt

2.2 Neliöjuuri ja sitä koskevat laskusäännöt . Neliöjuuri ja sitä koskevat laskusäännöt MÄÄRITELMÄ 3: Lukua b sanotaan luvun a neliöjuureksi, merkitään a b, jos b täyttää kaksi ehtoa: 1o b > 0 o b a Esim.1 Määritä a) 64 b) 0 c) 36 a) Luvun 64 neliöjuuri

Lisätiedot

MS-A0402 Diskreetin matematiikan perusteet Esimerkkejä ym., osa I

MS-A0402 Diskreetin matematiikan perusteet Esimerkkejä ym., osa I MS-A040 Diskreetin matematiikan perusteet Esimerkkejä ym., osa I G. Gripenberg Aalto-yliopisto. maaliskuuta 05 G. Gripenberg (Aalto-yliopisto) MS-A040 Diskreetin matematiikan perusteet Esimerkkejä. ym.,

Lisätiedot

Reaalilukuvälit, leikkaus ja unioni (1/2)

Reaalilukuvälit, leikkaus ja unioni (1/2) Luvut Luonnolliset luvut N = {0, 1, 2, 3,... } Kokonaisluvut Z = {..., 2, 1, 0, 1, 2,... } Rationaaliluvut (jaksolliset desimaaliluvut) Q = {m/n m, n Z, n 0} Irrationaaliluvut eli jaksottomat desimaaliluvut

Lisätiedot

Approbatur 3, demo 1, ratkaisut A sanoo: Vähintään yksi meistä on retku. Tehtävänä on päätellä, mitä tyyppiä A ja B ovat.

Approbatur 3, demo 1, ratkaisut A sanoo: Vähintään yksi meistä on retku. Tehtävänä on päätellä, mitä tyyppiä A ja B ovat. Approbatur 3, demo 1, ratkaisut 1.1. A sanoo: Vähintään yksi meistä on retku. Tehtävänä on päätellä, mitä tyyppiä A ja B ovat. Käydään kaikki vaihtoehdot läpi. Jos A on rehti, niin B on retku, koska muuten

Lisätiedot