如何使用 mysqli 准备语句绑定字符串数组?

新手上路,请多包涵

我需要将一组值绑定到 WHERE IN(?) 子句。我怎样才能做到这一点?

这有效:

 $mysqli = new mysqli("localhost", "root", "root", "db");
if(!$mysqli || $mysqli->connect_errno)
{
    return;
}
$query_str= "SELECT name FROM table WHERE city IN ('Nashville','Knoxville')";
$query_prepared = $mysqli->stmt_init();
if($query_prepared && $query_prepared->prepare($query_str))
{
    $query_prepared->execute();

但这我无法像这样使用 bind_param :

 $query_str= "SELECT name FROM table WHERE city IN (?)";
$query_prepared = $mysqli->stmt_init();
if($query_prepared && $query_prepared->prepare($query_str))
{
    $cities= explode(",", $_GET['cities']);
    $str_get_cities=  "'".implode("','", $get_cities)."'"; // This equals 'Nashville','Knoxville'

    $query_prepared->bind_param("s", $cities);
    $query_prepared->execute();

我究竟做错了什么?

我也尝试过 call_user_func_array ,但似乎无法获得正确的语法。

原文由 Mark 发布,翻译遵循 CC BY-SA 4.0 许可协议

阅读 333
1 个回答

从 PHP 8.1 开始,您可以直接传递一个数组来执行:

 $sql = "INSERT INTO users (email, password) VALUES (?,?)"; // sql
$stmt = $mysqli->prepare($sql); // prepare
$stmt->execute([$email, $password]); // execute with data!

对于早期版本,任务有点复杂但可行。对于一个简单的情况,当您已经有一个带有占位符的查询时,代码将是

$sql = "INSERT INTO users (email, password) VALUES (?,?)"; // sql
$data = [$email, $password]; // put your data into array
$stmt = $mysqli->prepare($sql); // prepare
$stmt->bind_param(str_repeat('s', count($data)), ...$data); // bind array at once
$stmt->execute();

虽然像您的情况一样,我们有任意数量的占位符,但我们将不得不添加更多代码。我将从我的文章 Mysqli prepared statement with multiple values for IN clause 中获取 解释:

  • 首先,我们需要创建一个字符串,其中包含 ? 标记数组中元素的数量。为此,我们将使用 str_repeat() 功能,该功能非常方便。
  • 然后必须将这个以逗号分隔的问号字符串添加到查询中。虽然它是一个变量,但在这种情况下它是安全的,因为它只包含常量值
  • 那么这个查询必须像任何其他查询一样准备
  • 然后我们需要创建一个字符串,其中包含要与 bind_param() 一起使用的类型。请注意,通常没有理由对绑定变量使用不同的类型——mysql 会很乐意将它们全部作为字符串接受。有一些极端情况,但极为罕见。对于日常使用,您始终可以保持简单并使用“s”来表示所有内容。 str_repeat() 再次来救援。
  • 然后我们需要将我们的数组值绑定到语句。不幸的是,您不能像这样将它写成单个变量 --- , --- bind_param() $stmt->bind_param("s", $array) 中只允许使用标量变量。幸运的是,有一个 参数解包运算符 可以完全满足我们的需要——将一组值发送到一个函数中,就好像它是一组不同的变量一样!
  • 剩下的和往常一样 - 执行查询,获取结果并获取数据!

所以正确的示例代码是

$array = ['Nashville','Knoxville']; // our array
$in    = str_repeat('?,', count($array) - 1) . '?'; // placeholders
$sql   = "SELECT name FROM table WHERE city IN ($in)"; // sql
$stmt  = $mysqli->prepare($sql); // prepare
$types = str_repeat('s', count($array)); //types
$stmt->bind_param($types, ...$array); // bind array at once
$stmt->execute();
$result = $stmt->get_result(); // get the mysqli result
$data = $result->fetch_all(MYSQLI_ASSOC); // fetch the data

尽管此代码相当大,但它比迄今为止本主题中提供的任何其他看似合理的解决方案都小得无法比拟。

原文由 Your Common Sense 发布,翻译遵循 CC BY-SA 4.0 许可协议

撰写回答
你尚未登录,登录后可以
  • 和开发者交流问题的细节
  • 关注并接收问题和回答的更新提醒
  • 参与内容的编辑和改进,让解决方法与时俱进
推荐问题
logo
Stack Overflow 翻译
子站问答
访问
宣传栏