迭代PDO查询的结果

时间:2013-01-03 21:14:51

标签: php mysql pdo

我想基于URL参数中的数据使用PDO运行查询(是的,我知道这很容易受到攻击,但是它的实用程序的内部代码)。

$user = 'USER';
$pass = 'PASSWORD';
$dsn = 'mysql:dbname=PRODUCTS;host=HOST'; 

try {
    $productDB = new PDO($dsn, $user, $pass); 
    $productDB->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
}
catch(PDOException $e) {
    $msg = 'PDO ERROR' . $e->getFile() . ' L.' . $e->getLine() . ' : ' . $e->getMessage();
    die($msg);
}
if(isset($_GET['cat'])) 
{
    $cat = $_GET['cat'];
    print "cat = $cat <br>";
    $products = $productDB->prepare('SELECT * FROM products WHERE cat_id LIKE ?');
    $products->execute(array($cat));
    $rows = $products->rowCount();
    print "$rows rows returned";
?>
<table border="1">
<tr>
    <td>product_id</td>
    <td>product_name</td>
</tr>
<?php
foreach ($products->fetchAll() as $row) {
    $id = $row['product_id'];
    $product_name = $row['product_name'];
    print "<tr>";
    print "<th scope=\"row\"><b>$id</b></th>";
    print "<td> $product_name </td>";
    print "<tr>";
    }
print "</table>";
}
?>

当我运行此代码时,它会根据查询打印正确的行数,但不会填充表。

我还尝试将prepareexecute行替换为:

$products = $productDB->query("SELECT * FROM products WHERE cat_id LIKE $cat");

返回正确的行数,但没有其他帮助。

最后,我尝试用以下内容替换foreach行:

$rows = $products->fetchAll();
foreach ($rows as $row) {

我尝试使用固定查询执行相同的操作都可以正常工作,但我无法确定如何在查询中放置变量元素,然后迭代结果。

2 个答案:

答案 0 :(得分:3)

你没有做任何事情来存储结果:

$products->execute(array($cat));

需要进入变量:

$result = $products->execute(array($cat));

然后,请使用$products->fetchAll()

,而不是调用$results->fetchAll()
foreach ($result->fetchAll() as $row)

我发现使用$query变量(prepare等)更容易,然后将结果转换为$result$product。使代码更容易阅读。

答案 1 :(得分:2)

试试这个(如果我理解正确的话):

$products = $productDB->prepare("SELECT * FROM products WHERE cat_id LIKE :cat");

// Now, you can either do this :
$products->bindParam('cat', '%'.$cat.'%');
$products->execute();

// or you can call execute with an associative array of your parameterized query.
$products->execute(array('cat' => '%'.$cat.'%'));

// Then, get all the results like this :
$rows = $products->fetchAll();
foreach ($rows as $row) {
    // Do work here ..
}

// Or, like this :
while ($row = $products->fetch(PDO::FETCH_ASSOC)) {
    // Do work here ..
}

我个人更喜欢while,因为你没有在一个var中获取整个查询,减少了所需的内存量。

我还建议您使用FETCH_*参数,以获得您想要的那种数组。

顺便说一下,您需要知道rowCount不应该用于计算SELECT返回的行数。正如php.net所说:

  

如果关联的PDOStatement执行的最后一条SQL语句是SELECT语句,则某些数据库可能会返回该语句返回的行数。但是,并不保证所有数据库都有这种行为,不应依赖于便携式应用程序。