C kezdőknek – 4. rész
Ebben a részben a ciklusokkal fogunk
foglalkozni. Mi is az a ciklus? Sokszor találkozhatunk olyan algoritmussal,
hogy egy tevékenységet vagy tevékenység csoportot többször végre szeretnénk
hajtani. Elvileg háromféle ciklust (iterációt) különböztetünk meg:
·
a léptető ciklust, amelyet akkor alkalmazunk, ha
tudjuk, hogy hányszor akarjuk végrehajtani az iterációt - pl. egy adatbázis
rekordjainak kiíratása, vagy tömbökön végzett műveletek, ennek szintaktikai
megvalósításra szolgál a for ciklus;
·
az elöltesztelő ciklust, amikor valamely feltétel
teljesüléséig hajtjuk végre az ismételt műveleteket, ennek tipikus alkalmazása
a beolvasás végjelig algoritmusa, szintaktikai megvalósítása
pedig a while ciklus; és
·
a hátultesztelő ciklust, amikor egyszer mindenképpen
végre akarjuk hajtani a ciklusmagban található utasításokat és egy bentmaradási
feltételt fogalmazunk meg, azaz addig végezzük az
ismételt tevékenységeket, amíg a feltétel igaz nem lesz. Ennek szintaktikai megvalósítása pedig a do-while
ciklus.
Nos, nézzünk ezekre példákat is! Mindegyik
példa esetében a kód szintaktikai "kerete" a következő:
#include
<stdio.h>
void main()
{
// ide jön a példa kódja
}
A for
ciklus szintaktikája és használata:
Képzeljük el, hogy van egy tömbünk, amelyet
fel akarunk tölteni a megfelelő elemekkel, vagy éppen ki akarjuk olvasni az
elemeket. Ilyen tömb a karaktertömb is, amelyben a C-nyelv keretei között
szövegeket tárolunk. Feladatunk például a karakterek, azok indexének és ASCII
kódjainak kiírása adott szövegben.
char szoveg[6] = "almafa";
for (int j=0; j<6; j++)
printf("\nA tömb %d. eleme: %c ", j, szoveg[j]);
Akkor is for
ciklusra esik a választásunk, amikor szükségünk van egy lépésenként növekvő
vagy csökkenő változóra, például ki akarjuk írni a négyzetszámokat ezerig.
for (int i=0; i*i<1000; i++)
printf("%d ", i*i);
Elemezzük a kódokat! A for ciklus fejének első utasításában előkészítjük a ciklust,
kezdőértéket adunk a ciklusváltozónak. A második paraméter adja meg, hogy
meddig fusson a ciklus - ez a feltétel kifejezés is lehet. Ha a feltétel nem
igaz, a ciklus leáll. Az utolsó pedig a léptetési
utasítás, „i++” a ciklusváltozó értékét eggyel növeli. Persze nagyobb lépésköz
is megadható, például: i = i + 2, de elegánsabban: i += 2. Figyeljük meg azt
is, hogy a printf() függvény egy ún. format sztringet
kap paraméternek, ezzel tudunk formázott érték kiíratásokat végezni.
Az iterációk között olyan is előfordulhat,
hogy nem tudjuk előre, meddig ismétlődjön egy utasítás(blokk),
hanem feltételhez szeretnénk kötni az ismételt végrehajtást. Ezekre mind kínál
a C megoldásokat - rögtön kettőt is - a rá jellemző áttekinthetően felépített
elegáns formában.
Elsőként a while ciklust tárgyaljuk, egy tipikus algoritmus keretében, amikor
számokat kérünk be végjelig (-1) ezeket összegezzük és kiszámítjuk, majd
kiírjuk a bevitt számok átlagát:
float szam=0, atlag=0;
int ct=0;
//úgynevezett előolvasást végzünk
printf("\nKérek egy számot, kilépés (-1): ");
scanf("%f", &szam);
while (szam != -1) { // kezdődik a ciklus
ct++; //segédváltozó, számolja a bevitt számokat
atlag += szam;
//beolvasás a ciklus belsejében, a következő iterációhoz
printf("Kérek egy számot, kilépés (-1): ");
scanf("%f", &szam);
} // ciklus vége
//kiszámítjuk és kiírjuk az átlagot, ha volt értékbevitel!
if (ct != 0) {
atlag /= ct;
printf("A beolvasott számok átlaga: %f", atlag);
}
A kommentek
magukért beszélnek, a változók is ún. "beszédes" azonosítók, tehát
látható rajtuk, mit tárolnak. Érdekes megfigyelni még a beolvasást is, amikor a
scanf() függvény a formázó karakternek megfelelően
(%f, azaz float) olvassa be a billentyűzetről, a standard inputról az adatot és
ezt a (&) címképző operátorral a változó címére írja a memóriában.
Mi van azonban akkor, ha a ciklusnak egyszer
mindenképpen le kell futnia - mint például egy menü megjelenítésekor? Ennek
szintaxisa a do-while ciklus, amit
most egy egyszerű menü elkészítésén keresztül mutatunk be:
int s ;
do {
printf("\nEgyszerű menü:");
// a menüpontok kiíratás
printf("\n1. menüpont (1) \n2. menüpont (2) \n3. menüpont (3) \n kilépés (0)\n"); a
scanf("%d", &s); // a pontválasztó szám beolvasása
// az esetszétválasztást a már ismert switch szerkezet végzi:
switch(s) {
case 1 :
printf("\n 1. menüpont végrehajtva");
break;
case 2 :
printf("\n 2. menüpont végrehajtva");
break;
case 3 :
printf("\n 3. menüpont végrehajtva");
}
} while (s != 0) ;
Mit keres a switch szerkezetben a break
utasítás? Azt, amit a neve sugall (törés), ezen a ponton a végrehajtás a
blokkból kilép és az utána következő első utasításra
ugrik. E nélkül - a belépési ponttól függően - a többi case utasítás is végrehajtásra kerülne. Használjuk ciklus
belsejében is, ha valami bonyolult, többrészes feltétel van, ami nem kezelhető
le jól a ciklus fejében - erre jó példa lehet egy játékprogram, ahol a játék
többféleképpen érhet véget.
A másik utasítás, amit szintén itt illik
megemlíteni, a continue. Ezt akkor
használjuk, ha valamiért szeretnénk kilépni a ciklus aktuális futásából és a
következő iterációval kívánjuk folytatni a program
végrehajtását - mondjuk, valami oda nem való érték került be a ciklusba vagy az
adott értéknél nincs értelme az aktuális iteráció végrehajtásának.
Persze a continue
hatására a ciklus tovább pörög, a következő körrel folytatjuk, amíg a ciklus
belépési vagy bentmaradási feltétele igaz nem lesz.
Akkor hát stílszerűen kiadjuk magunknak is a continue utasítást, ennyit erre a
hónapra, remélem a következő hónapban is megtisztelnek
érdeklődésükkel.
Szelei
Tamás - d4mi3n@mail.com