[python]map方法与并行执行

发布时间:2019-07-23 09:40:11编辑:auto阅读(1584)

    文章也可参考: 我的个人博客

    1. 内建方法map

    内建map方法可以通过一个序列的方式来实现函数之间的映射, 并且串行执行。如:

    import time
    from datetime import datetime
    
    def add(x, y):
        print(datetime.now(), "enter add func...")
        time.sleep(2)
        print(datetime.now(), "leave add func...")
        return x+y
    
    map(add, [1,2,3], [4,5,6])

    运行效果:

    2016-04-05 15:01:49.382314 enter add func...
    2016-04-05 15:01:51.383387 leave add func...
    2016-04-05 15:01:51.383471 enter add func...
    2016-04-05 15:01:53.385584 leave add func...
    2016-04-05 15:01:53.385676 enter add func...
    2016-04-05 15:01:55.387388 leave add func...
    [5, 7, 9]

    由上可见, 调用map, 相当于顺序调用了add(1,4), add(2,5), add(3,6)方法; 一行代码实现了方法的迭代调用, 简单快捷。
    那如果再优化一下,实现并行调用add方法, 应该怎么做呢?在python里也好实现, 利用multiprocessing模块就可以。

    2. multiprocessing模块与map方法

    import time
    from datetime import datetime
    from multiprocessing.dummy import Pool as ThreadPool
    from functools import partial
    
    
    def add(x, y):
        print(datetime.now(), "enter add func...")
        time.sleep(2)
        print(datetime.now(), "leave add func...")
        return x+y
    
    
    def add_wrap(args):
        return add(*args)
    
    
    if __name__ == "__main__":
        pool = ThreadPool(4) # 池的大小为4
        print(pool.map(add_wrap, [(1,2),(3,4),(5,6)]))
        #close the pool and wait for the worker to exit
        pool.close()
        pool.join()

    运行效果:

    2016-04-05 15:10:23.690059 enter add func...
    2016-04-05 15:10:23.690406 enter add func...
    2016-04-05 15:10:23.690906 enter add func...
    2016-04-05 15:10:25.693250 leave add func...
    2016-04-05 15:10:25.693409 leave add func...
    2016-04-05 15:10:25.693458 leave add func...
    [3, 7, 11]

    由上可以见, 我们已经实现了并行执行add方法

    3. 关于multiprocessing中pool的大小与性能

    from multiprocessing import Pool
    from multiprocessing.dummy import Pool as ThreadPool

    以上Pool和ThreadPool两个模块, 一个基于进程工作, 一个基于线程工作。

    一般来说, 使用进程池(multiprocessing pool)来执行CPU密集型的任务, 这样可以利用到多核的好处, 理论上(池越大)核越多速度越快;
    使用线程池(threading)来处理IO型任务, 则有个最佳线程池大小, 要根据实际情况来调节这个池的size(线程过多时, 切换线程的开销将严重影响性能)。

关键字