mysqli_stmt::store_result

mysqli_stmt_store_result

(PHP 5, PHP 7, PHP 8)

mysqli_stmt::store_result -- mysqli_stmt_store_result将结果集存储在内部缓冲区中

描述

面向对象风格

public mysqli_stmt::store_result(): bool

过程式风格

mysqli_stmt_store_result(mysqli_stmt $statement): bool

此函数应该仅在需要在 PHP 中缓冲完整结果集的情况下,才用于成功生成结果集(例如 SELECT, SHOW, DESCRIBE, EXPLAIN)的查询。每个后续的 mysqli_stmt_fetch() 调用将返回缓冲数据。

注意:

对于其他查询,无需调用 mysqli_stmt_store_result(),但如果你这样做,它不会造成任何损害或在所有情况下导致明显的性能损失。你可以通过检查 mysqli_stmt_result_metadata() 是否返回 false 来检测查询是否生成了结果集。

参数

statement

仅过程式风格:由 mysqli_stmt_init() 返回的 mysqli_stmt 对象。

返回值

成功时返回 true,失败时返回 false

错误/异常

如果启用了 mysqli 错误报告 (MYSQLI_REPORT_ERROR) 并且请求的操作失败,则会生成警告。此外,如果模式设置为 MYSQLI_REPORT_STRICT,则会抛出 mysqli_sql_exception 而不是警告。

示例

示例 #1 面向对象风格

<?php

mysqli_report
(MYSQLI_REPORT_ERROR | MYSQLI_REPORT_STRICT);
$mysqli = new mysqli("localhost", "my_user", "my_password", "world");

$query = "SELECT Name, CountryCode FROM City ORDER BY Name LIMIT 20";
$stmt = $mysqli->prepare($query);
$stmt->execute();

/* 将结果存储在内部缓冲区中 */
$stmt->store_result();

printf("行数:%d.\n", $stmt->num_rows);

示例 #2 过程式风格

<?php

mysqli_report
(MYSQLI_REPORT_ERROR | MYSQLI_REPORT_STRICT);
$link = mysqli_connect("localhost", "my_user", "my_password", "world");

$query = "SELECT Name, CountryCode FROM City ORDER BY Name LIMIT 20";
$stmt = mysqli_prepare($link, $query);
mysqli_stmt_execute($stmt);

/* 将结果存储在内部缓冲区中 */
mysqli_stmt_store_result($stmt);

printf("行数:%d.\n", mysqli_stmt_num_rows($stmt));

上面的示例将输出

Number of rows: 20.

参见

添加注释

用户贡献的注释 5 个注释

13
kitlum AT ukr DOT net
9 年前
花了好几个小时才弄明白如何将 mysqli_stmt 的多行结果保存到数组中,而 get_result 被禁止。
有效的想法是使用 store_result
$stmt=$this->mysqli->prepare("SELECT surname, name, user_id, last_m_own, last_m_str, role FROM users WHERE referer_id=(?)");
$stmt->bind_param('i',$referer_id);
$stmt->execute();
$stmt->store_result();
$stmt->bind_result($ans['surname'], $ans['name'], $ans['user_id'], $ans['last_m_own'], $ans['last_m_str'], $ans['role']);
$j=$stmt->num_rows;
for ($i=0;$i<$j;$i++){
$stmt->data_seek($i);
$stmt->fetch();
foreach ($ans as $key=>$value){
$result[$i][$key]=$value;
}
}
希望对像我这样的新手有所帮助
8
pcc at pccglobal dot com
14 年前
当使用 prepare 来准备检索 LOB 的语句时,方法的顺序很重要。
此外,方法 'store_result()' 必须调用,并且必须按正确的顺序调用。
不遵守此项会导致 PHP/MySQLi 崩溃或返回错误的值。
正确的过程顺序是:prepare -> execute -> store_result -> bind -> fetch
以下内容适用于运行 IIS/6.0 + PHP 5.2.1 的 Windows SBS 服务器
MySQL 服务器版本 5.0.26-community-nt,客户端版本 5.0.51a

<?php
$database
= "test" ;
$table = "test" ;
$column = "flongblob" ;
$mysqli = new mysqli("localhost", "root", "<secret_password>", $database);
// 正确的流程顺序:准备 -> 执行 -> 存储结果 -> 绑定 -> 获取
$stmt = $mysqli->prepare("SELECT `$column` FROM `$table`") ;
$stmt->execute();
$stmt->store_result();
// 获取记录。将结果绑定到名为 'value' 的变量并获取。
$stmt->bind_result($value) ;
$res = $stmt->fetch() ;
if(
$res)
{
// strlen($value) 应该有 LOB 长度,而不是 1 或零。
echo "$column 数据长度为 " . strlen($value) . " 字节。\n" ;
}
else
{
echo ((
false !== $res) ? "数据结束" : $stmt->error) . "\n" ;
break ;
}
// 获取另一条记录。
$res = $stmt->fetch() ;
if(
$res)
{
// strlen($value) 应该有 LOB 长度,而不是 1 或零。
echo "$column 数据长度为 " . strlen($value) . " 字节。\n" ;
}
else
{
echo ((
false !== $res) ? "数据结束" : $stmt->error) . "\n" ;
break ;
}
$stmt->close() ;
$mysqli->close() ;
exit ;
?>

上面的例子应该输出
flongblob 数据长度为 932353 字节。
flongblob 数据长度为 867300 字节。

如果流程顺序错误,MySQLi 会崩溃或输出
flongblob 数据长度为 0 字节。
flongblob 数据长度为 867300 字节。
4
neromir at hotmail dot com
15 年前
上面在函数的初始描述中的措辞可能会让人困惑(如下面的引用)。

"对于每个成功生成结果集(SELECT、SHOW、DESCRIBE、EXPLAIN)的查询,你必须调用 mysqli_stmt_store_result(),而且只有当你希望客户端缓冲整个结果集时,这样后续的 mysqli_stmt_fetch() 调用才会返回缓冲数据。"

我最初理解“只有当你希望缓冲...”这句话的意思是,只有当你希望缓冲结果集时才需要调用这个函数。然而,事实并非如此,这种误解给我带来了很多麻烦。

所以,为了澄清对于那些有同样误解的人来说,只要我知道,你必须 ALWAYS 为每个生成结果集的查询调用这个函数(如上面引文中括号内的内容所列)。
2
UCFirefly (at) yahoo.com
18 年前
fetch_fields() 似乎与这里使用的准备语句不兼容。如果你使用通配符,就会变得很困难。我想这在某种程度上是为了安全。
0
Typer85 at gmail dot com
17 年前
针对我下面关于 mysqli_fetch_fields 与准备语句不兼容的说法。

这是不正确的,但是你需要做一些额外的操作。我建议你使用某种包装函数来处理这些麻烦事,但基本思路是一样的。

假设你有一个准备好的语句,如下所示。为了简单起见,我将使用过程式方法,但同样的思路也可以用面向对象的方式实现。

<?php

// 连接等等。

$connectionLink = mysqli_connect( .... );

// 查询等等。

$query = "Select `Id` From `Table` Where `Id` = ?";

// 准备查询。

$prepareObject = mysqli_prepare( $connectionLink , $query );

// 绑定查询。

mysqli_stmt_bind_param( $prepareObject , 'i' , 1 );

// 执行查询。

mysqli_stmt_execute( $prepareObject );

?>

现在,以上所有对熟悉使用准备语句的人来说都很不错,但如果我想使用 mysqli_fetch_fields 或任何其他获取结果集元信息的函数,但这些函数不适用于准备语句呢?

使用特殊函数 mysqli_stmt_result_metadata。它可以按如下方式使用,假设以下代码段紧接在上面代码段之后。

<?php

$metaData
= mysqli_stmt_result_metadata( $prepareObject );

// 我现在可以使用变量
// $metaData 作为参数调用 mysqli_fetch_fields。

$fieldInfo = mysqli_fetch_fields( $metaData );

// 或者这个。

$fieldInfo = mysqli_num_fields( $metaData );

?>

查看 mysqli_stmt_result_metatdata 函数的手册条目,了解如何用准备语句公开它的完整细节。

祝你好运,
To Top