我刚刚写了一个生成器的一部分,并达到了正确运行的地步,但需要进行一些重构。该方法的结构如下:拆分PHP生成器
public function getFlattenedList(array $elements) {
foreach ($elements as $element) {
if ($this->someCondition($element)) {
// A pile of stuff here
if ($anotherCondition) {
for ($i = 0; $i < $this->someValue(); $i++) {
yield $this->anotherOperation($element);
}
}
}
else {
yield $this->someOperation($element);
}
}
}
这种方法是大/复杂的。最明显的做法是将if分支的主体移出自己的方法。事情是这样的
public function getFlattenedList(array $elements) {
foreach ($elements as $element) {
if ($this->someCondition($element)) {
// ???
$this->getFlattenedElement($element);
}
else {
yield $this->someOperation($element);
}
}
}
private function getFlattenedElement() {
// A pile of stuff here
if ($anotherCondition) {
for ($i = 0; $i < $this->someValue(); $i++) {
yield $this->anotherOperation($element);
}
}
}
但我当然不能只是返回这个新功能的结果,因为它也是一台发电机。 (我希望它是一个发电机,所以工作只在需要的值时完成)。我做的工作是在if条件的内部添加另一个循环:
public function getFlattenedList(array $elements) {
foreach ($elements as $element) {
if ($this->someCondition($element)) {
foreach ($this->getFlattenedElement($element) as $flattened) {
yield $flattened;
}
}
else {
yield $this->someOperation($element);
}
}
}
是否有可能避免必须添加该循环,同时保持生成器行为并很好地分离该方法?我之前没有使用过发电机,所以可能会漏掉一些明显的东西。
为什么不消除'foreach($ this-> getFlattenedElement($ element)$ flattened){ yield $ flattened; } '带一个简单的'yield $ this-> getFlattenedElement($ element)''试试看!你的循环是由'getFlattenedElement()'生成器处理的 – 2014-10-31 18:37:41
我试过了,但是然后我的测试失败了,所以它绝对不是等价的。如果我这样做,它会产生发电机,从而产生'Generator'类型的结果? – 2014-10-31 18:40:31
那么它没有理由不应该工作:它不应该产生发电机,但应该产生发电机的结果....递归发电机做的工作 – 2014-10-31 18:45:03