python 進程相關 (八)

通用線程模塊:multiprocessing

multiprocessing與線程的threading模塊方法、結構類似,但多進程需要對每一個Process對象調用join()方法,以防止該進程成爲殭屍進程

process.PID            可以獲取進程的ID,進程start之前爲空
process.terminate()    強行終止進程(在join()前使用)
process.is_alive()     可以判斷該進程是否還在運行

簡單的啓動進程
process = multiprocessing.Process(target=func, args=(1,2))
process.start()
process.join()

繼承multiprocessing.Process,重寫run()方法

class Task(multiprocessing.Process):
    def __init__(self):
        pass
        
    def run(self):
        '重寫run方法,start啓動的時候會調用run方法'
        pass
        
process = Task()
process.satrt()
process.join()

多進程管理

Pool的參數processes爲線程池的數量,調用join之前,要先調用close() 函數,否則會出錯, close()執行後不會有新的進程不能加入到pool,join函數等待所有子進程結束

pro_list = []
pool = multiprocessing.Pool(processes = 2)
for i in range(5):
    res = pool.apply_async(func, args, kwds, callback)
    pro_list.append(res)
pool.close()
pool.join()
for pro in pro_list:
    #獲取各個進程返回值
    print pro.get()

也可以使用 pool.map(func, args_list) 啓動多線程,args_list,爲參數隊列

pool.apply()        #阻塞方式(當一個進程運行完成,進程池空出來了後纔會運行新的線程)
pool.apply_async    #非阻塞方式(多進程之間來回調度)


multiprocessing.Lock(),與線程鎖操作基本相同

隊列
進程隊列multiprocessing.Queue(maxsize),與線程隊列操作基本相同

注意:logging日誌模塊只是線程安全的,在多進程中使用,可能會產生錯誤


subprocess模塊

subprocess模塊通常用來執行第三方程序或命令

subprocess.Popen(args, bufsize=0, executable=None,
                 stdin=None, stdout=None, stderr=None,
                 preexec_fn=None, close_fds=False, shell=False,
                 cwd=None, env=None, universal_newlines=False,
                 startupinfo=None, creationflags=0)

常用參數

args                    執行的命令,類型爲字符串時,是所要執行的命令;爲列表或元組時,是命令參數
bufsize                 緩存大小
stdin,stdout,stderr     表中輸出、輸入、錯誤:可以爲PIPE 管道,或文件描述符,文件對象
shell                   是否爲shell命令True/False (linux下必須,在windows下不要使用)
close_fds               關閉某些文件描述符(不太明白,如果沒有使用該參數,有些文件描述符不會關閉,然後達到最大值,產生錯我)

Popen對象方法和屬性

poll()                 檢查是否結束,設置返回值
wait()                 等待結束,設置返回值
communicate()          參數是標準輸入,返回標準輸出和標準出錯
send_signal()          發送信號 (主要在unix下有用)
terminate()            終止進程(在kill之前使用,不然kill會失效)
kill()                 殺死進程
stdin stdout stderr    參數中指定PIPE時,有用
pid                    進程id
returncode             進程返回值

例子:

process = subprocess.Popen(cmd,stdin = subprocess.PIPE, stdout = subprocess.PIPE, stderr = subprocess.PIPE, shell=True ,close_fds=True)
num = 0
timeout = 3600
while process.poll() == None:
    if num >= timeout:
        try:
            process.terminate()
            print process.stdout.read()
            process.kill()
            process.wait()
            print "time out"
        except:
            errmsg = get_err_msg()
            log.CmdRun_Logger.error(errmsg)
    time.sleep(1)
    num+= 1
            
if process.poll() is not None:
    print process.stdout.read()
    process.wait()
    print 'end'


發佈了44 篇原創文章 · 獲贊 10 · 訪問量 15萬+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章