mysqli_stmt_bind_param - 期待引用

时间:2017-02-01 06:17:16

标签: php mysqli

我知道我们必须传递对mysqli_stmt_bind_param的引用。我正在做以下

    $ref = refValues($data);
    function refValues($arr){
        $refs = array();
        foreach($arr as $key => $value)
            $refs[$key] = &$arr[$key];
            var_dump(implode(",", $refs));
            return $refs;
    return $arr;
}

我将所有值都放在数组中。我正在使用上面的函数来获取引用。 Got the above answer from SO

我的PHP版本是5.6

我以下列方式绑定了params。

mysqli_stmt_bind_param($stmt, $types, $ref);

$stmt是通过mysqli_prepare创建的声明。它返回错误号0。

$types只是$types = str_pad('',count($data),'s');

我也验证了$types数据。它返回预期的类型数。即ssssssss

如果我执行,我收到以下错误。

 Only variables should be passed by reference in test.php

我在SO中找到了this解决方案。我不能分配100个变量。我认为这不可行。

我发现另一种选择是call_user_func_arrary

$values =  refValues($data);
call_user_func_array(array($stmt, 'bind_param'), $values);

返回number of bind type doesn't match number of values。这对我来说很奇怪。我已经验证了数组和值。两个计数都匹配。我不知道call_user_func_array的内部实现。

请让我知道有没有办法有效地解决这个问题。

2 个答案:

答案 0 :(得分:3)

这一行

mysqli_stmt_bind_param($stmt, $types, $ref);

表示您有一个引用绑定。

为什么呢?我们来看看:

  • 第一个参数是一个声明
  • 第二个参数是一个类型为
  • 的字符串
  • 以下参数是对应绑定的值的引用。

当您传递一个参数(它是$ref)时 - 您尝试仅绑定一个值。并且$ref 是引用,它是引用的值数组。看到不同?引用数组与引用。

所以,你采取了第二种方法,这是正确的方法:

$values =  refValues($data);
call_user_func_array(array($stmt, 'bind_param'), $values);

这里的错误是什么?您没有通过类型$types

// do not assign anything to a variable
// pass results of `refValues` directly to `call_user_func_array`
call_user_func_array(array($stmt, 'bind_param'), array_merge(array($types), refValues($data)));

我们在这里做什么:我们试图调用$stmt->bind_param并将此函数参数作为数组传递。

$stmt->bind_param的论点是什么?

  • 第一个参数是类型($types
  • 以下参数是对值($values
  • 的引用

现在应该可以了。

答案 1 :(得分:1)

有两种方法可以避免这种麻烦:

  1. 使用PDO。你目前的问题只是你使用mysqli的许多WTF中的第一个。在这种特殊情况下,它将像一样简单

    $stmt = $db->prepare($sql);
    $stmt->execute($data);
    
  2. 好的,你有一种使用mysqli的心血来潮。然后,只要您使用受支持的PHP版本you can use a splat or a three dot operator

    $stmt = $db->prepare($sql);
    $types = str_repeat('s', count($data));
    $statement->bind_param($types, ...$data);
    $statement->execute();