在一般的场景中,php作为一个脚本,执行完毕就会释放调所有的内存,所以一般我们也不会太考虑内存问题,对象 数组随便复制引用
但是现在如果我们换到了swoole 或者其他的进程式的程序栈中,我们如何保证内存不会越来越高,或者如果我们要自己写一套高效率的框架,那我们的内存到底如何分配才合理
带着这些疑问,我就就行了一下测试,得出了一下结论,供大家参考
1.对象何时销毁
<?php
class AObject
{
public function print()
{
echo "A 对象活着!\n";
}
}
class BObject
{
private $aObject;
public function __construct(AObject &$aObject)
{
$this->aObject = &$aObject;
}
public function print()
{
echo is_null($this->aObject) ? "A对象已经被销毁" : "A对象还存在";
}
}
echo "开始运行时候的内存大小:" . memory_get_usage() . "\n";
$aObject = new AObject();
echo "创建A对象了的内存大小:" . memory_get_usage() . "\n";
$bObject = new BObject($aObject);
echo "创建B对象并且传入A对象的内存大小:" . memory_get_usage() . "\n";
$bObject->print();
$aObject = null;
$bObject->print();
echo "销毁B对象后的内存大小:" . memory_get_usage() . "\n";
注意,传值必须是双 & 取内存地址,否则少一个都释放不了,还有一点,如果对象里面不牵扯到【修改】外部传入的变量值时候,尽量不要取内存地址,因为直接传入比在取内存地址要少占用内存!
【但是】这就是绝对了吗,继续往下看看
2.内存引用问题
<?php
echo "开始运行时候的内存大小:" . memory_get_usage() . "\n";
$a = [];
for ($i = 0; $i < 100; $i++) {
$a[] = $i;
}
echo "创建A数组,里面100个元素后的内存大小:" . memory_get_usage() . "\n";
$c = $a;
echo "c数组直接 copy一个a数组后的内存大小:" . memory_get_usage() . "\n";
$c[0] = 5000;
echo "修改c数组里面的第一个元素后的内存大小:" . memory_get_usage() . "\n";
可以看出,直接copy是不占内存的,还是a,但是我现在修改c数组之后,你可以看看,内存直接狂增,这是为什么呢,因为php如果传入的不是内存地址的话,修改是修改本数组,但不能修改之前的数组,所以他必须copy一个新的数组,然后再修改,所以,如果不牵扯修改的话,推荐第一种传值方式,直接传入,如果要修改数组的话,原数组影响不影响也无所谓的话,建议取内存地址进行修改,下面给你看看,取内存地址修改后的内存大小
<?php
echo "开始运行时候的内存大小:" . memory_get_usage() . "\n";
$a = [];
for ($i = 0; $i < 100; $i++) {
$a[] = $i;
}
echo "创建A数组,里面100个元素后的内存大小:" . memory_get_usage() . "\n";
$c = &$a;
echo "c数组直接 copy一个a数组后的内存大小:" . memory_get_usage() . "\n";
$c[0] = 5000;
echo "修改c数组里面的第一个元素后的内存大小:" . memory_get_usage() . "\n";
可以看出,除了c数组copy a数组时候,多占用了一点24b内存,然后修改,内存不会增加