Toistokäsky for ja range-funktio

Toinen Python-kielessä käytettävä toistokäsky on for. Se on tarkoitettu tilanteisiin, jossa käydään läpi jonkin lukujonon tai rakenteen kaikki alkiot järjestyksessä. Perehdymme for-käskyn käyttämiseen eri rakenteiden yhteydessä myöhemmin, kun näitä rakenteita (lista, merkkijonot, sanakirja) esitellään tarkemmin. Tässä vaiheessa tarkastellaan kuitenkin lyhyesti for-käskyn käyttöä lukujonojen yhteydessä.

Python-kielessä saa generoitua kokonaislukujonon haluamaltaan väliltä funktion range avulla. Käsky range(n) generoi lukujonon, joka sisältää järjestyksessä kaikki kokonaisluvut nollasta n-1:een saakka. Jos nyt kirjoitetaan käsky

for i in range(n):
    kasky

tarkoittaa se: suorita kasky vuorotellen jokaiselle i:n arvolle, joka kuuluu range(n):n generoimaan lukujonoon. Ensimmäisellä kierroksella siis kasky suoritetaan niin, että i:n arvo on 0, toisella kierroksella i:n arvo on 1, kolmannella 2 ja niin edelleen, kunnes viimeisellä kierroksella i:n arvo on n-1. Yhden käskyn sijaan toistettavana voi jälleen olla useamman käskyn jono, ja sisennysten avulla osoitetaan, mikä ohjelman osa kuuluu toistettavaan osaan. Esimerkiksi alla oleva ohjelma tulostaa 6:n kertotaulun (niin, että myös laskun 0 * 6 tulos on mukana):

def main():
    for i in range(11):
        tulo = i * 6
        print(i, "* 6 =", tulo)

main()

Ohjelman tulostus siis näyttää seuraavalta:

0 * 6 = 0
1 * 6 = 6
2 * 6 = 12
3 * 6 = 18
4 * 6 = 24
5 * 6 = 30
6 * 6 = 36
7 * 6 = 42
8 * 6 = 48
9 * 6 = 54
10 * 6 = 60

Tutki ohjelman toimintaa vielä animaation avulla. Animaatiossa kierrosten määrää on pienennetty, jotta animaatiosta ei tulisi liian pitkää:

Joka kierroksella laskettavaa tuloa ei tarvitse välttämättä tallentaa muuttujaan, vaan kertolasku voidaan antaa myös suoraan tulostuskäskyssä:

def main():
    for i in range(11):
        print(i, "* 6 =", i * 6)

main()

Ohjelman tulostus on täsmälleen sama kuin edellä.

Huomautus: käsite lukujono ei ole täysin oikea, kun puhutaan range-käskyn suorituksesta. Täsmälleen oikean käsitteen ymmärtäminen vaatii kuitenkin tietoa sellaisista Python-kielen ominaisuuksista, joita ei käsitellä tällä kurssilla. Toistokäskyn for ja käskyn range suorituksen ymmärtämiseen riittää se, että kuvittelee range-käskyn tekevän lukujonon, jota for-käskyssä käydään läpi.

Toistettaviin käskyihin voi kuulua mitä tahansa Python-kielen käskyjä, esimerkiksi if-käskyjä tai toisia toistokäskyjä. Seuraavassa esimerkkiohjelmassa käyttäjä antaa haluamansa määrän lukuja (määrä kysytään ensin käyttäjältä), ja ohjelma laskee annetuista luvuista positiivisten lukujen summan. Negatiivisia lukuja ei siis oteta summaan mukaan. Toistokäskyn sisällä käytetään if-käskyä tarkistamaan, onko viimeksi luettu luku positiivinen.

def main():
    rivi = input("Anna lukujen maara.\n")
    lkm = int(rivi)
    summa = 0
    print("Anna luvut yksi kerrallaan.")
    for i in range(lkm):
        rivi = input()
        luku = float(rivi)
        if luku > 0:
            summa += luku
    print("Positiivisten lukujen summa on", summa)


main()

Tässä ohjelmassa muuttujaa i ei ole käytetty toistokäskyn sisällä mitenkään. Sen avulla pidetään vain huoli siitä, että kierroksia suoritetaan täsmälleen käyttäjän antama määrä, joka on ohjelman alussa tallennettu lkm-muuttujaan. Summan tulostavaa riviä ohjelman lopussa ei ole enää sisennetty for-käskyn sisään, koska tulostus tehdään vasta toistokäskyn päätyttyä, ei joka kierroksella.

Funktio range luo siis oletusarvoisesti lukujonon, jonka ensimmäinen alkio on 0. Jos lukujonon halutaan alkavan jostain muusta luvusta, voidaan se tehdä antamalla range-funktiolle sulkujen sisällä ensin haluttu lähtöarvo, esimerkiksi range(1,n) tuottaa lukujonon, joka sisältää kokonaisluvut luvusta 1 lukuun n-1 asti. Seuraava ohjelma tulostaa kuuden kertotaulun niin, että siinä ei ole mukana riviä, joka sisältää kertolaskun 0 * 6.

def main():
    for i in range(1, 11):
        print(i, "* 6 =", i * 6)

main()

Oletusarvoisesti range-funktio luo lukujonon, joka sisältää kaikki halutun välin kokonaisluvut järjestyksessä. Jos kuitenkin halutaan, että lukujonossa peräkkäisten lukujen erotus on suurempi kuin 1, voidaan haluttu väli antaa range-funktiolle kolmantena tietona. range(alaraja, ylaraja, vali) tuottaa lukujonon, jossa esiintyvät vali:n välein olevat luvut alkaen alarajasta ja päättyen viimeiseen lukuun, joka on pienempi kuin ylaraja. Esimerkiksi käsky

for i in range(5, 19, 3):
    print(i)

Tulostaa

5
8
11
14
17