【问题标题】:php mysqli bind_param Wrong parameter countphp mysqli bind_param 参数计数错误
【发布时间】:2012-08-09 02:21:52
【问题描述】:

这里有很多关于此的问题,但我找不到我的问题。

使用存储为属性的 mysqli 的 DB 类。使用魔法调用方法触发准备、绑定和执行:

public static function __callStatic($name, $arg)
{
    echo '<pre>';
    var_dump($arg);
    echo '</pre>';
    if($name == 'Prepare'){
        self::$Stmt = self::$mysqli->prepare(implode(', ', $arg));
        $return = self::$Stmt;
    }elseif($name == 'Bind')
        $return = self::$Stmt->bind_param(implode(', ', $arg));
    elseif($name == 'Execute')
        $return = self::$Stmt->execute();
    else
        $return = self::$mysqli->$name(implode(', ', $arg));
    if(!self::GetErr())
        return $return;
}

我还有一个生成 SQL 语句的类。这是准备语句中使用的输出:

INSERT INTO account (UName, FName, LName, Email, Password, RecQuestion, RecAnswer, Admin) VALUES (?, ?, ?, ?, ?, ?, ?, ?) 

代码如下:

DB::Prepare(SQL::Table('account')->Insert([
    'UName' => '?',
    'FName' => '?',
    'LName' => '?',
    'Email' => '?',
    'Password' => '?',
    'RecQuestion' => '?',
    'RecAnswer' => '?',
    'Admin' => '?'
]));
DB::Bind('sssssssi', $userName, $fName, $lName, $email, $password, $recQ, $recA, $admin);
DB::Execute();

正如我所见,它有 8 种类型和 8 个值...

这也是var_dump($arg) 的输出,用于调用 DB::Bind 时

array(9) {
  [0]=>
  string(8) "sssssssi"
  [1]=>
  string(4) "user"
  [2]=>
  string(5) "first"
  [3]=>
  string(4) "last"
  [4]=>
  string(15) "email@email.com"
  [5]=>
  string(64) "$2a$10$Tw4eOkUYA6SX8WP8XJfKZeFfOM9htVRJyP0d1iYlka0jNCV/qPGzazakT"
  [6]=>
  string(7) "recover"
  [7]=>
  string(64) "$2a$10$LrfK2EdkRi6pPdx1tUtPWe8p24T8ISdQHYhW0N06RjbvCrU4Flqiie4jU"
  [8]=>
  int(1)
}

【问题讨论】:

  • DB::Bind('sssssssi', $userName, $fName, $lName, $email, $password, $recQ, $recA, $admin); 有 9 个。你真的需要这个 'sssssssi' 吗?
  • 是的,应该是这样吗?第一个是 8 种类型,然后是 8 个值。 php.net/manual/en/mysqli-stmt.bind-param.php
  • 上次我检查过。 1) $userName, 2) $fName, 3) $lName, 4) $email, 5) $password, 6) $recQ, 7) $recA, 8) $admin 第 9 个值在哪里?
  • -_- 查看文档。 'sssssssi' 是列类型的必需参数。 s=string 和 i=int;
  • 尝试删除问号周围的引号。

标签: php mysql mysqli prepared-statement


【解决方案1】:

implode(', ', $arg) 返回一个字符串,所以它只得到一个参数。解决这个问题的正确方法是使用call_user_func_array();

但它并不像看起来那么明显。 bind_param() 期望通过引用而不是值传递参数。 __callStatic($name, $arg) 有一个值数组而不是引用,因此需要一个包含对这些值的引用的本地副本。

解决方案:

elseif($name == 'Bind'){
    foreach($arg as &$v)
        $Arg[] = &$v;
    $return = call_user_func_array(array(self::$Stmt, 'bind_param'), $Arg);
}

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2015-09-01
    • 2012-04-20
    • 1970-01-01
    • 2023-03-25
    • 2022-01-14
    相关资源
    最近更新 更多