Является ли ваша страница & amp; страница b часть того же углового сайта? Если это так, то вы можете сохранить свой массив как глобальный объект в слое сервиса. Когда вы вернетесь на страницу b, просто получите доступ к значению и, если оно не равно нулю, не выполняйте вызовы службы. Другой вариант - использовать локальное хранилище, как описано выше
.Есть несколько возможных точек утечки памяти в php:
Довольно сложно найти и исправить первые 3 без глубокого реверс-инжиниринга или знания исходного кода php. Для последнего вы можете использовать двоичный поиск кода утечки памяти с помощью memory_get_usage
PHP не имеет сборщика мусора. Он использует подсчет ссылок для управления памятью. Таким образом, наиболее частым источником утечек памяти являются циклические ссылки и глобальные переменные. Боюсь, что если вы используете фреймворк, вам придется перебирать много кода, чтобы найти его. Самый простой инструмент - выборочно разместить вызовы к memory_get_usage
и сузить его до места утечки кода. Вы также можете использовать xdebug для создания трассировки кода. Запустите код с трассировками выполнения и show_mem_delta
.
Однажды я заметил в старом скрипте, что PHP поддерживает переменную «as» в области видимости даже после моего цикла foreach. Например,
foreach($users as $user){
$user->doSomething();
}
var_dump($user); // would output the data from the last $user
Я не уверен, исправят ли это будущие версии PHP или нет, с тех пор, как я это видел. Если это так, вы можете unset ($ user)
после строки doSomething ()
, чтобы удалить его из памяти. YMMV.
Если то, что вы говорите о том, что PHP выполняет сборку мусора только после того, как функция становится истинной, вы можете обернуть содержимое цикла внутри функции в качестве обходного пути / эксперимента.
Недавно я столкнулся с этой проблемой в приложении, при, как я полагаю, аналогичных обстоятельствах. Скрипт, который запускается в PHP cli и проходит множество итераций. Мой сценарий зависит от нескольких базовых библиотек. Я подозреваю, что причиной является конкретная библиотека, и я потратил несколько часов напрасно, пытаясь добавить соответствующие методы уничтожения к ее классам, но безрезультатно. Столкнувшись с длительным процессом преобразования в другую библиотеку (которая может иметь те же проблемы), я придумал грубый способ решения проблемы в моем случае.
В моей ситуации на Linux cli я перебирал несколько пользовательских записей и для каждой из них создавал новый экземпляр нескольких созданных мною классов. Я решил попробовать создать новые экземпляры классов с помощью метода PHP exec, чтобы этот процесс выполнялся в «новом потоке». Вот действительно базовый пример того, что я имею в виду:
foreach ($ids as $id) {
$lines=array();
exec("php ./path/to/my/classes.php $id", $lines);
foreach ($lines as $line) { echo $line."\n"; } //display some output
}
Очевидно, что этот подход имеет ограничения, и нужно осознавать опасность этого, поскольку было бы легко создать кроличью работу, однако в некоторых редких случаях это может помочь преодолеть трудное положение, пока не будет найдено лучшее решение, как в моем случае.