2011-01-28 10 views
32

Mam następujące funkcje:Jak niech Pool.map wziąć funkcję lambda

def copy_file(source_file, target_dir): 
    pass 

Teraz chciałbym użyć multiprocessing do wykonywania tej funkcji na raz:

p = Pool(12) 
p.map(lambda x: copy_file(x,target_dir), file_list) 

Problemem jest to, , lambda nie może być marynowana, więc to się nie udaje. Jaki jest najbardziej schludny (pythonic) sposób, aby to naprawić?

Odpowiedz

45

pomocą obiektu Funkcja:

class Copier(object): 
    def __init__(self, tgtdir): 
     self.target_dir = tgtdir 
    def __call__(self, src): 
     copy_file(src, self.target_dir) 

Aby uruchomić Pool.map:

p.map(Copier(target_dir), file_list) 
+2

Dzięki, to jest rzeczywiście to, co potrzebne ! –

+1

Dzięki! Naprawdę żałuję, że nie mogą przyjąć funkcji lambda! – yeelan

15

Odpowiedź poniżej został dotknięty, bo to does not actually work w python2 od functools.partial obiektów (w python2) nie są picklable.

functools.partial Obiekty zostały wykonane w Pythonie3, jednak to rozwiązanie działa.


Można użyć functools.partial:

import functools 
copier=functools.partial(copy_file,target_dir=target_dir) 
p.map(copier,file_list) 

+0

Ten wygląda jeszcze czystszy ... Zdecyduję później, który z nich odpowiedzieć: –

+0

@Peter Smit: Ups, widziałeś mój wpis, zanim go usunąłem. Usuwam to, żeby ogłosić, że nie ma działa z powodu błędu w Python2. – unutbu

+0

Ah, ok. Szukałem w dokumentach i nie widziałem komentarza na temat możliwości, więc założyłem, że są ... Przyjmuję drugą odpowiedź, ponieważ wydaje się, że to jest droga. –

0

Pytanie jest nieco stary, ale jeśli nadal używać Pythona 2 moja odpowiedź może być przydatna.

Sztuczka polega na wykorzystaniu części projektu pathos: multiprocess Rozwidlenie wieloprocesowości. Pozbywa się denerwującego ograniczenia oryginalnego multiprocesu.

instalacji: pip install multiprocess

Zastosowanie:

>>> from multiprocess import Pool 
>>> p = Pool(4) 
>>> print p.map(lambda x: (lambda y:y**2)(x) + x, xrange(10)) 
[0, 2, 6, 12, 20, 30, 42, 56, 72, 90] 
0

Od this odpowiedź, patos niech Ci uruchomić lambda p.map(lambda x: copy_file(x,target_dir), file_list) bezpośrednio, zapisując wszystkie obejścia/hacki