我正在尝试使用带有LIKE语句查询和通配符运算符的mysqli预处理语句。调试后,在整个代码中使用echo语句,我可以看到我的while语句没有执行。你能看到我在这里做错了吗?
这是我第一次在这个论坛上提问,所以如果这不是一个好问题我会道歉;我花了6个小时试图让我的代码的准备好的语句部分工作,我找不到任何解决我的问题的线程,这些线程并没有完全超出我的想法(例如How can I put the results of a MySQLi prepared statement into an associative array?)。我找到的最接近的两个是:
Using wildcards in prepared statement - MySQLi 和Combine PHP prepared statments with LIKE。
以下是我的代码的相关摘录:
//set up and execute queries
$titleQuery = "SELECT keyframeurl, videoid, title, creationyear, sound, color,
duration, genre FROM openvideo WHERE title LIKE CONCAT ('%', ?, '%')
ORDER BY $order";
if($stmt = mysqli_prepare($db, $titleQuery)){
//bind parameters
mysqli_stmt_bind_param($stmt, 's', $trimmedTitleSearch);
//execute query
mysqli_stmt_execute($stmt);
//bind results
mysqli_stmt_bind_result($stmt, $keyframeurl, $videoid, $title, $year, $sound,
$color, $duration, $genre);
//store result so num rows can be counted
$result = mysqli_stmt_store_result($stmt);
//fetch results
while ($row = mysqli_fetch_array($result, MYSQL_ASSOC)) {
echo "<tr>";
echo "<td><a href=\"".$row['keyframeurl']."\">".$row['videoid']."</a></td>";
echo "<td>" . $row['title'] . "</td>";
echo "<td>" . $row['year'] . "</td>";
echo "<td>" . $row['sound'] . "</td>";
echo "<td>" . $row['color'] . "</td>";
echo "<td>" . $row['duration'] . "</td>";
echo "<td>" . $row['genre'] . "</td>";
echo "</tr>";
}
}
else {
// Error
printf("Prepared Statement Error: %s\n", $db->error);
}
感谢您的任何建议!
答案 0 :(得分:1)
您正在混合两种取样结果。要么使用丑陋的bind_result方式(然后使用fetch()
来获取数据),要么尝试使用get_result()
- 所以,您将能够使用fetch_array()
(尽管不能保证)。< / p>
无论如何,只需摆脱所有混乱并使用PDO。
$titleQuery = "SELECT keyframeurl, videoid, title, creationyear, sound, color,
duration, genre FROM openvideo WHERE title LIKE CONCAT ('%', ?, '%')
ORDER BY $order";
$stmt = $pdo->prepare($titleQuery);
$stmt->execute(array($trimmedTitleSearch));
$data = $stmt->fetchAll();
foreach ($data as $row ) {
// the rest is the same as yours
我希望您正确清理您的$ order变量。最好的办法显然是通过占位符添加它,因此,您需要一个允许它的库,SafeMysql例如:
$sql = "SELECT * FROM openvideo WHERE title LIKE CONCAT ?s ORDER BY ?n";
$data = $db->getAll($sql,"%$trimmedTitleSearch%", $order);
foreach ($data as $row ) {
// the rest is the same as yours
请注意代码量,并与当前使用的原始API调用负载进行比较
答案 1 :(得分:0)
@Your Common Sense - 你看,没有必要让allenbell_nc“......只是摆脱所有的混乱并使用PDO”就像你推断的那样。仅仅因为你用预先准备好的陈述对mysqli扩展有错误的印象并不意味着其他人应该在一丝不苟的麻烦中废除它,而不是进行深入但痛苦的研究。毕竟,这就是stackoverflow的意义所在,不是吗?很好的研究答案..
@allenbell_nc - 为了回答你的问题,我不认为你的问题与你使用Wild卡和东西有关。问题出在您尝试使用的代码行中
mysqli_fetch_array()
。这很可能会引发一个抱怨参数1($ result)的错误,因为mysqli_stmt_store_result()
用于以后要查找从查询返回的行数的情况,因此它返回boolean(true或false) )而不是结果集。
INSTEAD,在执行调用后使用mysqli_stmt_bind_result()
然后在while条件下调用mysqli_stmt_fetch()
,最后在while条件体中使用array_push()
,这将帮助您存储并随后回显你的ASSOCIATIVE数组的内容。
快速示例(由Carson McDonald先生提供的创意@ [http://www.ioncannon.net/programming/889/php-mysqli-and-multiple-prepared-statements/] [1]):
...
$ comments = array();
$comment_stmt->bind_param('i', $post_id);
if ($comment_stmt->execute())
{
$comment_stmt->bind_result($user_id);
while ($comment_stmt->fetch())
{
array_push($comments, array('user_id' => $user_id));
//Now you can go ahead and make use of $comments however you want, whether as stored in an $_SESSION array variable or just to echo it out! As Demonstrated Below:
$_SESSION = $comments;
echo $_SESSION['user_id'];
}
}
...
希望对您有所帮助 - 第一次询问您,这也是我第一次回答您的项目。
答案 2 :(得分:-1)
echo "<td>" . $row['color'] . "</td>";
echo "<td>" . $row['duration'] . "</td>";
echo "<td>" . $row['genre'] . "</td>";
echo "</tr>"; while ($row = mysqli_fetch_array($stmt, MYSQL_ASSOC))
或while ($row = mysqli_stmt_fetch($stmt))
编辑:
mysqli_stmt_bind_result($stmt, $keyframeurl, $videoid, $title, $year, $sound,
$color, $duration, $genre);
//store result so num rows can be counted
$result = mysqli_stmt_store_result($stmt);
//fetch results
while (mysqli_stmt_fetch($stmt)) {
echo "<tr>";
echo "<td><a href=\"".$keyframeurl."\">".$videoid."</a></td>";
echo "<td>" . $title . "</td>";
echo "<td>" . $year . "</td>";
echo "<td>" . $sound . "</td>";
echo "<td>" . $color . "</td>";
echo "<td>" . $duration . "</td>";
echo "<td>" . $genre. "</td>";
echo "</tr>";
}