#php #windows #memory-management #command-line-interface #ram
#php #Windows #управление памятью #интерфейс командной строки #ОЗУ
Вопрос:
В последнее время я тестировал материалы, связанные с памятью. Ознакомьтесь с этим:
$data = load_in_huge_file('test.csv');
while (1)
{
var_dump(memory_get_usage(false));
var_dump(memory_get_usage(true));
sleep(4);
unset($data);
}
Для первого цикла это выводит огромное значение для первого вызова memory_get_usage и второго.
Для второго (и последующего) цикла это выводит небольшое значение для первого вызова memory_get_usage и огромное значение для второго.
Это означает, что фактическая «выделенная» память остается прежней, даже если я сброшу значение переменной, содержащей все данные.
То же самое произойдет, если я сделаю:
$data = load_in_huge_file('test.csv');
while (1)
{
var_dump(memory_get_usage(false));
var_dump(memory_get_usage(true));
sleep(4);
unset($data);
gc_collect_cycles();
}
Выделенная «реальная» память остается неизменной после ее выделения и не «освобождается».
(Функция load_in_huge_file в основном запускает fopen blabla, за которым следует fclose .)
Что мне с этим делать? Кажется, что PHP все еще «использует» оперативную память, и мои сверхмощные скрипты PHP CLI в конечном итоге истощают всю мою оперативную память при обработке множества файлов CSV, один за другим, и память не возвращается.
Я не думаю, что понимаю, что gc_collect_cycles()
вообще делает. Руководство по меньшей мере неясно.
Может быть, достаточно unset(), но это «занимает некоторое время»? Может быть, «реальная» выделенная память просто запутывает терминологию и на самом деле не означает, что оперативная память «занята»?
(Все, что касается компьютеров, постоянно меня смущает. Ничто никогда не может быть по-настоящему изучено, без бесконечных дополнительных уровней сложности для каждой мельчайшей детали.)
Комментарии:
1. PHP не выделяет оперативную память. Он выделяет память, и задача ОС — определить, какие части этой памяти занимают оперативную память, а какие нет. Тем не менее, PHP имеет недетерминированный сборщик мусора, который запускается по мере увеличения объема памяти. Если у вас нет реальной проблемы, вам ничего не нужно делать.
Ответ №1:
Исходя из нашего опыта программирования, мы не рекомендуем сохранять целые данные в переменную (в память)
Лучше использовать цикл с помощью: https://www.php.net/manual/en/function.fgetcsv.php
Загружайте только 1 строку в память, а не весь файл.
Комментарии:
1. Хотя я знаю о существовании fgetcsv(), у меня есть комментарии, сделанные для себя о том, что это был сломанный кошмар, и что я должен «никогда, никогда не пытаться использовать его снова». Я уверен, что написал это по уважительной причине, и я смутно помню, насколько это было проблематично… Но даже помимо этого, мой общий вопрос все еще остается в силе.
2. PHP не является настольным приложением, которое по какой-либо причине загружает большую память данных. Обработка данных с использованием fgetcsv является эффективным способом, и многие разработчики используют его. Он создан по этой причине, чтобы свести к минимуму злоупотребление использованием памяти.
3. Откуда у вас возникла довольно абсурдная идея, что только «настольные приложения» загружают большой объем данных? Я бы сказал, что все совсем наоборот.
4. На самом деле, оказывается, что я
fgetcsv
все-таки использовал. Таким образом, проблема возникает даже с этим методом. Но опять же, в любом случае, это всего лишь пример. Основная проблема не связана с файлами fgetcsv () или CSV.