Kezdőoldal » Számítástechnika » Programozás » Több művelet elvégzése egyszer...

Több művelet elvégzése egyszerre, adagolva Pythonban?

Figyelt kérdés

Egy olyan szkriptet írok, mely sok (több száz), hálózaton elérhető hosztról kérdez le adatokat.

A szkript remekül működik, viszont mivel egy ciklusban megyek végig a hosztokon, a szkript sokáig fut.

De mivel az idő pénz, a lustaság fél egészség - fel szeretném gyorsítani a folyamatokat.


Erre a célra meg is találtam a threading modult, ami jó is lenne, csak ha gyors egymásutánjában indítom el a hosztokról történő adatlekérést, akkor az hibás működést eredményez.


Ezért keresnék olyan elegáns megoldást, amivel "adagolva" indítaná el a műveleteket - mi lenne az?



2015. máj. 4. 18:32
1 2
 1/11 anonim ***** válasza:
100%
Pedig a szálkezelés szerintem jó út, csak olvass utána, hogy kell használni. (Van néhány csapda, amit a kezdők elkövetnek.)
2015. máj. 4. 18:35
Hasznos számodra ez a válasz?
 2/11 anonim ***** válasza:
Meg ugye mit értesz az alatt, hogy "adagolva"? És milyen működési hibát kaptál?
2015. máj. 4. 18:36
Hasznos számodra ez a válasz?
 3/11 anonim ***** válasza:
0%

Használj olyan nyelvet ami támogatja a többszálú működést. Ha a Python "ügyesen" használja a zárakat még lassabb is lehet. Itt az ideje keresni valami mást vagy hagyni egyszálon az egész (esetleg átrakhatod C-be a kód egy részét).


[link]

2015. máj. 4. 18:40
Hasznos számodra ez a válasz?
 4/11 anonim ***** válasza:
Én a wxPython-t javaslom szálkezeléshez.
2015. máj. 4. 18:43
Hasznos számodra ez a válasz?
 5/11 anonim ***** válasza:
100%

Nem igazán értem a kérdést, nem azért akarod párhuzamosítani hogy felgyorsítsd és ne egyenként kelljen "adagolni"? Azt is elfelejtetted leírni hogy mi a hiba pontosan, nehéz úgy segíteni.


Több száz vagy akár több ezer szál indítása nem igen szerencsés dolog, programnyelvtől függetlenül. Ha el is tudna indítani ennyit, olyan overhead lenne hogy a program nem tudna megfelelően működni, főleg olyan feladatoknál ahol egyes szálak futási ideje korlátozva van (ez esetben a válasz idő legyen kisebb mint a packet timeout idő).


A megoldás itt is a mikroszálasítás. Pythonban a modul neve greenlet, de van egy erre épülő networking modul is, amit geventnek neveznek. Telepítsd és használd:


[link]

2015. máj. 4. 19:11
Hasznos számodra ez a válasz?
 6/11 A kérdező kommentje:

"Meg ugye mit értesz az alatt, hogy "adagolva"?"

Azt értem, hogy a több száz hoszt adatlekérését nem több száz egyszerre futó szálon szeretném végezni, hanem mondjuk egyszerre maximum 10 szál fusson - ha egy szál befejezte a futását, menjen a helyére egy másik új.


"És milyen működési hibát kaptál?"

Ha ciklusban, szépen egyesével megyek végig a hosztokon, akkor ez szépen - bár lassan - lefut, lekéri az adatokat a hosztoktól


Viszont ha nyitok több száz szálat, akkor az adatokat lekérő függvény kapcsolati hibával elszáll.

2015. máj. 4. 19:13
 7/11 anonim ***** válasza:
100%
Én ezt nem úgy csinálnám, hogy a 10 lekérdezés 10 szál lenne, hanem összesen kettő: egy, ami elküldi a lekérdezéseket, egy másik pedig, ami feldolgozza a beérkező válaszokat.
2015. máj. 4. 19:33
Hasznos számodra ez a válasz?
 8/11 anonim ***** válasza:

> Azt értem, hogy a több száz hoszt adatlekérését nem több száz egyszerre futó szálon szeretném végezni, hanem mondjuk egyszerre maximum 10 szál fusson - ha egy szál befejezte a futását, menjen a helyére egy másik új.


Amiről beszélsz az a thread pool, és az is a fentebb említett gevent része. A lényege hogy csinálsz egy meghatározott méretű pool-t amiben futnak a szálak és ha az egyik szál befejezte a futást kilép a pool-ból hogy egy másik szál be tudjon lépni a helyére.


Példa a gevent használatára:



from gevent import monkey

#hogy minden stdlib együttműködjön a greenlettel, pl. urllib

monkey.patch_all()


from gevent.pool import Pool


def valami_fuggveny(url):

> #a függvenyed ami adatokat kérdez le a hosztoktól

> pass



#a hosztok címe

urls = [' [link] ' [link] ' [link]


#egyszerre max 20 szál legyen a pool-ban

pool = Pool(20)


#átadod az url-eket egyenként a függvényednek

pool.map(valami_fuggveny, urls)



Elég egyszerű és nagyon rugalmas tud lenni. Alapból még a pool sem kéne mert ezek mikroszálak, nem igazi szálak aminek közel sincs akkora overheadje (bár 50-100 fölött azért itt is érdemes), ráadásul még szálbiztos is. Érdemes olvasgatni a dokumentációját, vagy egy tutorialt róla.

2015. máj. 4. 23:31
Hasznos számodra ez a válasz?
 9/11 anonim ***** válasza:

Két szálat indítani (az egyik olvas és a másik feldolgoz)? Pont ez a két dolog nem tud átlapolódni. A Pythonban csak a párhuzamos IO műveletek tudnak egyidejűleg végrehajtódni. Tehát nyugodtan elvégezheted egy szálon is és megspórolod a zárkezelés miatti oda-vissza váltást.


A kérdés nem a szálkezelésről szólt, hanem hogyan gyorsítsuk fel a programot (komoly különbség!). Ha pedig valóban jól tudná a szálakat kezelni a Python (nincs így), akkor annyi szálat kellene elindítani ammennyi számítási egységed van (mivel így a legnagyobb az áteresztőképesség). Pl. 4 mag esetén egyszerre 4 választ kéne egyidejűleg feldolgoznod. Itt legfeljebb a sok letöltést oldhatod meg több szállal (ami az IO műveletek miatt átlapolódik), majd feldolgozhatod egy szálról.

2015. máj. 4. 23:33
Hasznos számodra ez a válasz?
 10/11 anonim ***** válasza:
0%

Tuti, hogy Pythonban akarod ezt megoldani?

Marmint oke, szalkezelessel megoldhato lenne, hogy van 10 worker szal es hajra, dolgozzanak, de ahogy irtak annyival nem biztos, hogy sokkal jobb lenne az eredmeny.


Go-ban ez mondjuk valoszinulag egy par soros koddal megoldhato lenne es garantaltan sokkal gyorsabban futna. De persze teljesen mas nyelv, amit tanulni kell...

2015. máj. 5. 12:02
Hasznos számodra ez a válasz?
1 2

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!