個(gè)別重點(diǎn)自己在此記錄下泻仙,希望大家還是參考鳥哥博客的那個(gè)文章
迭代生成器
(迭代)生成器也是一個(gè)函數(shù),不同的是
這個(gè)函數(shù)的返回值是依次返回
( 迭代生成器其實(shí)是生成了一個(gè)對(duì)象),而不是只返回一個(gè)單獨(dú)的值
.
或者,換句話說,生成器使你能更方便的實(shí)現(xiàn)了迭代器接口.下面通過實(shí)現(xiàn)一個(gè)
xrange
函數(shù)來簡單說明:
function xrange($start,$end,$step=1){
for ($i=$start; $i<=$end; $i+=$step){
yield $i;
}
}
//xrange(1,10) ;
foreach (xrange(1,10,2) as $key=>$num){
echo $key.'=>'.$num.'<br>';
}
// 打印
0=>1
1=>3
2=>5
3=>7
4=>9
function xrange($start,$end,$step=1){
for ($i=$start; $i<=$end; $i+=$step){
yield $i;
}
}
var_dump(xrange(1,10,2));
// 打印得到 object(Generator)#1 (0) { }
鳥哥原本的例子是
解析:上面這個(gè)xrange()
函數(shù)提供了和PHP的內(nèi)建函數(shù)range()
一樣的功能.但是不同的是range()函數(shù)返回的是一個(gè)包含值從1到100萬0的數(shù)組
,而xrange()函數(shù)返回的是依次輸出這些值的一個(gè)迭代器
, 而不會(huì)真正以數(shù)組形式返回.
這種方法的優(yōu)點(diǎn)是顯而易見的.它可以讓你在處理大數(shù)據(jù)集合的時(shí)候不用一次性的加載到內(nèi)存中
.甚至你可以處理無限大的數(shù)據(jù)流.
當(dāng)然,也可以不同通過生成器來實(shí)現(xiàn)這個(gè)功能,而是可以通過繼承Iterator接口實(shí)現(xiàn).但通過使用生成器實(shí)現(xiàn)起來會(huì)更方便,不用再去實(shí)現(xiàn)iterator接口中的5個(gè)方法了.
使用數(shù)組
function xrange($start,$end,$step=1){
for ($i=$start; $i<=$end; $i+=$step){
echo $i.'<br>';
}
}
xrange(1,10,2);
// 打印
1
3
5
7
9
生成器為可中斷的函數(shù)
要從生成器認(rèn)識(shí)協(xié)程, 理解它內(nèi)部是如何工作是非常重要的: 生成器是一種可中斷的函數(shù), 在它里面的yield構(gòu)成了中斷點(diǎn).
還是看上面的例子, 調(diào)用xrange(1,1000000)的時(shí)候, xrange()函數(shù)里代碼其實(shí)并沒有真正地運(yùn)行. 它只是返回了一個(gè)迭代器:
<?php
$range = xrange(1, 1000000);
var_dump($range); // object(Generator)#1
var_dump($range instanceof Iterator); // bool(true)
?>
這也解釋了為什么xrange叫做迭代生成器, 因?yàn)樗祷匾粋€(gè)迭代器, 而這個(gè)迭代器實(shí)現(xiàn)了Iterator接口.