Управление памятью PHP - PullRequest
7 голосов
/ 26 июля 2010

У меня есть несколько трудоемких и (потенциально) интенсивно использующих память функций в моем веб-приложении LAMP. Большинство из этих функций будут выполняться каждую минуту через cron (в некоторых случаях задание cron будет выполнять несколько экземпляров этих функций).

Поскольку память ограничена, я не хочу сталкиваться с проблемами, когда пытаюсь выполнить функцию, которую среда больше не может обрабатывать. Каков хороший подход к решению проблем с памятью?

Я предполагаю, что мне нужно определить, сколько памяти доступно для меня, сколько памяти требует каждая функция перед ее выполнением, определить, какие другие функции выполняются cron И их использование памяти и т. д.

Кроме того, я не хочу сталкиваться с проблемой, когда определенная функция каким-то образом получает приоритет выполнения над другими функциями. Если какой-либо приоритет будет отдан, я бы хотел каким-то образом это контролировать.

Ответы [ 5 ]

1 голос
/ 28 июля 2010

вы можете взглянуть на технологии кэширования, такие как APC , которые позволяют вам записывать данные прямо в оперативную память, чтобы вы могли быстро получить к ним доступ, что пригодится, если вы не хотите многократно выполнять дорогостоящие задачи, такие как запросы mysql.

Примером кеширования, о котором я мог подумать, было бы то, что вы могли бы кешировать электронные письма, а не получать их снова и снова с почтового сервера. По сути, кэширование в оперативной памяти - очень полезный метод, если в вашем скрипте есть вещи, которые вы хотите сохранить для следующего выполнения скрипта, но если ваш скрипт выполняет уникальные вещи каждый раз, когда он выполняется, он будет бесполезен. также как и для contoll, вы можете вызывать memory_get_usage () при каждом выполнении скрипта и записывать это значение в кэш apc, чтобы каждый cron мог получить это значение и посмотреть, достаточно ли памяти для его завершения.

что касается среднего использования, вы могли бы написать массив с последними значениями, скажем, 100 выполнений функций, и при повторном вызове этой функции он может apc_fetch вычислить это из оперативной памяти и вычислить среднее использование памяти для этой функции, а затем сравнить его с количеством оперативной памяти. используется сейчас, а затем решите, начать ли. Более того, он может записать эту оценку в текущую переменную использования памяти, чтобы предотвратить запуск других сценариев. в конце этой функции вы снова вычитаете эту сумму из переменной. ТЛ; др: посмотрите на функции apc_fetch, apc_store и memory_get_usage

0 голосов
/ 31 июля 2010

На вашем месте я бы подумал написать демона, а не полагаться на cron.Демон может отслеживать очередь и знать количество дочерних процессов, которые он выполняет.Управление несколькими процессами определенно не самая большая сила php, но вы можете сделать это .Груша даже включает System_Daemon пакет.

Ваш демон может использовать memory_get_usage и вызывать free, uptime и друзей, чтобы регулировать количество работников в соответствии с условиями системы.

У меня нет прямого опыта с этим, и я не слишком удивлюсь, если демон, написанный на PHP, постепенно вытечет из памяти.Но если это приемлемо медленно, cron может периодически запускать демона ...

0 голосов
/ 26 июля 2010

Частью вашей проблемы может быть тот факт, что вы делаете cron каждую минуту?Почему бы не установить некоторые флаги, чтобы только один экземпляр этого cron работал до того, как другой выполнит полную логику?то есть создайте плоский файл, который удален в конце cron, чтобы действовать как «блокировка».Это обеспечит полное завершение одного процесса cron до того, как другие начнут работать.Однако я призываю вас сослаться на мой комментарий к вашему посту, чтобы я и другие могли дать вам более твердый совет.

0 голосов
/ 28 июля 2010

Попробуйте оптимизировать свои алгоритмы.Например ...

  • Как только вы закончили работу с переменной, вы должны уничтожить ее, если она вам больше не нужна.
  • Закрыть соединения MySQL после того, как вы поработаете с ними.
  • Используйте рекурсию.

Также, как сказал Jauzsika, измените свой предел памяти в php.ini, хотя не делайте его слишком высоким.Если вам требуется более 256 МБ ОЗУ, я бы предложил перейти на другой язык вместо PHP.

0 голосов
/ 26 июля 2010

Вы можете узнать, сколько памяти в данный момент используется вашим скриптом, используя memory_get_usage Но вы не можете определить, сколько потребуется вашей следующей функции, прежде чем выполнять ее. Вы можете видеть только после выполнения, используя memory_get_usage. Однако вы можете сохранить память, которую ваша функция использовала в последний раз, в базе данных и рассчитать ее со средним объемом памяти.

Что касается приоритета выполнения, я не думаю, что это возможно определить с помощью PHP. Apache (или любой используемый вами веб-сервер) порождает несколько процессов, и операционная система планирует, какой из них будет выполняться в каком порядке.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...