精华内容
下载资源
问答
  • 进程池与线程

    2020-02-11 19:59:43
    虽然使用多进程能提高效率,但是进程的创建会消耗大量的计算机资源(进程Process的创建远远大于线程Thread创建占用的资源),需要注意的是,在Windows上要想使用进程模块,就必须把有关进程的代码写在if name == ...

    pyhton 中 一般进程不超过100 线程不超过1000 推荐io 多路复用 来解决问题 而不是开多线程或者进程
    虽然使用多进程能提高效率,但是进程的创建会消耗大量的计算机资源(进程Process的创建远远大于线程Thread创建占用的资源),需要注意的是,在Windows上要想使用进程模块,就必须把有关进程的代码写在if name == ‘main’ 内,否则在Windows下使用进程模块会产生异常。Unix/Linux下则不需要。

    一.进程池Pool介绍

    Pool类可以提供指定数量的进程供用户调用,当有新的请求提交到Pool中时,如果池还没有满,就会创建一个新的进程来执行请求。如果池满,请求就会告知先等待,直到池中有进程结束,才会创建新的进程来执行这些请求。

    # 导入进程模块
    import multiprocessing
    # 最多允许3个进程同时运行
    pool = multiprocessing.Pool(processes = 3)
    

    1、apply() — 该函数用于传递不定参数,主进程会被阻塞直到函数执行结束(不建议使用,并且3.x以后不在出现),函数原型如下:

    apply(func, args=(), kwds={})
    

    2、apply_async — 与apply用法一致,但它是非阻塞的且支持结果返回后进行回调,函数原型如下:

    apply_async(func[, args=()[, kwds={}[, callback=None]]])
    

    join方法

    import time
    from multiprocessing import Process
    
    def f(name):
        print('hello',name)
        time.sleep(1)
        print('我是子进程')
    
    if __name__ == '__main__':
        p = Process(target=f,args=(3,))
        p.start()
        p.join()
        print('我是父进程')
    '''
    不使用join()方法的时候,先执行主进程,再执行子进程,子进程在等待主进程执行完后再执行
    使用join()方法的时候:主进程等待子进程完成,才继续执行,参数为最多等待时间
    强调:属主线程处于等待的状态,而子进程(p)是处于运行的状态
    '''
    


    使用join方法时
    在这里插入图片描述
    不使用join方法时

    join多进程执行

    import time
    from multiprocessing import Process
    
    def f(name):
        print('hello',name)
        time.sleep(1)
    
    if __name__ == '__main__':
        p_lst = []
        for i in range(5):
            p = Process(target=f,args=('fioergh',))
            p.start()
            p_lst.append(p)
    
            p.join()# 这里选择开启和关闭join()方法
            # [p.join() for p in p_lst]
        print('父进程在执行')
    

    在这里插入图片描述

    进程池Pool的使用

    import time
    # 导入多进程包
    from multiprocessing import Pool
    # 迅雷下载器
    def down_load(movie_name):
        # 下载多少个电影
        for i in range(5):
            print('电影名:{},下载进度{}%'.format(movie_name,(i/4 * 100))) # 下载进度%多少
            # 休息一秒
            time.sleep(1)
        return movie_name
    
    def alert(movie_name):
        print('恭喜{}你下载成功'.format(movie_name))
    move_list = ['西红柿首付','功夫熊猫','囧妈','泰囧','红海行动','攀登者']
    
    if __name__ == '__main__':
        pool = Pool(3)  # 创建进程池,一次下载3个
        for move_name in move_list:
            # 调用进程池
            pool.apply_async(down_load,(move_name,),callback = alert) # 使用下载函数
        pool.close()
        pool.join()
    

    在这里插入图片描述

    线程

    线程分为单线程和多线程
    有了单线程的话,什么又是多线程?可以这么理解:一个线程执行一个代码块,多个线程可以同时执行多个代码,使用多线程能让程序效率更高。举个例子,你今天有两件事需要完成,分别是洗衣服和打扫房间,分别来看看单线程和多线程如何完成:

    单线程:先用洗衣机洗衣服30分钟,等衣服洗完之后再打扫房间60分钟,累计总耗时:90分钟;

    多线程:把衣服放到洗衣机并且30分钟后自动结束,然后立刻开始打扫房间60分钟,累计耗时:60分钟;

    由此可见,完成同样的事情,单线程是一件事情做完之后继续下一件事情,而多线程可以同时执行多件事情,所以多线程比单线程效率更高!

    一.线程解释

    线程是cpu最小调度单位,一个程序中至少有一个或者多个线程(至于进程暂时不做讲解,后面文章会有详细解释)!在开发中使用线程可以让程序运行效率更高,多线程类似于同时执行多个不同代码块。

    创建线程

    # 导入线程模块
    import threading
    
    def zsj():
        print('lalall')
    # 创建线程并初始化
    t = threading.Thread(target=zsj)
    
    # 启动线程
    t.start()
    

    详细介绍

    # 导入线程threading模块
    import threading
    # 导入内置模块time
    import time
     
    def wash_clothes():
        print("洗衣服开始...")
        # sleep 5 秒,默认以秒为单位
        time.sleep(5)
        print("洗衣服完成...")
     
    def clean_room():
        print("打扫房间开始...")
        # sleep 5 秒,默认以秒为单位
        time.sleep(5)
        print("打扫房间完成...")
     
    if __name__ == "__main__":
     
        # 创建线程并初始化 -- 该线程执行wash_clothes中的代码
        t1 = threading.Thread(target=wash_clothes)
         # 创建线程并初始化 -- 该线程执行clean_room中的代码
        t2 = threading.Thread(target=clean_room)
     
        t1.start()
        t2.start()
    

    线程传参

    如果在线程中需要传递参数怎么办呢?

    threading.Thread()函数中有两个缺省参数 args 和 kwargs ,args 是元组类型,kwargs 是字典类型,缺省值默认为空,除此之外,其实还可以设置线程的名字等,其函数声明如下:

        def __init__(self, group=None, target=None, name=None,
                     args=(), kwargs=None, *, daemon=None):
            """This constructor should always be called with keyword arguments. Arguments are:
    
            *group* should be None; reserved for future extension when a ThreadGroup
            class is implemented.
    
            *target* is the callable object to be invoked by the run()
            method. Defaults to None, meaning nothing is called.
    
            *name* is the thread name. By default, a unique name is constructed of
            the form "Thread-N" where N is a small decimal number.
    
            *args* is the argument tuple for the target invocation. Defaults to ().
    
            *kwargs* is a dictionary of keyword arguments for the target
            invocation. Defaults to {}.
    
            If a subclass overrides the constructor, it must make sure to invoke
            the base class constructor (Thread.__init__()) before doing anything
            else to the thread.
    
            """
    

    线程结束

    在上面这份代码中一共有几个线程呢?并非两个,一共是三个线程:

    线程一:__name__ == “__main__” 作为主线程;
    线程二:t1 作为子线程;
    线程三:t2 作为子线程;
    

    注意:主程序会等待所有子程序结束之后才会结束!

    相关函数介绍

    1.threading.Thread() — 创建线程并初始化线程,可以为线程传递参数 ;

    2.threading.enumerate() — 返回一个包含正在运行的线程的list;

    3.threading.activeCount(): 返回正在运行的线程数量,与len(threading.enumerate())有相同的结果;
    在这里插入图片描述

    4.Thread.start() — 启动线程 ;

    5.Thread.join() — 阻塞函数,一直等到线程结束为止 ;

    6.Thread.isAlive() — 返回线程是否活动的;

    7.Thread.getName() — 返回线程名;

    8.Thread.setName() — 设置线程名;

    9.Thread.setDaemon() — 设置为守护线程,这里默认是False,设置为True之后则主线程不会再等待子线程结束才结束,而是主线程结束意味程序退出,子线程也立即结束,注意调用时必须设置在start()之前;

    setDaemon()方法

    # encoding:utf-8
    _date_ = '2020/2/10 21:14'
    import time
    # 导入创建线程的包
    import threading
    def sing(num):
        for i in range(num):
            print('唱第{}首歌'.format(i+1))
            time.sleep(1)
    def dance(num):
        for i in range(num):
            print('跳第{}支舞'.format(i+1))
            time.sleep(1)
    def main():
        t1 = threading.Thread(target=sing,args=(3,))
        t2 = threading.Thread(target=dance,args=(3,)) # 这里的参数可以改变,将args中的数值,传递给num
        t1.setDaemon(True)  # 将t1线程设置为守护主线程的守护线程
        t2.setDaemon(True)  # 将t2线程设置为守护主线程的守护线程
        # 启动
        t1.start()
        t2.start()
    if __name__ == '__main__':
        main()
        print('主线程')
    
    

    默认主线程会等待所有子线程结束之后才会结束,主线程结束意味着程序退出;如果setDaemon设置为True,主线程则不会等待子线程,主线程结束,子线程自动结束;

    使用继承的方式开启线程

    # 导入线程包的两种方式
    # from threading import Thread
    import threading
    import time
    # 定义一个类继承threading.Thread类
    class MyThread(threading.Thread):
        def __init__(self,num):
            # 重写父类的初始化方法
            super().__init__()
            # 可以传递创建线程的数量
            self.num = num
        # 重写r父类threading.Thread的run方法
        def run(self):
            for i in range(self.num):
                print('...run...',i)
                time.sleep(1)
    if __name__ == '__main__':
        #实例化类对象
        my_thread = MyThread(3) # 正常方式传递参数
        my_thread.start()
    

    在这里插入图片描述

    共享全局变量的问题

    # 导入线程threading中的Thread包
    # from threading import Thread
    import threading
    import time
    import random
    # 全局变量
    g_num =100
    
    def work1():
        #修改全局变量
        global g_num
        for i in range(3):
            g_num += 1
            time.sleep(random.random()) # 因为这里加了随机休息
            print('in work1,g_num=%d' %g_num)
    def work2():
        global g_num
        for i in range(3):
            g_num += 1
            time.sleep(random.random())
            print('in work2,g_num=%d'%g_num)
    
    if __name__ == '__main__':
        w1 = threading.Thread(target=work1)
        w2 = threading.Thread(target=work2)
        w1.start()
        w2.start()
    

    在这里插入图片描述

    展开全文
  • python 进程池pool简单使用 平常会使用到多进程,可以是用进程池pool来进行自动控制进程 需要注意的是,在windows想要使用进程模块,就必须把有关代码写在if__name__=='main'语句下面才能正常使用,Unix和Linux下...

    python 进程池pool简单使用

    平常会使用到多进程,可以是用进程池pool来进行自动控制进程

    需要注意的是,在windows想要使用进程模块,就必须把有关代码写在if__name__=='main'语句下面才能正常使用,Unix和Linux下则不需要

    Pool类可以提供指定数量的进程供用户调用,当有新的请求提交到Pool中时,如果池还没有满,就会创建一个新的进程来执行请求。如果池满,请求就会告知先等待,直到池中有进程结束,才会创建新的进程来执行这些请求。 

    下面介绍一下multiprocessing 模块下的Pool类下的几个方法:

    1、apply()

        函数原型:apply(func[, args=()[, kwds={}]])

        该函数用于传递不定参数,同python中的apply函数一致,主进程会被阻塞直到函数执行结束(不建议使用,并且3.x以后不在出现)。

    2、apply_async

        函数原型:apply_async(func[, args=()[, kwds={}[, callback=None]]])

        与apply用法一致,但它是非阻塞的且支持结果返回后进行回调。

    3、map()

         函数原型:map(func, iterable[, chunksize=None])

        Pool类中的map方法,与内置的map函数用法行为基本一致,它会使进程阻塞直到结果返回。 

        注意:虽然第二个参数是一个迭代器,但在实际使用中,必须在整个队列都就绪后,程序才会运行子进程。

    4、map_async()

        函数原型:map_async(func, iterable[, chunksize[, callback]])

        与map用法一致,但是它是非阻塞的。其有关事项见apply_async。

    5、close()

        关闭进程池(pool),使其不在接受新的任务。

    6、terminal()

        结束工作进程,不在处理未处理的任务。

    7、join()

        主进程阻塞等待子进程的退出, join方法要在close或terminate之后使用。

     

    展开全文
  • concurrent.futures模块 -----进程池 ---线程池 ---回调 concurrent.futures模块提供了高度封装的异步调用接口,它内部有关的两个池 ThreadPoolExecutor:线程池,提供异步调用,其基础就是老版的...

    concurrent.futures模块提供了高度封装的异步调用接口,它内部有关的两个池

    ThreadPoolExecutor:线程池,提供异步调用,其基础就是老版的Pool

    ProcessPoolExecutor: 进程池,提供异步调用

    方法

    ProcessPoolExecutor(n):n表示池里面存放多少个进程,之后的连接最大就是n的值

    submit(fn,*args,**kwargs) 异步提交任务 map(func, *iterables, timeout=None, chunksize=1) 取代for循环submit的操作 shutdown(wait=True) 相当于进程池的pool.close()+pool.join()操作 wait=True,等待池内所有任务执行完毕回收完资源后才继续,--------》默认 wait=False,立即返回,并不会等待池内的任务执行完毕 但不管wait参数为何值,整个程序都会等到所有任务执行完毕 submit和map必须在shutdown之前
    result(timeout
    =None) #取得结果 add_done_callback(fn) #回调函数
    from concurrent.futures import ThreadPoolExecutor,ProcessPoolExecutor
    import time,random,os
    
    def task(n):
        print('%s is running'% os.getpid())
        time.sleep(random.randint(1,3))
        return n**2
    def handle(res):
        res=res.result()
        print("handle res %s"%res)
    
    if __name__ == '__main__':
        # #同步调用
        # pool=ProcessPoolExecutor(8)
        #
        # for i in range(13):
        #     pool.submit(task, i).result() #变成同步调用,串行了,等待结果
        # # pool.shutdown(wait=True) #关门等待所有进程完成
        # pool.shutdown(wait=False)#默认wait就等于True
        # # pool.submit(task,3333) #shutdown后不能使用submit命令
        #
        # print('主')
    
        #异步调用
        pool=ProcessPoolExecutor(8)
        for i in range(13):
             obj=pool.submit(task,i)
             obj.add_done_callback(handle) #这里用到了回调函数
        pool.shutdown(wait=True) #关门等待所有进程完成
        print('')
    ProcessPoolExecutor
    #提交任务的两种方式
    #同步调用:提交完任务后,就在原地等待,等待任务结束,拿到任务的返回值,才能继续下一行代码,导致程序串行执行
    #异步调用+回调机制:提交完任务后,不在原地等待,任务一旦执行完毕就会触发回调函数的执行,程序是并发执行
    
    #同步有可能是计算任务而在等待
    #ProcessPoolExcutor基于pool开发的
    
    #进程的执行状态
    #阻塞:遇到i/o进入的一种状态,等待
    #非阻塞:
    进程其他说明
    from concurrent.futures import ThreadPoolExecutor
    from urllib import request
    from threading import current_thread
    import time
    
    def get(url):
        print('%s get %s'%(current_thread().getName(),url))
        response=request.urlopen(url)
        time.sleep(2)
        # print(response.read().decode('utf-8'))
        return{'url':url,'content':response.read().decode('utf-8')}
    
    def parse(res):
        res=res.result()
        print('parse:[%s] res:[%s]'%(res['url'],len(res['content'])))
    
    # get('http://www.baidu.com')
    if __name__ == '__main__':
        pool=ThreadPoolExecutor(2)
    
        urls=[
            'https://www.baidu.com',
            'https://www.python.org',
            'https://www.openstack.org',
            'https://www.openstack.org',
            'https://www.openstack.org',
            'https://www.openstack.org',
            'https://www.openstack.org',
            'https://www.openstack.org',
    
        ]
    
        for url in urls:
            pool.submit(get,url).add_done_callback(parse)
    ThreadPoolExecutor
    from concurrent.futures import ThreadPoolExecutor,ProcessPoolExecutor
    
    import os,time,random
    def task(n):
        print('%s is runing' %os.getpid())
        time.sleep(random.randint(1,3))
        return n**2
    
    if __name__ == '__main__':
    
        executor=ThreadPoolExecutor(max_workers=3)
    
        # for i in range(11):
        #     future=executor.submit(task,i)
    
        executor.map(task,range(1,12)) #map取代了for+submit
    map用法

    回调 略

    posted on 2018-08-10 10:24 dawn-liu 阅读(...) 评论(...) 编辑 收藏

    转载于:https://www.cnblogs.com/mmyy-blog/p/9453453.html

    展开全文
  • 为应用程序'XXXXX'提供服务的进程意外终止。进程ID是'XXXX'。进程退出代码是'0x80'。有关更多信息,请参阅在http://go.microsoft.com/fwlink/events.asp的帮助和支持中心。原因:...
    为应用程序池 'XXXXX' 提供服务的进程意外终止。进程 ID 是 'XXXX'。进程退出代码是 '0x80'。 
    有关更多信息,请参阅在 http://go.microsoft.com/fwlink/events.asp 的帮助和支持中心。 
    原因: 
    CAUSE 
    Together with each worker process that IIS creates under a separate identity, the system creates a new desktop object by allocating memory from the configured desktop heap. This issue occurs because, when that heap has been exhausted, IIS cannot create more worker processes. Clients then receive the "service unavailable" error message in their Web browsers when they try to visit Web sites that those application pools host. 
    独立进程的 内存堆戋消耗完了,IIS不能创建更多的进程工作空间来处理 
    解决方法: 
    警告:需要修改服务器的注册表,请修改前备份相关键值 
    add the UseSharedWPDesktop registry key to your computer that is running IIS. This registry key permits all worker processes to run in one shared desktop, regardless of their worker process identities. 
    To add the UseSharedWPDesktop registry key: 

    1. HKEY_LOCAL_MACHINE\System\CurrentControlSet\Services\W3SVC 
    2. 在Parameters键下新建一个DWORD项,名字为:UseSharedWPDesktop 值为1 重启IIS 
    MS关于此键值描述: 
    UseSharedWPDesktop 
    注册表路径:HKEY_LOCAL_MACHINE\System\CurrentControlSet\Services\W3SVC\Parameters 
    数据类型:REG_DWORD 
    默认值: 0 
    范围: 0 - 1 

    如果您正使用唯一标识设置应用程序池,那么根据服务器上的应用程序和内存资源,将会达到大约 60 个应用程序池的上限。某些分配了单个新登录会话的系统资源存在一定的限制。这表明可以有 60 个进程以不同的帐户同时运行。IIS 6.0 支持在单个共享的工作站和桌面中运行这些进程,所需的成本为在所有各方之间共享单个用户会话的单个封装。要扩展到 60 个应用程序池以上并共享单个桌面,可将 UseSharedWPDesktop 更改为 DWORD 值 1。更改此注册表项之后,应当可以扩展到上百个应用程序池已及上百个同时运行的工作进程



    本文转自 佛哒 51CTO博客,原文链接:http://blog.51cto.com/fodaa/1732948,如需转载请自行联系原作者

    展开全文
  • 我们公司旗下的红黑互联会遇到这种问题 ...为应用程序 XXXXX 提供服务的进程意外终止。进程 ID 是 XXXX。进程退出代码是 0x80。 有关更多信息,请参阅在 asp">http://go.microsoft.com...
  • 正在进行调试的Web服务器进程已由Internet信息服务(IIS)终止。可以通过在IIS中配置应用程序Ping设置来避免这一问题。有关更多详细信息,请参见“帮助” 解决方法如下:
  • 错误日志为: 为应用程序 'DefaultAppPool' 提供服务的进程意外终止。进程 ID 是 '3056'。进程退出代码是 '0xffffffff'。 有关更多信息,请参阅在 http://go.microsoft.com/fwlink/events.asp 的帮助和支持中心。 ...
  • 创建进程

    2018-03-26 20:43:00
    multiprocess模块 仔细说来,multiprocess不是一个...由于提供的子模块非常多,为了方便大家归类记忆,我将这部分大致分为四个部分:创建进程部分,进程同步部分,进程池部分,进程之间数据共享。 import os ...
  • multiprocess模块 仔细说来,multiprocess...由于提供的子模块非常多,为了方便大家归类记忆,我将这部分大致分为四个部分:创建进程部分,进程同步部分,进程池部分,进程之间数据共享。 进程的pid 父进程...
  • python之进程

    2019-01-08 14:52:00
    multiprocess不是一个模块而是python中一个操作、管理进程的包,几乎包含了...进程池部分 进程之间数据共享 class Process(object): def __init__(self, group=None, target=None, name=None, args=(), kwar...
  • 进程(代码)

    2019-09-22 08:22:40
     大致可以分为四个部分: 创建进程, 进程同步, 进程池, 进程之间数据共享.  强调: 进程没有任何共享状态, 进程修改的数据, 仅限于进程内部, 但是通过一些特殊的方法可以实现进程之间数据的共享. 1. Process模块...
  • 一、关于multiprocessing (关于进程的模块)模块Process方法 关于multiprocess包的介绍: ...由于提供的子模块非常多,为了方便记忆,我将这部分大致分为四个部分:创建进程部分,进程同步部分,进程池部分,进程之...
  • 由于提供的子模块非常多,为了方便大家归类记忆,我将这部分大致分为四个部分:创建进程部分,进程同步部分,进程池部分,进程之间数据共享。重点强调:进程没有任何共享状态,进程修改的数据,改动仅限于该进程内,...
  • 什么是IIS应用程序以及应用程序详解(二) 一起来 看看有关应用程序的一些问题。应用程序的“属性”对话框有四页——回收,性能,运行状况,标识,如图六所示。在这些选项页中,最引人注目的恐怕就是 “回收...
  • python 进程(程序操作)

    2019-09-24 18:29:31
    multiprocessing模块 仔细说来,multiprocessing不是一个模块...由于提供的子模块非常多,为了方便大家归类记忆,我将这部分大致分为四个部分:创建进程部分,进程同步部分,进程池部分,进程之间数据共享。 ...
  • multiprocess模块 ...由于提供的子模块非常多,为了方便大家归类记忆,我将这部分大致分为四个部分:创建进程部分,进程同步部分,进程池部分,进程之间数据共享。 multiprocess.process模块 pr...
  • 一. multiprocess模块 仔细说来,multiprocess...由于提供的子模块非常多,为了方便大家归类记忆,我将这部分大致分为四个部分:创建进程部分,进程同步部分,进程池部分,进程之间数据共享。 process模块介绍 ...
  • 由于提供的子模块非常多,为了方便大家归类记忆,我将这部分大致分为四个部分:创建进程部分,进程同步部分,进程池部分,进程之间数据共享。重点强调:进程没有任何共享状态,进程修改的数据,改动仅限于该进程内 ...

空空如也

空空如也

1 2 3 4 5 ... 10
收藏数 191
精华内容 76
关键字:

有关进程池