PHP: Generators and PDO

25 Oct 2017 in PHP

Do you know that you can use Generators in PHP to efficiently fetch data from a database?

Consider this code to get something from a database table:

<?php
$stmt = $this->pdo->prepare("SELECT * FROM table");
$stmt->execute();
// large typing version...
$rows = [];
foreach ($stmt as $row) {
    $rows[] = $row;
}
return $rows;
// ...or short typing version
return $stmt->fetchAll();

On large datasets this have a direct impact on memory footprint and you are probably going to hit the memory limit.

To avoid this problem, you can use generators like below:

<?php
$stmt = $this->pdo->prepare("SELECT * FROM table");
$stmt->execute();
foreach ($stmt as $row) {
    yield $row;
}

Be warned that this returns an Iterator/Generator instead of an actual array so you may have to wrap it in iterator_to_array when used in functions expecting an array instead of an Iterator. Eg:

<?php
// use it like
array_map($callable, iterator_to_array($data));
// instead of
array_map($callable, $data);