PHP生成器中yield右侧变量的作用是什么?send传值场景解析
关于PHP生成器中
$v = yield $a;里$a的作用解析 这个问题问得特别戳中生成器的“双向特性”痛点——很多刚上手PHP生成器的朋友都会在这里卡壳,毕竟yield同时扮演了“输出”和“接收”两个角色,确实有点反直觉!
咱们先拆解$v = yield $a;这个语句里的两个核心部分:
1. yield $a:生成器向外输出值
当生成器执行到这个语句时,首先会把$a的值传递给生成器的调用者——这个值就是你用$generator->current()能拿到的内容,或者在foreach循环里迭代出来的元素。
完成这个输出后,生成器会暂停执行,等待调用者的下一次触发(比如next()或者send())。这时候,左边的$v还没有被赋值,因为赋值动作要等到生成器恢复执行时才会完成。
2. $v = yield ...:生成器接收外部传入的值
当你调用$generator->send($someValue)时,生成器会从暂停的位置恢复执行。此时,send()传入的$someValue会被赋值给$v,然后生成器继续执行后面的代码,直到遇到下一个yield或者函数结束。
这里要注意:send()本身的返回值,其实是下一个yield输出的值(或者当生成器结束时返回null)。
举个实实在在的例子
看这段代码,你就能瞬间明白两者的关系:
function numberGenerator() { // 第一次yield:输出10,然后暂停 $received = yield 10; echo "生成器收到了:$received\n"; // 第二次yield:输出20,然后暂停 $receivedAgain = yield 20; echo "生成器又收到了:$receivedAgain\n"; } // 初始化生成器 $gen = numberGenerator(); // 第一次获取值:生成器走到第一个yield,输出10 echo "调用者拿到:" . $gen->current() . "\n"; // 输出「调用者拿到:10」 // 发送"hello"给生成器:恢复执行,把"hello"赋值给$received,执行echo,然后走到第二个yield输出20 echo "调用者又拿到:" . $gen->send("hello") . "\n"; // 先输出「生成器收到了:hello」,再输出「调用者又拿到:20」 // 发送"world"给生成器:恢复执行,赋值给$receivedAgain,执行echo,生成器结束 $gen->send("world"); // 输出「生成器又收到了:world」
一句话总结
$v = yield $a;本质是把yield的双向通信能力打包在了一个语句里:
$a是生成器发给调用者的“输出值”;$v是生成器从调用者那里收到的“输入值”(通过send()传入)。
这两个动作完全独立,在生成器的不同生命周期阶段完成,互不干扰。如果用next()代替send(),那么$v会被赋值为null,因为next()等价于send(null)。
内容的提问来源于stack exchange,提问作者Chyaamoo
相关产品推荐
相关产品推荐

