gpt4 book ai didi

SQL查询的PHP大量内存使用

转载 作者:塔克拉玛干 更新时间:2023-11-03 05:39:19 25 4
gpt4 key购买 nike

我在优化 Apache + PHP 内存使用时偶然发现了一个奇怪的问题。基本上,当尝试绑定(bind) MySQLi 查询的结果时,代码会出现错误消息“ fatal error :允许的 16777216 字节的内存大小已耗尽(尝试分配 50331646 字节)”。

相关的表格是:

CREATE TABLE `note` (
`noteID` int(11) NOT NULL AUTO_INCREMENT,
`contentID` int(11) NOT NULL,
`text` mediumtext NOT NULL,
PRIMARY KEY (`noteID`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;

CREATE TABLE `content` (
`contentID` int(11) NOT NULL AUTO_INCREMENT,
`text` varchar(2048) NOT NULL,
`datestamp` datetime NOT NULL,
PRIMARY KEY (`contentID`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;

爆炸的查询是:

select content.contentID, 
content.text,
content.datestamp,
note.noteID,
note.contentID, note.text
from basereality.content as content
inner join basereality.note as note
on content.contentID = note.contentID
where content.contentID = 1028 ;

在服务器上的 MySQL 中运行查询运行正常,返回的 'note' 大小在千字节以下。

一件奇怪的事情是,它试图分配 50331646 的大小是十六进制的 0x2FFFFFE,这是一个可疑的整数。这几乎就像 PHP 试图分配一个足够大的缓冲区来容纳尽可能大的 mediumtext 字段,而不是实际为检索到的数据分配内存。

除了增加 PHP 允许的最大内存之外,有人知道解决这个问题的方法吗?

btw 其他人遇到了同样的问题,但似乎不知道如何解决。 Out of memory (allocated 50855936) (tried to allocate 50331646 bytes)

爆炸的确切行是:

$statement->bind_result(
$content_contentID,
$content_text,
$content_datestamp,
$note_noteID,
$note_contentID,
$note_text);

将查询更改为选择“'A test string' as note”,而不是获取列不再显示大量内存使用。

顺便说一句,我确定我不是在尝试检索大数据。这显示了注释表中 mediumtext 字段的实际长度:

 select length(text) from basereality.note;
+--------------+
| length(text) |
+--------------+
| 938 |
| 141 |
| 1116 |
| 431 |
| 334 |
+--------------+

最佳答案

我在另一个问题中找到了答案并评论:

Allowed memory size of 67108864 bytes exhausted

基本上,在旧的 MySQL 连接器库中,不是只分配字段“文本”的实际大小来存储结果,而是分配类型 mediumtext 的最大可能大小。

即即使结果字段只有 100 KB,也总是分配 16 兆字节。

解决此问题的最简单且可能是最好的方法是切换到使用不会显示此行为的新 MySQLND 连接器。

关于SQL查询的PHP大量内存使用,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/11913818/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com