Elmagyarázná valaki, mi történik ebben a kódban egyáltalán? (C)
Próbálom megérteni, hogyan működnek a C-ben a tömbök, de nem járok sikerrel. Deklarálok egy 10 elemű tömböt, aztán elkezdem feltölteni számokkal. Azt várnám, hogy 9-nél kidobjon egy hibaüzenetet, de ehelyett töltögeti fel tovább, és 2787-nél áll meg.
main()
{
int x[10], y, *p;
for(y=0;1;y++) {x[y]=y+1; printf("%d\n", x[y]);}
}
Nem azt kérem, hogy javítsuk ki a kódot, hanem azt szeretném megérteni, hogy EZ a kód, miért viselkedik úgy, ahogy, miért nem áll meg 10 elemnél, miért különleges a 2787, és mit jelent az, hogy "Szegmentálási hiba (core készült)"
"Csak azt nem értem, hogy miért megy tovább a 10. elemnél, amikor csak 10 van lefoglalva."
Azért, mert ha lefoglalsz egy 10 elemű tömböt az azt jelenti, hogy az a 10 elem méretű hely a tömbödé, oda csak az írhat, nem pedig azt, hogy azon kívül viszont nem írhatsz.
Ettől a C és a C++, hogy nincsenek ilyen managelt ellenőrzések, ettől gyors a kód, erre a programozónak kell figyelnie.
Valami más történik a két esetben, csak még most sem értem, hogy mi az.
int x[5] = {1, 2, 3, 4, 5}
esetben nem engedélyezett az, hogy x[5], mert x[4] a tömb utolsó eleme.
De ha a kérdésben szereplő kóddal hozok létre tömböt, x[y] bármilyen nagy y esetén is használható, még akkor is, ha nincs inicializálva, nem "memóriaszemetet" ad vissza, hanem nullát. Pont úgy, mintha
int z[10] = {1,2,3}
esetén z[7]-re hivatkoznék.
10-nél azért fut tovább mert ez egy végtelen ciklus:
for(y=0;1;y++)
a ciklus feltételnél csak egy 1 szám van megadva ezt a fordító úgy értelmezi:
for(y=0,true,y++) mivel true örökké igaz ezért ez végtelen ciklus.
Ez csak javaban történne így de ott is leállna a program ArrayIndexOfBound exceptionnel. Ami biztonságosabb ennél mert közbe valszeg a programod felülírta az eip-t 2708-as elemnél és amikor itt "kidobna" a program érvénytelen memóriacímre mutat. Ezt hívják buffer overflownak. ( puffer túlcsordulásnak). Ha javítani akarsz rajta akkor ne legyen végtelen a ciklus vagy tedd try catch ciklusmagot vagy használj std::vector-t a sima tömb helyett, persze ez inkább c++-os cucc c-ben csak annyitt tehetsz 1.) kihagyod a végtelen ciklust és csak 10 -ig mész 2.) A ciklusmagban ellenőrzöd 10-nél nagyobb-e a ciklusváltozó, ha igen kilépsz a ciklusból.
A fordítónak nem feladata ellenőrizni a tömbök indexhatárait, te csak annyitt "mondtál a gépnek" hogy 0-tól töltse fel a tömbödet az ciklusváltozó+1 értékkel és ez menjen örökké. egy alap for ciklusba csak egy feltétel van, emellet másmilyen ellenörzés nincs. ( hacsak a programozó be nem tesz ilyet kézzel).
Kapcsolódó kérdések:
Minden jog fenntartva © 2024, www.gyakorikerdesek.hu
GYIK | Szabályzat | Jogi nyilatkozat | Adatvédelem | Cookie beállítások | WebMinute Kft. | Facebook | Kapcsolat: info(kukac)gyakorikerdesek.hu
Ha kifogással szeretne élni valamely tartalommal kapcsolatban, kérjük jelezze e-mailes elérhetőségünkön!