2017-01-30 6 views
5

Я пытаюсь написать функцию, которая может принимать два аргумента, а затем добавить ее в multiprocessing.Pool и распараллелить ее. У меня были некоторые осложнения, когда я пытался написать эту простую функцию.Python: использование карты и многопроцессорности

df = pd.DataFrame() 
df['ind'] = [111, 222, 333, 444, 555, 666, 777, 888] 
df['ind1'] = [111, 444, 222, 555, 777, 333, 666, 777] 

def mult(elem1, elem2): 
    return elem1 * elem2 

if __name__ == '__main__': 
    pool = Pool(processes=4) 
    print(pool.map(mult, df.ind.astype(int).values.tolist(), df.ind1.astype(int).values.tolist())) 
    pool.terminate() 

Это возвращается ошибка:

TypeError: unsupported operand type(s) for //: 'int' and 'list' 

Я не могу понять, что случилось. Может ли кто-нибудь объяснить, что означает эта ошибка, и как я могу это исправить?

ответ

6

Модуль многопроцессного пула принимает список аргументов, которые вы хотите обрабатывать многократно, и поддерживает только один аргумент. Вы можете исправить это, выполнив следующие действия:

from multiprocessing import Pool 
import pandas as pd 

df = pd.DataFrame() 
df['ind'] = [111, 222, 333, 444, 555, 666, 777, 888] 
df['ind1'] = [111, 444, 222, 555, 777, 333, 666, 777] 

def mult(elements): 
    elem1,elem2 = elements 
    return elem1 * elem2 

if __name__ == '__main__': 
    pool = Pool(processes=4) 
    inputs = zip(df.ind.astype(int).values.tolist(), df.ind1.astype(int).values.tolist()) 
    print(pool.map(mult, inputs)) 
    pool.terminate() 

Что я сделал здесь пронестись ваши два итерируемых в список с каждым элементом является два аргумента, которые вы хотели ввести. Теперь я изменяю ввод вашей функции, чтобы распаковать эти аргументы, чтобы они могли обрабатываться.

+0

Соблазн создать тестовый чехол. Может ли это не обрабатываться внутри 'pandas', чтобы избежать GIL и работать в C? Могут ли накладные расходы на создание пула и его координация означают, что это неразумный подход (несмотря на устранение трудности ОП)? – roganjosh

+0

Я уверен, что есть способ правильно создать входные данные в Pandas, чтобы он лучше масштабировался. Что касается накладных расходов, это, вероятно, будет специфичным для приложения, поэтому мне будет трудно ответить. Честно говоря, я немного новичок в использовании многопроцессорности, поэтому не думаю, что я знаю лучший ответ на ваши вопросы. Однако я столкнулся с конкретной проблемой, с которой сталкивается OP. – tmwilson26

+0

Я буду исследовать, хотя я, возможно, не смогу получить свой собственный тестовый документ сегодня вечером. У многопроцессорности наверняка есть большие накладные расходы в процессах нереста, и я понимаю, что это можно было бы векторизовать просто ... до такой степени, что это делает недействительным такой подход. Я поддержал хотя, потому что вы аккуратно отвечаете на вопрос, я просто думаю, что предпосылка подхода ошибочна, но учиться сама :) – roganjosh