Kezdőoldal » Számítástechnika » Programozás » Pascal: fájlokból rekordokba...

Pascal: fájlokból rekordokba történő beolvasási probléma? (bővebben lent)

Figyelt kérdés

Van egy adatbázis, amelyben az adatok egyszerűen, "," karakterrel elválasztva szerepelnek. Ezeket szeretném beolvasni rekordokba.

A program bizonyos fájlnál kiakad, tapasztalataim szerint az 5. fájlnál. Nem tudom, ez memória hiba -e, vagy másnak köszönhető.

Ez az adatbázis konkrétan a GTFS adatbázis, amely a BKK menetrendet tartalmazza.

Mondjuk nem csodálom, ha kiakad, mert az összes fájl mérete 322 MB körül van, igaz gépben 3 GB van, de nem tudom miként kezeli a memóriát a program.

Mit lehetne tenni, hogy a memóriában elférjen, "packed record"-ot használni vagy egyebet?

Aki tud más programozási nyelven megírt kódot, ami jól lekezeli, az érdekelne.

Python-t találtam, de az egyenlőre számomra még túl bonyolult, szerteágazónak tűnik mert nem értek hozzá. :-(

Egyenlőre Pascal-ban szeretném megoldani, ha ez lehetséges.

Az általam írt program hivatkozása:

pastebin(pont)com/bgtsp98N

A GTFS adatbázis:

[link]

A program relatív útvonalon keresi a fájlokat, tehát zip fájl kicsomagolása után a fájlok mellé másolva aktuális könyvtárban nyitja meg őket.

A fájl első sorát azért nem teszem be sehova, mert a fájlok első sora mindig a fejléc, arra pedig nincs szükségem, mert azért hoztam létre a rekordokat.

Olvas függvényben a "pos" eljárással elegánsabb lett volna léptetni és abban sem vagyok biztos, ha üres egy mező (",,") azt jól kezeli -e, bár ekkor elvileg a hossza 1 és nem tartalmaz karaktert...

Mit csináltam rosszul?



2018. dec. 5. 18:10
1 2 3
 21/28 tabaki ***** válasza:

@#16: „...ez a rendkívül egyszerű split nagyon jó, ami kommentem előtt olvasható.”

Azért továbbra is gondolj arra, hogy nem mindegyik vessző adatelválasztó is egyben. Ennek a problémának a kezelését én nagyon primitíven oldottam meg, vagyis veszedelmes bizalommal feltételeztem, hogy a címekbe írt vesszők után mindenütt hibátlanul kitették a szóközt. Valójában arra illenék figyelni, hogy az idézőjelek közti részekben szereplő vesszők azok, amelyeket nem elválasztóként kell értelmezned, hanem a szöveg részeként.

2018. dec. 9. 00:28
Hasznos számodra ez a válasz?
 22/28 A kérdező kommentje:

Nekem "3.0 RC2" fordítóm van, nem gondoltam, hogy ez lehet a hiba forrása, de ezekszerint igen.


Hát igen, "lenne még hova fejleszteni". :-)

Egy kedves illető nagyon sokat segített nekem, megmutatta, miként lehet SQL-be importálni a táblákat. :-)

Ha ezt ismertem volna, szerintem nem megyek Pascal-irányba. :-)

SQL-ről hallottam már, de eddig még soha nem használtam.

2018. dec. 9. 03:45
 23/28 anonim ***** válasza:

A file-okban hatalmas a redundancia.

Ezt lehet csökkenteni, méghozzá jelentősen, ha a redundáns adatokat rövidítjük és pl. Csillaghegy helyett csak Csh-t tárolunk, vagy a földrajzi koordináták esetén elhagyjuk a "47."-et és a "19."-et, mivel ezen adatokat úgy is tudjuk. Tök fölösleges harmincezerszer eltárolni őket. Csak ezzel az egy lépéssel 6 byte-ot nyerhetünk soronként.

De van lehetőség a time stamp-ek és egyebek kompresszálására is. >>BKK<< hatmilliószor??? OMG!

Összességében a 315 MB-nyi adat letárolható kb. a felére, 150 MB-ra, tömörítetlenül.

A beolvasás meg nem úgy megy, hogy soronként, mert a vizet sem cseppenként töltjük a pohárba, hanem be kell olvasni a memóba és ott memorystream-ként kezelni, ami fénysebességet jelent a feldolgozásnál a soronkénti vergődéshez képest. Így megszűnik a bottleneck. A soronkénti beolvasás iszonyú lassú, mert azt már az opre végzi, ráadásul annyiszor, ahány sor létezik. Ez horror.

Nem vagyok abban sem biztos, hogy a kérdező nyer bármit is az SQL-re konvertálással, de ő tudja mit csinál.

2018. dec. 9. 08:14
Hasznos számodra ez a válasz?
 24/28 A kérdező kommentje:

Én is így látom, amit írtál, az egyszerűsítésre gondoltam is, dehát a GTFS formátum márcsak ilyen...

Az volt a célom, hogy a táblákat egyben lehessen kezelni, lekérdezésekkel és ezt az SQL-be konvertálás megvalósította.

Tényleg a memóriába lett volna érdemes beolvasni, majd ezután egyben elvégezni rajta a kívánt műveletet és nem soronként olvasva.

2018. dec. 9. 08:46
 25/28 anonim ***** válasza:

"10: Dehogy. A pascalban a stringek memóriafoglalása erősen implementáció függő, de a freepascal-ra hagyatkozva, abban legalábbis egészen biztosan optimális, ami annyit tesz, hogy a szükséges memóriaméretet foglalja le csak, annál egy bytettal sem többet."


Amit utána írtam még lehetséges változatot ezen kívül azt mintha nem vennéd figyelembe. Meg úgy írod mintha az operációs szintű heap kezelés az mindig optimális lenne, mintha a lyukak mindig optimálisan helyezkednének el. Továbbá mintha nem kettő valahanyadik hatványa többszöröse szerint foglalódna le ténylegesen a memória oprendszer szinten.


"A short string (string[length]) meg végképp nem memóriafaló, mivel az a string tényleges hosszát foglalja, plusz egy karaktert ami a hosszat jelzi, valóban a nulladik indexen."


Az én hibám volt hogy nem volt egyértelmű hogy sima mezei string alatt kellett volna máshogy megfogalmazni hogy string[length]-et nem veszem bele,hanem csak a string-et így írva ebben a formában hogy "string".

Nem mondod hogy van egy sokelemes tömböd mely string[length] elemeket tartalmaz és mindegyik pontosan length hosszúságú kivétel nélkül. Pl ha string[40] akkor nincs egyetlen 39 hosszú se közte sose. Ha így lenne akkor meg azért nem a legoptimálisabb memória használatú mert akkor meg felesleges külön-külön mindnek tárolni a hosszát, hisz vakon elhisszük hogy pontosan 40 karakter hosszú lesz bármelyik is közülük mindig minden esetben.


"Hát ilyenek nincsenek, hacsak nem a UNICODE stringekre gondoltál, mivel azok 2 byte/char hosszúak, de hát, ezért állnak UNICODE karakterből. Ez nem pascal specialitás, másutt is ez az ábra, a unicode karakterek két byte-osak."

Tudom hogy nem pascal specialitás, de itt több részt is nem arról van szó, hanem többek között operációs rendszer szintű memória menedzsment. Egyébként meg ha tudnád hogy nem csak olyan változata van az unicode kódolásnak, az UTF-8 kódolás lehetett amire gondoltam ami változó hosszúságú kódolással képezi le a Unicode karaktertáblát, 1-től 4 bájtig lehet egyébként egy karakter hossza, ezt innen : "de pluszba hozzátesz hogy vannak karakterek melyek több bájtosok " lehetett volna vágni hogy erről volt szó, csak konkrétan nem neveztem meg. Ha meg azt a változatot vesszük amire gondoltál az több memóriát eszik általában.


"Szóval a C ajánlgatása, éppen string-manipulációs célra nem volt túl jó ötlet a pascallal szemben, mivel köztudott, hogy ha valaminek, hát éppen a C-nek nincs semmiféle string-kezelő függvénye"

Igen és a string.h-ban sincs semmi string kezelő művelet. Egyébként meg az a c inkább c++ akart lenni, lehet nem voltam egyértelmű.


"ősidők óta tartalmaz efféléket, nem is unit, hanem mindjárt natív nyelvi szinten (persze ez implementáció függő)"

Azt inkább adott implementációbeli fícsörnek mondanám, amitől a hajam is égnek áll. X verzióba valaki leporgramozta kihasználva azt a fícsörét, nálam meg az Y verzióba nem megy vagy éppen fordítva.


"Nagyon köszönöm mindenki hasznos válaszát, ez a rendkívül egyszerű split nagyon jó, ami kommentem előtt olvasható.


Nagyon köszönöm annak is, aki megírta Pascal-ban a split-et, ráadásul Python-ban is megírta."


Szívesen, bár ahogy írják így még se válaszható el mivel nem minden vessző elválasztó is egyben.

2018. dec. 10. 12:06
Hasznos számodra ez a válasz?
 26/28 anonim ***** válasza:
Még az jutott eszembe, hogy szerintem csv fájlkezelő kellene neked ha pascalba oldod meg akkor pascalba, ha bármi másba akkor is. Szóval pascal esetén ilyen unit után kell nézni.
2018. dec. 10. 12:29
Hasznos számodra ez a válasz?
 27/28 anonim ***** válasza:

25:


"Meg úgy írod mintha az operációs szintű heap kezelés az mindig optimális lenne, mintha a lyukak mindig optimálisan helyezkednének el. "


Persze, hogy nem, hiszen multitaszk rendszereknél az optimális memóriafoglalás csak elérhetetlen álom. Ezért is van reallokáció, címfordítás, virtuális cím, stb. De ez nem a pascal hibája.



"Nem mondod hogy van egy sokelemes tömböd mely string[length] elemeket tartalmaz és mindegyik pontosan length hosszúságú kivétel nélkül."


Nem. Én azt mondom, hogy ha a tömböm mondjuk 30 elemű és az elemek hossza pl. 7 char, akkor, még ha a karakterhelyek fele-harmada nincs is kihasználva, akkor is jobban járok ezzel, mert így a tömböm belefér egyetlen string foglalásba ((30 x (7+1) = 240) < 256) harminc helyett.


"Azt inkább adott implementációbeli fícsörnek mondanám, amitől a hajam is égnek áll. X verzióba valaki leporgramozta kihasználva azt a fícsörét, nálam meg az Y verzióba nem megy vagy éppen fordítva."


Hát, ez a sport ilyen. ANSI C, WATCOM C, Borland C, folytassam?


"Egyébként meg ha tudnád hogy nem csak olyan változata van az unicode kódolásnak, az UTF-8 kódolás lehetett amire gondoltam"


Ebben igazad van, én túlságosan hozzánőttem az UCS-2-höz, abban meg minden karakter két byte.


"bár ahogy írják így még se válaszható el mivel nem minden vessző elválasztó is egyben."


Ez nem akkora probléma, hiszen az idézőjelek párban állnak és azokat fel lehet használni a delimiter vizsgálatának ideiglenes felfüggesztésére (boolean).

2018. dec. 10. 13:24
Hasznos számodra ez a válasz?
 28/28 anonim ***** válasza:

"Persze, hogy nem, hiszen multitaszk rendszereknél az optimális memóriafoglalás csak elérhetetlen álom. Ezért is van reallokáció, címfordítás, virtuális cím, stb. De ez nem a pascal hibája."

Nem is állítottam hogy annak a hibája lenne, csak hogy nem optimális mint írtad.


"Nem. Én azt mondom, hogy ha a tömböm mondjuk 30 elemű és az elemek hossza pl. 7 char, akkor,..."


Ezt tudom, csak úgy lehetett érteni.


"Hát, ez a sport ilyen. ANSI C, WATCOM C, Borland C, folytassam?"


Az ANSI C kakukktojás hiszen az egy standard c szabvány. Azoknál is csúnya dolog az ilyesmi fajta fícsör, éppen ezért szigorú szabványkövetés megkövetelésére érdemes beparaméterezni a fordítót, láttam már céget hogy így is teszi.

"szemben a pascallal, amely más ősidők óta tartalmaz efféléket, nem is unit, hanem mindjárt natív nyelvi szinten (persze ez implementáció függő)."

Még ehhez kiegészítés. Nem tartom többre azt hogy natív nyelvi szinten benne van, vagy pedig a standard keretrendszer része mint pl c esetében a string.h.


"Ez nem akkora probléma, hiszen az idézőjelek párban állnak és azokat fel lehet használni a delimiter vizsgálatának ideiglenes felfüggesztésére (boolean)."


Igen meg még a különböző esetek amibe kár bele is menni most, ami nem feltétlenül fordul elő ezekben a fájlokban, de akkor már legyen egy normális implementáció ami képes helyesen kezeli a különböző eseteket. Ezért mondom, hogy inkább egy meglevő csv parser-t használjon hozzá, hiszen ezek tulajdonképpen csv fájlok, csak txt-nek van a kiterjesztése.

2018. dec. 10. 21:02
Hasznos számodra ez a válasz?
1 2 3

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

A weboldalon megjelenő anyagok nem minősülnek szerkesztői tartalomnak, előzetes ellenőrzésen nem esnek át, az üzemeltető véleményét nem tükrözik.
Ha kifogással szeretne élni valamely tartalommal kapcsolatban, kérjük jelezze e-mailes elérhetőségünkön!