ohjelmointitekniikka

C# - kieli
• 1. ohjelman selitystä
– Muutamien ohjelman yksityiskohtien läpikäyntiä
class MainClass
{
public static void Main(string[] args)
{
Console.WriteLine("Hei maailma!");
}
}
– jokainen C#-ohjelma on aina luokka (class)
– luokassa voidaan määritellä metodeita
• jokaisessa itsenäisessä C#-ohjelmassa on main-metodi
• main-metodi on julkinen (public), luokan oma (static) ja arvoa palauttamaton
(void)
• main-metodilla on merkkijonotyyppinen (String) parametri args
– lause ”Console.WriteLine...” tulostaa kuvaruudulle tekstin ”Hei maailma!”
Ohjelman muoto
• Ohjelman luettavuus
– Kirjoitetaan jokainen lause omalle riville
• Useampiakin voit kirjoittaa mutta se haittaa luettavuutta
– Käytä sisennyksiä
– Kirjoita kommentteja
• Kommentit
– kommentti on vapaamuotoinen selitysteksti, joka ei vaikuta ohjelman
suorittamiseen
– ilmaus ”/*” aloittaa kommentin ja ”*/” lopettaa kommentin
– ilmaus ”//” kertoo, että tokarivi on kommenttia
// Tämä on kommenttirivi
/* Tämä on kommenttitekstiä,
ja se jatkuu usealle
riville.
*/
1
Kommentit
• Jokaisen ohjelman ekaun kannattaa kirjoittaa kommentit
• Esim.
/*
* Ohjelma : Tervehdys
* tekijä: Juha Stenfors
* valmis: 28.8.2005
* muutos: 10.9.2005 / Tulostustekstit muutettu
* muutos: 18.9.2005 / lisätty kommentteja
*/
• Tee jokaiselle sellaiselle riville kommentti, joita haluat selventää
• Auttaa jatkossa, kun tutkit ohjelmaa ja sen logiikkaa
Tietotyypit
• (tieto)tyyppi liittyy moneen asiaan ohjelmointikielessä:
–
–
–
–
muuttujalla on aina tyyppi
arvolla on aina tyyppi
parametrilla on aina tyyppi (käsitellään myöhemmin)
metodin paluuarvolla on aina tyyppi (käsitellään myöhemmin)
• C#-kieli on ns. vahvasti tyypitetty kieli
– sijoitusoperaatioissa ja vertailuissa vaaditaan aina yhteensopivuus
arvojen kesken
2
Tietotyypit
Tietotyyppi
Tunnus
Muisti
.Net tyyppi
Arvoalue
lyhyt kokonaisluku
kokonaisluku
pitkä kokonaisluku
yksinkert. tark. liukuluku
kaksoistarkkuden liukuluku
pitkä liukuluku
totuusarvo
tavu
merkki
short
int
long
float
double
decimal
bool
byte
char
2 tavua
4 tavua
8 tavua
4 tavua
8 tavua
16 tavua
1 tavu
1 tavu
8 tavua
Int16
Int32
Int64
Single
Double
Decimal
Boolean
Byte
Char
-32768 – 32767
-2147483648 – 2147483647
-9223372036 854 775 808 - 9223372036 854 775 807
-3.4028235E38 – 3.402835E38
-1.79769313486231E308 - 1.79769313486231E3080
enintään +/- 79228 * 10 ^24
True tai False
0 - 255
Mikä tahansa Unicode – symboli välillä 0 – 65535
* Huom! Desimaalierotin ohjelmassa on piste!
Tietotyypit
• Merkki (char)
– jokaista merkkiä vastaa tietty numeroarvo
– C#:ssa merkit on koodattu ns. Unicode-merkkijärjestelmällä
• sisältää maailman useimpien kirjoitusjärjestelmien kirjain- ja
numeromerkit
• vakioarvot esitetään heittomerkkien sisällä: ’c’, ’C’, ’6’, ’;’
– erikoismerkkejä:
’\t’
tabulaattori
’\\’
kenoviiva
’\n’
rivinvaihto
’\”’
lainausmerkki
’\’’
heittomerkki
3
Tietotyypit
• Merkkijono (string)
–
–
–
–
merkkijono alkaa ja tokau lainausmerkkeihin
saa sisältää mitä tahansa merkkejä
voidaan yhdistellä katenaatio-operaattorin (+) avulla
esimerkkejä:
”Auto”
”Auto on kulkuväline”
”Auto\n on\n kulkuväline”
( \n = rivinvaihtomerkki )
”Auto” + ” ” + ”on” + ” ” + ”kulkuväline”
Tietotyypit
• Totuusarvo (boolean)
– mahdolliset arvot: true (= tosi) ja false (= epätosi)
– loogisen lausekkeen arvo on aina totuusarvo
– esimerkkejä: true, false, x > 0, (x ==5) && (y != 3)
4
Muuttujat
• muuttuja määritellään ennen käyttöä muodossa
tyyppi muuttujan_nimi;
• muuttujan nimi alkaa aina kirjaimella
• pienet ja isot kirjaimet ymmärretään eri merkeiksi: esim. Kissa ja kissa ovat
eri nimiä
• esimerkkejä:
int lkm, kpl;
// lkm ja kpl ovat kokonaislukutyyppisiä
double pinta_ala;
// pinta_ala on desimaalilukutyyppinen
boolean totuus;
// totuus on totuusarvotyyppinen
string nimi;
// nimi on merkkijonoarvoinen
• useasti on tapana nimeämissä käyttää muuttujan nimessä 1. kirjaimena
tyypin ensimmäistä kirjainta tai tyypin kolmea ensimmäistä kirjainta
• int iLuku;
• string sNimi;
Muuttujat
• nimeämisessä suositaan seuraavaa tapaa:
–
–
–
–
–
nimen 1. kirjain on pieni
jokainen seuraava sana nimessä alkaa isolla kirjaimella
kaikki muut kirjaimet ovat pieniä
skandeja (ääkkösiä) ei pitäisi käyttää
nimi ei saa olla C#-kielen varattu sana
• esimerkkejä muuttujanimistä
nelionPintaAla
autonRenkaanIlmanPaine
keski_ika
iYhteensa
sKatuOsoite
5
Sijoituslauseita
• sijoitusoperaattori on yhtäsuuruusmerkki (=)
muuttuja = lauseke;
• huom. älä sekoita sijoitusoperaattoria yhtäsuuruusoperaattoriin, joka on
kaksi yhtäsuuruusmerkkiä (==)
• muuttujan ja lausekkeen tulee olla sijoitusyhteensopivia (eli lähes aina
samaa tyyppiä)
• esimerkkejä:
int luku;
double pinta_ala;
boolean totuus;
string postiosoite;
luku = 1237;
pinta_ala = 9887.120;
totuus = true;
postiosoite = ”Tiedepuisto 3”;
Sijoituslauseita
• muuttujille voidaan antaa ekaarvo jo määrittelyssä:
int luku = 1237;
double pinta_ala = 9887.120;
boolean totuus = true;
string postiosoite = ”Tiedepuisto 3”;
• algoritmeissa muuttujan uusi arvo lasketaan usein vanhasta
arvosta
luku = luku + 10;
pinta_ala = pinta_ala - 3;
– näissä on mahdollista käyttää erityisiä sijoitusoperaattoreita
luku += 10;
pinta_ala -= 3;
– usein muuttujan arvoa kasvatetaan/vähennetään yhdellä
luku = luku + 1;
on sama kuin
++luku; luku++;
pinta_ala = pinta_ala - 1; on sama kuin pinta_ala--;
6
Laskutoimitukset
•
•
•
•
•
•
yhteenlasku (+)
vähennyslasku (-)
jakolasku (/)
kertolasku (*)
jäännösjako (%)
jakolaskussa jaettavan ja jakajan ollessa kokonaisluku tuloskin on aina
kokonaisluku (= ns. kokonaisjako)
• jäännösjako on kokonaislukujen jakolaskun jakojäännös
• esimerkki
int
luku = 5, kpl = 100;
double leveys = 2.2, korkeus = 5;
kpl = luku / 2;
luku = 22 % 3;
leveys = korkeus / 2;
// arvo on 2 (eikä 2.5)!
// arvo on 1
// arvo on 2.5
Katenointi
• katenointi tarkoittaa merkkijonojen liittämistä toisiinsa
• katenointioperaattori on +-merkki
• jos lauseke on muotoa merkkijono + numeerinen arvo,
yhteenlasku tulkitaan katenaatioksi
• esimerkki
string eka = ”luokka”, toka = ”huone”, yht;
yht
yht
yht
yht
=
=
=
=
eka + toka;
// arvo on ”luokkahuone”
toka + eka;
// arvo on ”huoneluokka”
eka + ” ” + toka; // arvo on ”huone luokka”
toka + eka + ”an ” + toka;
// arvo on ”huoneluokkaan huone”
yht = toka + 210;
// arvo on ”huone210”
7
Kirjoittaminen ja lukeminen
• näytölle tulostetaan valmiiksi määritellyn nimiavaruuden System
avulla (using System;)
Console.WriteLine(”Hei maailma!”); // tulostaa tekstin
Console.Write(”Hei maailma!”); // tulostaa tekstin
ja rivinvaihdon
• tulostettava on aina vain yksi arvo
– jos halutaan tulostaa esim. tekstiä ja lukuarvoja, niistä on tehtävä
yksi merkkijono
string sNimi = ”Juha”;
Console.WriteLine(”Moi ” + sNimi + ”!”);
– tämä tulostaisi (näytölle):
Moi Juha!
Kirjoittaminen ja lukeminen
Console.WriteLine(”Jos haluat tulostaa \”lainausmerkit\”!”);
Console.WriteLine(”Tyhjiä rivejä kaksi:\n\n”);
Console.WriteLine(”\tYksi tabulointi”);
Console.WriteLine(”\t\t\tTabuloitu kolme kertaa”);
Console.WriteLine(”C:\\>”);
Console.WriteLine(”\\\\alfa\\yleiset”);
Jos haluat tulostaa ”lainausmerkit”!
Tyhjiä rivejä kaksi:
Yksi tabulointi
Tabuloitu kolme kertaa
C:\>
\\alfa\yleiset
8
Loogiset lausekkeet
• lähtökohtana bool - tietotyyppi
• arvot true (tosi) ja false (epätosi)
• looginen lauseke (eli totuusarvoinen lauseke) muodostuu
– ehtolausekkeista ja niitä yhdistävistä loogisista operaattoreista
• ehtolausekkeen yleinen muoto:
arvo vertailuoperaattori arvo
muuttuja,
>
>=
muuttuja,
vakio,
<
<=
vakio,
lauseke
== !=
lauseke
Loogiset lausekkeet
• esimerkkejä:
luku >= 0
iMaara == 100
arvo < (luku * 2.4)
– älä sekoita yhtäsuuruusoperaattoria (==) ja sijoitusoperaattoria (=):
luku == 10
luku = 10
// ”onko luku:n arvo 10?”
// ”luku saa arvokseen 10”
• merkkijonoja voit verrata samalla tavalla kuten lukuja
sNimi == ”Juha”
// ”onko sNimi:n arvo Juha?”
• ehtolausekkeita voidaan yhdistellä loogisin operaattorein:
&&
ja (and)
||
tai (or)
^
poissulkeva tai (xor)
!
ei (not)
9
Loogiset lausekkeet
• esimerkki
int iLuku = 2;
double dPi = 3.14;
bool b1, b2, b3;
b1 = (i == 2) && (dPi > 10.0);
b2 = (i == 2) && (dPi < 10.0);
// b1 saa arvon false
// b2 saa arvon true
b1 = (i == 2) || (dPi > 10.0);
b2 = (i != 2) || (dPi > 10.0);
// b1 saa arvon true
// b2 saa arvon false
b3 = !b1 || !!b2;
// b3 saa arvon false
Tehtävä
Alustetaan seuraavat muuttujat:
int a, b, c;
short x, y, z;
Kirjoita looginen lauseke seuraaviin tapauksiin:
1. a on parillinen
2. b on nollaa suurempi, ja b on pienempi kuin 120
3. b on suurempi kuin c, ja b on pienempi kuin a
4. -11.2 < x < -2.42
5. joko a on 4 ja b on negatiivinen tai y on suurempi kuin z:n ja x:n erotus
6. z < -1.7 tai z > 23.1, c:n ja a:n summa on parillinen ja b ei ole 543
7. joko a on 7 tai b on c, mutta eivät molemmat
8. joko x on positiivinen tai y on negatiivinen, mutta eivät molemmat
10
Ratkaisu
1.
2.
3.
4.
5.
6.
7.
8.
a % 2 == 0
(b > 0) && (b < 120)
(b > c) && (b < a)
(x >-11.2) && (x < -2.42)
(a == 4) && (b < 0) || (y > z – x)
((z < -1.7) || (z > 23.1)) && ((a + c) % 2 == 0) && (b != 543)
(a == 7) ^ (b == c)
(x > 0) ^ (y < 0)
if-lause
• ehdollisella lauseella eli if-lauseella on kaksi muotoa:
if (ehtolauseke)
lause;
jos ehto on tosi, niin lause
suoritetaan
eli
ehtolauseke ehdollistaa
lauseen suorituksen
if (ehtolauseke)
lause1;
else
lause2;
jos ehto on tosi, niin
suoritetaan lause1, muuten
suoritetaan lause2
eli
lauseet lause1 ja lause2
ovat vaihtoehtoisia
11
if-lause
double dLuku1, dLuku2;
Console.Write(”Anna luku1: ”);
dLuku1 = Convert.ToDouble(Console.ReadLine());
Console.Write(”Anna luku2: ”);
dLuku2 = Convert.ToDouble(Console.ReadLine());
if (dLuku1 < dLuku2){
Console.WriteLine(”Luku1 on pienempi.”);
}
else {
Console.WriteLine(”Luku2 on suurempi tai yhtäsuuri kuin luku1.”);
}
if-lause
• if-lauseessa voidaan ehdollistaa/vaihtoehtoistaa vain yksittäisiä lauseita
– jos valittava vaihtoehto muodostuu useammasta kuin yhdestä lauseesta
tulee käyttää koottua lausetta (= aaltosulkuparin sisällä olevat lauseet)
– kootun lauseen perässä EI ole koskaan puolipistettä!
if (ehtolauseke) {
lause;
...
lause;
}
if (ehtolauseke) {
lause;
...
lause;
}
else {
lause;
...
lause;
}
– huom. kootun lauseen sisällä määriteltyä muuttujaa ei voi käyttää
kootun lauseen ulkopuolella
12
switch-lause
• valintalausetta eli switch-lausetta käytetään silloin kun
valintavaihtoehtoja on useita
• valintalause on muotoa:
switch (lauseke) {
case vakio1:
lause1;
break;
case vakio2:
case vakio3:
lause2;
lause3;
break;
default:
lause4;
break;
}
switch-lause
int iKK, iPv;
Console.Write(”Anna kuukauden numero: ”);
iKK = Convert.ToInt32(Console.ReadLine());
switch (iKK) {
case 1: case 3: case 5: case 7: case 8: case 10: case 12:
iPv = 31;
break;
case 2:
iPv = 28;
break;
case 4: case 6: case 9: case 11:
iPv = 30;
break;
default:
iPv = 0;
}
Console.WriteLine(”Kuukaudessa ” + iKK + ” on ” + iPv + ” päivää.”);
13
while-lause
• while-lause on ns. alkuehtoinen toistolause
– toistokertojen määrä ei tarvitse olla etukäteen tiedossa
– voidaan käyttää myös lukumääräiselle toistolle (laskurimuuttujan
avulla)
• while-lauseen muoto:
while (ehto) {
lause;
...
lause;
}
Ehto on totuusarvoinen
lauseke ja sen arvo
tarkastetaan aina ennen
toistokerran suorittamista.
Kun ehto saa arvon
epätosi, siirrytään whilelausetta seuraavaan
lauseeseen.
(Koottua) lausetta
toistetaan niin kauan, kun
ehto on tosi.
while-lause
int iLuku, iSumma;
Console.WriteLine(”Yhteenlaskuohjelma, negatiivinen luku lopettaa.”);
iLuku = Convert.ToInt32(Console.ReadLine());
while (iLuku >= 0) {
iSumma = iSumma + iLuku;
Console.WriteLine(”Summa nyt: ” + iSumma);
iLuku = Convert.ToInt32(Console.ReadLine());
}
Console.WriteLine(”Loppu!”);
14
Tehtävä
• Ohjelman tulee tulostaa luvut 1, 2, 3 ja 4. Täytä puuttuvat kohdat:
int iLaskuri ;
iLaskuri = ______;
while (iLaskuri _____ 4 ) {
Console.WriteLine(iLaskuri);
iLaskuri = iLaskuri + _____;
}
Ratkaisu
• Ohjelman tulee tulostaa luvut 1, 2, 3 ja 4. Täytä puuttuvat kohdat:
int iLaskuri ;
iLaskuri = 1;
while (iLaskuri <= 4 ) {
Console.WriteLine(iLaskuri);
iLaskuri = iLaskuri + 1;
}
15
Tehtävä
• Ohjelman tulee tulostaa luvut 10 Î -10. Täytä puuttuvat kohdat:
int iLaskuri ;
iLaskuri = ______;
while (iLaskuri _____ ) {
Console.WriteLine(iLaskuri);
iLaskuri = iLaskuri _____;
}
Ratkaisu
• Ohjelman tulee tulostaa luvut -10 Î 10. Täytä puuttuvat kohdat:
int iLaskuri ;
iLaskuri = 10;
while (iLaskuri >= -10) {
Console.WriteLine(iLaskuri);
iLaskuri = iLaskuri - 1;
}
16
Tehtävä
• Mitä ao. koodi tekee?
double dLuku1 = 1, dLuku2 = 0, dLuku3 = 0;
while (dLuku1 != 0) {
Console.WriteLine("Anna luku: ");
dLuku1 = Convert.ToDouble(Console.ReadLine());
if (dLuku1 != 0) {
dLuku2 = dLuku2 + 1;
dLuku3 = dLuku3 + dLuku1;
}
}
Console.WriteLine(dLuku3 / dLuku2);
Ratkaisu
• Ohjelma siis kysyy käyttäjältä lukuja, niin kauan kuin ne ovat
erisuuria kuin 0. Jos luku ei ole nolla lisätään se muuttujaan dLuku3
ja samalla lisätään yhdellä muuttujan arvoa dLuku2.
Lopuksi jaetaan dLuku3 dLuku2:lla eli saadaan keskiarvo syötetyistä
luvuista ja tulostetaan se.
17
Tehtävä
• Tee ohjelma, joka pyytää käyttäjältä alku- ja loppuarvon sekä
tulostaa kaikki kokonaisluvut näiden arvojen väliltä.
• Käytä toteutukseen while-lausetta.
• Kirjoita paperille vastaus ja käytä mahdollisimman eksaktia C# syntaksia.
Ratkaisu
int iAlku, iLoppu;
Console.WriteLine("Anna alkuarvo: ");
iAlku = Convert.ToInt32(Console.ReadLine());
Console.WriteLine("Anna loppuarvo: ");
iLoppu = Convert.ToInt32(Console.ReadLine());
while (iAlku <= iLoppu) {
Console.WriteLine(iAlku);
iAlku = iAlku + 1;
}
18
do-while -lause
• do-while –lause on ns. loppuehtoinen toistolause
– toistokertojen määrä ei ole etukäteen tiedossa
• do-while -lauseen muoto:
do {
lause;
...
lause;
} while(ehto);
(Koottua) lausetta
toistetaan niin kauan, kun
ehto on tosi.
Huomaa puolipiste!
Ehto on totuusarvoinen lauseke ja sen
arvo tarkastetaan aina toistokerran
suorittamisen jälkeen.
Kun ehto saa arvon epätosi, siirrytään
while-lausetta seuraavaan lauseeseen.
do-while -lause
int iAlku, iLoppu;
Console.WriteLine("Anna alkuarvo: ");
iAlku = Convert.ToInt32(Console.ReadLine());
Console.WriteLine("Anna loppuarvo: ");
iLoppu = Convert.ToInt32(Console.ReadLine());
do {
Console.WriteLine(iAlku);
iAlku = iAlku + 1;
} while (iAlku <= iLoppu);
19
Tehtävä : Mitä tulostaa ao. koodi ( syöte: 2 ja 5)
int iAlku, iLoppu;
Console.Write("Anna alkuarvo: ");
iAlku = Convert.ToInt32(Console.ReadLine());
Console.Write("Anna loppuarvo: ");
iLoppu = Convert.ToInt32(Console.ReadLine());
Console.WriteLine("while - rakenteen avulla ");
while (iAlku <= iLoppu) {
Console.WriteLine(iAlku);
iAlku = iAlku + 1;
}
Console.WriteLine("vielä do while - rakenteen avulla ");
do {
Console.WriteLine(iAlku);
iAlku = iAlku + 1;
} while (iAlku <= iLoppu);
Console.WriteLine("");
Ratkaisu
Miksi näin?
20
for-lause
• for-lause on ns. lukumääräinen toistolause
– toistokertojen määrä on etukäteen tiedossa
• for-lauseen muoto:
for (alkuasetus; ehto; eteneminen) {
lause;
...
lause;
}
Alkuasetus suoritetaan
yhden kerran ennen
toistokertojen alkamista.
Alkuasetusta käytetään
toistokertojen lukumäärää
ylläpitävän laskurimuuttujan
(eli ns. indeksimuuttujan)
määrittelyyn.
Ehto on totuusarvoinen
lauseke ja sen arvo
tarkastetaan aina ennen
toistokerran suorittamista.
Eteneminen on lause, joka
suoritetaan jokaisen
toistokerran jälkeen.
Etenemistä hallitaan
laskurimuuttujan arvon
muuttamisella.
for – lause; esimerkki
int iLkm;
Console.WriteLine(”Montako tähteä haluat: ”);
iLkm = Convert.ToInt32(Console.ReadLine());
for (int i = 0; i < iLkm; i=i+1) {
Console.Write(”*”);
}
21
for – lause; harjoitus
• Miten muuttaisit edellistä tehtävää, jotta saisit seuraavanlaisen
lopputuloksen?
for – lause; ratkaisu
int iLkm, iRivit, i, x;
Console.Write("Montako tähteä riville haluat: ");
iLkm = Convert.ToInt32(Console.ReadLine());
Console.Write("Montako riviä tähtiä haluat: ");
iRivit = Convert.ToInt32(Console.ReadLine());
Console.WriteLine("");
for (x = 0; x < iRivit; x = x+1){
for (i = 0; i < iLkm; i=i+1) {
Console.Write("* ");
}
Console.WriteLine("");
}
Console.WriteLine("");
22
for – lause; tehtävä
• Tee ohjelma, joka pyytää käyttäjältä alku- ja loppuarvon sekä
tulostaa kaikki kokonaisluvut näiden arvojen väliltä. Tee ohjelmasta
sellainen, että se toimii suuremmasta luvusta pienempään eli siis
tulostaa esim . numerot alkuarvosta 6 Î 0.
• Käytä toteutukseen for-lausetta.
for – lause; ratkaisu
int iAlku, iLoppu, i;
Console.Write("Anna alku: ");
iAlku = Convert.ToInt32(Console.ReadLine());
Console.Write("Anna loppu: ");
iLoppu = Convert.ToInt32(Console.ReadLine());
for (i = iAlku ; i >= iLoppu ; i = i - 1) {
Console.WriteLine(i);
}
23
Taulukko
• jos tarvitaan n kappaletta keskenään samantyyppisiä
muuttujia, ne voidaan koota taulukoksi
• esimerkki: pyydetään käyttäjältä 8 kokonaislukua
– ensin ilman taulukkoa:
int iLuku1, iLuku2, iLuku3, iLuku4, iLuku5, iLuku6, iLuku7,
iLuku8;
Console.Write(”Anna 1. luku:”);
iLuku1 = Convert.ToInt32(Console.ReadLine());
Console.Write(”Anna 2. luku:”);
iLuku2 = Convert.ToInt32(Console.ReadLine());
Console.Write(”Anna 3. luku:”);
iLuku3 = Convert.ToInt32(Console.ReadLine());
...
Console.Write(”Anna 7. luku:”);
iLuku7 = Convert.ToInt32(Console.ReadLine());
Console.Write(”Anna 8. luku:”);
iLuku8 = Convert.ToInt32(Console.ReadLine());
Taulukko
–ja sitten sama taulukon avulla
int i;
int[] iLuku = new int[8];
for (i=0; i<8; i=i+1) {
Console.Write(”Anna ” + (i+1) + ”. luku:”);
iLuku[i] = Convert.ToInt32(Console.ReadLine());
}
• taulukko koostuu keskenään samantyyppisistä
(muuttujatyyppejä) alkioista
100
23
123
265
2
34
554
3
alkio
24
Taulukko
• taulukolla on nimi
• taulukon alkioihin viitataan nimen
ja alkion järjestysnumeron (eli
indeksin) avulla
–indeksointi alkaa aina nollasta!
Taulukko: iLuku
indeksi
100
23
123
265
2
34
554
3
0
1
2
3
4
5
6
7
iLuku[0]
iLuku[1]
iLuku[2]
iLuku[3]
iLuku[4]
iLuku[5]
iLuku[6]
iLuku[7]
– alkioita käytetään kuten tavallisia muuttujia
iLuku[2] = 12;
iLuku[3] = iLuku[3] + 2;
iLuku[4] = iLuku[1] + iLuku[2] + iLuku[3];
Taulukko
• taulukko on nimi on muotoa: tietotyyppi[]
– esim. kokonaislukutaulukko int[], jonka alkioiden arvoina voi olla inttyyppisiä arvoja
• taulukkotyyppisen muuttujan tietotyyppinä on taulukko
• uusi taulukko luodaan siis tyyliin tietotyyppi[n], jossa n kertoo
alkioiden lukumäärän
– esim. 8-alkioinen kokonaislukutaulukko luodaan Î int[8]
• taulukkomuuttujan määrittely
tietotyyppi[] nimi = new tietotyyppi[n];
int[] luku = new int[8];
25
Taulukko
int[] iLuku = new int[8];
int i;
// sijoitetaan luvut taulukoon
for (i=0; i<8; i = i + 1) {
iLuku[i] = i;
}
// tulostetaan syötetyt luvut
for (i=0; i<8; i = i + 1) {
Console.WriteLine(”Alkiossa ” + i + ”:” + iLuku[i]);
}
• 1. tenttiin tuleva aineisto päättyy tähän !
26
Olio-ohjelmointi
• olioperustaisuus on eräs ohjelmointiparadigma
– paradigma = esikuva, malli, kaava
– tapa kuvata erilaisten järjestelmien rakennetta ja toimintaa
– terminologia on osin vakiintumatonta
• miksi?
– tarve systematisoida ohjelmistojen rakentamista
– vastaa hyvin ihmisen tapaa hahmottaa maailmaa
Oliotermistöä
• keskeistä olioajattelussa on tiedostaa ero abstraktin ja konkreettisen
välillä
abstrakti käsite
konkreettinen ilmentymä
teos
Visual C# .NET - kirja
auto
Nissan Primera –auto parkkipaikalla
henkilö
opiskelija Matti Möttönen
• abstrakti käsite kirjoitetaan C#-kielessä luokaksi ja jokainen sen
pohjalta luotu konkreettinen ilmentymä on olio
27
Oliotermistöä
• se, mitä abstraktille käsitteelle (luokalle) voidaan tehdä, kirjoitetaan
metodeiksi
• kaikki tieto, mikä abstraktiin käsitteeseen (luokkaan) liittyy,
kirjoitetaan kentiksi
• esimerkki:
luokka Henkilö
kenttä syntymäaika
kenttä nimi
kenttä ikä
metodi ristiminen()
metodi tervehdi()
metodi vanhene()
Oliotermistöä
• luokan perusteella luodaan konkreettisia (fyysisiä) olioita
Henkilö – luokka
kenttä syntymäaika
kenttä nimi
kenttä ikä
metodi ristiminen()
metodi tervehdi()
metodi vanhene()
Luodaan
uusi olio
Henkilö – olio
12.4.1982
Matti Möttönen
23 v
ristiminen()
tervehdi()
vanhene()
Matti Möttönen oliota siis käytetään metodiensa välityksellä. Hän kentät
perintönä luokalta ja osaa toimia metodien mukaan.
28
Tehtävä
• Suunnittele luokka Auto.
• Mitä tietoja autoon liittyy? = kentät
• Mitä autolla voidaan tehdä? = metodit
Ratkaisu
Auto-luokka
• kentät:
– polttoainesäiliön tilavuus
– merkki
– malli
– hinta
– moottoritilavuus
• Metodit:
– LisääPolttoAinetta(litramäärä)
– UusiHinta(uusi hinta)
– AvaaOvet()
– KäynnistäMoottori()
– Aja(suunta)
29
Kenttä
• kentät kuvaavat kaikki tiedot, jotka luokkaan liittyvät – luokan pohjalta
luodun olion kentillä on oliota kuvaavat arvot
• kenttiä käsitellään tyypillisesti vain metodien kautta
• kenttä määritellään lähes samoin kuin muuttuja:
näkyvyysmääreitä tyyppi nimi;
– näkyvyysmääreillä säädellään kentän käytettävyyttä
• private = kenttä on käytettävissä vain luokan metodien välityksellä
• public = kenttä on käytettävissä luokan ulkopuolelta
• esimerkki:
private string sSukuNimi;
private string sEtuNimi;
private int iIka;
Metodi
• metodilla toteutetaan jokin palvelu, ja sitä ohjataan parametriensa
välityksellä
• Esimerkki
– Onko vuosi 2005 karkausvuosi?
– karkausVuosiko(2005)
”Ei”
karkausVuosiko(vuosi)
1.
2.
3.
Vastaanotetaan parametrina vuosi
Selvitetään vuodesta karkausvuosi
Palautetaan paluuarvona vastaus
30
Metodi
• Metodin toiminta perustuu seuraavaan kaavaan:
– lähtötiedot Î
toiminta Î
vastaus
• Esimerkki C# - metodina Î tulo - metodi
public int Tulo(int iLuku1, int iLuku2) {
int iTulos;
iTulos = iLuku1 * iLuku2;
return iTulos;
}
Metodi
• metodien avulla luokkaa voidaan käsitellä jollakin tavalla – luokasta luotua
oliota käytetään vain metodiensa välityksellä
• metodin määrittely (kirjoitetaan johonkin luokkaan elementiksi):
[näkyvyysmääreitä] paluuarvon_tyyppi nimi (parametrit) {
algoritmi
}
– näkyvyysmääreillä säädellään metodin käytettävyyttä
• private = luokan omassa käytössä oleva metodi
• public = muiden luokkien käytössä oleva metodi
• static = luokkametodi, jota kutsutaan luokan kautta (kaikille luokan olioille
yhteinen)
– paluuarvon tyyppi
• tietotyyppi, joka kertoo, minkä tyyppisen arvon metodi palauttaa
• void = metodi ei palauta lainkaan arvoa
31
Metodi
• esimerkki:
public void ristiminen(string n) {
nimi = n;
}
public void tervehdi() {
Console.WriteLine(”Morjens, olen ” + nimi);
}
• metodi käynnistetään kutsumalla sitä
– metodikutsu muodostuu metodin nimestä sekä
mahdollisten parametrien arvoista
• esimerkki:
ristiminen(”Matti Möttönen”);
tervehdi();
Metodi
• metodin parametrit
– ovat metodin muuttujia, joita käytetään välittämään tietoa metodille
sen kutsumisen yhteydessä
– parametrit saavat aina (alku)arvonsa metodin kutsumisen
yhteydessä – parametrin arvoa ei voi muuttaa itse metodissa
– parametrin määrittely on samanlainen kuin muuttujalla:
–
tietotyyppi nimi
• Esimerkki koodista
public void Toista(string sText, int iKerta) {
int i;
for (i=0; i < iKerta; i = i + 1) {
Console.WriteLine(sText);
}
}
Koodissa kutsu tapahtuu seuraavasti:
Toista(”Hello World”, 2);
Î
Hello World
Hello World
32
Metodi
•
metodin paluuarvo
– osa metodeista on arvon palauttavia
– paluuarvon tyyppi kirjoitetaan metodimäärittelyyn ennen metodin nimeä
• void tarkoittaa, että paluuarvoa ei ole
– jos metodi palauttaa arvon, siinä on oltava return-lause, joka ilmaisee palautettavan arvon
• kun return-lause suoritetaan, metodin suoritus päättyy
•
esimerkki
public int KuukaudessaPaivia(int iKk) {
switch (iKk) {
case 1: case 3: case 5: case 7: case 8: case 10: case 12:
return(31);
break;
case 2:
return(28);
break;
case 4: case 6: case 9: case 11:
return(30);
break;
default:
return (0);
}
}
Miten olio luodaan? Miten käytetään?
public static void Main(string[] args)
{
PapuKaija pk = new PapuKaija(); // luodaan pk niminen olio luokasta PapuKaija
pk.Ristiminen("Polly");
// kutsutaan metodia Ristiminen
pk.Toista("Terve maailma", 2);
// kutsutaan metodia Toista
}
-------------------------------------------------------// HUOM! Tämä eri tiedostoon
class PapuKaija
{
private string sNimi;
// määritellään kenttä sNimi , luokalle
public void Toista(string sText, int iKerta) // toistetaan haluttua tekstiä haluttu määrä
{
int i;
for (i=0; i < iKerta; i = i + 1)
{
Console.WriteLine(sText);
}
}
public void Ristiminen(string sText) // tämä metodi asettaa oliolle ( PapuKaijalle) nimen eli siis muuttaa kentän sNimi arvoa
{
sNimi = sText;
}
}
33
Miten metodeja käytetään samassa tiedostossa?
public static void Main(string[] args)
{
Ristiminen("Polly");
// kutsutaan metodia Ristiminen
Toista("Terve maailma", 2);
// kutsutaan metodia Toista
}
private static string sNimi;
// määritellään kenttä sNimi luokalle
public static void Toista(string sText, int iKerta) // toistetaan haluttua tekstiä haluttu määrä
{
int i;
for (i=0; i < iKerta; i = i + 1)
{
Console.WriteLine(sText);
}
}
// tämä metodi asettaa nimen eli siis muuttaa kentän sNimi arvoa
public static void Ristiminen(string sText)
{
sNimi = sText;
}
// kun metodit samassa tiedostossa kuin Main – metodi pitää avainsana static lisätä näkyvyysmääreen (public)
perään sekä metodeilla että kentillä.
Metodi
• itsenäisessä (= suoritettavassa) C#-ohjelmassa on
aina main()-metodi
public static void main(string[] args)
– C#-ohjelman suoritus tarkoittaa käytännössä mainmetodin suorittamista
34
Metodi
• luokassa voi olla myös useita samannimisiä metodeja, joilla on
erilaiset parametrit
– tätä ilmiötä kutsutaan kuormittamiseksi
– esimerkki:
public void TulostaNelio(double dSivunPituus)
public void TulostaNelio(int iSivunPituus)
public void TulostaNelio(int iSivu1, int iSivu2)
– esim. metodi Console.WriteLine() on kuormitettu useille erityyppisille
parametreille
– C# - kääntäjä päättää suoritettavan metodin kutsussa olevien
parametriarvojen tyyppien perusteella
Olio
•
•
•
•
olio luodaan luokka-määrityksen pohjalta
jokaisella oliolla on omat kentät ja metodit
luominen tehdään operaatiolla new
luokkaa käytetään samoin kuin tietotyyppiä
– muuttujan tyypiksi voidaan asettaa luokka
• esimerkki
– olkoon määritelty luokka Henkilo
– nyt voidaan määritellä tätä tyyppiä oleva muuttuja:
Henkilo henk;
– muuttujan arvoksi sijoitetaan luokasta luotu (new-operaatio) olio:
henk = new Henkilo();
– tämän jälkeen muuttujan arvona olevan olion metodeja voidaan suorittaa:
henk.Ristiminen(”Matti Möttönen”);
henk.Tervehdi();
35
Olio
Olio
Olio
A
B
Ristiminen()
Tervehdi()
nimi: Polly
2.
3.
Ristiminen()
Tervehdi()
nimi: Pedro
Ohjelma
…
1. Luo PapuKaija-olio A;
2. A.ristiminen(”Polly”);
3. A.tervehdi();
...
4. Luo PapuKaija-olio B;
5. B.ristiminen(”Pedro”);
6. B.tervehdi();
....
4.
1.
Luokka
Papukaija
nimi
Ristiminen()
Tervehdi()
Olio
main.cs:
class MainClass {
public static void main(String[] args)
{
PapuKaija pkA, pkB;
PapuKaija.cs:
public class PapuKaija {
private string sNimi;
public void Ristiminen(string n) {
sNimi = n;
}
public void Tervehdi(string sText, int iKrt ) {
int i;
for ( i = 0;i < iKrt; i++)
{
Console.WriteLine(sText + ” olen ” + sNimi );
}
}
pkA = new PapuKaija();
pkA.Ristiminen(”Polly”);
pkA.Tervehdi(”Terve”, 2);
pkB = new Henkilo();
pkB.Ristiminen(”Pedro”);
pkB.Tervehdi(”Moro”,3);
}
}
}
36
Konstruktori
• luokassa voi olla metodi, jota käytetään olion luomiseen
• tällaista metodia kutsutaan konstruktoriksi eli rakentajaksi
– konstruktorin nimi on aina sama kuin luokan nimi
• esimerkiksi luokan Henkilo konstruktori on Henkilo()
– konstruktorin määrittelyssä ei käytetä lainkaan paluuarvon tyyppi –määrettä
– konstruktori asettaa tyypillisesti kenttien alkuarvoja
• kenttien alkuarvoja ei siis tule asettaa kentän määrittelyssä vaan
konstruktorissa
– luokassa voi olla useita konstruktoreita
• keskenään samannimisiä, mutta parametriosat ovat erilaisia (=
kuormittaminen)
– jos luokassa ei ole määritelty konstruktoria, suoritetaan oliota luotaessa
parametriton ns. oletuskonstruktori
• käynnistää ns. yliluokan konstruktorin
– liittyy olio-ohjelmoinnin käsitteeseen periytyminen, jota emme ole käsitelleet
Konstruktori
public class Piste {
private int x;
private int y;
public Piste() {
x = 0;
y = 0;
}
public Piste(int iArvoX, int iArvoY) {
x = iArvoX;
y = iArvoY;
}
public int GetX() {
return x;
}
public int GetY() {
return y;
}
public void Siirry(int iArvoX, int iArvoY) {
x = x + iArvoX;
y = y + iArvoY;
}
// kentät
// konstruktori
// konstruktori
// metodi
// metodi
// metodi
}
37
Aksessori
• Käsittele luokkien kenttiä ”vain” metodien avulla
• metodi, joka asettaa kenttään arvon tai palauttaa
paluuarvonaan kentän arvon, kutsutaan aksessorimetodiksi
• aksessorimetodit nimetään tyypillisesti Get- ja Set-alkuisiksi
• esimerkki
public class Henkilo {
private int iIka
// kenttä
public Henkilo() {
iIka = 0;
}
public void SetIka(int iArvo) {
iIka = iArvo;
}
public int GetIka() {
return iIka;
}
// konstruktori
// set-aksessorimetodi
// get-aksessorimetodi
Aksessorit tapa 2.
•
Toinen tapa käyttää aksessoria
public class Henkilo {
private int iIka;
// kenttä
public Henkilo() { // konstruktori
iIka = 0;
}
public int Ika {
get {
//aksessori
return iIka;
//palautetaan arvo
iIka = value;
//asetetaan arvo value - nimisen parametrin avulla
}
set {
}
}
}
38
Aksessorit; Miten käytetään?
• voit käyttää kumpaa tahansa
• Aksessori – metodia käytät kuten metodeja yleensä
• Tapa 2 eli aksessoria käytät seuraavasti:
public static void Main(string[] args)
{
Henkilo h = new Henkilo();
// olio.aksessori
h.Ika++; // voit käyttää aksessoria kuten sekoittaen metodin ja muuttujan
Console.WriteLine(h.Ika);
// tulostuksessa viittaa suoraan aksessoriin
}
39