天天看點

python多線程協程配合使用_python 多線程 ----協程

協程(corouutine):輕量級的線程,不存在上下文切換,能在多個任務之間排程的多任務方式,可以使用,yield實作

線程和程序的操作是由程式觸發系統接口,最後的執行者是系統,它本質上是作業系統提供的功能。而協程的操作則是程式員指定的,在python中通過yield,人為的實作并發處理。

協程存在的意義:對于多線程應用,CPU通過切片的方式來切換線程間的執行,線程切換時需要耗時。協程,則隻使用一個線程,分解一個線程成為多個“微線程”,在一個線程中規定某個代碼塊的執行順序。

協程的适用場景:當程式中存在大量不需要CPU的操作時(IO)。

簡單多任務協程實列:

import time

import threading

def task_1():

print(threading.current_thread())

while True:

print('---1---')

time.sleep(1)

yield

def task_2():

print(threading.current_thread())

while True:

print('---2---')

time.sleep(1)

yield

def main():

t1=task_1()

t2=task_2()

while True:

next(t1)

next(t2)

if __name__ == '__main__':

main()

在不需要自己“造輪子”的年代,同樣有第三方子產品為我們提供了高效的協程,這裡介紹一下greenlet和gevent。本質上,gevent是對greenlet的進階封裝,是以一般用它就行,這是一個相當高效的子產品。

在使用它們之前,需要先安裝,可以通過源碼,也可以通過pip。

greenlet

def test1():

print(12)

gr2.switch()

print(34)

gr2.switch()

def test2():

print(56)

gr1.switch()

print(78)

gr1 = greenlet(test1)

gr2 = greenlet(test2)

gr1.switch()

gevent

from gevent import monkey; monkey.patch_all()

import gevent

import requests

def f(url):

print('GET: %s' % url)

resp = requests.get(url)

data = resp.text

print('%d bytes received from %s.' % (len(data), url))

gevent.joinall([

gevent.spawn(f, 'https://www.python.org/'),

gevent.spawn(f, 'https://www.yahoo.com/'),

gevent.spawn(f, 'https://github.com/'),

])