带有准备好的语句的 PDO bindParam() 不起作用

Posted

技术标签:

【中文标题】带有准备好的语句的 PDO bindParam() 不起作用【英文标题】:PDO bindParam() with prepared statement isn't working 【发布时间】:2013-11-11 08:42:36 【问题描述】:

好的,这就是问题所在:

这行得通:

$STH = $DBH->prepare("SELECT * FROM juegos WHERE id = 1");
$STH->execute();

这不是:

$STH = $DBH->prepare("SELECT * FROM juegos WHERE id = :id");
$STH->bindParam(':id', '1', PDO::PARAM_STR);
$STH->execute();

我到底做错了什么?它甚至不会抛出异常

谢谢大家!

另外,这是整个代码

<?php
    try 
        $DBH = new PDO("everything is", "ok", "here");

        $DBH->setAttribute( PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION );

        $STH = $DBH->prepare("SELECT * FROM juegos WHERE id = :id");
        $STH->bindParam(':id', '1', PDO::PARAM_STR);
        $STH->execute();

        $STH->setFetchMode(PDO::FETCH_ASSOC);

        while($row = $STH->fetch()) 
            echo $row['nombre']."<br/>";
        

        $DBH = null;

        echo "Todo salió bien";

     catch (PDOException $e) 
        echo "Error";
    

?>

【问题讨论】:

我“可以”或“不能”,因为这也不起作用:$STH = $DBH-&gt;prepare("SELECT nombre FROM juegos WHERE id = :id"); $STH-&gt;bindParam(':id', 1, PDO::PARAM_INT); $STH-&gt;execute(); 您可以在表名上使用参数。抱歉,打错字了 bindParam的第二个参数必须是引用。你不能直接传递值1。作为替代方案,请尝试bindValue 【参考方案1】:

使用bindParam(),变量为bound as a reference。

一个字符串can't be passed by reference。

下面的东西可以通过引用传递:

变量,即 foo($a)

新语句,即 foo(new foobar())

从函数返回的引用

尝试使用bindValue()

$STH->bindValue(':id', '1', PDO::PARAM_STR);

【讨论】:

非常适合做动态 WHERE ;)【参考方案2】:

PHP bindParam() 将 PHP 变量绑定到用于准备语句的 SQL 语句中的相应命名或问号占位符。

bindParam的正确使用方式是:

$id = 1;
$sth = $DBH->prepare("SELECT * FROM juegos WHERE id = :id");
$sth->bindParam(':id', $id, PDO::PARAM_INT);// use bindParam to bind the variable
                          // ^ PDO::PARAM_INT - the value of the variable $id should be an int
                     // ^ $id - the variable being represented by ':id',
              // ^ :id - represents the variable
              // $id - the variable being represented by ':id',

PHP bindValue() 将值绑定到用于准备语句的 SQL 语句中的相应命名或问号占位符。

$id=10;
$name=roadkill;
$sth = $dbh->prepare('SELECT *
    FROM juegos
    WHERE id < :id AND name = :name');
$sth->bindValue(':id', $id, PDO::PARAM_INT);// use bindValue to bind the variable's value
$sth->bindValue(':name', $name, PDO::PARAM_STR);// use bindValue to bind the variable's value

这两种方法的主要区别在于,与PDOStatement::bindValue() 不同,bindParam() 将变量绑定为引用,并且只会在调用PDOStatement::execute() 时进行评估。

【讨论】:

【参考方案3】:

:tabla 参数的值将被 PDO 自动引用和转义。执行的查询将变为:

SELECT * FROM 'juegos'

这不是有效的 SQL。

【讨论】:

那为什么这也不起作用? $STH = $DBH-&gt;prepare("SELECT nombre FROM juegos WHERE id = :id"); $STH-&gt;bindParam(':id', 1, PDO::PARAM_INT); $STH-&gt;execute(); @arielnmz 因为您没有按照应有的方式打开错误报告 错误报告与prepared statements中命名参数的绑定有什么关系? @arielnmz 它会错误报告,它会向您报告错误。 好的,所以你说需要“打开”错误报告才能使 bindParam() 工作?问题比较简单,你说的也没什么用,不过还是谢谢你的回答【参考方案4】:

不要将值直接传递给 BindParam。

try 
       // $DBH = new PDO("everything is", "ok", "here");
        $DBH = new PDO("mysql:host=localhost;dbname=test", 'root', '');
        $DBH->setAttribute( PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION );
        $STH = $DBH->prepare("SELECT * FROM statstracker WHERE SrNo = :id");
        $id = 1; // here you should keep it as variable and pass it to param
        $STH->bindParam(':id', $id, PDO::PARAM_STR);
        $STH->execute();

        $STH->setFetchMode(PDO::FETCH_ASSOC);

        while($row = $STH->fetch()) 
            echo $row['SrNo']."<br/>";
        

        $DBH = null;

        echo "Todo salió bien";

     catch (PDOException $e) 
        echo "Error";
    

【讨论】:

这个问题已经有了答案。不需要再添加了。 哦,但是这个人没有将他的问题标记为已回答,我认为您给我的-1是为了注意,您可以看到这个问题没有回答。 offcorse 在网上有很多更棘手的问题,我的回答是准确的。 很抱歉耽搁了很久(我在 13 年不习惯一边倒)。正确答案是:1. 我不能使用 prep'd 语句来定义表或列名和 2. 如果我使用引用作为参数,我必须使用 bindParam,如果我正在使用 bindValue表达式结果的直接常量,例如$var."foo"。但这是一种解决方法,也很有用。【参考方案5】:

对我来说,用单引号替换双引号解决了这个问题。

上一个:

$STH = $DBH->prepare("SELECT * FROM statstracker WHERE SrNo = :id");

解决方案:

$STH = $DBH->prepare('SELECT * FROM statstracker WHERE SrNo = :id');

它有效,但不知道为什么。

希望对你有帮助!

【讨论】:

以上是关于带有准备好的语句的 PDO bindParam() 不起作用的主要内容,如果未能解决你的问题,请参考以下文章

带有 SQL Server 和准备好的语句的 PHP PDO

带有命名占位符的 PDO 准备好的语句 IN 子句无法按预期工作 [重复]

如何使用带有 BIT(1) 列的 PDO 准备语句?

PDO bindParam 不允许语句返回结果

用于“IN”语句的变量/字符串的 PHP PDO bindParam...? [复制]

SELECT PDO 准备好的语句中的 SELECT [重复]