使用 mysqli_stmt_prepare 准备查询,在 WHERE 之后绑定逻辑条件

Posted

技术标签:

【中文标题】使用 mysqli_stmt_prepare 准备查询,在 WHERE 之后绑定逻辑条件【英文标题】:Preparing a query with mysqli_stmt_prepare binding a logical criteria after WHERE 【发布时间】:2017-05-10 00:14:03 【问题描述】:

我需要根据随时间变化的过滤器动态启动查询。每次过滤器都在字符串变量$filter中。 我可以在WHERE 之后绑定它吗,就像下面的代码一样?它似乎不起作用。我期望的结果查询是SELECT NAME FROM PERSONA WHERE GENDER='F'

$filter = "GENDER='F'";
$stmt = mysqli_stmt_init($connection);
mysqli_stmt_prepare($stmt, "SELECT NAME FROM PERSONA WHERE ?");
mysqli_stmt_bind_param($stmt, 's', $filter);

【问题讨论】:

这是一种奇怪的绑定方式。我希望看到WHERE GENDER = ?,而您会将F 绑定到该参数... Can I parameterize the table name in a prepared statement?的可能重复 ^ 这也适用于列。 这个想法是 $filter 可能会改变并且并不总是指代 GENDER:它可能是 CITY='NY' 等等。 【参考方案1】:

您只能绑定值,不能绑定语法元素。所以要么保留gender 条件,然后绑定F 值:

mysqli_stmt_prepare($stmt, "SELECT NAME FROM PERSONA WHERE GENDER=?");
mysqli_stmt_bind_param($stmt, 's', 'F');

或者使用字符串操作来构造查询:

mysqli_stmt_prepare($stmt, "SELECT NAME FROM PERSONA WHERE $filter");

【讨论】:

【参考方案2】:

另一个答案显然是错误的。因为第一个建议根本没有回答这个问题,而第二个建议只适用于性别。虽然即使是城市也是不可能的。

因此您必须动态创建查询。With mysqli it's too toilsome 所以我将展示如何使用 PDO 来做到这一点:

$sql = "SELECT NAME FROM PERSONA WHERE 1";
$filters = [];
$params = []
if ($gender)

    $filters[] = " AND GENDER=:gender";
    $params['gender'] = $gender;

$sql .= implode("", $filters);
$stmt = $pdo->prepare($sql);
$stmt->execute($params);
$data = $stmt->fetchAll();

【讨论】:

以上是关于使用 mysqli_stmt_prepare 准备查询,在 WHERE 之后绑定逻辑条件的主要内容,如果未能解决你的问题,请参考以下文章

我讨厌php help plz

如何使用 MySQL 准备好的语句缓存?

Golang使用准备好的SQL语句

我啥时候应该使用准备好的语句?

如何在 Android sqlite 中使用准备好的语句? [复制]

使用 PDO 准备好的语句 MySQL 错误