Pour rendre mon code plus "pythonique" et plus rapide, j'utilise le "multitraitement" et une fonction de carte pour l'envoyer a) la fonction et b) la plage d'itérations.
La solution implantée (c'est-à-dire, appelez tqdm directement sur la plage tqdm.tqdm (plage (0, 30)) ne fonctionne pas avec le multitraitement (tel que formulé dans le code ci-dessous).
La barre de progression s'affiche de 0 à 100% (lorsque python lit le code?), Mais elle n'indique pas la progression réelle de la fonction de carte.
Comment afficher une barre de progression indiquant à quelle étape se trouve la fonction 'map'?
from multiprocessing import Pool
import tqdm
import time
def _foo(my_number):
square = my_number * my_number
time.sleep(1)
return square
if __== '__main__':
p = Pool(2)
r = p.map(_foo, tqdm.tqdm(range(0, 30)))
p.close()
p.join()
Toute aide ou suggestion est la bienvenue ...
Solution trouvée: soyez prudent! En raison du multitraitement, le temps d'estimation (itération par boucle, temps total, etc.) peut être instable, mais la barre de progression fonctionne parfaitement.
Remarque: Le gestionnaire de contexte pour le pool est uniquement disponible à partir de Python version 3.3.
from multiprocessing import Pool
import time
from tqdm import *
def _foo(my_number):
square = my_number * my_number
time.sleep(1)
return square
if __== '__main__':
with Pool(processes=2) as p:
max_ = 30
with tqdm(total=max_) as pbar:
for i, _ in tqdm(enumerate(p.imap_unordered(_foo, range(0, max_)))):
pbar.update()
Utilisez imap au lieu de map, qui renvoie un itérateur de valeurs traitées.
from multiprocessing import Pool
import tqdm
import time
def _foo(my_number):
square = my_number * my_number
time.sleep(1)
return square
if __== '__main__':
with Pool(2) as p:
r = list(tqdm.tqdm(p.imap(_foo, range(30)), total=30))
sur la base de la réponse de Xavi Martínez, j’ai écrit la fonction imap_unordered_bar
. Il peut être utilisé de la même manière que imap_unordered
à la seule différence qu'une barre de traitement est affichée.
from multiprocessing import Pool
import time
from tqdm import *
def imap_unordered_bar(func, args, n_processes = 2):
p = Pool(n_processes)
res_list = []
with tqdm(total = len(args)) as pbar:
for i, res in tqdm(enumerate(p.imap_unordered(func, args))):
pbar.update()
res_list.append(res)
pbar.close()
p.close()
p.join()
return res_list
def _foo(my_number):
square = my_number * my_number
time.sleep(1)
return square
if __== '__main__':
result = imap_unordered_bar(_foo, range(5))
Vous pouvez utiliser p_tqdm
à la place.
https://github.com/swansonk14/p_tqdm
from p_tqdm import p_map
import time
def _foo(my_number):
square = my_number * my_number
time.sleep(1)
return square
if __== '__main__':
r = p_map(_foo, list(range(0, 30)))
Cette approche simple et ça marche.
from multiprocessing.pool import ThreadPool
import time
from tqdm import tqdm
def job():
time.sleep(1)
pbar.update()
pool = ThreadPool(5)
with tqdm(total=100) as pbar:
for i in range(100):
pool.apply_async(job)
pool.close()
pool.join()