php - PHP - 内存泄漏 - 对象不会从 ram 中取消设置,而 gc_collect_cycles 什么也不做
问题描述
我编写了一个示例代码来了解如何在 php 上的长脚本中使用内存。
但我就是无法意识到这种行为
这段代码应该从未使用的对象中清除内存,但它几乎什么都不做
<?php
memory_using('start');
class a
{
public $v = [];
public function init()
{
for ($i = 0; $i <= 1000000; $i++)
{
$this->v[$i] = [rand(10000, 99999), rand(10000, 99999), rand(10000, 99999)];
}
}
}
$a = new a;
memory_using('before init');
$a->init();
memory_using('after init');
unset($a);
memory_using('after unset a');
gc_collect_cycles();
memory_using('after gc_collect_cycles');
xdebug_debug_zval('a');
function memory_using($where = null)
{
echo(sprintf("Memory using: %4s %s\n", convertToReadableSize(memory_get_usage(true)), $where));
}
function convertToReadableSize($size)
{
$base = log($size) / log(1024);
$suffix = array("B", "KB", "MB", "GB", "TB");
$f_base = floor($base);
return round(pow(1024, $base - floor($base)), 1) . $suffix[$f_base];
}
这是代码的结果:
Memory using: 2MB start
Memory using: 2MB before init
Memory using: 394MB after init
Memory using: 360MB after unset a
Memory using: 360MB after gc_collect_cycles
a: no such symbol
解决方案
memory_get_usage 的文档为参数声明了以下内容:“将其设置为 true 以获取从系统分配的总内存,包括未使用的页面。”
您看到的内存包含尚未被其他应用程序占用的未使用内存(因为您正在立即收集内存转储)。如果在 gc_collect_cycles 之后添加 sleep 命令,您会看到数字会下降。
推荐阅读
- javascript - 稍后以编程方式将捕获添加到多个承诺
- ios - UICollectionViewCell 点击将无法正确注册
- python - matplotlib 以我希望他们的工作方式计算
- ruby-on-rails - Rails 嵌套表单与 has_many :through
- c++ - 使用 ReadFile 和 WriteFile 时出现死锁
- ios - NSLayoutConstraints 在 UITableViewCell 中不受尊重
- java - 在 opencv 3.2 和 Java 中未检测到 IP 摄像头
- git - 没有双星,gitignore 模式不起作用
- java - hashCode() 是否被视为散列函数?
- c# - 如何阻止移动的用户控件与相同类型的其他用户控件相交?