美文网首页高并发编程
通过多线程/多进程提高任务处理速度

通过多线程/多进程提高任务处理速度

作者: nextbang | 来源:发表于2017-01-10 13:42 被阅读30次

有的时候一个任务需要进行大量的网络、磁盘或数据库请求,比如后台抓取网页,比如离线数据统计等,完成任务需要多次迭代,每次都会产生网络IO、磁盘IO或数据库连接等待,导致任务执行时间很长。但是,任务又有一个特点,迭代之间不需要顺序执行,这就是多线程/多进程非常适合的场景。

在python里,因为GIL的限制,导致没有真正的多线程,所以ThereadPool也在官网提示使用multiprocessing来代替。

This module is OBSOLETE and is only provided on PyPI to support old projects that still use it. 
Please DO NOT USE IT FOR NEW PROJECTS! 
Use modern alternatives like the multiprocessing module in the standard library or even an asynchroneous approach with asyncio.
multiprocessing 的简单用法:
from multiprocessing import Pool
def f(x): 
    return x*x
if __name__ == '__main__': 
    with Pool(5) as p: 
        print(p.map(f, [1, 2, 3]))

这种方式,采用的依然是同步顺序执行的方式,发挥多进程威力的异步方式如下:

from multiprocessing import Pool
import time

def f(x):
    time.sleep(1)                                                                                                      
    return x,x*x

if __name__ == '__main__':
    res_list = []  
    # apply  
    with Pool(5) as p:
        for i in xrange(1,20):
            res = pool.apply_async(f,[i])
            res_list.append(res)

    # print
    for res in res_list:
        print(res.get())

    pool.close()
    pool.join()

需要特别注意的几个地方:

  1. res.get() 需要在进程调用完成后,统一获取,否则就是同步方式了
  2. pool.join() 使主进程等待所有子进程完成后,再退出
  3. 需要在join前调用pool.close()
也可以直接定义Processing
from multiprocessing import Process
import os
import time

def info(title):
    print(title)                                                                                                                                                                                           
    print('module name:', __name__)
    print('parent process:', os.getppid())
    print('process id:', os.getpid())

def f(name):
    time.sleep(1)
    info('function f')
    print('hello', name)

if __name__ == '__main__':
    info('main line')
    for i in xrange(10):
        p = Process(target=f, args=(i,))
        p.start()
        # p.join()

备注:

  1. 通过os.getppid()和os.getpid() 获取父进程及当前进程的ID
  2. 如果希望线程顺序执行,可调用p.join()

相关文章

  • 通过多线程/多进程提高任务处理速度

    有的时候一个任务需要进行大量的网络、磁盘或数据库请求,比如后台抓取网页,比如离线数据统计等,完成任务需要多次迭代,...

  • 7.多任务-多线程-进程

    多任务-多线程-进程 并发:任务数多于CPU核数,通过调度算法,实现多任务一起执行,切换速度很快。宏观是任务同时运...

  • 进程和线程

    这周开发做了个技术改造,提高财务付款速度。 开发设计时提到了进程和线程,是走多线程,还是进程里多配几个job。 在...

  • 多线程

    一.什么是多线程 1个进程中可以开启多条线程,每条线程可以并行(同时)执行不同的任务进程,多线程技术可以提高...

  • 线程——java学习之<17>

    多进程的作用不是提高执行速度,而是提高cpu的使用率。多线程的作用不是提高执行速度,而是提高应用程序的使用率。新建...

  • 浅析python的GIL

    Python中的GIL锁 在Python中,可以通过多进程、多线程和多协程来实现多任务。 在多线程的实现过程中,为...

  • 简单了解进程、线程、协程

    当单任务不能满足工作的需要,只是需要使用多任务,多任务分为多进程,多线程,多协程 先有进程,进程创建线程,线程依附...

  • 爬虫学习(四)多线程

    1.多线程 简单说就是在一个任务进程中,采用多个线程来分别完成子任务,从而提高运行速度及效率,需要用到的模块为th...

  • gevent实现静态web服务器(协程实现)

    写在前面 为提高web服务器的服务质量,一般通过多线程/多进程实现多任务来服务大量用户,但线程和进程往往要消耗较多...

  • HTTP的多线程下载

    多线程下载是加快下载速度的一种方式,通过开启多个线程去执行一个任务,可以使任务的执行速度变快。多线程的任务下载时常...

网友评论

    本文标题:通过多线程/多进程提高任务处理速度

    本文链接:https://www.haomeiwen.com/subject/raykbttx.html