Szerző Téma: Gvar vagy sima tömb változók lenne jobb egy házrendszerbe?  (Megtekintve 1558 alkalommal)

Gvar vagy sima tömb változók lenne jobb egy házrendszerbe?
« Dátum: 2013. szeptember 16. - 23:22:15 »
0 Show voters
Szeretnénk írni egy saját házrendszert.
Tegyük fel, hogy mondjuk, 4000 házat szeretnénk létrehozni.
Én úgy tudom, hogy maximum a pawno-ba 1024 körül van a tömbök mérete.
Ha 4 ezer házat szeretnénk létrehozni, akkor csak gvar maradt mint lehetõség?
Viszont a gvar sokkal lassabb mint a sima változók, és egy ilyen nagy adatmennyiségnél ez hátrány.
« Utoljára szerkesztve: 2013. szeptember 16. - 23:23:55 írta bbTamas »

Gvar vagy sima tömb változók lenne jobb egy házrendszerbe?
« Válasz #1 Dátum: 2013. szeptember 17. - 08:28:18 »
+1 Show voters
A 4000-et még simán elbírja a sima tömb változó is, sõt még annál többet is csak figyelni kell a stack/heap méretére és ha kell akkor meg kell növelni a #pragma dynamic segítségével a megfelelõ méretre.



#include <a_samp>
public
OnFilterScriptInit()
{
new
teszt[4000];
for(new i; i < 4000; i++)
{
teszt = random(4000);
printf(\"%d\", teszt);
}
return 1;
}

 
 

Stack/heap size:      16384 bytes; estimated max. usage=4010 cells (16040 bytes)
1 cells = 4 bytes

Nem elérhető Flash

  • 5726
  • (っ◕‿◕)っ
    • Profil megtekintése
Gvar vagy sima tömb változók lenne jobb egy házrendszerbe?
« Válasz #2 Dátum: 2013. szeptember 17. - 11:35:03 »
+1 Show voters
4000 háznak felesleges a GVar, írd meg sima változókkal és ahhoz plugint se kell felhasználnod.

Nem elérhető krisk

  • 2380
    • Profil megtekintése
Gvar vagy sima tömb változók lenne jobb egy házrendszerbe?
« Válasz #3 Dátum: 2013. szeptember 17. - 16:14:33 »
+1 Show voters
A GVar annyira jó, hogy ha több scripten (fs/gm) között szeretnél változókat tárolni, akkor abban egyszerûbb.
Ezen kívül teljesen felesleges használni, mivel nem támogat több adattípust, mint a PAWN.
Elméleti síkon ha a stacked elég nagy a tömbhöz, akkor rendben van. Mivel a PAWN compiler fordítása során a célplatformnak megfelelõen állítja be a \"cella\" méretét, ezért ez változni fog. A SAMP által használt PAWN fordító 32 bites platformra készült, tehát 1 cella 32 bit = 4 bájt.
Ennek megfelelõen az integer max 32 bites = 1 cellás lehet.
Tehát azon függvény kezeléséhez, amiben használod majd a változót, alsó hangon is 4000 cella = 16000 bájtnyi stack terület szükséges. Ez azt jelenti, hogy amint a függvény meghívódik, 16000 bájt (~ 15 kb) stack terület lefoglalódik, nagyobb scripteknél ezért ajánlatos, ha már van bekalibrált stack méret, a 4000 cellát HOZZÁADNI, ha még nincs, akkor úgy bekalibrálni, hogy a többszörösen beágyazott függvények esetében se fussál ki a stack területbõl, mert akkor szimplán ki fog fagyni a szerver.
Már alapból a függvény meghívása során pluszba adódnak a stackre rápakolt egyéb adatok (visszatérési pointer, stb.), így jön ki a Zsoleszka által leírt 4010 cella.
« Utoljára szerkesztve: 2013. szeptember 17. - 19:41:26 írta krisk »

Gvar vagy sima tömb változók lenne jobb egy házrendszerbe?
« Válasz #4 Dátum: 2013. szeptember 17. - 21:13:54 »
0 Show voters
Nekem a GVar által kívánt adattípusok megfelelnek, és tetszik az benne, hogy dinamikusan foglalja a memóriát, és nem növeli az amx fájl méretét, és nem kell tömb mérete miatt aggódni.
Nagy amx fájlméret egyenértékû, lassabban fut a szerver?
Viszont egyesek szerint lassabb, de én nem ezt olvastam.
Viszont a tömbök elvben gyorsabbak mint a dimanikus memória.
Elvben meddig növelhetõ tömbök mérete #pragma dynamic -al?
Ezt a felíratott, hogy lehet elõcsalni a fordítóból?
 
Stack/heap size:      16384 bytes; estimated max. usage=4010 cells (16040 bytes)
1 cells = 4 bytes

 
Szerintetek melyik lenne a jobb választás?
Mert a 4 ezres szám nem egy köbe vésett érték, lehet sokkal több is.
A legfontosabb melyik a stabilabb?
Tudom, hogy sokat kérdezek, de nem sok információt találok a gvar-ról.
« Utoljára szerkesztve: 2013. szeptember 17. - 21:16:31 írta bbTamas »

Nem elérhető krisk

  • 2380
    • Profil megtekintése
Gvar vagy sima tömb változók lenne jobb egy házrendszerbe?
« Válasz #5 Dátum: 2013. szeptember 18. - 18:52:47 »
+1 Show voters
A fenti adatot úgy lehet kicsalni a fordítóból, hogy valami extrém kicsire állítod be a stack méretet a
 
#pragma dynamic [szám]

 
direktívával. A fordító minden olyan esetben kiírja a hibát, ha gyanítja, hogy a többszörösen beágyazott függvények esetén felmerülhet az a gyanú, hogy stack overflow történhet (ez gyk. azt jelenti, hogy a lentrõl felfele növekvõ stack belír az \"elõtte\" lévõ memóriába - ezt a SAMP szerver egy elegáns azonnali kilépéssel reagálja le).
Dinamikusan foglalja a memóriát: ez bajos. A dinamikus memóriával nagyon óvatosan kell bánni. Kicsi figyelmetlenség és lesz egy rohadt nagy memórialyuk (vagy ki tudja, hogy hívják ezt magyarul, memory leak) a SAMP szerveredben. Ezt így kell érteni:
 

RandomFuggveny()
{
   for(new i=0; i<5000; i++)
   {
      SetGVarInt(\"teszt\",i,i);
   }
}
main()
{
   RandomFuggveny();
   return 1;
}

 
A fenti kód hibája, hogy a lefoglalt memóriát nem szabadította fel a heap-bõl, ezzel okozva egy \"memórialyukat\", mely a szerver futásáig megmarad. Nyilván, ha ez a memórialyuk egy többször használatos függvényben fordul elõ, akkor minden egyes meghíváskor elszivárog ez a memóriamennyiség, elõbb utóbb kifogyva a lehetséges memóriából. Még a világklasszis programokban (khm, Windows, khm, Firefox) is nem egy ilyen hiba van, és ha õk elkövetik, te is el fogod.
A változók maguk nem foglalnak helyet a PAWN kódban, mivel a PAWN csak a változó helyére mutató pointert raktároz el (amennyiben a változó globális). Lokális változók esetén pedig a \"fájlnövekedés\" annyi, hogy pár bájttal több az assembly kód (hiszen 0x0FA0 több, mint mondjuk 0x64, az elõbbi csak 2 bájtba fér be).
A felhasznált memória, amennyiben a tömböket lokálisan [függvényen belül] akarod használni, csak addig lesz nagy, amíg a függvény futása zajlik. A függvény visszatérése után a stackrõl lepakolódik a változó és a változó miatt lefoglalt memória, önmagától (ezért a dinamikus memória esetén leírt memóriaszivárgás nem probléma).
Az elérés sebessége lassabb lesz (ez az ún. \"overhead\" miatt van, a pluginban elérhetõ függvények lefuttatása több idõbe telik), DE a plugin kevesebb memóriát fog enni, hiszen annyit foglalsz csak le, amennyi kell.
Fontos továbbá, hogy a GVar plugin (szándékosan) nem támogat komplexebb adatstruktúrákat, ha valami olyat szeretnél, akkor muszáj lesz a stack változókat használni.
Elméleti síkon egyébként a maximális tömbhossz az, ami egy cellát teljesen túltölt (4 bájt), de ezt nyilván nem fogod elérni, mivel annyi kocsit az életbe nem fogsz lerakatni a SAMP-pal.
« Utoljára szerkesztve: 2013. szeptember 18. - 18:59:18 írta krisk »

Gvar vagy sima tömb változók lenne jobb egy házrendszerbe?
« Válasz #6 Dátum: 2013. szeptember 18. - 20:26:31 »
0 Show voters
Az elérés sebessége lassabb lesz (ez az ún. \"overhead\" miatt van, a pluginban elérhetõ függvények lefuttatása több idõbe telik), DE a plugin kevesebb memóriát fog enni, hiszen annyit foglalsz csak le, amennyi kell.
Érdekes én ennek pont az ellenkezõjét tapasztaltam.
Csináltam egy tesztett GVAR-ral.
Létrehoztam egy tömböt amely Float tizedestört értékeket tartalmaz.(Négy jegyû és négy tizedesjegy pontosságú).
Abból kiválasztottam véletlenszerûen egy értéket, és annak az értékét hozzárendeltem egy változóhoz.
 
        start = GetTickCount();
for(new i2 = 0;i2 < 3000000;i2++)
{
new rand = random(sizeof(randspawn));
SetGVarFloat(\"gvarfloat\",randspawn[rand][0],i2);
}
end = GetTickCount();
        printf(\"Változók létrehozása, és a változókhoz értékek hozzárendelése %d ezredmásodpercig tartott\",end-start);

 
2584 ezredmásodperc ~ 2,6 másodperc.
Feladatkezelõben 837mb írt ki a samp-server.exe
Úgyanezt sima tömbbel csinálva \"csak\" 27 mb-t ír ki.
Sima tömbbel ahogy sejteni lehetett sokkal gyorsabb 496  ezredmásodperc ~0,5 másodperc alatt létrehozta a változókat.
« Utoljára szerkesztve: 2013. szeptember 18. - 20:30:18 írta bbTamas »

Nem elérhető krisk

  • 2380
    • Profil megtekintése
Gvar vagy sima tömb változók lenne jobb egy házrendszerbe?
« Válasz #7 Dátum: 2013. szeptember 18. - 20:42:31 »
+1 Show voters
Az elérés sebessége, ahogyan te is leírtad, lassabb pluginnal (amit leírtál, abból én azt veszem ki, hogy erre a konklúzióra jutottál).
A memória, pedig ahogy leírtam, csak akkor lesz kevesebb, ha pont annyit foglalsz le, amennyi kell neked. Ha egy 20 slotos szerón éppen csak 5-en vannak, akkor nem kell a maradék 15 blokkot létrehozni. A plugin futtatása eleve memóriát eszik, de a lefoglalt memória mértékét jobban lehet optimalizálni a pluginnal. Ennek az ára a fenti \"memóriaszivárgás\": egy apró figyelmetlenség és hamar kifagyhat a szerver.
« Utoljára szerkesztve: 2013. szeptember 18. - 20:45:55 írta krisk »

Gvar vagy sima tömb változók lenne jobb egy házrendszerbe?
« Válasz #8 Dátum: 2013. szeptember 19. - 00:57:35 »
0 Show voters
Most az én gvar-os példámban \"memóriaszivárgás\" történt, azért foglalt le a samp-server.exe magának 800mb-t? Ha számít main() függvény alá raktam a kódot.
Memóriaszivárgás nem értem száz százalékosan.
Holnap újra nekifutok ennek a megértésére.
« Utoljára szerkesztve: 2013. szeptember 19. - 00:59:42 írta bbTamas »

Nem elérhető krisk

  • 2380
    • Profil megtekintése
Gvar vagy sima tömb változók lenne jobb egy házrendszerbe?
« Válasz #9 Dátum: 2013. szeptember 19. - 13:18:24 »
0 Show voters
A memóriaszivárgás a következõ:
a dinamikusan lefoglalható memória azért dinamikusan lefoglalható, mert egy adott hosszúságú memóriaszakaszt lefoglalhatsz saját használatra az ún. \"heap-bõl\" (az most lényegtelen, hogy mi, ha érdekel, elmondom). A memóriaszakasz hosszát nem kell meghatároznod futtatás elõtt, elég futtatás alatt. Ettõl \"dinamikus\". A memóriaszakaszt azonban, amennyiben a használat után nem szabadítod fel, keletkezik egy \"lyuk\"  -- azaz a memória, amit lefoglaltál, elveszik: hisz nem szabadítottad fel.
Pl. ha egy függvényben 2 kb memóriát lefoglalsz, de a függvény végeztével nem szabadítod fel, minden egyes alkalommal, mikor a függvény lefut, 2kb memória el fog veszni. Ez elõbb utóbb a memória kikezdésével fog járni.
Az a memória, amit lefoglaltál a ciklusoddal, ott marad a samp szerver névterébe, mivel a használat után nem szabadítottad fel. Az, hogy önmagában mennyi memóriát eszik a plugin, könnyû kideríteni: fogd a plugint, és indítsd el egy tök üres scripttel, nézd meg, mennyit foglal. Ha már magától is sokat foglal, akkor mérlegelni kell, hogy hosszú távon megtérülhet-e a használata.
A memóriaszivárgás nem akkora nagy probléma a GVar pluginnal, mivel a változóknak van id-jük és nevük, de pl. egy C++-ban ha a függvényben, amiben lefoglaltad a memóriát, nem szabadítod fel, akkor elveszik a mutató a memóriára, tehát egy végleges vesztésrõl beszélünk.
Amit meg kell jegyezni: a dinamikus memória esetén TE kezeled azt, hogy mennyit foglalsz le, és mennyit szabadítasz fel. Ha nem szabadítod fel, akkor a memória ott fog maradni a szerver névterében, használatlanul, addig, míg le nem állítod azt.
« Utoljára szerkesztve: 2013. szeptember 19. - 13:21:36 írta krisk »

Gvar vagy sima tömb változók lenne jobb egy házrendszerbe?
« Válasz #10 Dátum: 2013. szeptember 20. - 19:41:53 »
0 Show voters
Érdekel a téma szívesen meghallgatom, mert errõl például sehol nem olvastam. Azt vettem ki, hogy azért foglalt le 800mb server.exe mert nem szabadítottam fel a memóriát, ott maradt a server névterében.
De most ez a memóriafelszabadításos nem világos.
SetGVarFloat beállítom a változó értékét.
DeleteGVar törlöm magát a változót.
Ha létrehoztam a változót akkor utána hogyan \"szabadítsam\" fel? Mert 800mb akkor is sok, sima változóhoz 27 mb-jához képest.
Értem, hogy nyilván akkor szabadítsam fel, amikor már nincs rá szükségem, de pl:. házrendszernél szükség van az összes változóra nem törölhetem.

Nem elérhető krisk

  • 2380
    • Profil megtekintése
Gvar vagy sima tömb változók lenne jobb egy házrendszerbe?
« Válasz #11 Dátum: 2013. szeptember 21. - 15:12:20 »
0 Show voters
Jól gondolod. Az én véleményem az (volt, és marad is), hogy PAWN esetében nem igazán érdemes használni semmiféle dinamikus memórián alapuló dolgot. Alapjában véve konstans dolgok tárolásához meg még annyira sincs értelme.
Ha tényleg, tényleg szeretnél dinamikus memória allokációt, és nincs szükséged a scriptek közti elérésekre, van rá egy y_malloc nevû függvénykönyvtár, Y_Less írta a C-s malloc/alloc/free függvények alapján. Elvileg gyorsabb és mivel alap PAWN, nem plugin, ezért gyk. 0 memóriafogyasztással rendelkezik.
De, mint mondtam, alapjában, fõleg egy házrendszer adataihoz, fölösleges dinamikusan lefoglalható memória.
« Utoljára szerkesztve: 2013. szeptember 21. - 15:14:07 írta krisk »

Gvar vagy sima tömb változók lenne jobb egy házrendszerbe?
« Válasz #12 Dátum: 2013. szeptember 21. - 15:18:16 »
0 Show voters
Köszönöm mindenkinek a segítséget, és a választ. :)
Maradok a sima tömbnél mert gyorsabb és nem kell törõdni memóriakezeléssel se.
Külön köszönet krisk-nek. :)
Mindenki kapott egy pontott.

 

SimplePortal 2.3.7 © 2008-2024, SimplePortal