Задача буферизованного запроса PHP PDO

У меня возникли серьезные проблемы с функциями объекта данных PHP. Я пытаюсь пройти через значительный набор результатов (~ 60k строк, ~ 1gig), используя буферный запрос, чтобы избежать выборки всего набора.

Независимо от того, что я делаю, сценарий просто зависает на PDO :: query () – кажется, что запрос работает небуферизованным (почему еще изменилось бы изменение размера набора результатов?). Вот мой код, чтобы воспроизвести проблему:

<?php $Database = new PDO( 'mysql:host=localhost;port=3306;dbname=mydatabase', 'root', '', array( PDO::ATTR_ERRMODE => PDO::ERRMODE_EXCEPTION, PDO::MYSQL_ATTR_USE_BUFFERED_QUERY => true ) ); $rQuery = $Database->query('SELECT id FROM mytable'); // This is never reached because the result set is too large echo 'Made it through.'; foreach($rQuery as $aRow) { print_r($aRow); } ?> 

Если я ограничу запрос некоторым разумным числом, он отлично работает:

 $rQuery = $Database->query('SELECT id FROM mytable LIMIT 10'); 

Я попытался сыграть с PDO :: MYSQL_ATTR_MAX_BUFFER_SIZE и использовать PDO :: prepare () и PDO :: execute () (хотя в вышеприведенном запросе нет параметров), и это не помогло. Любая помощь будет оценена по достоинству.

Если я понимаю это правильно, буферизованные запросы включают в себя указание PHP, что вы хотите дождаться всего набора результатов перед началом обработки. До PDO это было по умолчанию, и вам нужно было вызвать mysql_unbuffered_query если вы хотите немедленно mysql_unbuffered_query результаты.

Почему это не объясняется на странице драйвера PDO MySQL, я не знаю.

Вы можете попытаться разбить его на куски, которые недостаточно велики, чтобы вызвать проблемы:

 <?php $id = 0; $rQuery = $Database->query('SELECT id FROM mytable ORDER BY id ASC LIMIT 100'); do { stuff($rQuery); $id += 100; } while ( $rQuery = $Database->query( 'SELECT id FROM mytable ORDER BY id ASC LIMIT 100 OFFSET '.$id ) ); ?> 

Во всяком случае, у вас есть идея.

Или, может быть, вы можете попробовать mysql-функции:

 while ($row = mysql_fetch_row($query)) { ... } 

Который определенно будет быстрее, поскольку этот оператор foreach производит впечатление на использование fetchAll() вместо fetch() каждой строки