php - 将 bind_param 与数组和循环一起使用

标签 php mysql arrays mysqli prepared-statement

根据准备好的语句的这个example,我首先绑定(bind)参数,然后为参数设置值。

假设我有一个二维数组 $alias

$array1 = [
    'id' => 1,
    'tstamp' => 123456789,
    'alias' => '$alias',
];

$array2 = [
    'id' => 1,
    'tstamp' => 123456789,
    'alias' => '$alias2',

];

$alias = [$array1, $array2];

为什么这段代码有效
$insert = 'INSERT INTO abcdef VALUES (?,?,?)';
$insertStmt = $conn->prepare($insert);
foreach ($alias as $array) {
    $insertStmt->bind_param('iis', $array['id'], $array['tstamp'], $array['alias']);
    $insertStmt->execute();
}

这不是吗?
$insert = 'INSERT INTO abcdef VALUES (?,?,?)';
$insertStmt = $conn->prepare($insert);
$insertStmt->bind_param('iis', $array['id'], $array['tstamp'], $array['alias']);
foreach ($alias as $array) {
   $insertStmt->execute();
}

如果我必须一直绑定(bind)参数,那么流量会更多,不是吗?

最佳答案

bind_param()通过引用特定的 zval container 进行绑定(bind).在循环的每次迭代中,都会为新的数组符号表分配其自己的 zval 容器。如果在绑定(bind)时 zval 容器不存在,它们将被创建。这可以通过以下代码显示:

$insertStmt = $conn->prepare('INSERT INTO abcdef VALUES (?,?,?)');
$insertStmt->bind_param('sss', $array['id'], $array['tstamp'], $array['alias']);
var_dump($array);

输出:
array (size=3)
  'id' => null
  'tstamp' => null
  'alias' => null

即使我们没有声明 $array在任何地方,绑定(bind)都使用空值隐式创建它。绑定(bind)将继续指向这个空数组。

当然,当我们开始迭代别名数组时,$array每次都会重新创建。我们绑定(bind)参数的旧数组符号表现在已经不存在了。我们没有将任何东西绑定(bind)到新数组。

要解决此问题,您只需移动 bind_param()里面foreach循环为:
$insertStmt = $conn->prepare('INSERT INTO abcdef VALUES (?,?,?)');
foreach ($alias as $array) {
    // bind to the new zval containers every iteration
    $insertStmt->bind_param('sss', $array['id'], $array['tstamp'], $array['alias']);
    $insertStmt->execute();
}

关于php - 将 bind_param 与数组和循环一起使用,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/36777813/

相关文章:

php - 将样式文件或脚本引入 WordPress 模板

mysql - 索引 3 个整数字段的 mysql 表

c - 从标准输入读取一个字符数组

android - 房间库不接受字节数组

java - 用偶数和奇数分隔文件中的行

php - MySQL - 我如何/解决方法按组函数的结果排序

php - 我们如何在 PHP 中添加两个日期间隔

php 在使用澳大利亚/悉尼时区时给出错误答案

mysql - Mysql中NULL和空值的区别

c# - MySql和 Entity Framework 导致 "Object reference not set to an instance of an object."