Na! Ez itt a C rovat, és benne még mindig én. Akkor talán kezdjük is!

Ha már az előző számban a break, és continue utasításpárral foglalkoztunk, amit ugye nem szoktunk használni, de néha szükség lehet rá, nézzünk még egy ilyet.

GOTO utasítás és a címkék

Mint általában a programozási nyelvekben, a C-ben is létezik GOTO, így aztán címkék is. Ahogy mindenhol, a C-ben is az a valami címke, ami kettősponttal záródik. Tehát a GOTO azt csinálja, hogy a mögéje írt címkére ugrik. Azonban a ciklusvezérlő utasítások, és a függvényhívási lehetőség mára már csaknem feleslegessé tették használatát. Szükség azért lehet rá. pl.: 

1. olyan ciklust akarunk csinálni, ahol nincs ciklusfeltétel :

ciklus:
...
...
goto ciklus;

2. többszörösen egymásbaágyazott ciklusok mindegyikéből hirtelen kedvünk támad kilépni (leggyakoribb):

while(...)
{
for(...)
{
do
{
if (error) goto kakivan;
} while(...) 
}
}

kakivan:

printf("kakivan");

3. egyszerűen csak azt akarjuk, hogy lamernek nézzenek. 

Erre nem írok példát, mindenki válasszon tetszés szerint. (lehet bőven találni)

A GOTO elvileg csak olyan címkére tud ugrani, ami vele azonos függvényben van. Azonban vannak compilerek, amik megengedik a másik függvénybe való beleugrást. Hát ilyet akkor se tegyünk ,ha öten is bíztatnak, mert ettől aztán minden lesz a program csak strukturált nem. Persze az is kétséges, hogy működni fog-e. 

Mit is mondjak még, asszem ennyi.

BITMŰVELETEK

A C nyelv, lévén matematikai nyelv, ismeri a legáltalánosabb bitműveleteket:

& bitenkénti és

| bitenkénti vagy

^ bitenkénti kizáró vagy

~ egyes komplemens

! C nyelv logikai nem

<< balra léptetés

>> jobbra léptetés

Akik valamelyest otthon vannak assembly-ben, azoknak azt hiszem nem kell elmagyarázni, mit is jelentenek ezek a műveletek, akik pedig nincsenek, azoknak ajánlom figyelmébe az assembly rovatot. Az összes operátor működése megegyezik az az assembly párjával, kivéve a ! (nem). Mivel ez a nem , nem az assembly not utasítása, hanem egy logikai nem, ami annyit tesz, ha a paraméter nem nulla, akkor nulla lesz, ha nulla, akkor egy lesz.

Talán a jobbra, és balra léptetésre térnék ki egy kicsit. Ezek az utasítások remekül alkalmazhatók kettő hatványaival való villámgyors osztás, szorzás elvégzésére. pl.:

a= a<<4 ugyanaz, mint a=a*16

a=a>>7 ugyanaz, mint a=a/128

Hozzárendelési operátorok

Hangzatos nem? Ahhoz képest egy igen egyszerű dolgot jelöl. C-ben a kétváltozós műveletek (+,-,*,/ stb.) összekapcsolhatók az egyenlőséggel, ezzel új hozzárendelési műveleteket alkotva. pl.:

x -= 10;

ugyanaz, mint x=x-10;

vagy x >>= 2; ugyanaz, mint x=x >> 2; (vagy x /= 4;(ld. bitműveletek))

Használatukkal nem lehet semmi különöset, eddig ismeretlent elérni, de a program áttekinthetőbb lehet.

Szóval eddig lettek volna a C nyelv szigorúan vett alapjai. Persze ez nem azt jelenti, hogy ennyi ismerettel bárki is meg tudna írni bármilyen programot, de már jó valamire. Na igen most jut eszembe, hogy a tömbökről még egy árva szó nem esett. Látszólag még az alapokhoz tartozna, csak az a baj, hogy C-ben igencsak összefolyik a pointerekkel, na nem baj! Mivel gondolom unja már mindenki ezt a száraz rizsát, nézzünk már valami használható programot is. Csináljunk mondjuk egy buborékos rendezést. 

#define SZAM 12 /*ezt már ismerjük */
void main(void)
{ /*idáig ok*/
int szamok[SZAM]={1,2,7,5,3,8,9,4,2,9,0,6}; /*Na ez egy tömb*/
int i,x; 
int megen=1;
while(megen) /*ciklusok agyba-főbe*/
{
megen=0;
for(i=0;i<SZAM-1;i++)
{
if (szamok[i]<szamok[i+1]) /*ha a következő elem nagyobb, akkor csere*/
{
x=szamok[i];
szamok[i]=szamok[i+1];
szamok[i+1]=x;
megen=1; /*csere volt, újból át kell nézni a tömböt */
}//if
}//for
}//while
}//main

Ennyi a program. Hát, van baja. Először is nem írja ki a végeredményt, (szar ügy) másodszor is nem kérdezi meg a kedves felhasználót, milyen számokat (és hányat) kell rendbe tenni, hanem a saját adataival dolgozik, harmadszor is ez nem az igazi buborékrendezés, hanem annál lassabb. Ezeket természetesen korrigálni fogjuk, de most nézzük, mi is az a tömb (ha van aki esetleg nem tudná - igen valószínűtlen -).

Tehát a tömb olyan mint egy magas sokfiókos szekrény, aminek minden fiókja meg van számozva lentről felfelé(nem semmi hasonlatokat tudok ám...). A tömb elemei a fiókok. Az egyszerűség kedvéért C-ben ez a számozás nullától kezdődik, és a tömb elemei-1 -ig tart. A tömb elemei a memóriában címfolytonasan (egymás után) helyezkednek el. (majd a pointereknél lesz jelentősége) A tömb egyes elemeit ugyanúgy kezelhetjük, mint bármely más változónkat. A tömb egy elemére így hivatkozhatunk:

tombnev[elem]

Deklarálni is más változókhoz hasonlóan kell, csak szögletes zárójelben meg kell adni a tömb elemszámát. 

típus tombnev[elemszam];

Rögtön értékeket is adhatunk neki:

típus tombnev[elemszam]={...,...,...,...,};

Ha ezt megtesszük annyi értéket kell felsorolnunk amennyi eleme van a tömbnek.

Ja, egy tömb lehet több dimenziós is. Ez annyit jelent, a szekrényes példánál maradva, hogy most (egy egy dimenziós tömbnél) a fiók magasságával(ez a száma) egyértelműen meg tudom határozni az adott elemet, egy két dimenziós tömbnél pedig kell a magasság, és az oszlop is(ez egy nagy négyzet alakú szekrény). Három dimenziós tömböknél bejön a mélység(, négydimenziósnál pedig a téridő -ez poén akart lenni-). És így tovább a sokadik dimenzióig. Ezekkel majd később bajlódunk.

Most ennyit a tömbökről. 

Akkor nézzük meg a rendezés elvét. (Ez szintén közismert, de rekordot akarok önteni. Megírom életem leghosszabb cikkét).

Szóval az az ábra, hogy egymás melletti elemeket hasonlítgatunk, ha nem úgy állnak ahogy az nekünk tetszik, felcseréljük a kettőt. Az egyszerűség kedvéért nézzük a példánkat, a csökkenő sorrendbe való rendezést. Továbbléptünk egy elemmel, és ha az előbb felcseréltünk akkor megint azzal az elemmel lesz dolgunk ami az előbb nem felelt meg a helyén. Tehát ha az az elem a legkisebb, végig fogjuk hurcolászni a tömbön. Így aztán mire végigérünk a tömbön a legkisebb elem lesz a tömb végén. Azonban a többi elemmel nem törődtünk, azok össze-vissza állnak. Ezért újból el kell játszanunk az egészet. (Ezt a megen nevű változó biztosítja) Most már a legkisebbnél egyel nagyobb elemet fogjuk kivonszolni az utolsó előtti helyre. És így tovább megy a verkli, egész addig, amíg egyszer csak végigértünk visszafele a tömbön, és mindenki a helyén lesz. Ekkor a megen nevű változónk is nulla marad, és már kész is vagyunk. De ugye már mindenkinek feltűnt, hogy felesleges dolgokat is csinálunk. Mindig újból az egész tömbön végigmegyünk, holott tudjuk, hogy a vége már rendben van. (Az első menet után a helyén van a legkisebb, a második után a második legkisebb, és így tovább.) Ezt úgy oldhatjuk meg, hogy bevezetünk egy újabb változót, amit minden menet után növelünk, és a for ciklusunkban csak SZAM-menetszam-1 -et megyünk. Szóval az egyik hiba megvan. Egy másikat (végeredmény kiíratása) már ki-ki maga is meg kell(ene) hogy tudja csinálni. A számok bekérését is meg lehet már oldani ennyi ismeretanyagból, de ez a keményebb. Ha nem megy, csak erőltessük. Ha akkor se megy várjuk meg a következő számot, ahol is adok majd egy lehetséges megoldást. 

Első olvasatra lehet hogy egy kicsit tömény és érthetetlen, de nem kell csüggedni. Lesz ez még így se ! Nem kell visszariadni attól a kis gondolkodástól.

Hiszen a gondolkodásba még nem halt bele senki. (Szerk.: De lehet, hogy lesznek első áldozatok ... )