3. Muistin hallinta. 3.1 Erityyppiset muistit

Koko: px
Aloita esitys sivulta:

Download "3. Muistin hallinta. 3.1 Erityyppiset muistit"

Transkriptio

1 Muistin hallinta Muistin hallinta Tämä luku käsittelee erityyppisiä muisteja ja ohjelman sijoittelua muistiin, dynaamisen muistin hallintaa ja yleensä muistinhallintaa. Pääpaino on siinä, miten muisti näkyy ohjelmoijalle, ja siksi monet laitteiston toteutusyksityiskohdat on sivuutettu, vaikka ne sinänsä mielenkiintoisia ovatkin. 3.1 Erityyppiset muistit Ohjelmoijan kannalta tärkein jako muisteille on se, voiko niiden sisältöä muuttaa vai ei. Tosin muuttamisen helppous tai vaikeus on myös tärkeää, ja joidenkin muistien kohdalla onkin hieman tulkinnanvaraista, minkä tyyppinen muisti oikeastaan onkaan. Yleensä jako tehdään lukumuisteihin ja luku kirjoitusmuisteihin. Tällöin lukumuisteiksi luetaan kaikki sellaiset muistit, joiden sisältöä ei voi muuttaa normaalilla suorittimen kirjoitusjaksolla. Voimme tehdä jaon myös periaatteella haihtumattomat muistit haihtuvat muistit. Tällöin korostamme sitä, säilyykö muistin sisältö sähkökatkoksen yli vai ei Luku kirjoitusmuistit Luku kirjoitusmuistit (RAM, random access memory 7 ) ovat yleisimpiä muisteja tietokoneissa. Oikeastaan voidaan sanoa, että tämä on muistin oletusarvo. Tavallisen luku kirjoitusmuistin sisältö ei säily sähkökat- 7. Nimi on itseasiassa kummajainen. Random viittaa siihen, että voidaan viitata mihin muistipaikkaan tahansa riippumatta edellisestä viittauksesta. Tämä erottaa muistin ikivanhasta muistitekniikasta, jossa voitiin viitata sujuvasti vain seuraavaan tai muutaman askelen päässä edessä olevaan muistipaikkaan. Tässä mielessä myös nykyiset lukumuistit ovat RAM-muisteja, mutta niitä ei koskaan tarkoiteta termillä RAM. Vain aniharvoin RAM-muistiin viitataan loogisemmalla termillä RWM, read-write memory.

2 52 Sulautettu ohjelmointi koksessa, joten tämä muistityyppi edustaa haihtuvia muisteja. Kuten muistin (suomenkielinen) nimi kertoo, suoritin voi lukea tai muuttaa muistin sisältöä yhden muistijakson aikana. Luku kirjoitusmuisti on yleensä nopeaa. Luku kirjoitusmuisteja on toteutustekniikaltaan erilaisia. Muisti voi olla staattista (SRAM), jolloin tieto säilyy muistissa niin kauan kuin käyttöjännite piirille on olemassa. Staattinen muisti on nopeaa, mutta se vaatii enemmän piipinta-alaa kuin sen päävaihtoehto, dynaaminen muisti (DRAM), joka vie bittiä kohden neljäsosan SRAMin vaatimasta piipinta-alasta. Dynaaminen muisti tallettaa muistitiedon kapasitansseihin, jotka purkaantuvat hiljalleen. Tämän takia muistia pitää virkistää säännöllisesti, jotta tieto ei katoaisi. Muistin virkistys tapahtuu joko ohjelmallisesti tai kuten yleensä on asian laita laitteistolla. Dynaaminen muisti on myös voitu tehdä ulkoisesti staattisen näköiseksi eli siinä on sisäänrakennettu virkistyslogiikka. Varsinkin dynaamisen muistin piirit voivat olla sellaisia, joissa käsiteltävä osoite kirjoitetaan muistiin kahdessa tai useammassa osassa: esimerkiksi siten, että ensin kirjoitetaan muistin ylimmät bitit ("riviosoite") ja sitten alimmat bitit ("sarakeosoite"). Muisti ajatellaan siis matriisiksi. Tästä rakenteesta johtuu edelleen se, että samalla rivillä olevia muistipaikkoja on nopeampi osoittaa kuin eri riveillä olevia, koska muistiosoitteesta ei tarvitse ladata kuin alaosa (niin sanottu page-mode, EDORAM). Ominaisuutta voidaan ainakin yrittää hyödyntää ohjelmien tai tietorakenteiden sijoittelussa, mutta käytännössä tämä tulee kyseeseen yleensä vain melko pieniä järjestelmiä rakennettaessa, sillä tavallisesti muut suunnittelunäkökulmat ovat huomattavasti merkittävämpiä. Erityyppisiä muisteja on monia, eikä ohjelmoijan yleensä tarvitse tietää niiden ominaisuuksista paitsi ehkä yllämainitusta samalta riviltä lukemisen paremmuudesta. Mikäli laitteessa on erityyppisiä muisteja, voi tulla tarpeen miettiä niiden käyttöä. Eroja voi olla ainakin muistin leveydessä (mikäli suoritin sallii erileveyksisiä muisteja) ja muistin saantiajoissa Lukumuistit Peruslukumuisti (ROM, read only memory) on muisti, jonka sisältö langoitetaan tekovaiheessa. Tällaisia muisteja ei nykyään käytetä kuin korkeintaan suorittimen sisällä joitain erikoistarkoituksia varten. Tavallisempaa onkin, että käytetään piiriä, jonka sisältö voidaan ohjelmoida jollain tavalla (PROM, programmable ROM). Mikäli ohjelmointi on

3 Muistin hallinta 53 mahdollinen vain kerran, piiristä tulee jätettä, mikäli sen sisältöä pitäisi muuttaa. Tämän takia kertaohjelmoitava piiri on lähinnä historiaa, eikä sillä ole juuri käytännön merkitystä. Myös edellistä käyttökelpoisemmat EPROM-piirit (erasable ROM) ovat pikku hiljaa käyneet vanhanaikaiseksi. Tällainen piiri voidaan tyhjentää jollain menetelmällä, tavallisesti ultraviolettivalolla, ja kirjoittaa sen jälkeen uudestaan. Kirjoittaminen tarvitsee usein poikkeavan jännitteen, eikä sitä voi tehdä enää "tuotantokäytössä". Edellä olevilla muisteilla on ohjelmoijan kannalta yksi yhteinen tekijä: käytössä olevan piirin sisältöä ei voi mitenkään muuttaa ohjelmallisesti. Lukumuisteille voidaan sijoittaa vain sellaista tietoa, joka ei muutu. Tavallisesti tämä tarkoittaa suoritettavaa ohjelmaa ja alustettua dataa, esimerkiksi merkkijonovakioita. Tässä kuvatut perinteiset lukumuistit ovat käyneet harvinaiseksi, ja niiden tilalle on tullut uudentyyppisiä ns. haihtumattomia muisteja Haihtumattomat muistit Lukumuistit ovat tietenkin kaikki haihtumattomia. Tämän takia niitä ei yleensä lasketa haihtumattomiksi muisteiksi, vaan haihtumattomalla muistilla tarkoitetaan muistia, jonka sisältöä voidaan muuttaa ja jonka sisältö säilyy sähkökatkoksen yli. Useimmat tällaiset muistit ovat hitaita ja joskus hankaliakin käyttää. Patterivarmistettu luku kirjoitusmuisti Ohjelmoijan kannalta yksinkertaisin haihtumaton muisti on tavallinen luku kirjoitusmuisti, jonka sähkönsyöttö on turvattu erityisjärjestelyin (esimerkiksi patterivarmistus). Tällaisena lukumuistina voi käytännössä olla vain staattinen muisti, sillä dynaaminen muisti vaatii virkistämistä joten pelkkä sähkönsyötön lisääminen ei riitä. Tällaisia muisteja ei kuitenkaan käytetä kovin paljoa, koska on harvinaista, että jatkuvasti päivitettäviä tietoja pitäisi säilyttää mahdollisen katkoksen yli. Esimerkkinä hieman poikkeuksellisesta käytöstä voisi mainita NFS-kiihdyttimen, jonka tarkoitus on nopeuttaa NFS-järjestelmän (network file system) toimintaa. Levypalvelin siirtää asiakkaalta tulleen tiedon ensin NFS-kiihdyttimen muistiin ennen levylle kirjoittamista. Itse levylle kirjoittaminen voidaan tehdä myöhemmin levyn käytön kokonaisoptimoinnin kannalta hyvään aikaan, mutta jo tässä vaiheessa voidaan "valehdella" asiakaskoneelle tiedon olevan levyllä, koska sen

4 54 Sulautettu ohjelmointi sisältö on turvassa sähkökatkolta. Toisin sanoen koko kiihdytin onkin itse asiassa patterivarmistettu luku kirjoitusmuisti. Sähköisesti tyhjennettävä muisti Sähköisesti tyhjennettävä muisti eli EEPROM (electrically erasable PROM) mahdollistaa muistipaikan sisällön muuttamisen, kun muistipaikka on erikseen ensin tyhjennetty. Ensimmäisen sukupolven laitteet vaativat erityisjännitteen tietojen muuttamiseen, minkä takia muutos ei yleensä onnistunut itse käyttölaitteella, vaan muutoksia varten piiri piti poistaa käyttölaitteesta. Tämän takia muistin käyttö oli hankalaa, mutta sitä voitiin käyttää tallentamaan esimerkiksi laitteen sarjanumero tai muu tunnistetieto tai järjestelmän tarvitsemia parametreja. Uuden sukupolven EEPROM tunnetaan paremmin nimellä Flash- ROM. Sen sisältöä voidaan muuttaa tavallisella käyttöjännitteellä, ja näin siihen voidaan tehdä muutoksia itse käyttölaitteessakin. Ensimmäiset Flash-ROM-piirit piti tyhjentää kokonaan ennen muutoksia, mutta nykyiset voidaan tyhjentää lohko kerrallaan. Kirjoittaminen voidaan tehdä muistipaikka kerrallaan. Flash-ROM-piireillä on rajoituksia siihen, montako kertaa piiri voidaan ohjelmoida uudestaan. Tämän takia pyritään siihen, että muutokset eivät kuluta loppuun yhtä lohkoa, vaan tieto tallennetaan peräkkäisillä kerroilla eri sivuille. Uusimmissa laitteissa ongelmat ovat yleensä pienempiä, sillä muistia on usein yli välittömän tarpeen, ja lisäksi sallittujen kirjoituskertojen määrä on kasvanut. Flash-ROM on hidas lukea ja kirjoittaa, ainakin luku kirjoitusmuistiin verrattuna. Tämän takia sen sisältö tavallisesti luetaan lukukirjoitusmuistiin käytön ajaksi nopean lukemisen mahdollistamiseksi. Näin tehdään erityisesti silloin, kun muistilla on ajettavaa ohjelmakoodia. Kirjoittamista tämä ei nopeuta, koska kirjoittaminen tulee tehdä aina itse flash-muistille asti. 3.2 Flash-muistin käytöstä Flash-muistin käyttöä rajaa eniten se, että sitä ei voi tyhjentää muistipaikka kerrallaan, vaan ainoastaan lohko kerrallaan. Näin yhtä muistipaikkaa ei voida muuttaa suoraan, vaan koko lohko on tyhjennettävä ja sitten kirjoitettava uudelleen. Tämä tapa ei ole käyttökelpoinen, sillä sähkökatkos juuri siinä välissä, kun vanha tieto on poistettu, mutta uutta

5 Muistin hallinta 55 ei ole vielä talletettu, johtaa tiedon katoamiseen. Lohkon tiedot pitää siis kirjoittaa ensin jonnekin, ja sitten vasta tyhjentää vanha lohko. Flash-muistia käytetään tässä esitetyn tavan lisäksi paljon viihdeelektroniikassa muun muassa digitaalisten kameroiden siirrettävänä kuvamuistina Kirjoituskertojen rajoitukset Toinen ongelma on flash-muistin kirjoituskertojen (write endurance) rajoitukset. Luotettavan kirjoittamisen raja voi olla suhteellisen matala. Laitteen käyttötarkoituksen ja odotettavissa olevien kirjoituskertojen mukaan voidaan päätellä, kauanko laite kestää käytössä. Kirjoituskertojen määrä vaihtelee tekniikan mukaan tuhansista yli miljoonaan kirjoituskertaan. Suurikaan kirjoitusmäärä ei täysin ratkaise ongelmaa, jos määrä kuitenkin on rajallinen, joten käyttökonteksti on siksi keskeinen tekijä laitteistoa valittaessa. Esimerkiksi harjoitustyökäytössä olevan laitteen suorittimen voi ohjelmoida 1000 kertaa luotettavasti. Mikäli oletetaan, että jokaisen harjoitusryhmän tulee tehdä ohjelmointi 10 kertaa, laite kestää sadan ryhmän käytön. Kun suorittimen hinta on noin kymmenen euroa, ja se on vaihdettavassa kannassa, tulee ryhmäkohtaiseksi kustannukseksi noin kymmenen senttiä. Tämä on promillen osia koko opintojakson kustannuksista, joten muistin käyttöä ei kannata optimoida. Toisaalta kyseessä voi olla loppukäyttäjällä oleva laite, jonka tulee kestää ainakin viisi, mieluiten kymmenen vuotta, ennen kuin se lakkaa toimimasta. Tällaisessa laitteessa täytyy haihtumattoman muistin eri osia käyttää mahdollisimman tasaisesti, ettei jokin tietty paljon muuttuva kohta pala loppuun paljon ennen muita. Täytyy tietenkin pitää mielessä, että tässäkin kohtaa on olennaista kirjoituskertojen määrä, ei laitteen ikä Muistitiedon päivittämisestä Flash-muisteja on kahta perustyyppiä. Toinen liitetään tietokoneeseen sarjaliitynnän avulla, ja sitä voi kirjoittaa ja lukea vain lohko kerrallaan. Tällaisia ovat esimerkiksi muistitikkujen sisällä olevat muistit. Toinen perustyyppi mahdollistaa viittaamisen muistipaikka kerrallaan. Muistipaikka kerrallaan viitattavat muistit jakaantuvat nekin kahteen ryhmään lohkojen koon mukaan. Toisessa on vakiokokoiset lohkot, joita käytetään symmetrisesti (niin sanottu FAT-tyyppi). Toisessa taas on muutama suurehko lohko ja monta pientä lohkoa (niin sanottu

6 56 Sulautettu ohjelmointi bootsector-tyyppi). Suuret lohkot on tarkoitettu ohjelmakoodille ja pienet usein muuttuvalle datalle. Ohjelmalohkot voidaan myös suojata kirjoittamiselta. Tällainen piirityyppi on yleinen tietokoneen alustusmuistin tallennuspaikkana (boot rom, bios). Flash-muistipiirillä on oheislaitteen tavoin ohjaus- ja tilarekistereitä, joiden avulla voidaan ohjata piirin toimintaa, muun muassa muistin tyhjentäminen tapahtuu ohjausrekisterien avulla. Monet Flashpiirit noudattavat standardiliittymää, joka mahdollistaa eri valmistajien muistin käytön samalla ohjelmalla 8. Bittien nollaus Tavallisesti tyhjä tieto muistipaikassa tarkoittaa sitä, että bitit ovat kaikki ykkösiä. Kirjoittamalla voidaan nollata bittejä, mutta niitä ei voi palauttaa ykköseksi tyhjentämättä koko lohkoa. Hyvin suunnitelluilla tietorakenteilla ja tiedon esittämistavoilla voidaan vähentää koko lohkon tyhjentämistarvetta siten, että (normaalitapauksessa) muuttujan elinajan arvot kulkevat ykkösbiteistä nollabitteihin päin. Esimerkiksi lukematon viesti on hyvä merkitä ykkösbitillä, jonka voi nollata lukemisen merkiksi. Edelleen viestin tuhoaminen on jonkin bitin nollaus. Tällöin ei tarvitse kirjoittaa ja tyhjentää koko lohkoa yhden bitin takia. Niin sanottuja WORM-levyjä (write once, read mostly) varten on tehty tiedostojärjestelmiä ylläkuvatuilla periaatteilla. Näitä periaatteita voidaan hyvin soveltaa myös Flash-muistiin. Nykylaitteista WORMlevyn tyyppisiä ovat CD-R- ja DVD-R-levyt. Lohkon tunnistaminen Koska tiedon päivitystä ei voi tehdä kuin aivan poikkeustapauksissa muuttamalla muistipaikan sisältöä suoraan, täytyy koko lohko uusine arvoineen kirjoittaa ensin toiseen paikkaan ja vasta sitten vapauttaa alkuperäinen lohko. Tästä seuraa se, että muuttujien paikat muistiavaruudessa muuttuvat, mutta käytännössä muutosta ei osoiteavaruudessa haluta nähdä. Tämä voidaan toteuttaa muistinhallinnan avulla. Suurempi ongelma onkin siinä, miten käynnistettäessä tunnistetaan käytössä oleva muisti. Tietoa aktiivisesta muistilohkosta ei voi tallettaa mihinkään vakiopaikkaan, koska silloin tästä osoitteesta tulisi koko järjestelmän heikoin lenkki, jonka vikaantuessa koko järjestelmä 8. Näin ainakin paperilla käytännössä eroja voi olla paljonkin.

7 Muistin hallinta 57 // Algoritmissa on varsin vapaasti käytetty sopivia aliohjelmia apuna struct {byte kaytto; byte tyyppi; int aikaleima; tiedot data} otsikko; const KAYTOSSA = 0x7f; const VANHA = 0; lohko *kirjoita_korvaava(lohko* vanha, tiedot *uudet_tiedot) { otsikko *vapaa = etsi_vapaa_lohko(); vapaa->kaytto = KAYTOSSA; copy(uudet_tiedot, &(vapaa->data) ); vapaa->aikaleima = time(); vapaa->tyyppi = vanha->tyyppi; vanha->kaytto = VANHA; } Ohjelma 3.1: Eräs flash-muistin käyttöalgoritmi. muuttuisi hyödyttömäksi. Tämän takia jokaisen lohkon tulee sisältää tieto siitä, mitä tietoa siihen on talletettu Päivitysesimerkki Käydään seuraavaksi läpi pieni esimerkki, jossa on kyseessä tiedon tallentaminen lohkoittain. Kun lohkon tietoa tulee muuttaa, eikä se onnistu vain bittejä nollaamalla edellisessä kohdassa esitetyllä tavalla, on pakko kirjoittaa lohko kokonaan uudestaan. Oletamme, että jokaisen lohkon alussa on yksi 8-bittinen tavu, joka kertoo lohkon tilan. Tyhjä lohko on FF 16, eli kaikki bitit ovat ykkösiä. Lohkon kirjoittaminen alkaa siis siitä, että etsitään vapaa lohko. Tämän jälkeen lohko merkitään otetuksi käyttöön nollaamalla ylin bitti. Muuttujassa on nyt siis arvo 7F 16. Tämän jälkeen kirjoitetaan varsinainen tieto lohkoon. Kirjoittamisen päätyttyä voidaan lohkon otsikkotietoihin eli lohkon käyttötavua seuraaviin tavuihin kirjoittaa lohkon aikaleima ja tyyppi. Kun tyyppi poikkeaa arvosta FF 16, se merkitsee, että lohko on loppuun kirjoitettu. Tämä voitaisiin varmistaa vielä sillä, että lohkon käyttötavun arvoksi asetetaan 3F 16, eli nollaamme toisenkin bitin ensimmäisestä tavusta, mutta tämä ei ole välttämätöntä. Edellä oleva on kuvattu myös ohjelmassa 3.1. Vanhan, käyttämättömäksi jääneen lohkon voimme merkitä nollaamalla käyttötavun bitit. Toinen vaihtoehto olisi tyhjentää lohko heti, mutta koska tyhjentäminen kestää suhteellisen kauan (esimerkiksi noin millisekunnin luokkaa), tyhjentäminen kannattaa jättää sellaiseen vaiheeseen, jossa järjestelmän käyttö on muuten vähäistä. Viivästettyä tyhjentämistä voidaan käyttää myös sen varmistamiseksi, että samaa lo-

8 58 Sulautettu ohjelmointi hkoa ei käytetä jatkuvasti. Toinen vaihtoehto olisi toteuttaa vapaan lohkon etsintä siten, että uudeksi lohkoksi valitaan se vapaa lohko, joka seuraa viimeksi käyttöön otettua lohkoa. Kun järjestelmä käynnistetään, pitää lohkoista etsiä oikea tieto. Periaatteessa riittää etsiä ensimmäinen oikeaa tyyppiä oleva lohko, jonka status on käytössä ja käytämme sitä. On tietenkin mahdollista, että sähköt katosivat juuri ennen kuin vanha lohko ehdittiin merkitä vanhaksi (ohjelman 3.1 viimeinen rivi). Emme siis lopeta etsintää ensimmäiseen löydettyyn, vaan jatkamme, ja jos löytyy muista vastaavansisältöisiä lohkoja, otamme käyttöön sen, jonka aikaleima on suurin. Muut voidaan merkitä vanhoiksi tässä vaiheessa. Esimerkissä erityyppisiä sivuja on vain yhden tavun verran (eli 255, koska FF 16 on keskeneräisen kentän tunnus). Koska muistit ovat paljon tätä suurempia, käytännössä tunnuksen arvoalueen tulee olla suurempi. 3.3 Ohjelman sijoittelu muistiin Sulautetuissa järjestelmissä varsinkin niissä pienimissä muistitilan käytön suunnittelu on pitkälti käsityötä. Tyypillisiä jakotapoja edustavat seuraavat näkökohdat: ajettava ohjelma, sijoitetaan lukumuistiin (ROM, Flash) alustettu data, kirjoitussuojattu, sijoitetaan lukumuistiin (ROM, Flash) staattinen muistialue, sijoitetaan luku kirjoitusmuistiin (RAM) järjestelmän asennusparametrit 9, esimerkiksi tunnistetiedot tai muu sellaiset sijoitetaan johonkin haihtumattomaan muistiin (patterivarmistettu RAM, Flash) dynaaminen muistialue, pino, sijoitus luku kirjoitusmuistiin (RAM) oheislaitteet, sijoitus absoluuttiosoitteisiin (näyttävät tavallisesti RAMilta) keskeytysvektorit, sijoitus absoluuttiosoitteisiin (ROM); käynnistyssekvenssissä vektorit voidaan siirtää RAM-muistiin. Varsinkin pienen sulautetun järjestelmän muistinhallinta eroaa tavanomaisesta PC-ympäristöstä monin tavoin. Ensinnäkin ohjelma on tyypillisesti valmiiksi muistissa eikä sitä ladata levyltä keskusmuistiin osana 9. Ovat loogisesti staattisia muuttujia, mutta näitä ei alusteta kertaakaan järjestelmää käynnistettäessä.

9 Muistin hallinta 59 ohjelman käynnistymistä. Lisäksi osa osoitteista on suoraan laiteosoitteita ja keskeytysvektori vie osan osoitteistosta. Järjestelmässä myöskään voida suoraviivaisesti toteuttaa alustetun data aluetta, jota voidaan muuttaa ohjelman ajon aikana, vaan toteutuksessa esimerkiksi kopioidaan alustettu data lukumuistiin (osa kääntäjistä saattaa tehdä tämän automaattisesti, osa jättää asian ohjelmoijan vastuulle). Toisaalta mitä suuremmasta sulautetusta järjestelmästä on kyse, sitä todennäköisempää on, että mukana on paljon automatisoituja rutiineja liittyen käynnistykseen ja lataamiseen. Tällöinkin ohjelmoija tosin voi usein vaikuttaa sijoitteluun esimerkiksi parametrein ja konfiguraatiotiedostoin. 3.4 Ohjelman sisäinen muistinhallinta Ohjelmaa rakennettaessa ohjelmistosuunnittelija joutuu jatkuvasti tekemään ratkaisuja, jotka vaikuttavat muistin kulutukseen ohjelman suorituksen aikana. Se, miten muuttujat ja tietorakenteet sijoitellaan muistiin, luonnollisesti määrittelee reunaehdot sille, mitä vähintään tarvitaan. Tämän lisäksi myös ohjelman suorituksessa välttämättömät tietorakenteet, joista tärkein on suorituspino, vaikuttavat siihen, miten sijoittelu kannattaa tehdä. Yksittäisen muuttujan kannalta ainakin seuraavat kolme vaihtoehtoa tulevat kyseeseen: 1. staattisesti varattu muuttuja, joka sijaitsee muistissa vakiopaikalla, ehkä jopa ROMissa 2. dynaamisesti varattu muuttuja, joka on sijoitettu pinoon (käytännössä siis joko aliohjelman sisäinen muuttuja tai parametri) 3. dynaamisesti varattu muuttuja, joka on sijoitettu kekoon (heap), josta muistia voidaan varata ohjelmoijan toimesta käyttäen ohjelmointikielen tarjoamia operaatiota, kuten vaikkapa C-kielen malloc-rutiinia. Käymme seuraavassa lyhyesti läpi näiden vaihtoehtojen hyvät ja huonot puolet Staattisesti varattu muuttuja Staattisesti varatut muuttujat ovat ohjelman suorituksen alussa luotuja muuttujia, joiden muistiosoite ei muutu. Näiden muuttujien varaaminen muistiin on yleensä helppoa lukuunottamatta tilanteita, joissa muistia ei

10 60 Sulautettu ohjelmointi kerta kaikkiaan ole tarpeeksi. Muuttujaan viittaaminenkin on yksinkertaista, sillä se voidaan aina tehdä saman muistiosoitteen kautta. Vaikka staattisesti varatut muuttujat ovat oikeastaan globaaleja, niiden näkyvyysalueiden rajaaminen esimerkiksi vain yhteen aliohjelmaan voi usein johtaa modulaarisuuden kannalta parempaan ratkaisuun. Jos arvoa oikeasti tarvitaan jossakin muuallakin, on sen arvo mahdollista välittää esimerkiksi seuraavaan tapaan: int* osoitin_staattiseen_muuttujaan() { static int x = 0; return &x; } Abstraktioihin liittyvistä syistä näin ei kuitenkaan yleensä ole suositeltavaa toimia, vaan kannattaa pyrkiä muihin, ohjelmistoteknisesti selkeämpiin ratkaisuihin Dynaamisesti varattu muuttuja pinossa Dynaamisesti luodut muuttujat, jotka sijaitsevat ohjelman suorituspinossa, ovat aliohjelmien sisäisiä muuttujia ja parametreja. Koska kyseessä ovat dynaamisesti luodut muuttujat, uusia muuttujia syntyy ja vanhoja katoaa sitä mukaa, kun uusia aliohjelmakutsuja tehdään ja vanhoja kutsuja saadaan suoritettua loppuun. Koska muuttujat elävät vain sen aikaa kuin mitä ne omistavan aliohjelman suoritus kestää, on oltava huolellinen sen suhteen, mitä aliohjelmasta voidaan palauttaa tai paljastaa muille operaatioille. Tällöin muuttujaa käytettäessä se ei ehkä enää olekaan olemassa, sillä operaation suoritus on jo päättynyt, kuten vaikkapa seuraavassa esimerkissä: // VAROITUS: Negatiivinen esimerkki, älä koskaan tee näin! int * osoitin_paikalliseen_muuttujaan() { int x = 0; return &x; } Joissakin ohjelmankirjoitusohjeissa esitetään jopa, että viitettä olioon, joka sijaitsee pinossa, ei koskaan pitäisi välittää eteenpäin. Tämä on kuitenkin ehkä hätävarjelun liioittelua, sillä ne metodit, joita olion omistava metodi tai proseduuri suorittaa, voivat kyllä luottaa siihen, että olio säilyy muistissa niiden suorituksen loppuun saakka. Sen sijaan viitettä olioon ei tietenkään saa palauttaa kutsujalle.

11 Muistin hallinta 61 Koska jokaista tehtyä metodi- tai proseduurikutsua kohti joudutaan ohjelman suorituspinosta varaamaan tilaa uuden aliohjelman sisäisille muuttujille, parametreille, paluuarvolle ja ohjelmaa suoritettaessa tarvittavalle kirjanpitodatalle, aivan pienimmissä sulautetuissa järjestelmissä joudutaan joskus pohtimaan, miten syviä proseduurikutsuketjuja voidaan sallia. Jopa matkapuhelimien ohjelmoinnissa tämän suhteen voi tulla ongelmia, jos pinossa olevat oliot ovat suuria, ja niitä joudutaan kopioimaan metodista toiseen. Tästä syystä kannattaa ehkä pohtia viitteen välitystä olioon uuden kopion rakentamisen sijaan, vaikka periaatteessa viitteen välitystä pinosta varattuun olioon ei suositellakaan. Lisäksi rekursion suhteen kannattaa sulautettuja järjestelmiä suunniteltaessa olla huolellinen. Jos rekursio halutaan sallia, kannattaa ainakin varmistaa, että rekursiivisilla kutsuilla on joku riittävän pieni yläraja, jotta voidaan yhtäältä varmistua siitä, että muistia ei voi kulua tiettyä määrää enempää, ja toisaalta siitä, että ohjelma ei ryhdy suorittamaan liian pitkää laskentaa, vaan vasteajat pysyvät edelleen järkevissä rajoissa Dynaamisesti varattu muuttuja keossa Dynaamisesti muistiin allokoidut rutiinit, joissa ohjelmoija varaa muistin keosta (heap) eroavat pinossa sijaitsevista muuttujista sikäli, että keosta varatut muistialueet ovat jatkuvasti ohjelmoijan koordinoimia. Muistia voidaan varata joko ohjelmointikielen keinoin (esimerkiksi C++:n new) tai käyttäen kirjastorutiineja (esimerkiksi C:n malloc). Jälkimmäiset saattavat olla järjestelmäkohtaisia, ja niiden toteutus voi vaihdella rajustikin. Esimerkiksi seuraava koodirivi varaa muuttujan verran muistia keosta: int* x = (int*) malloc(sizeof(int)); *x = 0; Dynaamisesti keosta varattuja muuttujia (ja niille varattuja muistialueita) ei (yleensä) vapauteta automaattisesti läheskään kaikissa ohjelmointikielissä, vaan ohjelmoija joutuu itse tekemään päätöksen siitä, milloin muistialue voidaan vapauttaa.

12 62 Sulautettu ohjelmointi 3.5 Dynaamisen muistin hallinta osana ohjelmistosuunnittelua Dynaamisen muistin käyttöä koetetaan välttää sulautetuissa järjestelmissä, koska siihen liittyvien virheiden tekeminen on liiankin helppoa. Lisäksi virheet voivat ilmetä vasta pitkän ajan jälkeen, ja niiden löytäminen on vaikeaa. Kolmas syy dynaamisen muistin välttämiseen on siinä, että sen ylläpito vie paljon aikaa, ja muistin käyttöasteesta ja pirstoutumisesta riippuen sopivankokoisen muistin löytämisen aika vaihtelee, mikä taas on ongelma reaaliaikajärjestelmissä Joitakin tyypillisiä haasteita Tyypillisiä virheitä ovat jäänneviittaukset eli viittaukset jo vapautettuihin alkioihin, jotka on pahimmassa tapauksessa jo uudestaan käytössä, ja roskaantuminen eli se, että käyttämätöntä muistia ei vapauteta. Edellisistä jäänneviittaukset ilmenevät yleensä nopeasti ohjelman toiminnan sotkeentumisena, mutta roskaantuminen voi ilmoittaa itsestään vasta hyvinkin pitkän ajan kuluttua. Hoitamaton roskaantuminen aiheuttaa väistämättä muistin loppumisen, mikäli laite on päällä tarpeeksi pitkään. Valitettavasti tarvittava aika voi olla niin pitkä, ja roskaamisen aikaansaamiseksi tarvittavat operaatiot voivat olla niin monimutkaisia, että kaikkia mahdollisia ongelmia on mahdoton löytää järjestelmää testaamalla. Kolmas melko tavallinen ongelma, joka liittyy dynaamiseen muistin varaamiseen, on muistin pirstoutuminen. Pirstoutumisella tarkoitetaan eri kokoisten muistialueiden varaamisen ja vapauttamisen aiheuttamia eri kokoisia varattuja ja vapaita muistialueita. Toisin kuin jäänneviittaukset ja roskaantuminen, pirstoutuminen ei välttämättä johdu varsinaisesta sovellusohjelmoijan ohjelmointi- tai suunnitteluvirheestä, vaan pikemminkin siitä, miten dynaamisen muistin varausrutiinit on toteutettu ja miten niitä sovelluksesta käytetään. Ongelmia voi yleensä välttää pyrkimällä vapauttamaan muisti mahdollisimman aikaisin, ja varaamalla tarvittava muisti mahdollisimman myöhään. Tällöin parhaiten tarkoitukseen sopiva muistialue voidaan yleensä löytää helpommin. Turvallinen kompromissiratkaisu dynaamisuuden, joustavuuden ja staattisen varauksen turvallisuuden välillä on varata kaikki dynaaminen tila heti käynnistysvaiheessa, jonka jälkeen dynaamisia varauksia ei enää tehdä. Valitettavasti tämä ratkaisu ei aina ole mahdoll-

13 Muistin hallinta 63 inen, sillä usein se rajoittaa huomattavasti mahdollisten toimintojen määrää. Seuraavassa esitellään joitakin tapoja ja näkökulmia dynaamisen muistin käsittelemiseen sulautetussa ympäristössä Vain varauksia -vaihtoehto Tämä vaihtoehto on yksinkertaisin kaikista vaihtoehdoista. Se ei silti ole täysin poissuljettu, sillä dynaamista muistinvarausta saatetaan käyttää vain siksi, että laite olisi parametroitava. Tällöin muistivaraukset tehdään kaikki käynnistysvaiheessa, eikä tämän jälkeen sen koommin varata kuin vapautetakaan muistia. Vain varauksia sisältävä toteutus on varsin yksinkertainen, mikäli niin halutaan. Toteutukseen ei tarvita kuin kaksi muuttujaa: address alkumuisti; int koko; Alustusrutiinin tehtävänä on alustaa nämä muistipaikat siten, että alkumuisti osoittaa dynaamisen muistialueen alkuun ja koko sisältää vapaana olevan muistin koon. Vaikka sovellukset eivät dynaamista muistia tarvitsisikaan, tällä tavoin voi käyttöjärjestelmä varata prosessien tarvitsemat pinot. Itse varausrutiini palauttaa NULLin, mikäli muistia ei ole haluttua määrää, muutoin se palauttaa muistin alkuosoitteen: address malloc (int varaa) { address apu; if (varaa > koko) { return NULL; } apu = alkumuisti; alkumuisti += varaa; koko -= varaa; return apu; } Jokaiselle prosessille voidaan antaa oma dynaaminen muistialue, joka varataan tällaisen rutiinin avulla ja josta edelleen kukin prosessi varaa muistia tällä samalla tai muilla rutiineilla. Vain varauksia -vaihtoehto on usein paras mahdollinen ratkaisu, kun halutaan rakentaa järjestelmä, jonka toimintaa on mahdollista testata hyvin huolellisesti. Voidaan jopa ajatella, että kyseessä on yksi ainoa tietorakenne, joka sisältää kaikki ohjelman tarvitsemat muuttujat.

14 64 Sulautettu ohjelmointi Tämän jälkeen testaamisessa tarvittavat erilaiset tilat on huomattavasti helpompi rakentaa kuin mitä dynaamisia muistinvarauksia tehdessä kävisi Sekä varauksia että vapautuksia Dynaamiselle muistille on olemassa monta erilaista ratkaisua. Näitä menetelmiä on käsitelty tarkemmin algoritmikursseilla. Kaikissa järjestelmissä tarvitaan varsinaisen hyötykuorman lisäksi hallinnollista tietoa, mitä ei tarvittu juurikaan edellä olleessa vain varauksia sallivassa vaihtoehdossa. Eri ratkaisut suhtautuvat hieman eri tavoin siihen, miten helposti muisti pirstoutuu pienemmiksi paloiksi. Mikäli varattava muistialue on aina saman kokoinen, tilanne yksinkertaistuu huomattavasti. Tällaisen järjestelmän alustuksessa muistialueista muodostetaan yksisuuntainen linkkilista, josta varaus ja vapauttaminen käyvät hyvin yksinkertaisesti: address vapaa; /* Alustetaan vapaan tilan alkuun */ address varaa () { alkio *v; if (vapaa == NULL) { return NULL; } v = vapaa; vapaa = vapaa->seuraava; return (address) v; } void vapauta (address vapautettava) { alkio *v = (alkio *) vapautettava; v->seuraava = vapaa; vapaa = v; return; } Hyvänä puolena on sekin, että vaikka linkkilistan ylläpitoon tarvitaan osoitin, osoitinta ei tarvita muistin ollessa käytössä. Varjopuolena on siis se, että varattavien muistialkioiden tulee olla samansuuruisia. On myös muunlaisia toteutuksia, joihin eri ohjelmointikielet voivat tarjota mahdollisuuksia. Esimerkiksi Ada-kielessä voidaan jokaiselle osoitintyypille varata oma altaansa, josta tyypin dynaamiset muuttujat varataan. Näissä varauksissa voidaan käyttää hyväksi tämäntyyppistä optimointimahdollisuutta tarvittaessa, mutta siirrettävyys- ja

15 Muistin hallinta 65 ylläpidettävyyssyistä kannattaa yleisesti ottaen mieluummin pyrkiä hyvään lopputulokseen ohjelmistosuunnittelun keinoin yksittäisten työkalujen ja työkaluversioiden tarjoamien mahdollisuuksien hyödyntämisen sijaan. Kannattaa myös ottaa huomioon, että muistinvaraus on usein suorituskyvyn kannalta raskas operaatio. Tästä syystä joskus toimitaan siten, että samalla muistinvarauksella varataan tilaa usealle tietorakenteelle, jotka sitten voidaan sijoittaa samaan varattuun muistialkioon. Tällöin saavutetaan myös jonkin verran etua välimuistin suhteen, sillä yhteen tietorakenteeseen viitattaessa saattaa käydä niin, että koko muistialkio haetaan välimuistiin, ja muihin tietorakenteisiin viittaaminen on siten nopeampaa Muistinhallinnan algoritmeista On huomattava, että olio-ohjelmointi tuo luonnostaan dynaamisia alkioita järjestelmään. Tällöin dynaamista muistia on käytännössä pakko käyttää. Edelläolevista algoritmeista ei oikein ole tähän tilanteeseen apua, vaan on parempi käyttää jotain tehokkaampaa menetelmää. Muistinkäytön kannalta tehokkaimmasta päästä on algoritmi, joka linkkilistaa läpikäydessään ottaa ensimmäisen tarpeeksi suuren lohkon (first fit -algoritmi). Tämän algoritmin ongelma on siinä, että pahimmillaan sopivan kokoisen muistialkion löytämiseksi täytyy selata koko linkkilista läpi. Lisäksi muistia vapautettaessa pitää osata yhdistää vierekkäiset vapaat lohkot yhteen. Yksi suhteellisen hyvä menetelmä on binaarinen vieruskaverimenetelmä (binary buddy system), jossa yhdistäminen on helppoa. Algoritmeja ja niiden keskeisimpiä ominaisuuksia käsitellään tarkemmin tietorakenteiden kursseilla, joten niihin ei paneuduta tämän tarkemmin tässä yhteydessä Dynaaminen muisti monelle prosessille Yksinkertaisinta on pitää kullekin prosessille omaa dynaamisen muistin aluetta, josta se varaa muistia. Tällöin kyseinen prosessi ja sen suunnittelijat ovat vastuussa prosessin muistinkulutuksesta. On myös mahdollista asettaa rajat prosessin haltuun annettavalle muistialueelle. Tämä mahdollistaa sen, että kokonaisjärjestelmän muistinkulutusta on mahdollista arvioida jo silloin, kun järjestelmää ollaan rakentamassa. Lisäksi, kun suunnittelijat tietävät käytettävissä olevan muistin määrän, on muistinkulutusta helpompi optimoida. Myös testattavuuteen liittyvät

16 66 Sulautettu ohjelmointi syyt puoltavat sitä, että jokaiselle prosessille allokoidaan tietty alue sulautettua järjestelmää rakennettaessa. Toisaalta etukäteen suoritettu muistin allokointi eri prosesseille on joskus hyvin rajoittavaa. Paljon joustavampi ratkaisu on luoda yksi ainoa dynaamisen muistin alue, jolta kaikki varaavat muistia. Tällöin tulee varaus- ja vapautusrutiineissa muistaa huolehtia poissulkemisesta, sillä muussa tapauksessa sama muistialue voi päätyä usean eri prosessin käyttöön. Uusien virhemahdollisuuksien lisäksi myös testaaminen vaikeutuu merkittävästi, sillä järjestelmän kokonaistilaa ei voida enää konstruoida yksittäisten sovellusten tilan yhdistelmänä, vaan myös dynaamisen muistin varaustilanne on otettava huomioon. Mikäli prosessit voivat päättyä, eikä voida luottaa siihen, että ne vapauttavat muistinsa, hallintatietoon tulee lisätä muistin varanneen prosessin tunnus, jolloin dynaaminen muistitila voidaan prosessin päättyessä vapauttaa. Tämä tieto voidaan kerätä myös prosessin kuvaajaan (prosessielementtiin). Mikäli käytettävissä on jonkinlainen käyttöjärjestelmä, eikä ohjelmistoa toteuteta suoraan laitteiston päälle, tarjoaa käyttöjärjestelmä yleensä riittävät palvelut yllä mainittujen tehtävien suoritukselle Roskaantuminen Muistin roskaantuminen on yksi suurimpia ongelmia, mikäli järjestelmä käyttää aktiivisesti dynaamista muistia ja se on päällä pitkiä aikoja yhteen menoon. Tällöin muistia varataan ja vapautetaan useita kertoja, ja pienetkin virheet muistinhallintaan liittyvissä rutiineissa voivat johtaa ongelmiin kumuloituessaan ajan kuluessa. Roskaantumiseen liittyvien ongelmien pienentämiseksi on mahdollista toteuttaa erilaisia rutiineja, joiden avulla järjestelmä voi itse yrittää vapauttaa tarpeettomia, mutta edelleen varattuja muistialkioita. Mikäli muistipalat ovat keskenään samanlaisia kuten kohdan esimerkkitapauksessa, voidaan melko helposti merkitä sellaiset alkiot, joihin on vielä olemassa viittaus aktiivisista muuttujista. Joissain kielissä, kuten Lispissä, tämä on suorastaan kieleen sisäänrakennettu ominaisuus, olkoonkin että Lisp on äärimmäisen harvinainen sulautetuissa järjestelmissä. Ehkä parempi esimerkki on Java, jossa muistinhallinta huolehtii roskien keruusta automaattisesti. Roskien keruuta varten on olemassa useita algoritmeja, joiden toiminta voidaan jakaa karkeasti kahteen kategoriaan. Näistä yksinkertaisempi, niin sanottu stop-the-world-roskienkeruu, perustuu siihen,

17 Muistin hallinta 67 että ohjelman suoritus pysäytetään, käyttämättömät varatut muistialueet vapautetaan, ja sitten ohjelman suoritusta jatketaan. Toinen perusvaihtoehto on suorittaa roskienkeruurutiinia koko ajan rinnakkain ohjelman suorituksen kannalta, mikä on huomattavasti monimutkaisempaa kuin roskien keruu käyttäen stop-the-world-tyyppistä algoritmia. Koska sulautettu järjestelmä on yleensä reaaliaikainen, järjestelmää ei ole vara pysäyttää satunnaisena ajankohtana roskienkeruuta varten. Tämän takia, mikäli mahdollista, roskienkeruuta ajetaan rinnakkain sovelluksen kanssa. Algoritmeja on useita, joista osa perustuu käytössä olevien olioiden kopiointiin ja vanhojen muistialueiden vapauttamiseen, osa käytettyjen alueiden merkkaamiseen ja muiden vapauttamiseen (niin sanottu mark-and-sweep), ja osa hyödyntää viitteiden laskentaa. Lisäksi näiden algoritmien erilaiset kombinaatiot ja olioiden eliniän huomiointi ovat mahdollisia, esimerkiksi siten, että koska suurin osa olioista elää vain vähän aikaa, vastikään luotujen olioiden roskankeruussa voidaan hyödyntää algoritmia, joka siivoaa selvät tapaukset nopeasti, ja jo pitkään olemassa olleiden olioiden roskienkeruu puolestaan voi olla hitaampaa mutta huolellisempaa Ohjelmointikielistä dynaamisen muistin kannalta Kolmesta ehkä sulautettujen järjestelmien kannalta tärkeimmästä kielestä (C, C++, Java) C on dynaamisten ominaisuuksien osalta turvallisin, sillä ohjelmoija pystyy siinä täysin päättämään siitä, milloin dynaamista muistia käytetään. C++ on C-kieltä sikäli "vaarallisempi", että se saattaa yllättää ohjelmoijan siinä, milloin se varaa ja vapauttaa dynaamista muistia. Samoin rakentajien ja purkajien suoritus saattaa joissain tilanteissa yllättää ohjelmoijan, sillä uusia olioita saattaa joissakin tilanteissa syntyä vahingossa. Java on näistä vaihtoehdoista ongelmallisin, koska käyttäjä ei voi pakottaa muistin vapauttamista tiettyyn hetkeen ohjelmallisesti. Näin muistin vapauttaminen voi yllättää pahassa paikassa. Javasta on kuitenkin olemassa myös deterministisempi ja reaaliaikajärjestelmien kannalta soveliaampi versio Real-Time Specification for Java (JSR-001), jota käyttäen myös Javaa voidaan käyttää vaativienkin sulautettujen järjestelmien toteuttamisessa. Yllä mainittujen kielten lisäksi Ada-kieltä on käytetty jonkin verran erityisesti ilmailussa ja avaruusteknologiassa. Kieli tarjoaa suuren

18 68 Sulautettu ohjelmointi joukon erilaisia ominaisuuksia, ja eri ajoajan ympäristöt tarjoavat niistä suorituskyvyltään ja muistinkulutukseltaan vaihtelevia toteutuksia. Tästä syystä voidaan kielen tarjoamien ominaisuuksien joukkoa rajoittaa sellaiseen alijoukkoon, joka tarjoaa riittävän ilmaisuvoiman, mutta joka takaa riittävästi ennustettavuutta liittyen dynaamisen muistin käyttöön. Esimerkiksi kielen tarjoaman tehtävämekanismin sijaan voidaan päätyä käyttämään sovellusympäristön tarjoamia prosesseja, tai poikkeusten käyttö voi olla rajoitettua. Samaan tapaan on tietysti mahdollista rajata myös muiden kielten ominaisuuksia sovelluskohteeseen mahdollisimman hyvin sopivaksi käyttäen erilaisia ohjelmointikäytäntöjä. Lisäksi monet ympäristöt tarjoavat mahdollisuuden käyttää jotain dynaamista ohjelmointikieltä sovellusohjelmointiin skriptinomaisesti. Tällaisilla ohjelmointikielillä toteutetut ohjelmat ja niiden ajoajan ympäristön ominaisuudet ovat yleensä melko vaikeasti ennakoitavissa. Tästä syystä näitä ympäristöjä käytetään lähinnä tarjoamaan jonkinasteista laajennettavuutta ja konfiguroituvuutta, jota olisi vaikea toteuttaa muuten. 3.6 Muistinhallintayksikkö ja välimuisti Varsinaisten muistipiirien lisäksi myös muistinhallintayksikkö ja välimuisti voidaan laskea osaksi muistinhallintaan käytettyä laitteistoa. Käymme seuraavassa läpi nämä toiminnot pääpiirteissään Muistinhallintayksikkö Muistinhallintayksikön (MMU, Memory Management Unit) päätehtävänä on suojata prosesseja toisiltaan ja saada kunkin prosessin muisti pidettyä hallinnassa eli kätkeä mahdolliset epäjatkuvuuskohdat fyysisessä muistissa ja saada kaikkien prosessien muisti näyttämään rakenteeltaan samankaltaiselta. Vaikka muistinhallintayksikön yhteydessä puhutaan virtuaaliosoitteista (joskus loogisista osoitteista), tämä ei välttämättä tarkoita, että koneessa olisi käytössä virtuaalimuisti. Muistinhallintayksikön toiminta Muistinhallintayksiköt ovat hyvinkin erilaisia. Käyttöjärjestelmäkirjoissa on esitelty näitä tarkemmin. Tyypillisesti muistinhallintayksikkö sisältää erilliset rekisterit käyttäjä- ja käyttöjärjestelmätiloille (muuten

19 Muistin hallinta 69 keskeytykset voisivat olla hankalia). Kumpaakin tilaa varten voi olla erilliset muunnokset datalle ja koodille. Edelleen osoitteen jakautuminen osiin on tyypillisesti ohjelmoitavissa (esimerkiksi sivunpituutta voi muuttaa). Muistinhallintayksikkö sisältää myös TLB:n (Table Lookahead Buffer), joka voi esiintyä myös hieman erinimisenä (esimerkiksi ATC, Address Translation Cache). Muistiviittauksen tullessa TLB:stä tarkastetaan, onko viitatun sivun tiedot valmiina ja jos on, muunnos tapahtuu heti ilman lisäkuormaa. Jos tulee huti, muistinhallintayksikkö generoi viittauksia keskusmuistiin, joiden avulla osoitteenmuunnokseen tarvittava tieto siirretään muistinhallintayksikölle. Näiden siirtojen jälkeen jatketaan kuin hutia ei olisi ollutkaan. Jos sivua ei löydy, generoidaan virhekeskeytys, samoin, jos sivun suojauksia loukataan. Muistinhallintayksikössä yhteisen muistin hallintaan voi olla erikoispiirteitä. Esimerkkimuistinhallintayksikkö kuvassa 3.1 on kaksitasoiseen sivutauluun perustuva. Tasoja voi olla useampiakin, mutta tavallisesti kaksi tasoa riittää. Taulun juuri Virtuaaliosoite taulun A indeksi taulun B indeksi siirtymä A-taulu B-taulu sivutaulun osoite & sivutilan numero muistiosoite & Kuva 3.1 Kaksitasoinen sivutaulu Muistinhallintayksikön käyttö Konetta käynnistettäessä muistinhallintayksikkö tiputetaan automaattisesti pois käytöstä. Alustusrutiinit rakentavat käyttöjärjestelmätilan muunnostaulut keskusmuistiin ja herättävät muistinhallintayksikön

20 70 Sulautettu ohjelmointi toimimaan. Vastaavasti prosessia luotaessa kirjoitetaan prosessien muunnostaulut keskusmuistiin. Muistinhallintayksikössä voidaan kertoa sivukohtaisesti muun muassa seuraavia tietoja (vaihtelevat yksiköstä toiseen): miten sivua voi käsitellä käyttöjärjestelmätilassa (luku/kirjoitus) miten sivua voi käsitellä käyttäjätilassa (luku/kirjoitus) onko sivu olemassa onko sivu pinon vai tavallisen muistin osa (vaikuttaa joissain ratkaisuissa laillisen osoitteen laskentaan) käytetäänkö sivulle muunnosta vai päästetäänkö sivun osoitteet suoraan väylälle onko välimuisti päällä vai ei (esimerkiksi oheislaitteiden ohjausja tilarekisterien kohdalla ei saa olla päällä). Prosessia vaihdettaessa muistinhallintayksikön rekisterit tyhjennetään ja uuden muunnostaulun alkuosoite siirretään muistihallintayksikköön, jonka jälkeen laitteisto hakee sivujen tiedot rekistereihin sitä mukaa, kun sivuihin viitataan. Mahdollisia virhetilanteita Muistinhallintayksikön avulla voidaan havaita sellaisia virheitä, joita on erittäin vaikeaa tai jopa mahdotonta huomata ilman sitä. Tällaisia virhetilanteita ovat muun muassa kirjoittaminen ohjelmakoodin päälle, joka ei välttämättä vaikuta mitään, jos muisti on lukumuistia, mutta kyseessä on silti virhe, sillä onhan selvää, ettei se tarkoitettukaan muistipaikka päivity tässä tilanteessa. Yleisin havaittu virhe lienee se, että osoitteenmuunnoksen aikana havaitaan, että osoitetta vastaavaa sivua ei ole olemassa. Mikäli kyseessä on virtuaalimuistijärjestelmä, käsitellään tämä tilanteesta riippuen joko aitona virheenä tai läsnäolokeskeytyksenä. Jos kyseessä on läsnäolokeskeytys, viittauksen käsittelyä jatketaan virtuaalimuistin käsittelyn tapaan. Jos taas kyseessä on aito virhe, se aiheuttaa ytimestä ja sen palveluista riippuen joko ohjelman päättämisen tai signaalin lähettämisen ohjelmalle. Tällöin voidaan generoida bus error tai muu vastaava virhe. Sulautetuissa ja reaaliaikajärjestelmissä virtuaalimuisti on harvinainen, koska se aiheuttaa ajoituksen ennustamiseen ongelmia. Tämän takia emme käsittele virtuaalimuistia tämän enempää. Tarkempia kuvauksia löytyy mistä tahansa käyttöjärjestelmäkirjasta.

3. Luento: Muistin hallinta. Tommi Mikkonen,

3. Luento: Muistin hallinta. Tommi Mikkonen, 3. Luento: Muistin hallinta Tommi Mikkonen, tommi.mikkonen@tut.fi Agenda Erityyppiset muistit Ohjelman sijoittelu muistiin Ohjelman sisäinen muistinhallinta Muistinhallintayksikkö Välimuisti Yhteenveto

Lisätiedot

Arto Salminen, arto.salminen@tut.fi

Arto Salminen, arto.salminen@tut.fi 3. Luento: Muistin hallinta Arto Salminen, arto.salminen@tut.fi Agenda Mitä väliä? Erityyppiset muistit Ohjelman sijoittelu muistiin Ohjelman sisäinen muistinhallinta Muistinhallintayksikkö Välimuisti

Lisätiedot

11/20: Konepelti auki

11/20: Konepelti auki Ohjelmointi 1 / syksy 2007 11/20: Konepelti auki Paavo Nieminen nieminen@jyu.fi Tietotekniikan laitos Informaatioteknologian tiedekunta Jyväskylän yliopisto Ohjelmointi 1 / syksy 2007 p.1/11 Tämän luennon

Lisätiedot

815338A Ohjelmointikielten periaatteet Harjoitus 3 vastaukset

815338A Ohjelmointikielten periaatteet Harjoitus 3 vastaukset 815338A Ohjelmointikielten periaatteet 2015-2016. Harjoitus 3 vastaukset Harjoituksen aiheena ovat imperatiivisten kielten muuttujiin liittyvät kysymykset. Tehtävä 1. Määritä muuttujien max_num, lista,

Lisätiedot

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

Sisältö. 22. Taulukot. Yleistä. Yleistä Sisältö 22. Taulukot Yleistä. Esittely ja luominen. Alkioiden käsittely. Kaksiulotteinen taulukko. Taulukko metodin parametrina. Taulukko ja HelloWorld-ohjelma. Taulukko paluuarvona. 22.1 22.2 Yleistä

Lisätiedot

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

Olion elinikä. Olion luominen. Olion tuhoutuminen. Olion tuhoutuminen. Kissa rontti = null; rontti = new Kissa(); Sisällys 7. Oliot ja viitteet Olio Java-kielessä. Olion luominen, elinikä ja tuhoutuminen. Viitteiden käsittelyä: sijoitus, vertailu ja varautuminen null-arvoon. Viite metodin paluuarvona.. 7.1 7.2 Olio

Lisätiedot

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

Ohjelmassa muuttujalla on nimi ja arvo. Kääntäjä ja linkkeri varaavat muistilohkon, jonne muuttujan arvo talletetaan. Osoittimet Ohjelmassa muuttujalla on nimi ja arvo. Kääntäjä ja linkkeri varaavat muistilohkon, jonne muuttujan arvo talletetaan. Muistilohkon koko riippuu muuttujan tyypistä, eli kuinka suuria arvoja muuttujan

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

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

Sisältö. 2. Taulukot. Yleistä. Yleistä Sisältö 2. Taulukot Yleistä. Esittely ja luominen. Alkioiden käsittely. Kaksiulotteinen taulukko. Taulukko operaation parametrina. Taulukko ja HelloWorld-ohjelma. Taulukko paluuarvona. 2.1 2.2 Yleistä

Lisätiedot

Harjoitustyö: virtuaalikone

Harjoitustyö: virtuaalikone Harjoitustyö: virtuaalikone Toteuta alla kuvattu virtuaalikone yksinkertaiselle olio-orientoituneelle skriptauskielelle. Paketissa on testaamista varten mukana kaksi lyhyttä ohjelmaa. Ohjeita Noudata ohjelman

Lisätiedot

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

Sisällys. 7. Oliot ja viitteet. Olion luominen. Olio Java-kielessä Sisälls 7. Oliot ja viitteet Olio Java-kielessä. Olion luominen, elinikä ja tuhoutuminen.. Viitteiden vertailu. Varautuminen null-arvoon. Viite metodin paluuarvona.. Muuttumattomat ja muuttuvat merkkijonot.

Lisätiedot

Käyttöjärjestelmän rakenne

Käyttöjärjestelmän rakenne Käyttöjärjestelmän rakenne Tietokonejärjestelmä = Laitteisto + ohjelmisto Sovellus saa laitteiston käyttöönsä kj:n avustuksella CPU ja muisti Oheislaitteet KJ tarjoaa laitteiston käytössä tarvittavat palvelunsa

Lisätiedot

ltöä (Luennot 5&6) Luento 5: YKSINKERTAINEN SEGMENTOINTI JA SIVUTUS Pikakertaus: : a) b) c) Dyn.. part.: sijoitus Kuva Buddy System: esimerkki

ltöä (Luennot 5&6) Luento 5: YKSINKERTAINEN SEGMENTOINTI JA SIVUTUS Pikakertaus: : a) b) c) Dyn.. part.: sijoitus Kuva Buddy System: esimerkki Käyttöjärjestelmät t I Luento 5: YKSINKERTAINEN SEGMENTOINTI JA SIVUTUS Stallings, Luku 7 Sisält ltöä (Luennot 5&6) Yleistä muistinhallinnasta (luku 7.1) Yksinkertainen muistinhallinta a) kiinteät partitiokoot

Lisätiedot

LOAD R1, =2 Sijoitetaan rekisteriin R1 arvo 2. LOAD R1, 100

LOAD R1, =2 Sijoitetaan rekisteriin R1 arvo 2. LOAD R1, 100 Tiedonsiirtokäskyt LOAD LOAD-käsky toimii jälkimmäisestä operandista ensimmäiseen. Ensimmäisen operandin pitää olla rekisteri, toinen voi olla rekisteri, vakio tai muistiosoite (myös muuttujat ovat muistiosoitteita).

Lisätiedot

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

Yleistä. Nyt käsitellään vain taulukko (array), joka on saman tyyppisten muuttujien eli alkioiden (element) kokoelma. 2. Taulukot 2.1 Sisältö Yleistä. Esittely ja luominen. Alkioiden käsittely. Kaksiulotteinen taulukko. Taulukko operaation parametrina. Taulukko ja HelloWorld-ohjelma. Taulukko paluuarvona. 2.2 Yleistä

Lisätiedot

2 Konekieli, aliohjelmat, keskeytykset

2 Konekieli, aliohjelmat, keskeytykset ITK145 Käyttöjärjestelmät, kesä 2005 Tenttitärppejä Tässä on lueteltu suurin piirtein kaikki vuosina 2003-2005 kurssin tenteissä kysytyt kysymykset, ja mukana on myös muutama uusi. Jokaisessa kysymyksessä

Lisätiedot

TIEP114 Tietokoneen rakenne ja arkkitehtuuri, 3 op. Assembly ja konekieli

TIEP114 Tietokoneen rakenne ja arkkitehtuuri, 3 op. Assembly ja konekieli TIEP114 Tietokoneen rakenne ja arkkitehtuuri, 3 op Assembly ja konekieli Tietokoneen ja ohjelmiston rakenne Loogisilla piireillä ja komponenteilla rakennetaan prosessori ja muistit Prosessorin rakenne

Lisätiedot

7. Oliot ja viitteet 7.1

7. Oliot ja viitteet 7.1 7. Oliot ja viitteet 7.1 Sisällys Olio Java-kielessä. Olion luominen, elinikä ja tuhoutuminen. Viitteiden sijoitus. Viitteiden vertailu. Varautuminen null-arvoon. Viite metodin paluuarvona. Viite metodin

Lisätiedot

5. Luento: Rinnakkaisuus ja reaaliaika. Tommi Mikkonen, tommi.mikkonen@tut.fi

5. Luento: Rinnakkaisuus ja reaaliaika. Tommi Mikkonen, tommi.mikkonen@tut.fi 5. Luento: Rinnakkaisuus ja reaaliaika Tommi Mikkonen, tommi.mikkonen@tut.fi Agenda Perusongelmat Jako prosesseihin Reaaliaika Rinnakkaisuus Rinnakkaisuus tarkoittaa tässä yhteydessä useamman kuin yhden

Lisätiedot

Dynaaminen muisti. Pasi Sarolahti Aalto University School of Electrical Engineering. C-ohjelmointi Kevät 2017.

Dynaaminen muisti. Pasi Sarolahti Aalto University School of Electrical Engineering. C-ohjelmointi Kevät 2017. C! Dynaaminen muisti 9.2.2017 Agenda Kertausta merkkijonoista Dynaaminen muisti Valgrind-perusteet ja esimerkkejä Seuraava luento to 2.3. Ei harjoituksia arviointiviikolla 13.2. 17.2. 2 Palautetta merkkijonoihin

Lisätiedot

Tietorakenteet ja algoritmit

Tietorakenteet ja algoritmit Tietorakenteet ja algoritmit Muuttujat eri muisteissa Ohjelman muistialueen layout Paikallisen ja globaalin muuttujan ominaisuudet Dynaamisen muistinkäytön edut Paikallisten muuttujien dynaamisuus ADT

Lisätiedot

TIEP114 Tietokoneen rakenne ja arkkitehtuuri, 3 op. Assembly ja konekieli

TIEP114 Tietokoneen rakenne ja arkkitehtuuri, 3 op. Assembly ja konekieli TIEP114 Tietokoneen rakenne ja arkkitehtuuri, 3 op Assembly ja konekieli Tietokoneen ja ohjelmiston rakenne Loogisilla piireillä ja komponenteilla rakennetaan prosessori ja muistit Prosessorin rakenne

Lisätiedot

MUISTIPIIRIT H. Honkanen

MUISTIPIIRIT H. Honkanen MUISTIPIIRIT H. Honkanen Puolijohdemuistit voidaan jaotella käyttötarkoituksensa mukaisesti: Puolijohdemuistit Luku- ja kirjoitusmuistit RAM, Random Access Memory - Käytetään ohjelman suorituksen aikaisen

Lisätiedot

Pong-peli, vaihe Aliohjelman tekeminen. Muilla kielillä: English Suomi. Tämä on Pong-pelin tutoriaalin osa 3/7. Tämän vaiheen aikana

Pong-peli, vaihe Aliohjelman tekeminen. Muilla kielillä: English Suomi. Tämä on Pong-pelin tutoriaalin osa 3/7. Tämän vaiheen aikana Muilla kielillä: English Suomi Pong-peli, vaihe 3 Tämä on Pong-pelin tutoriaalin osa 3/7. Tämän vaiheen aikana Jaetaan ohjelma pienempiin palasiin (aliohjelmiin) Lisätään peliin maila (jota ei voi vielä

Lisätiedot

2. Olio-ohjelmoinista lyhyesti 2.1

2. Olio-ohjelmoinista lyhyesti 2.1 2. Olio-ohjelmoinista lyhyesti 2.1 Sisällys Yleistä. Oliot ja luokat. Attribuutit. Olioiden esittely ja alustus. Rakentajat. Olion operaation kutsuminen. 2.2 Yleistä Olio-ohjelmointia käsitellään hyvin

Lisätiedot

Ohjelmointi 2 / 2010 Välikoe / 26.3

Ohjelmointi 2 / 2010 Välikoe / 26.3 Ohjelmointi 2 / 2010 Välikoe / 26.3 Välikoe / 26.3 Vastaa neljään (4) tehtävään ja halutessa bonustehtäviin B1 ja/tai B2, (tuovat lisäpisteitä). Bonustehtävät saa tehdä vaikkei olisi tehnyt siihen tehtävään

Lisätiedot

LUKUJA, DATAA KÄSITTELEVÄT FUNKTIOT JA NIIDEN KÄYTTÖ LOGIIKKAOHJAUKSESSA

LUKUJA, DATAA KÄSITTELEVÄT FUNKTIOT JA NIIDEN KÄYTTÖ LOGIIKKAOHJAUKSESSA LUKUJA, DATAA KÄSITTELEVÄT FUNKTIOT JA NIIDEN KÄYTTÖ LOGIIKKAOHJAUKSESSA Tavallisimmin lukuja käsittelevien datasanojen tyypiksi kannattaa asettaa kokonaisluku 16 bitin INT, jonka vaihtelualueeksi tulee

Lisätiedot

1 Tehtävän kuvaus ja analysointi

1 Tehtävän kuvaus ja analysointi Olio-ohjelmoinnin harjoitustyön dokumentti Jyri Lehtonen (72039) Taneli Tuovinen (67160) 1 Tehtävän kuvaus ja analysointi 1.1 Tehtävänanto Tee luokka, jolla mallinnetaan sarjaan kytkettyjä kondensaattoreita.

Lisätiedot

Oliosuunnitteluesimerkki: Yrityksen palkanlaskentajärjestelmä

Oliosuunnitteluesimerkki: Yrityksen palkanlaskentajärjestelmä Oliosuunnitteluesimerkki: Yrityksen palkanlaskentajärjestelmä Matti Luukkainen 10.12.2009 Tässä esitetty esimerkki on mukaelma ja lyhennelmä Robert Martinin kirjasta Agile and Iterative Development löytyvästä

Lisätiedot

Tietokoneen rakenne: Harjoitustyö. Motorola MC68030 -prosessori

Tietokoneen rakenne: Harjoitustyö. Motorola MC68030 -prosessori kevät 2004 TP02S-D Tietokoneen rakenne: Harjoitustyö Motorola MC68030 -prosessori Työn valvojat: Seppo Haltsonen Pasi Lankinen RAPORTTI 13.5.2004 Sisällysluettelo sivu Tiivistelmä... 1 Lohkokaavio... 2

Lisätiedot

Ohjelmoinnin perusteet Y Python

Ohjelmoinnin perusteet Y Python Ohjelmoinnin perusteet Y Python T-106.1208 15.3.2010 T-106.1208 Ohjelmoinnin perusteet Y 15.3.2010 1 / 56 Tiedostoista: tietojen tallentaminen ohjelman suorituskertojen välillä Monissa sovelluksissa ohjelman

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

Ohjelmoinnin perusteet Y Python

Ohjelmoinnin perusteet Y Python Ohjelmoinnin perusteet Y Python T-106.1208 16.3.2009 T-106.1208 Ohjelmoinnin perusteet Y 16.3.2009 1 / 40 Kertausta: tiedostosta lukeminen Aluksi käsiteltävä tiedosto pitää avata: tiedostomuuttuja = open("teksti.txt","r")

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

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

Ohjelmistojen mallintamisen ja tietokantojen perusteiden yhteys

Ohjelmistojen mallintamisen ja tietokantojen perusteiden yhteys Ohjelmistojen mallintamisen ja tietokantojen perusteiden yhteys Tällä kurssilla on tutustuttu ohjelmistojen mallintamiseen oliomenetelmiä ja UML:ää käyttäen Samaan aikaan järjestetyllä kurssilla on käsitelty

Lisätiedot

Osio 2: Luennot 5-8 Muistinhallinta

Osio 2: Luennot 5-8 Muistinhallinta Käyttöjärjestelmät I Osio 2: Luennot 5-8 Muistinhallinta Tiina Niklander; kalvot Auvo Häkkinen Tietojenkäsittelytieteen laitos Helsinin yliopisto "!$#%#'&)(*+,(.-0/1#'-243 0# 5 Stallins, Luku 7 KJ-I S2004

Lisätiedot

Luento 7: VIRTUAALIMUISTIN SIVUTUS JA SEGMENTOINTI

Luento 7: VIRTUAALIMUISTIN SIVUTUS JA SEGMENTOINTI Käyttöjärjestelmät t I Luento 7: VIRTUAALIMUISTIN SIVUTUS JA SEGMENTOINTI Stallings, Luku 8.1 KJ-I S2005 / Tiina Niklander; kalvot Auvo Häkkinen 7-1 Sisält ltö Käänteinen sivutaulu Segmentointi Segmentointi

Lisätiedot

Kuva 8.7. u Muunnos prosessin sivunumerosta sivutilanumeroksi u Kussakin alkiossa: u Katenoimalla. u MMU:ssa; juuri äsken käytettyjä muunnoksia

Kuva 8.7. u Muunnos prosessin sivunumerosta sivutilanumeroksi u Kussakin alkiossa: u Katenoimalla. u MMU:ssa; juuri äsken käytettyjä muunnoksia Käyttöjärjestelmät t I Luento 7: VIRTUAALIMUISTIN SIVUTUS JA SEGMENTOINTI Stallings, Luku 8.1 Sisält ltö Käänteinen sivutaulu Segmentointi Segmentointi ja sivutus yhdistettynä Yhteiskäytöstä KJ-I S2005

Lisätiedot

815338A Ohjelmointikielten periaatteet 2015-2016. Harjoitus 5 Vastaukset

815338A Ohjelmointikielten periaatteet 2015-2016. Harjoitus 5 Vastaukset 815338A Ohjelmointikielten periaatteet 2015-2016. Harjoitus 5 Vastaukset Harjoituksen aiheena ovat aliohjelmat ja abstraktit tietotyypit sekä olio-ohjelmointi. Tehtävät tehdään C-, C++- ja Java-kielillä.

Lisätiedot

Ohjelmoinnin perusteet Y Python

Ohjelmoinnin perusteet Y Python Ohjelmoinnin perusteet Y Python T-106.1208 1.4.2009 T-106.1208 Ohjelmoinnin perusteet Y 1.4.2009 1 / 56 Tentti Ensimmäinen tenttimahdollisuus on pe 8.5. klo 13:00 17:00 päärakennuksessa. Tämän jälkeen

Lisätiedot

Sisällys. 15. Lohkot. Lohkot. Lohkot

Sisällys. 15. Lohkot. Lohkot. Lohkot Sisällys 15. Lohkot Tutustutaan lohkoihin. Muuttujien ja vakioiden näkyvyys sekä elinikä erityisesti operaation lohkossa. Nimikonfliktit. Muuttujat operaation alussa vai myöhemmin? 15.1 15.2 Lohkot Aaltosulkeet

Lisätiedot

ITKP102 Ohjelmointi 1 (6 op)

ITKP102 Ohjelmointi 1 (6 op) ITKP102 Ohjelmointi 1 (6 op) Tentaattori: Antti-Jussi Lakanen 22. huhtikuuta 2016 Vastaa kaikkiin tehtäviin. Tee jokainen tehtävä erilliselle konseptiarkille! Kirjoittamasi luokat, funktiot ja aliohjelmat

Lisätiedot

ltö Luento 6: VIRTUAALIMUISTI Luento 7: Segmentointi Segmentointi ja sivutus yhdistettynä Yhteiskäytöstä Suoritus virtuaalimuistissa

ltö Luento 6: VIRTUAALIMUISTI Luento 7: Segmentointi Segmentointi ja sivutus yhdistettynä Yhteiskäytöstä Suoritus virtuaalimuistissa Käyttöjärjestelmät t I Luento 6: VIRTUAALIMUISTI Stallings, Luku 8.1 Sisält ltö Ohjelman suoritus virtuaalimuistissa Sivutus Osoitemuunnospuskuri TLB Lisää sivutauluista Luento 7: Segmentointi Segmentointi

Lisätiedot

Ongelma(t): Jotta tietokone olisi mahdollisimman yleiskäyttöinen ja suorituskykyinen, niin miten tietokoneen resurssit tulisi tarjota ohjelmoijalle,

Ongelma(t): Jotta tietokone olisi mahdollisimman yleiskäyttöinen ja suorituskykyinen, niin miten tietokoneen resurssit tulisi tarjota ohjelmoijalle, Ongelma(t): Jotta tietokone olisi mahdollisimman yleiskäyttöinen ja suorituskykyinen, niin miten tietokoneen resurssit tulisi tarjota ohjelmoijalle, sovellusohjelmille ja käyttäjille? 2012-2013 Lasse Lensu

Lisätiedot

4. Lausekielinen ohjelmointi 4.1

4. Lausekielinen ohjelmointi 4.1 4. Lausekielinen ohjelmointi 4.1 Sisällys Konekieli, symbolinen konekieli ja lausekieli. Lausekielestä konekieleksi: - Lähdekoodi, tekstitiedosto ja tekstieditorit. - Kääntäminen ja tulkinta. - Kääntäminen,

Lisätiedot

Esimerkkiprojekti. Mallivastauksen löydät Wroxin www-sivuilta. Kenttä Tyyppi Max.pituus Rajoitukset/Kommentit

Esimerkkiprojekti. Mallivastauksen löydät Wroxin www-sivuilta. Kenttä Tyyppi Max.pituus Rajoitukset/Kommentit Liite E - Esimerkkiprojekti E Esimerkkiprojekti Olet lukenut koko kirjan. Olet sulattanut kaiken tekstin, Nyt on aika soveltaa oppimiasi uusia asioita pienen, mutta täydellisesti muotoiltuun, projektiin.

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

Dynaaminen muisti Rakenteiset tietotyypit

Dynaaminen muisti Rakenteiset tietotyypit C! Dynaaminen muisti Rakenteiset tietotyypit 1.3.2016 Agenda Kertausta Dynaaminen muisti Valgrind-perusteet ja esimerkkejä Yhteenveto tietorakenteista Vilkaisu 3. kierroksen tehtäviin Esim: miten linkitetty

Lisätiedot

Ohjelmiston testaus ja laatu. Ohjelmistotekniikka elinkaarimallit

Ohjelmiston testaus ja laatu. Ohjelmistotekniikka elinkaarimallit Ohjelmiston testaus ja laatu Ohjelmistotekniikka elinkaarimallit Vesiputousmalli - 1 Esitutkimus Määrittely mikä on ongelma, onko valmista ratkaisua, kustannukset, reunaehdot millainen järjestelmä täyttää

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

Luento 6: VIRTUAALIMUISTI

Luento 6: VIRTUAALIMUISTI Käyttöjärjestelmät t I Luento 6: VIRTUAALIMUISTI Stallings, Luku 8.1 KJ-I S2005 / Tiina Niklander; kalvot Auvo Häkkinen 6-1 Sisält ltö Ohjelman suoritus virtuaalimuistissa Sivutus Osoitemuunnospuskuri

Lisätiedot

etunimi, sukunimi ja opiskelijanumero ja näillä

etunimi, sukunimi ja opiskelijanumero ja näillä Sisällys 1. Algoritmi Algoritmin määritelmä. Aiheen pariin johdatteleva esimerkki. ja operaatiot (sijoitus, aritmetiikka ja vertailu). Algoritmista ohjelmaksi. 1.1 1.2 Algoritmin määritelmä Ohjelmointi

Lisätiedot

811120P Diskreetit rakenteet

811120P Diskreetit rakenteet 811120P Diskreetit rakenteet 2016-2017 1. Algoritmeista 1.1 Algoritmin käsite Algoritmi keskeinen laskennassa Määrittelee prosessin, joka suorittaa annetun tehtävän Esimerkiksi Nimien järjestäminen aakkosjärjestykseen

Lisätiedot

Tietorakenteet ja algoritmit syksy Laskuharjoitus 1

Tietorakenteet ja algoritmit syksy Laskuharjoitus 1 Tietorakenteet ja algoritmit syksy 2012 Laskuharjoitus 1 1. Tietojenkäsittelijä voi ajatella logaritmia usein seuraavasti: a-kantainen logaritmi log a n kertoo, kuinka monta kertaa luku n pitää jakaa a:lla,

Lisätiedot

Ohjelmointi 2. Jussi Pohjolainen. TAMK» Tieto- ja viestintäteknologia , Jussi Pohjolainen TAMPEREEN AMMATTIKORKEAKOULU

Ohjelmointi 2. Jussi Pohjolainen. TAMK» Tieto- ja viestintäteknologia , Jussi Pohjolainen TAMPEREEN AMMATTIKORKEAKOULU Ohjelmointi 2 Jussi Pohjolainen TAMK» Tieto- ja viestintäteknologia Tietotyypeistä C++ - kielessä useita tietotyyppejä Kirjaimet: char, wchar_t Kokonaisluvut: short, int, long Liukuluvut: float, double

Lisätiedot

ATK tähtitieteessä. Osa 3 - IDL proseduurit ja rakenteet. 18. syyskuuta 2014

ATK tähtitieteessä. Osa 3 - IDL proseduurit ja rakenteet. 18. syyskuuta 2014 18. syyskuuta 2014 IDL - proseduurit Viimeksi käsiteltiin IDL:n interaktiivista käyttöä, mutta tämä on hyvin kömpelöä monimutkaisempia asioita tehtäessä. IDL:llä on mahdollista tehdä ns. proseduuri-tiedostoja,

Lisätiedot

14. Luento: Kohti hajautettuja sulautettuja järjestelmiä. Tommi Mikkonen,

14. Luento: Kohti hajautettuja sulautettuja järjestelmiä. Tommi Mikkonen, 14. Luento: Kohti hajautettuja sulautettuja järjestelmiä Tommi Mikkonen, tommi.mikkonen@tut.fi Agenda Johdanto Hajautettujen järjestelmien väyliä LON CAN Pienen laitteen sisäinen hajautus OpenCL Network

Lisätiedot

Luokassa määriteltävät jäsenet ovat pääasiassa tietojäseniä tai aliohjelmajäseniä. Luokan määrittelyyn liittyvät varatut sanat:

Luokassa määriteltävät jäsenet ovat pääasiassa tietojäseniä tai aliohjelmajäseniä. Luokan määrittelyyn liittyvät varatut sanat: 1. Luokan jäsenet Luokassa määriteltävät jäsenet ovat pääasiassa tietojäseniä tai aliohjelmajäseniä. Luokan määrittelyyn liittyvät varatut sanat: class luokan_nimi tyypit: enum, struct, class, typedef

Lisätiedot

815338A Ohjelmointikielten periaatteet Harjoitus 2 vastaukset

815338A Ohjelmointikielten periaatteet Harjoitus 2 vastaukset 815338A Ohjelmointikielten periaatteet 2015-2016. Harjoitus 2 vastaukset Harjoituksen aiheena on BNF-merkinnän käyttö ja yhteys rekursiivisesti etenevään jäsentäjään. Tehtävä 1. Mitkä ilmaukset seuraava

Lisätiedot

Ohjelmointi 1 Taulukot ja merkkijonot

Ohjelmointi 1 Taulukot ja merkkijonot Ohjelmointi 1 Taulukot ja merkkijonot Jussi Pohjolainen TAMK Tieto- ja viestintäteknologia Johdanto taulukkoon Jos ohjelmassa käytössä ainoastaan perinteisiä (yksinkertaisia) muuttujia, ohjelmien teko

Lisätiedot

1. Algoritmi 1.1 Sisällys Algoritmin määritelmä. Aiheen pariin johdatteleva esimerkki. Muuttujat ja operaatiot (sijoitus, aritmetiikka ja vertailu). Algoritmista ohjelmaksi. 1.2 Algoritmin määritelmä Ohjelmointi

Lisätiedot

Tietorakenteet ja algoritmit

Tietorakenteet ja algoritmit Tietorakenteet ja algoritmit Kurssin sisältö pääpiirteittäin Tarvittavat pohjatiedot Avainsanat Abstraktio Esimerkkiohjelman tehtäväkuvaus Abstraktion käyttö tehtävässä Abstrakti tietotyyppi Hyötyjä ADT:n

Lisätiedot

Rajapinnat ja olioiden välittäminen

Rajapinnat ja olioiden välittäminen Rajapinnat ja olioiden välittäminen Moduulit/oliot kutsuvat toisiaan kapseloitujen rajapintojen läpi Kutsuissa välitetään usein olioita paikasta toiseen Jos olion omistus (= tuhoamisvastuu) säilyy koko

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

Monipuolinen esimerkki

Monipuolinen esimerkki Monipuolinen esimerkki Lopuksi monipuolinen esimerkki, jossa ohjelmisto koostuu pääohjelmasta ja kahdesta aliohjelmasta, joista toinen on proseduuri ja toinen funktio. Funktio Sqrt(int n): int Sqrt(int

Lisätiedot

T740103 Olio-ohjelmointi Osa 5: Periytyminen ja polymorfismi Jukka Jauhiainen OAMK Tekniikan yksikkö 2010

T740103 Olio-ohjelmointi Osa 5: Periytyminen ja polymorfismi Jukka Jauhiainen OAMK Tekniikan yksikkö 2010 12. Periytyminen Johdantoa Käytännössä vähänkään laajemmissa ohjelmissa joudutaan laatimaan useita luokkia, joiden pitäisi pystyä välittämään tietoa toisilleen. Ohjelmien ylläpidon kannalta olisi lisäksi

Lisätiedot

Kuva 1. Jokaisen tavallisen kuvan tasotyökalussa näkyy vain yksi taso, tässä nimellä tausta.

Kuva 1. Jokaisen tavallisen kuvan tasotyökalussa näkyy vain yksi taso, tässä nimellä tausta. Gimp alkeet XII 9 luokan ATK-työt/HaJa Sivu 1 / 6 GIMP:in tasotyökalu Lue ensin nämä ohjeet! Harjoitus lopussa! GIMP:in tasotyökalu on nimensä mukaisesti työkalu, jolla hallitaan tasoja, niiden läpinäkyvyyttä,

Lisätiedot

TKHJ:ssä on yleensä komento create index, jolla taululle voidaan luoda hakemisto

TKHJ:ssä on yleensä komento create index, jolla taululle voidaan luoda hakemisto Indeksin luonti ja hävitys TKHJ:ssä on yleensä komento create index, jolla taululle voidaan luoda hakemisto Komentoa ei ole standardoitu ja niinpä sen muoto vaihtelee järjestelmäkohtaisesti Indeksi voidaan

Lisätiedot

Sisällys. 1. Omat operaatiot. Yleistä operaatioista. Yleistä operaatioista

Sisällys. 1. Omat operaatiot. Yleistä operaatioista. Yleistä operaatioista Sisällys 1. Omat operaatiot Yleistä operaatioista. Mihin operaatioita tarvitaan? Oman operaation määrittely. Yleisesti, nimeäminen ja hyvä ohjelmointitapa, määreet, parametrit ja näkyvyys. HelloWorld-ohjelma

Lisätiedot

Muuttujien roolit Kiintoarvo cin >> r;

Muuttujien roolit Kiintoarvo cin >> r; Muuttujien roolit Muuttujilla on ohjelmissa eräitä tyypillisiä käyttötapoja, joita kutsutaan muuttujien rooleiksi. Esimerkiksi muuttuja, jonka arvoa ei muuteta enää kertaakaan muuttujan alustamisen jälkeen,

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

Automaattinen muistinhallinta

Automaattinen muistinhallinta Automaattinen muistinhallinta Timo Tapanainen (ttapanai@cs.helsinki.fi) Helsinki 12. huhtikuuta 2004 HELSINGIN YLIOPISTO Tietojenkäsittelytieteen laitos Sisältö 1 Johdanto...1 2 Automaattinen muistinhallinta...1

Lisätiedot

1. Omat operaatiot 1.1

1. Omat operaatiot 1.1 1. Omat operaatiot 1.1 Sisällys Yleistä operaatioista. Mihin operaatioita tarvitaan? Oman operaation määrittely. Yleisesti, nimeäminen ja hyvä ohjelmointitapa, määreet, parametrit ja näkyvyys. HelloWorld-ohjelma

Lisätiedot

D B. Tiedostojen käsittely

D B. Tiedostojen käsittely Tietokantojen tietoja säilytetään yleensä apumuistissa, lähinnä levymuisteissa Apumuistiin tallentamisen merkittäviä etuja keskusmuistiin nähden ovat tiedon säilyvyys (virtakatkon yli) säilytyskapasiteetin

Lisätiedot

815338A Ohjelmointikielten periaatteet Harjoitus 6 Vastaukset

815338A Ohjelmointikielten periaatteet Harjoitus 6 Vastaukset 815338A Ohjelmointikielten periaatteet 2015-2016. Harjoitus 6 Vastaukset Harjoituksen aiheena on funktionaalinen ohjelmointi Scheme- ja Haskell-kielillä. Voit suorittaa ohjelmat osoitteessa https://ideone.com/

Lisätiedot

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

Sisällys. 11. Javan toistorakenteet. Laskurimuuttujat. Yleistä Sisällys 11. Javan toistorakenteet Laskuri- ja lippumuuttujat.. Tyypillisiä ohjelmointivirheitä: Silmukan rajat asetettu kierroksen verran väärin. Ikuinen silmukka. Silmukoinnin lopettaminen break-lauseella.

Lisätiedot

Sisällys. 3. Muuttujat ja operaatiot. Muuttujat ja operaatiot. Muuttujat ja operaatiot

Sisällys. 3. Muuttujat ja operaatiot. Muuttujat ja operaatiot. Muuttujat ja operaatiot 3. Muuttujat ja operaatiot Sisällys Muuttujat. Nimi ja arvo. Algoritmin tila. Muuttujan nimeäminen. Muuttujan tyyppi. Muuttuja ja tietokone. Operaattorit. Operandit. Arvon sijoitus muuttujaan. Aritmeetiikka.

Lisätiedot

Web-palvelu voidaan ajatella jaettavaksi kahteen erilliseen kokonaisuuteen: itse palvelun toiminnallisuuden toteuttava osa ja osa, joka mahdollistaa k

Web-palvelu voidaan ajatella jaettavaksi kahteen erilliseen kokonaisuuteen: itse palvelun toiminnallisuuden toteuttava osa ja osa, joka mahdollistaa k 1 Web-palvelu voidaan ajatella jaettavaksi kahteen erilliseen kokonaisuuteen: itse palvelun toiminnallisuuden toteuttava osa ja osa, joka mahdollistaa ko. toiminnallisuuden hyödyntämisen Web-palveluna.

Lisätiedot

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

Ohjelmointitaito (ict1td002, 12 op) Kevät Java-ohjelmoinnin alkeita. Tietokoneohjelma. Raine Kauppinen Ohjelmointitaito (ict1td002, 12 op) Kevät 2009 Raine Kauppinen raine.kauppinen@haaga-helia.fi 1. Java-ohjelmoinnin alkeita Tietokoneohjelma Java-kieli ja Eclipse-kehitysympäristö Java-ohjelma ja luokka

Lisätiedot

Ohjelmoinnin perusteet Y Python

Ohjelmoinnin perusteet Y Python Ohjelmoinnin perusteet Y Python T-106.1208 16.2.2010 T-106.1208 Ohjelmoinnin perusteet Y 16.2.2010 1 / 41 Kännykkäpalautetteen antajia kaivataan edelleen! Ilmoittaudu mukaan lähettämällä ilmainen tekstiviesti

Lisätiedot

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

Sisällys. 12. Javan toistorakenteet. Yleistä. Laskurimuuttujat Sisällys 12. Javan toistorakenteet Ylstä toistorakentsta. Laskurimuuttujat. While-, do-while- ja for-lauseet. Laskuri- ja lippumuuttujat. Tyypillisiä ohjelmointivirhtä. Silmukan rajat asetettu kierroksen

Lisätiedot

Yksikkötestaus. import org.junit.test; public class LaskinTest public void testlaskimenluonti() { Laskin laskin = new Laskin(); } }

Yksikkötestaus. import org.junit.test; public class LaskinTest public void testlaskimenluonti() { Laskin laskin = new Laskin(); } } Yksikkötestauksella tarkoitetaan lähdekoodiin kuuluvien yksittäisten osien testaamista. Termi yksikkö viittaa ohjelman pienimpiin mahdollisiin testattaviin toiminnallisuuksiin, kuten olion tarjoamiin metodeihin.

Lisätiedot

Java-kielen perusteet

Java-kielen perusteet Java-kielen perusteet Tunnus, varattu sana, kommentti Muuttuja, alkeistietotyyppi, merkkijono, Vakio Tiedon merkkipohjainen tulostaminen Ohjelmointi (ict1tx006) Tunnus (5.3) Javan tunnus Java-kirjain Java-numero

Lisätiedot

24.9.2015. Työasema- ja palvelinarkkitehtuurit (IC130301) Apumuistit. Kiintolevyt. 5 opintopistettä. Petri Nuutinen

24.9.2015. Työasema- ja palvelinarkkitehtuurit (IC130301) Apumuistit. Kiintolevyt. 5 opintopistettä. Petri Nuutinen Työasema- ja palvelinarkkitehtuurit (IC130301) 5 opintopistettä Petri Nuutinen 5 opintopistettä Petri Nuutinen Apumuistit Tarvitaan ohjelmien ja dokumenttien tallentamiseen, kiintolevyjen varmuuskopiointiin,

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

12. Näppäimistöltä lukeminen 12.1

12. Näppäimistöltä lukeminen 12.1 12. Näppäimistöltä lukeminen 12.1 Sisällys Arvojen lukeminen näppäimistöltä yleisesti. Arvojen lukeminen näppäimistöltä Java-kielessä. In-luokka. Luetun arvon tarkistaminen. Tietovirrat ja ohjausmerkit.

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

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

Alkuarvot ja tyyppimuunnokset (1/5) Alkuarvot ja tyyppimuunnokset (2/5) Alkuarvot ja tyyppimuunnokset (3/5) Alkuarvot ja tyyppimuunnokset (1/5) Aiemmin olemme jo antaneet muuttujille alkuarvoja, esimerkiksi: int luku = 123; Alkuarvon on oltava muuttujan tietotyypin mukainen, esimerkiksi int-muuttujilla kokonaisluku,

Lisätiedot

Sähköpostilla tulevien hinnastojen tallentaminen

Sähköpostilla tulevien hinnastojen tallentaminen Sivu 1/5 Sähköpostilla tulevien hinnastojen tallentaminen Yleistä Sähköposti on nykyään erittäin suosittu tapa viestiä sähköisesti. Tämä johtuu useistakin hyvistä puolista. Esim. sama viesti voidaan lähettää

Lisätiedot

C++11 lambdat: [](){} Matti Rintala

C++11 lambdat: [](){} Matti Rintala C++11 lambdat: [](){} Matti Rintala bool(*)(int) Tarve Tarve välittää kirjastolle/funktiolle toiminnallisuutta Callback-funktiot Virhekäsittely Käyttöliittymät Geneeristen kirjastojen räätälöinti STL:n

Lisätiedot

TIEP114 Tietokoneen rakenne ja arkkitehtuuri, 3 op. FT Ari Viinikainen

TIEP114 Tietokoneen rakenne ja arkkitehtuuri, 3 op. FT Ari Viinikainen TIEP114 Tietokoneen rakenne ja arkkitehtuuri, 3 op FT Ari Viinikainen Tietokoneen rakenne Keskusyksikkö, CPU Keskusmuisti Aritmeettislooginen yksikkö I/O-laitteet Kontrolliyksikkö Tyypillinen Von Neumann

Lisätiedot

Älykännykät ovat pieneen tilaan paketoituja, mutta suuret ominaisuudet omaavia tietokoneita.

Älykännykät ovat pieneen tilaan paketoituja, mutta suuret ominaisuudet omaavia tietokoneita. Mikä on tietokone PUNOMO NETWORKS OY 22.7.2016 pva, piirroskuvat J. Mansikkaviita Henkilökohtaisesti olen aina valmis oppimaan, vaikka en välitäkään tulla opetetuksi. - Winston Churchill Tietokone on elektroninen

Lisätiedot

Ehto- ja toistolauseet

Ehto- ja toistolauseet Ehto- ja toistolauseet 1 Ehto- ja toistolauseet Uutena asiana opetellaan ohjelmointilauseet / rakenteet, jotka mahdollistavat: Päätösten tekemisen ohjelman suorituksen aikana (esim. kyllä/ei) Samoja lauseiden

Lisätiedot

16. Ohjelmoinnin tekniikkaa 16.1

16. Ohjelmoinnin tekniikkaa 16.1 16. Ohjelmoinnin tekniikkaa 16.1 Sisällys For-lause lyhemmin. Vaihtoehtoisia merkintöjä aritmeettisille lauseille. Useiden muuttujien esittely ja alustaminen yhdellä lauseella. If-else-lause vaihtoehtoisesti

Lisätiedot

7/20: Paketti kasassa ensimmäistä kertaa

7/20: Paketti kasassa ensimmäistä kertaa Ohjelmointi 1 / syksy 2007 7/20: Paketti kasassa ensimmäistä kertaa Paavo Nieminen nieminen@jyu.fi Tietotekniikan laitos Informaatioteknologian tiedekunta Jyväskylän yliopisto Ohjelmointi 1 / syksy 2007

Lisätiedot

Käyttöjärjestelmät: Virtuaalimuisti

Käyttöjärjestelmät: Virtuaalimuisti Käyttöjärjestelmät: Virtuaalimuisti Teemu Saarelainen Tietotekniikka teemu.saarelainen@kyamk.fi Lähteet Stallings, W. Operating Systems Haikala, Järvinen, Käyttöjärjestelmät Eri Web-lähteet Muistinhallinta

Lisätiedot

Johdatus Ohjelmointiin

Johdatus Ohjelmointiin Johdatus Ohjelmointiin Syksy 2006 Viikko 2 13.9. - 14.9. Tällä viikolla käsiteltävät asiat Peruskäsitteitä Kiintoarvot Tiedon tulostus Yksinkertaiset laskutoimitukset Muuttujat Tiedon syöttäminen Hyvin

Lisätiedot

Ohjelmoinnin perusteet Y Python

Ohjelmoinnin perusteet Y Python Ohjelmoinnin perusteet Y Python T-106.1208 17.2.2010 T-106.1208 Ohjelmoinnin perusteet Y 17.2.2010 1 / 41 Sanakirja Monissa sovelluksissa on tallennettava rakenteeseen avain arvo-pareja. Myöhemmin rakenteesta

Lisätiedot