python 給生成器發信息

有如下函數:

def gen():
	li = [1, 2, 3, 4]
	for i in li:
		yield i

a = gen()
try:
	while True:
		print(a.next())
except StopIteration:
	print('generator ({}) has finished.'.format('a'))

print(gen)
print(a)
這裏,gen是個函數,而a是個生成器

所以輸出:

1
2
3
4
generator (a) has finished.
<function gen at 0x7f010d70c410> #gen果然是個函數
<generator object gen at 0x7f010d748d70> #a的確是個生成器
所以針對a,就把它當作一個類的實例來處理。

而如何給生成器發信息呢?

首先,生成器得有東西接收我們發的信息吧,如下添加:

def gen():
	li = [1, 2, 3, 4]
	for i in li:
		recvor1 = yield i
		print('generator received: {}'.format(recvor1))
這樣的話,給生成器發的信息會被存儲到recvor1中,那麼如何如何向生成器發送信息呢?

使用生成器的方法:send()

原型:

generator.send(value)
value僅僅表示說個值,你可以傳遞任何值,只要在生成器內部用匹配的結構接收就可以了

知道了方法,如何操作呢?

print(a.next())
print(a.send(15))
輸出:

1
generator received: 15
2

由於使用生成器的時候,第一次必須調用next,所以先調用next()方法,爲什麼呢?

看如下生成器的路由:

用戶調用next()->
開始進入gen->
創建li->
進入循環,執行第一次i的取值->
yield i 返回i,暫停生成器

用戶再次執行next()->
生成器繼續執行,從recvor = ...開始->
執行print語句->
第二次進入循環,爲i取值->
yield i返回i,暫停生成器

用戶再次執行next()->
生成器繼續執行,從recvor = ...開始->
執行print語句->
第三次進入循環,爲i取值->
yield i返回i,暫停生成器

直到StopIteration異常發生退出生成器
上面是個人總結。可以看出,使用send發信息,只有從第二次循環的yield才能接收數據,第一次沒有人接收

來發送一個元組試試:

def gen():
	li = [1, 2, 3, 4]
	for i in li:
		tuple1 = yield i
		print('generator received: {}'.format(tuple1))

a = gen()

print(a.next())
print(a.send((15, 16)))

輸出:

1
generator received: (15, 16)
2
那麼,如果沒有發送值,而是調用了next方法,會如何呢?首先,得知道next等同於send(None)
def gen():
	li = [1, 2, 3, 4]
	for i in li:
		tuple1 = yield i
		print('generator received: {}'.format(tuple1))

a = gen()

print(a.next())
print(a.next())
print(a.next())
print(a.send((15, 16)))
輸出:

1
generator received: None
2
generator received: None
3
generator received: (15, 16)
4
介紹完了。還有一點要備註,對於沒有正常執行完畢的生成器,即沒有拋出StopIteration異常的生成器,要調用close關閉它

def gen():
	li = [1, 2, 3, 4]
	for i in li:
		tuple1 = yield i
		print('generator received: {}'.format(tuple1))

a = gen()


try:
	print(a.next())
	while True:
		val = a.send(15)
		print(val)
		if val == 3:
			a.close()#要關閉
			break
except StopIteration:
	print('generator ({}) has finished.'.format('a'))


發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章