Etusivu Aloitus Kontrollit Metodit Muuttujat Ohjausrakenteet Silmukat Matematiikka Debuggaus Virheenkäsittely Vuorovaikutus Valikot Tiedostonkäsittely Ikkunat Leikepöytä Drag and Drop Tiedostopäätteet Linkkejä Harjoitukset

Johdanto ja tavoite

Tässä osiossa tutustutaan muuttujiin. Tämän osion jälkeen opiskelija tietää mitä muuttujat ovat ja osaa käyttää erilaisia muuttujia erilaisissa tilanteissa oikein.

Muuttuja

Muuttuja voidaan määritellä seuraavasti: muuttuja on tiedon säilytyspaikka tietokoneen muistissa. Esimerkiksi assembler -kielellä ohjelmia tehtäessä huomataan, että tieto säilytetään tietokoneen käyttömuistissaa (RAM -muisti), tietyssä osoitteessa. Sen sijasta, että pyydetään tietokonetta hakemaan tieto osoitteesta 0xc0, on helpompi määritellä muistipaikalle nimi, esim. luku1 equ 0xc0. Tämän jälkeen voimme pyytää tietokonetta hakemaan halutun tiedon muistipaikasta luku1.

VB:ssä meidän ei tarvitse käyttää assemblerissa käytettyä tiedon tallennustapaa vaan voimme määrittää ohjelmakoodissa suoraan muuttujan. Tällöin VB varaa muistista tietystä paikasta tilaa em. muuttujalle valitsemallamme nimellä. Alla on esitelty LONG -tyyppisen muuttujan määrittely:

Dim Luku1 As Long

Muuttujatyypit

VB:ssä on enemmän kuin yksi muuttujatyyppi. Tarvitsemme erityyppisiä muuttujia koska tallennettavan tiedon tyyppi vaihtelee. Joskus haluamme tallentaa tekstiä, joskus numeroita, joskus raha-arvoja, jne. Tämän vuoksi VB tarjoaa meille useamman muuttujatyypin. Alla on lueteltu muuttujatyyppejä ja niiden yleisempiä käyttötarkoituksia sekä tieto muuttujan tarvitsemasta muistimäärästä muistissa:

Muuttuja Muistimäärä Muuttujan arvoalue Käyttötarkoitus Nimeäminen
Integer 2 tavua -32768 to 32767 Pienten lukujen säilyttämiseen
Huom! Ei desimaalilukuja!
iMuuttuja
Long 4 tavua -2147483648 to 2147483647 Isojen lukujen säilyttämiseen!
Huom! Ei desimaalilukuja
lMuuttuja
Single 4 tavua -3.402823E38 to 3.402823E38 Pienten desimaalukujen säilyttämiseen sMuuttuja
Double 8 tavua -1.79769313486232E308 to 1.79769313486232E308 Suurten desimaalilukujen säilyttämiseen dMuuttuja
Currency 8 tavua -922337203685477.5808 to 922337203685477.5808 Rahamäärän säilyttämiseen curMuuttuja
String 1 tavu per yksi merkki 0-65535 merkkiä Tekstin säilyttämiseen strMuuttuja
Boolean 2 tavua True tai False Kyllä/Ei -arvojen säilyttämiseen bMuuttuja
Date 8 tavua 1.1.100 to 31.12.9999 Päivämäärän säilyttämiseen dateMuuttuja
Variant 16/22 tavua Muiden muuttujatyyppien arvoalueet Minkä tahansa tietotyypin tiedon säilyttämiseen varMuuttuja

Muuttujan käyttöönotto

Ennenkuin muuttuja voidaan ottaa käyttöön, tulee se määritellä joko Dim-, Global- tai Static -lauseella, muutoin sen tyypiksi tulee Variant. Alla on esitelty neljä tapaa määritellä muuttuja. Muuttujan määrittelyssä tulee huomioida A) paikka missä muuttuja määritellään ja B) muuttujan määrittelytapa:
Dim M1 As Long
Private M2 As Long
Public M3 As Long
'Global M4 as long
Em. muuttujat on määritelty lomakkeen ohjelmakoodiin. Muuttuja M1 "näkyy" (eli on käytettävissä) vain lomakkeen sisällä kuten myös yksityinen muuttuja M2. Muuttuja M3 näkyy myös lomakkeen ulkopuolelle koska se on määritelty julkiseksi. Kuten ehkä huomasit, neljäs vaihtoehto eli Global -määrittely EI onnistu lomakkeella. Voit määritellä jonkin muuttujan globaaliksi kirjoittamalla määrittelyn moduuliin.

Kuten ehkä huomasit, emme ole käsitelleet vielä staattista muuttujaa. Staattinen muuttuja (kuten nimikin jo sanoo) "muistaa" muuttujan arvonsa. Tämä tarkoittaa sitä, että jos määrittelemme muuttujan esim. metodissa Static -määritteellä, "muistaa" muuttuja arvonsa vaikka poistuisimme välillä metodista. Alla esimerkki "normaalin" muuttujan määrittelystä ja käytöstä ja staattisen muuttujan määrittelystä ja käytöstä:

Private Sub Command1_Click()

    ' Kutsutaan aliohjelmaa viisi kertaa
    kaynnit
    kaynnit
    kaynnit
    kaynnit
    kaynnit

End Sub

Private Sub kaynnit()

    Static lStaattinenMuuttuja As Long
    Dim lNormaaliMuuuttuja As Long

    lStaattinenMuuttuja = lStaattinenMuuttuja + 1
    lNormaaliMuuuttuja = lNormaaliMuuuttuja + 1
    MsgBox "lStaattinenMuuttuja=" & lStaattinenMuuttuja & ", lNormaaliMuuuttuja=" & lNormaaliMuuuttuja

End Sub
Ohjelmakoodissamme kutsumme kaynnit -aliohjelmaa viisi kertaa peräkkäin. Aliohjelmassa on määritelty kaksi muuttujaa, staattinen muuttuja lStaattinenMuuttuja ja "normaali" muuttuja lNormaaliMuuttuja, molemmat Long -tyyppisiä. Jokaisella kerralla kun menemme aliohjelmaan, muuttuja lNormaaliMuuttuja alustetaan uudestaan arvolla nolla. Kun nollaan lisätään arvo 1, saadaan muuttujan arvoksi jokaisella kierroksella 1. Staattinen muuttuja alustetaan arvolla 0 kun menemme aliohjelmaan ensimmäisen kerran. Ensimmäisellä kierroksella staattisen muuttujan arvo on siis 1. Kun menemme toisen kerran aliohjelmaan, staattista muuttujaa ei alusteta koska se on jo alustettu ja siinä on tallessa edellisen kierroksena arvo 1 jota kasvatamme ykkösen verran.

Huom! Muista, että kahta samannimistä muuttujaa EI saa määritellä jos niiden voimassaoloalueet "risteävät"! Käytännössä tämä tarkoittaa sitä, että jos meillä on kaksi aliohjelmaa, jossa kussakin määrittelemme samannimiset muuttujat, ei siitä aiheudu ongelmia koska muuttujat eivät ole voimassa metodinsa ulkopuolella. Toisaalta jos määrittelemme kaksi globaalia, samannimistä muuttujaa, tulee siitä ongelmia koska muuttujien voimassaoloalueet menevät "ristiin", eli molemmat ovat voimassa.

Muuttujan voimassaoloalue

Kuten ehkä jo aikaisemmasta huomasit, muuttuja ei välttämättä ole voimassa koko projektin alueella. Alla on lyhyesti kerrottu muuttujien voimassaoloalueista.

Esimerkkejä muuttujamäärittelyistä

Alla on muutama esimerkki muuttujamäärittelyistä. Nämä kannattaa muistaa koska VB ei salli kirjoittaa esim. Global -määrittelyä lomakkeeseen, jne.

Muuttujan määrittely metoditasolla:

Dim lMetodiTasonMuuttuja As Long
Muuttujan määrittely lomaketasolla:
Private lYksityinenLomakeMuuttuja As Long
Public lJulkinenLomakeMuuttuja As Long
Muuttujan määrittely moduulitasolla:
' Määritellään globaali muuttuja
Global glKayttajaTunnus As Long
Kun käytät edellä esitettyjä muuttujan määrittelytapoja, voit olla varma, että muuttujat on määritelty oikeassa paikassa ja oikealla tavalla ja tiedät vielä niiden voimassaoloalueen.

Taulukot

Muuttujiin voidaan tallentaa tietoa mutta entäpä jos tarvitsemme muuttujatilaa esim. tuhannelle tiedolle? Yksi tapa on tietysti kirjoittaa tuhat riviä muuttujamäärittelyitä mutta se voi käydä työlääksi. Ja joskus voi tulla esiin vielä sellainen tilanne, että ohjelmaa kirjoitettaessa emme tiedä montako muuttujaa tulemme tarvitsemaan ohjelmaa ajettaessa! Tällaisia tilanteita varten meillä on käytössämme taulukot.

Kiinteä taulukko

Kuten aikaisemmin on jo kerrottu, samannimisiä muuttujia ei voi määritellä samaan voimassaoloalueeseen, eli metodin sisälle ei voi määritellä kahta lLuku -muuttujaa. Taulukkoa käytettäessä määrittelemme vain taulukon nimen (vrt. muuttujan nimi) joka koostuu n -kappaleesta (taulukon koko) muuttujia. Muuttujat erotellaan toisistaan ns. indeksinumerolla. Otetaan esimerkki, tarvitsemme kymmenen kappaletta Long -tyyppisiä muuttujia. Sen sijaan, että määrittelemme kymmenen eri muuttujaa, määrittelemmekin taulukon jonka koko on kymmenen ja tyyppi Long:
Dim lTaulukko(10) As Long

' Asetetaan taulukon ensimmäiseen alkioon arvo 1
lTaulukko(0) = 1
' Asetetaan taulukon viimeiseen alkioon arvo 10
lTaulukko(9) = 10

' Tulostamme taulukon molempien alkioiden arvot
MsgBox "Taulukon 1. alkion arvo on " & lTaulukko(0) & ", taulukon viimeisen alkion arvo on " & lTaulukko(9)
Ensimmäisellä rivillä määrittelemme Long -tyyppisen taulukon nimeltä lTaulukko jonka koko on kymmenen alkiota. Sitten asetamme taulukon ensimmäisen alkion arvoksi luvun 1. Muista, että taulukko alkaa aina indeksistä 0. Eli jos taulukon koko on kymmenen alkiota, viimeisen alkion indeksi on 9.
Kaavana: taulukon viimeisen indeksi on taulukon koko - 1.
Lopuksi tulostamme taulukon ensimmäisen ja viimeisen alkion arvot viestilaatikolla.

Dynaaminen taulukko

Aina emme välttämättä tiedä kuinka ison taulukon tarvitsemme. Tällöin voimme luoda taulukon dynaamisesti eli määrittelemme taulukon mutta emme kokoa. Kun haluamme käyttää taulukkoa, määrittelemme taulukon koon käyttäen ReDim -määritettä. Tämän määritteen "huonona" puolena on se, että jos taulukossa on jotain arvoja ennestään, nämä arvot menetetään uudelleenmäärittelyn johdosta. Jos haluamme säilyttää mahdolliset vanhat arvot, voimme lisätä määrittelyn perään Preserve -määritteen. Katsotaanpa alla olevaa esimerkkiä:
' Määritellään taulukko ilman kokoa
Dim lTaulukko() As Long

' Määritellään taulukon kooksi 5
ReDim lTaulukko(10) As Long

' Asetetaan taulukon ensimmäiseen alkioon arvo 1
lTaulukko(0) = 1
' Asetetaan taulukon viimeiseen alkioon arvo 10
lTaulukko(9) = 10

' Tulostamme taulukon molempien alkioiden arvot
MsgBox "Taulukon 1. alkion arvo on " & lTaulukko(0) & ", taulukon viimeisen alkion arvo on " & lTaulukko(9)

' Määritellään taulukon kooksi 5, vanhat arvot tuhoutuvat
ReDim lTaulukko(10) As Long

' Tulostamme taulukon molempien alkioiden arvot
MsgBox "Taulukon 1. alkion arvo on " & lTaulukko(0) & ", taulukon viimeisen alkion arvo on " & lTaulukko(9)

' Asetetaan taulukon ensimmäiseen alkioon arvo 1
lTaulukko(0) = 1
' Asetetaan taulukon viimeiseen alkioon arvo 10
lTaulukko(9) = 10

' Määritellään taulukon kooksi 5, säilytetään vanhat arvot
ReDim Preserve lTaulukko(10) As Long

' Tulostamme taulukon molempien alkioiden arvot
MsgBox "Taulukon 1. alkion arvo on " & lTaulukko(0) & ", taulukon viimeisen alkion arvo on " & lTaulukko(9)
Aluksi määrittelemme siis taulukon ilman kokoa. Tämän jälkeen määrittelemme taulukon jonka koko on viisi alkiota. Huom! Voit määritellä joka kerta taulukon eri kokoiseksi jos se on tarpeen! Päivitämme taulukon ensimmäistä ja viimeistä alkiota ja tulostamme ne. Tämän jälkeen määrittelemme taulukon koon uudestaan ja tulostamme taulukon muuttujien arvot. Nyt huomaamme, että ReDim -määrite oli "hukannut" taulukon alkioiden arvot. Lisäämme arvot taulukkoon ja määrittelemme taulukon koon taas uusiksi, nyt käytämme kuitenkin Preserve -määritettä jonka edun huomaamme taulukon alkioiden tietoja tulostettaessa: taulukon alkioiden tiedot ovat säilyneet taulukon koon uudelleenmäärittelystä huolimatta.

Huom! Taulukon läpikäymiseen kannattaa käyttää silmukoita!

Vakiot

Vakiot ovat muuttujia, joiden arvoa ei voida muuttaa. Voit esim. määritellä muuttujan dPii jonka arvoksi tulee 3,147 (piin likiarvo). Koska muuttujan arvoa ei tarvitse eikä saisi muuttaa, kannattaa se määritellä vakiotyyppiseksi:
Option Explicit

' Määritetään vakiomuuttuja arvolla 3.147
Private Const dPii = 3.147

Private Sub Form_Load()
    ' Tulostetaan vakiomuuttujan arvo
    MsgBox "dPii=" & dPii

    ' Yritetään muuttaa vakiomuuttujan arvoa
    'dPii = 4.4343
End Sub
Ihan ensimmäisenä huomaatkin Option Explicit -lausekkeen. Tämä ei sinällään liity mitenkään vakiomuuttujan määrittellyyn vaan se tarkoittaa sitä, että jos tämä lause löytyy ohjelmasta, täytyy kaikki muuttujat määritellä. Lause Private Const dPii = 3.147 -määrittelee vakiomuuttujan nimeltä dPii jonka arvo on 3,147. Kuten ehkä huomasit, VB:ssä desimaalit tulee kirjoittaa piste-erotinta käyttäen. Lomakkeen lataustapahtumassa tulostamme vakiomuuttujan arvon. Seuraava kohta onkin kommentoitu ('dPii = 4.4343) koska vakiomuuttujan arvoa EI voida muuttaa.

Tyyppimäärittely

Sinun ei tarvitse tyytyä pelkästään VB:n vakiomuuttujatyyppeihin vaan voit määritellä myös oman tyyppisiä muuttujia. Tätä kutsutaan tyyppimäärittelyksi. Alla olevassa ohjelmakoodissa on määritelty oma tyyppi nimeltä KayttajaTiedot:

Ohjelma vaatii toimiakseen yhden CommandButton -tyyppisen painikkeen lisäämistä lomakkeelle.

Private Type KayttajaTiedot
    Etunimi As String
    Sukunimi As String * 50
    Ika As Integer
    Lahiosoite As String
    Postinumero As String * 5
    Postitoimipaikka As String * 30
End Type

Private Sub Command1_Click()

    Dim TeppoTestaaja As KayttajaTiedot

    TeppoTestaaja.Etunimi = "Teppo"
    TeppoTestaaja.Sukunimi = "Testaaja"
    TeppoTestaaja.Lahiosoite = "Teponkuja 3 A 4"
    TeppoTestaaja.Postinumero = 93939
    TeppoTestaaja.Postitoimipaikka = "Teppola"

    MsgBox "Hei " & TeppoTestaaja.Etunimi & " " & TeppoTestaaja.Sukunimi & "!"

End Sub
Koska määrittelimme KayttajaTiedot -tyyppimäärittelyn lomakkeella, tulee tyyppimäärittelyn olla yksityinen. Jos määrittelisimme tyyppimäärittelyn moduulissa, voisi tyyppimäärittely olla julkinen ja käytettävissä koko projektin alueella, nyt käyttöalue on rajoittunut lomakkeelle missä ohjelmakoodi sijaitsee.

Tyyppimäärittely kirjoitetaan siis Type ja End Type -rivien väliin. Type -sanan edessä oleva Public/Private määrittää näkyvyysalueen ja Type -sanan perässä oleva teksti on tehtävän tyyppimäärittelyn nimi, tässä tapauksessa KayttajaTiedot.

Määrittelemme oman muuttujatyyppimme koostumaan kuudesta erillisestä muuttujasta (Etunimi, Sukunimi, Ika, Lahiosoite, Postinumero ja Postitoimipaikka). Kuten ehkä huomasit, muuttuja Etunimi on määritelty "normaalisti" mutta esim. muuttuja Sukunimi on määritelty siten, että muuttujan tyypin (tässä tapauksessa String) jälkeen on * 50. Käytännössä tämä tarkoittaa sitä, että jos meillä on merkki * ja jokin numero sen perässä (meidän tapauksessamme numero 5), määritämme tällöin String -muuttujan pituudeksi 50 merkkiä. Etunimessä em. merkintää ei ole käytössä joten etunimi voi olla maksimissaan 65535 merkkiä pitkä teksti.

Jotta määrittelemäämme "omaa muuttujaa" (tyyppimäärittely) voisi käyttää, tulee meidän luoda uusi muuttuja jonka tyyppi on em. KayttajaTiedot. Tämän jälkeen voimme asettaa muuttujamme (tässä tapauksessa TeppoTestaaja) arvoja, eli etunimen, sukunimen, iän, lähiosoitteen, postinumeron ja postitoimipaikan.

Lopuksi tulostamme muuttujan sisältämiä tietoja. Etunimi tulostuu normaalisti, sitten tulostamme välilyönnin ja lopuksi sukunimen ja perään huutomerkin. Kuten alla olevasta kuvasta voi huomata, sukunimi sisältää tyhjiä merkkejä 42 kpl (sukunimi -kentän pituus 50 merkkiä, tiedon pituus 8 merkkiä eli loput merkit ovat tyhjiä).

Esimerkkiohjelmamme tuloste
Esimerkkiohjelmamme tuloste.

Tilanteesta riippuen kannattaa käyttää tyyppimäärittelyssä vakiomittaisia kenttiä (eli laittaa * ja numero perään) tai sitten käyttää normaalimäärittelyä. Tällainen tilanne voisi olla esimerkiksi silloin kun tallennamme tiedostoon tietoa binäärisenä, tällöin tiedon on oltava vakiopituista.