代码之家  ›  专栏  ›  技术社区  ›  lovechillcool

在池映射中使用列表/多个参数的Python

  •  11
  • lovechillcool  · 技术社区  · 7 年前

    我试图将列表作为参数传递给 pool.map(co_refresh, input_list) . 然而 pool.map 没有触发函数 co_refresh . 也没有返回错误。看起来这一过程还在继续。

    from multiprocessing import Pool
    import pandas as pd
    import os
    
    account='xxx'
    password='xxx'
    threads=5
    co_links='file.csv'
    
    input_list=[]
    
    pool = Pool(processes=threads)
    def co_refresh(url, account, password, outputfile):
    
        print(url + ' : ' + account + ' : ' + password + ' : ' + outputfile)
    
        return;
    
    link_pool = pd.read_csv(co_links, skipinitialspace = True)
    
    for i, row in link_pool.iterrows():
    
        ln = (row.URL, account, password, os.path.join('e:/', row.File_Name.split('.')[0] + '.csv'))
    
        input_list.append(ln)
    
    pool.map(co_refresh, input_list)
    
    pool.close()
    

    然而,它从未触发该功能 co_刷新 . 如何将列表用作要传递给函数的参数?

    旧问题(简化):

    我有下面的input_列表,这是一个 list 属于 列表 :

    [a1, b1, c1, d1]
    [a2, b2, c2, d2]
    [a3, b3, c3, d3]
    

    def func(a, b, c, d)
       ###
        return;
    

    我想为这个函数使用多进程 func :

    from multiprocessing import Pool
    pool = Pool(processes=5)
    pool.map(func, input_list)
    pool.close()
    

    然而,它从未触发该功能 func公司 . 如何将列表用作要传递给函数的参数?

    3 回复  |  直到 7 年前
        1
  •  15
  •   georgexsh    7 年前

    你应该定义你的工作职能 之前 声明 Pool ,当您声明 水塘 , sub worker processes forked 从那个时起,辅助进程不会执行超出该行的代码,因此看不到您的工作功能。

    此外,你最好更换 pool.map 具有 pool.starmap 以适应您的输入。

    一个简化示例:

    from multiprocessing import Pool
    
    def co_refresh(a, b, c, d):
        print(a, b, c, d)
    
    input_list = [f'a{i} b{i} c{i} d{i}'.split() for i in range(4)]
    # [['a0', 'b0', 'c0', 'd0'], ['a1', 'b1', 'c1', 'd1'], ['a2', 'b2', 'c2', 'd2'], ['a3', 'b3', 'c3', 'd3']]
    
    pool = Pool(processes=3)
    pool.starmap(co_refresh, input_list)
    pool.close()
    
        2
  •  2
  •   Tarun Lalwani    7 年前

    考虑以下代码

    from multiprocessing.pool import Pool
    
    data = [["a1", "b1", "c1", "d1"],
            ["a2", "b2", "c2", "d2"],
            ["a3", "b3", "c3", "d3"], ]
    
    
    def someaction(a, b=1, c=2, d=3):
        print(a, b, c, d)
    

    当您使用池在脚本中调用它时

    pool = Pool(4)
    pool.map(someaction, data)
    

    输出为

    ['a1', 'b1', 'c1', 'd1'] 1 2 3
    ['a2', 'b2', 'c2', 'd2'] 1 2 3
    ['a3', 'b3', 'c3', 'd3'] 1 2 3
    

    所以 a 获取数组,其余所有参数均未传递。 Pool.map 要求函数只有一个参数。因此,为了使您的案例生效,您需要创建一个包装器函数

    def someaction_wrapper(data):
        someaction(*data)
    

    然后在池中调用这个包装器函数。现在你使用

    pool = Pool(4)
    pool.map(someaction_wrapper, data)
    

    输出为

    a1 b1 c1 d1
    a2 b2 c2 d2
    a3 b3 c3 d3
    

    我相信这就是你想要的

        3
  •  0
  •   lovechillcool    7 年前

    georgexsh的答案在Python 3中非常有效;关键是 starmap 允许将多个参数传递到函数中。

    然而,如果您使用Python 2,则需要使用Ahmed在问题下的评论中提到的Python经典解包 here .

    在我的例子中,我只需要在函数中首先“登记”参数。

    def func(args)
       (a, b, c, d) = args
       # You can then use a, b, c, d in your function
        return;