【问题标题】:Using PHP ini_set "memory_limit" safely安全地使用 PHP ini_set "memory_limit"
【发布时间】:2013-05-23 20:41:53
【问题描述】:

我目前有一个要运行很长时间的脚本(虽然在它自己的单独进程中分叉)。它不会经常运行,但是当它运行时,它将使用大量内存,主要用于处理(许多)XLS 文件(> 10 MB)。

当此脚本以 6000 秒的时间限制运行时,我目前将内存限制设置为 1024M。这些是上限,但实际上并不需要那么多时间(可能只需 5 分钟就足够了)。

因为需要大量内存,所以我想知道 PHP/Apache 如何管理内存。

  • 脚本终止时是否自动释放内存?如果没有,什么时候会。
  • 我需要隐式释放对象吗?
  • 是否可以从脚本中一次释放一点内存
  • 1024M是不是太大了,长期下来对服务器有什么影响。

顺便说一下,我正在使用 PHPExcel 库。

【问题讨论】:

标签: php memory optimization memory-management load


【解决方案1】:

简答:

PHP 使用引用计数,因此对象一旦没有被引用就会被释放。如果存在引用循环(例如,对象 A 引用对象 B,对象 B 又引用对象 A),垃圾收集器会不时处理它们。

当脚本结束时,所有剩余的内存都返回给系统。

长答案:

脚本终止时是否会自动释放内存?如果没有,什么时候会。

在脚本执行期间,只要不再引用对象/变量,就会释放内存。

如果由于某种原因在脚本末尾仍然引用了对象,它们将被强制销毁和释放。

然后,内存分配器被重置(这会释放少量剩余分配的内存,就像分配器自己的缓存一样)。

所以在脚本结束时,所有内容都被释放并可以再次分配。

如果分配器使用mmap() 在内部分配内存段(当 mmap() 可用时这是默认设置),那么大块的取消分配和内存分配器的重置也会将内存返回给系统。

我需要隐式释放对象吗?

没有。只需确保garbage collector is enabled,以便参考周期得到处理。

是否可以从脚本中一次释放一点内存

PHP 使用引用计数,并在对象不再被引用时立即释放它们:

$a = new stdClass;
$a = null; // the object is freed at this point

function foo () {
    $a = new stdClass;
    return; // the object referenced by $a is freed at this point
}

收集引用周期manually 可能会提前释放一些内存,尽管通常没有必要。

1024M是不是太大了,长期下来对服务器有什么影响。

如果您在单独的进程中运行这个占用大量内存的脚本,这不会影响服务器。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2012-11-09
    • 2023-02-09
    • 2023-03-09
    • 1970-01-01
    • 2012-05-31
    • 1970-01-01
    • 2017-09-13
    • 2011-07-01
    相关资源
    最近更新 更多