A Classic Use Case for PHP Iterative Generators

PHP

About PHP Iterative Generators

What is an iterative generator? I won’t elaborate here, because one of PHP’s core developers, Niao Ge, has already written an excellent explanation:

Using Coroutines in PHP for Multitask Scheduling

Instead of repeating the fundamentals, I’ll just document one classic application scenario for iterative generators.

The Scenario

When processing data with PHP, we often use ORM queries to fetch batches of data, like:

Users::all();

This is fine when the Users table is small, but if it’s large, it can easily cause memory overflow.

So how can we implement this elegantly and efficiently? The answer is iterative generators.

Improved Solution

<?PHP
class A {
protected function getUsers($count){
for ($i = 1; $i <= $count; $i++){
yield Users::where('id', $i)->first();
}
}
public function dealUser(){
$count = Users::count()
foreach ($this->getUsers($count) as $value){
$value->username;
// other code ....
}
}
}

Due to the nature of iterative generators, only one record is loaded at a time, perfectly solving the memory overflow problem with very minimal code changes.

Tip: This approach increases database connection time (since it queries one record at a time) — it’s a classic case of trading time for space.

Summary

This is just a simple example. I hope it can serve as food for thought and be applied to more scenarios.

Additionally, PHP 7 supports Generator Delegation as a new feature (see PHP 7.0 New Features: Generator Delegation).