[英]Error when using mysqli bind_param()
我试图在我的PHP项目的数据库中的29个字段中进行搜索。 我正在使用mysqli连接到我的数据库。 当我不尝试使用bind_param()时,我的查询工作正常,但在出现错误时却失败了:
PHP Warning: mysqli_stmt::bind_param() [<a href='mysqli-stmt.bind-param'>mysqli-stmt.bind-param</a>]: Number of variables doesn't match number of parameters in prepared statement in /search.php on line 6
我的代码如下:
<?php
$find = $_POST['find'];
if (strcasecmp($_POST['in'], 'users') == 0) {
$query = $db->prepare("SELECT u.id, u.group_id, u.username, u.email, m.credits, m.first_name, m.last_name, m.address1, m.address2, m.city, m.state, m.country, m.zipcode, m.about, m.account_status, m.vacation_status FROM kf_users u JOIN kf_usermeta m ON u.id = m.id WHERE u.id LIKE '%?%' OR u.group_id LIKE '%?%' OR u.ip_address LIKE '%?%' OR u.username LIKE '%?%' OR u.password LIKE '%?%' OR u.salt LIKE '%?%' OR u.email LIKE '%?%' OR u.activation_code LIKE '%?%' OR u.forgotten_password_code LIKE '%?%' OR u.remember_code LIKE '%?%' OR u.created_on LIKE '%?%' OR u.last_login LIKE '%?%' OR u.active LIKE '%?%' OR u.FUID LIKE '%?%' OR m.id LIKE '%?%' OR m.credits LIKE '%?%' OR m.rating LIKE '%?%' OR m.user_id LIKE '%?%' OR m.first_name LIKE '%?%' OR m.last_name LIKE '%?%' OR m.address1 LIKE '%?%' OR m.address2 LIKE '%?%' OR m.city LIKE '%?%' OR m.state LIKE '%?%' OR m.country LIKE '%?%' OR m.zipcode LIKE '%?%' OR m.about LIKE '%?%' OR m.account_status LIKE '%?%' OR m.vacation_status LIKE '%?%'");
$query->bind_param('sssssssssssssssssssssssssssss',$find,$find,$find,$find,$find,$find,$find,$find,$find,$find,$find,$find,$find,$find,$find,$find,$find,$find,$find,$find,$find,$find,$find,$find,$find,$find,$find,$find,$find);
$query->execute();
$query->bind_result($id, $group, $username, $email, $credits, $first_name, $last_name, $address1, $address2, $city, $state, $country, $zipcode, $about, $account_status, $vacation_status);
while ($query->fetch()) {
$result['id'] = $id;
$result['group'] = $group;
$result['username'] = $username;
$result['email'] = $email;
$result['credits'] = $credits;
$result['first_name'] = $first_name;
$result['last_name'] = $last_name;
$result['address1'] = $address1;
$result['address2'] = $address2;
$result['city'] = $city;
$result['state'] = $state;
$result['country'] = $country;
$result['zipcode'] = $zipcode;
$result['about'] = $about;
$result['account_status'] = $account_status;
$result['vacation_status'] = $vacation_status;
$output[] = $result;
}
$query->close();
}
?>
同样,如果我注释掉我的bind_param()行,并替换?
在我的搜索字词查询中,数据被返回,但还是出现错误,并且没有数据。 任何人对这里可能出现的问题有任何想法吗?
你有29岁?
的是你查询,29 s
在您的数据类型条目bind_param
列表,29 $find
变量但是绑定,当你封装你?
引号中的占位符-它们不再是占位符,它们只是字符串。 因此,MySQL看到要绑定的参数为零 ,而您试图绑定29。
要使用prepared语句执行简单的LIKE
子句,您需要执行以下操作:
$query = $db->prepare("SELECT * FROM some_table WHERE field LIKE ?");
$query->bind_param('s',$find);
您要匹配%$find%
。 您可以执行以下操作:
$query = $db->prepare("SELECT * FROM some_table WHERE field LIKE ?");
$query->bind_param('s', '%'.$find.'%');
甚至更复杂的是,您可以在每个参数上使用CONCAT()
:
$query = $db->prepare("SELECT * FROM some_table WHERE field LIKE CONCAT('%', ?, '%')");
$query->bind_param('s',$find);
使用现有代码和第一种方法('%'.$find.'%')
复制+粘贴:
$query = $db->prepare("SELECT u.id, u.group_id, u.username, u.email, m.credits, m.first_name, m.last_name, m.address1, m.address2, m.city, m.state, m.country, m.zipcode, m.about, m.account_status, m.vacation_status FROM kf_users u JOIN kf_usermeta m ON u.id = m.id WHERE u.id LIKE ? OR u.group_id LIKE ? OR u.ip_address LIKE ? OR u.username LIKE ? OR u.password LIKE ? OR u.salt LIKE ? OR u.email LIKE ? OR u.activation_code LIKE ? OR u.forgotten_password_code LIKE ? OR u.remember_code LIKE ? OR u.created_on LIKE ? OR u.last_login LIKE ? OR u.active LIKE ? OR u.FUID LIKE ? OR m.id LIKE ? OR m.credits LIKE ? OR m.rating LIKE ? OR m.user_id LIKE ? OR m.first_name LIKE ? OR m.last_name LIKE ? OR m.address1 LIKE ? OR m.address2 LIKE ? OR m.city LIKE ? OR m.state LIKE ? OR m.country LIKE ? OR m.zipcode LIKE ? OR m.about LIKE ? OR m.account_status LIKE ? OR m.vacation_status LIKE ?");
$query->bind_param('sssssssssssssssssssssssssssss','%'.$find.'%','%'.$find.'%','%'.$find.'%','%'.$find.'%','%'.$find.'%','%'.$find.'%','%'.$find.'%','%'.$find.'%','%'.$find.'%','%'.$find.'%','%'.$find.'%','%'.$find.'%','%'.$find.'%','%'.$find.'%','%'.$find.'%','%'.$find.'%','%'.$find.'%','%'.$find.'%','%'.$find.'%','%'.$find.'%','%'.$find.'%','%'.$find.'%','%'.$find.'%','%'.$find.'%','%'.$find.'%','%'.$find.'%','%'.$find.'%','%'.$find.'%','%'.$find.'%');
绑定参数与字符串插值不同; 您不能仅将变量替换为?
,也不应该引用它们。 占位符代表整个值。
相反,您应该像这样准备查询
$query = $db->prepare('SELECT ... WHERE u.id LIKE ? OR u.group_id LIKE ? ... ');
然后将值包装在通配符中
$find = '%' . $find . '%';
我强烈建议使用PDO代替MySQLi。 有了它,您可以使用命名占位符,例如
$stmt = $pdo->prepare('SELECT ... WHERE u.id LIKE :term OR u.group_id LIKE :term ... ');
$find = '%' . $find . '%';
$stmt->bindParam('term', $find);
$stmt->execute();
这样,您可以在整个查询中重复使用相同的占位符
如果这不起作用,那么您可能正在使用mariadb而不是mysql。 这个问题是两者之间的细微差别。
我对代码所做的更改是:
$search_text=$db->real_escape_string($search_text);
$stmt=$db->prepare("SELECT * FROM rentals WHERE search_text LIKE '%{$search_text}%'");
//TODO Put the bind_param back when it works someday; plus take out the escape.
//$stmt=$db->prepare("SELECT * FROM rentals WHERE search_text LIKE ?");
//$stmt->bind_param('s', '%'.$search_text.'%');
$stmt->execute();
粗略,但暂时是可行的解决方案。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.