A Goto esetén említésre került a ciklus fogalma. A ciklusok a programozás alapvető eszközei, ismétlődő feladatok végrehajtására szolgálnak. Kontrollált (nem végtelen) ciklust if utasítás és a goto kombinálásával hozhatunk létre, ahogy az alábbi példán is látszik:
using System;
namespace PeldaGotoCiklus
{
class Program
{
static void Main(string[] args)
{
Console.WriteLine("Goto ciklusszervezés");
int szamlalo = 0;
ciklus:
if (szamlalo < 10)
{
Console.Write($"{szamlalo}, ");
szamlalo++;
goto ciklus;
}
Console.ReadKey();
}
}
}
A program kimenete:
Goto ciklus szervezés
0, 1, 2, 3, 4, 5, 6, 7, 8, 9,
A fenti példa kód nagy problémája az, hogy a ciklus valódi kódrészlete (az if utasítás blokkjában szereplő utasítások) nem különül el jól a címkétől. Ezen probléma orvoslására vezettek be különböző típusú ciklusokat. Ezek közül az egyik legalapvetőbb a for ciklus, amit szoktak számláló ciklusnak is nevezni. Ennek oka az, hogy n alkalommal hajtja végre a ciklusmag utasításait.
A for utasítás működését és szintaxisát egy rövid példán keresztül a legegyszerűbb elmagyarázni:
for (int i=0; i<10; i++)
{
//Ciklusmag
}
A fenti kódrészlet tíz alkalommal ismétli a ciklusmagban elhelyezett utasításokat. A for utáni zárójelben található a ciklus vezérlése. Az int i=0; utasítás létrehozza a ciklus változót. Ez fogja tárolni, hogy hány alkalommal futott le a ciklus. A ciklusmagon belül értékét felhasználhatjuk. Az i < 10; utasítás a végfeltételt határozza meg, vagyis azt, hogy meddig ismétlődjön a ciklus végrehajtása. Az i++ utasítás az iteráció, vagyis az az utasítás vagy utasítás sorozat, amely segítségével a ciklus változó a kezdeti értékből el tud jutni a vég feltételbe.
Értelemszerűen, ha a vég feltétel és az iteráció nincs összhangban, vagy mondjuk az iteráció teljesen hiányzik, akkor végtelen ciklust kapunk. Az alábbi példa egy ilyen esetet mutat be:
for (int i=10; i>0; i++)
{
//végtelen lesz, mert i értéke növekszik minden futáskor
}
Valójában ez a ciklus nem lesz végtelen, mivel int típust használunk, ami a növelés miatt a gép sebességétől függően előbb-utóbb túlcsordul, de a ciklusmag utasításai így is lefutnak legalább 2 147 483 637 alkalommal, mire a túlcsordulás bekövetkezik, így nevezhetjük végtelen ciklusnak 🙂
Természetesen az iteráció és a vég feltétel is tartalmazhat tetszőlegesen bonyolult kifejezés sorozatot. Az alábbi példa néhány lehetséges alkalmazását mutatja be a for ciklusnak:
using System;
namespace PeldaFor
{
class Program
{
static void Main(string[] args)
{
Console.WriteLine("0 -> 10");
for (int i=0; i<10; i++)
{
Console.Write("{0}, ", i);
}
//itt már nem definiálhatunk i változót
//int i = 22;
Console.WriteLine("\n10 -> 0");
for (int i=10; i>=0; i--)
{
Console.Write("{0}, ", i);
}
Console.WriteLine("\n0 -> 60, minden 3.");
for (int i = 0; i < 60; i += 3)
{
Console.Write("{0}, ", i);
}
Console.ReadKey();
}
}
}
A program kimenete:
0 -> 10
0, 1, 2, 3, 4, 5, 6, 7, 8, 9,
10 -> 0
10, 9, 8, 7, 6, 5, 4, 3, 2, 1, 0,
0 -> 60, minden 3.
0, 3, 6, 9, 12, 15, 18, 21, 24, 27, 30, 33, 36, 39, 42, 45, 48, 51, 54, 57,
A fenti példában jól látszik, hogy ha a ciklus változónkat i néven hozzuk létre, akkor i néven nem definiálhatunk a ciklus után változót, de ugyanakkor i értékét nem tudjuk elérni a cikluson kívül. Ez némileg ellentmondás, mivel ha nem definiálhatunk ezen a néven, akkor a változónak léteznie kellene, de mivel nem érjük el, ezért azt feltételezhetnénk, hogy nem létezik. Mielőtt fordító hibára gyanakodnánk, ismerkedjünk meg a hatókör fogalmával.
Az i változó igenis létezik, azonban a hatóköre limitálva van a for ciklusra, mivel ott hoztuk létre. A fenti példában több ciklus is van, amiben definiáljuk i változót. Ez azért nem okoz fordítási hibát, mivel i változó szerepét definiáljuk felül egy újabb hatókörben, ami a program végrehajtásában csak később fog létezni, mikor már az előző ciklusnak vége van. Ebből adódóan ez nem jelent a működésben problémát.
Felmerülhet továbbá a kérdés, hogy miért pont i a változó neve? Ennek az oka a matematikában keresendő. Számos összegzési képletben i-vel van jelölve az ismétlés számlálása. Egy másik magyarázat szerint az i változónév az integer típus kezdőbetűjéből jön, mivel általában integer típussal van vezérelve egy ciklus. Sőt, ha belegondolunk, akkor egy ciklus csak egész számú alkalommal fog lefutni.
Ezen utolsó magyarázatot megerősíti az a tény is, hogy a Fortran, az egyik legrégebbi assemblynél1 magasabb szintű nyelvben i, j, k, l, m és n változónévvel lehetett csak integer típust létrehozni. Valószínűleg innen eredhet az, hogy ha több egymásba ágyazott ciklust látunk, akkor sorra i, j, k, l, m és n változónevekkel találkozhatunk.
-
Az assembly nyelv a gép bináris utasításkészletéhez legközelebb álló programozási nyelv. Nem keverendő össze a gépi kóddal, mivel az bináris utasítások sorozata. Az assembly viszont szöveges reprezentációja az adatoknak és az utasításoknak, amiből az assembler fordító gépi kódot tud készíteni.↩