Ir para conteúdo

POWERED BY:

Arquivado

Este tópico foi arquivado e está fechado para novas respostas.

Shinxa

Migração do ADODB para PDO, método moveFirst()

Recommended Posts

Atualmente utilizo a biblioteca ADODB em alguns projetos.

Eu quero migrar para o PDO que é nativo e também mais rápido.

 

Atualmente no ADODB quando eu preciso percorrer o resultado de UMA query várias vezes eu utilizo o método moveFirst() para não ter que realizar a consulta no banco para cada vez que eu desejo percorrer os resultados (desta forma econimizo o acesso ao banco)

Exemplo:

 

//Minha consulta
$rs = $conn->execute('select * from mytable');

//Loop dos resultados
while(!$rs->EOF) {
   echo $rs->fields('name');
   $rs->moveNext();
}

//Movo o ponteiro para o inicio da lista
$rs->moveFirst();

//Consulto o resultado novamente sem precisar executar a consulta novamente
while(!$rs->EOF) {
   echo $rs->fields('name');
   $rs->MoveNext();
}

 

É possível eu fazer no PDO de alguma forma equivalente sem ter que jogar os resultados em alguma váriavel auxiliar (array de resultados, etc)?

Compartilhar este post


Link para o post
Compartilhar em outros sites

Com PDO, você pode fazer o seguinte, leia todo resultado da consulta, coloque em um array, depois itere esse array qntas vezes forem necessárias.

 

Você também pode utilizar o CURSOR_SCROLL, que permite que você feche o resultado para ser iterado novamente.

 

:seta: http://en.wikipedia.org/wiki/Cursor_%28databases%29#Scrollable%5Fcursors

 

<?php
$ATTR = array ( PDO::ATTR_CURSOR => PDO::CURSOR_SCROLL ) ;
$stmt = $pdo->prepare ( 'SELECT * FROM <tabela>' , $ATTR ) ;

Compartilhar este post


Link para o post
Compartilhar em outros sites

Com PDO, você pode fazer o seguinte, leia todo resultado da consulta, coloque em um array, depois itere esse array qntas vezes forem necessárias.

 

O problema é que eu utilizo esse tipo de funcionalidade em toda aplicação, por este motivo que eu já informei no tópico em relação a não utilizar variáveis auxiliares.

 

Para a consulta ficar padrão em toda aplicação eu teria que criar uma classe secundária que pegasse todos os valores do resultado e me retornasse como array, por exemplo.

Mas por preferência minha eu gostaria de utilizar os resultados das consultas do PDO utilizando FETCH_OBJ, sendo assim, criando uma classe auxiliar eu não conseguiria ter este tipo de resultado (ao menos não sei como implementar).

Mas minha dúvida principal é: não é possível fazer de uma forma nativa?

Compartilhar este post


Link para o post
Compartilhar em outros sites

Sim, dá pra fazer com o CURSOR_SCROLL, mas o array você pode guardar o que for necessário, pode guardar objetos .. e afins, e não vejo motivo de criar uma classe pra fazer somente isso, colocar os dados no array ..

Compartilhar este post


Link para o post
Compartilhar em outros sites

Sim, dá pra fazer com o CURSOR_SCROLL, mas o array você pode guardar o que for necessário, pode guardar objetos .. e afins, e não vejo motivo de criar uma classe pra fazer somente isso, colocar os dados no array ..

 

Essa questão do armazenamento de objetos eu pequei mesmo, realmente posso guardar um array com os objetos do resultados da consulta.

 

Sobre o CURSOR_SCROLL, me informaram a mesma coisa no Stack Overflow e falaram que o MySQL não suporta.

Tanto é que fiz um teste aqui e realmente no segundo loop ele não retorna nada:

 

$ATTR = array(PDO::ATTR_CURSOR => PDO::CURSOR_SCROLL);
$rs = $conn->prepare('select * from tabela' , $ATTR);
$rs->execute();

echo '<b>Primeira vez:</b><br/>';
while($o = $rs->fetchObject()){
   echo $o->campo.'<br>';
   }
echo '<br>';

echo '<b>Segunda vez:</b><br/>';
while($o = $rs->fetchObject()) {            
   echo $o->campo.'<br>';
}

Compartilhar este post


Link para o post
Compartilhar em outros sites

É, você tem que aplicar o PDO::FETCH_ORI_FIRST indicando que o fetch será des-de a primeira linha do rowset, se não, não vai funcionar mesmo ..

 

:seta: http://php.net/manual/en/pdo.constants.php

PDO::FETCH_ORI_FIRST (integer)
Fetch the first row in the result set. Valid only for scrollable cursors.

 

Faça assim:

$ATTR = array(PDO::ATTR_CURSOR => PDO::CURSOR_SCROLL);
$rs = $conn->prepare('select * from tabela' , $ATTR);
$rs->execute();

echo '<b>Primeira vez:</b><br/>';
while($o = $rs->fetch(PDO::FETCH_OBJ, PDO::FETCH_ORI_FIRST)){
   echo $o->campo.'<br>';
   }
echo '<br>';

echo '<b>Segunda vez:</b><br/>';
while($o = $rs->fetch(PDO::FETCH_OBJ, PDO::FETCH_ORI_FIRST)) {            
   echo $o->campo.'<br>';
}

Compartilhar este post


Link para o post
Compartilhar em outros sites

Nem me fale, dá até nojo ao abrir os fontes do ADODB. :sick:

Mas eu não queria me sujeitar a outro contorno de situação (gambi).

 

Postando a solução para que se outra alma nesse mundo tiver o mesmo problema, consiga resolver:

 

function getSelect($sql) {

   global $conn;

   $rs = $conn->prepare($sql);
   $rs->execute();

   $r = array();
   while($o = $rs->fetch(PDO::FETCH_OBJ)){
       $r[] = $o;
   }

   return $r;
}

$rs = getSelect('select * from config_class');

echo '<b>Primeira vez:</b><br/>';
foreach($rs as $o) {
   echo $o->name.'<br>';
}
echo '<br>';

echo '<b>Segunda vez:</b><br/>';
foreach($rs as $o) {
   echo $o->name.'<br>';
}

 

Antes que critiquem meu código, isso é só um teste.

Isso com certeza virará uma classe.

Compartilhar este post


Link para o post
Compartilhar em outros sites

×

Informação importante

Ao usar o fórum, você concorda com nossos Termos e condições.