Создание объекта времени Ruby, вызывающего проблему сбора мусора - PullRequest
2 голосов
/ 12 мая 2011

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

Я пытаюсь написать небольшую программу ruby, которая будет жить в папке базы данных моего сайта. Каждые 15 минут (пока система работает в режиме онлайн), я хочу, чтобы она опрашивала данные от инверторов наших клиентов (через соединение TCPSocket к шлюзу, подключенному к инвертору клиентов) и обновляла файл базы данных моего сайта новыми данными , У меня цикл выглядит примерно так:

last_min = Time.new.min

while(1) do

tsec = Time.new.sec
tmin = Time.new.min

  if ( ( tsec == 0 ) && ( tmin - last_min == 1 ) )    # test using one minute
     # poll inverters, update database
     last_min = tmin
  end

end

Когда я запускал его сначала, он выдавал ошибку Segmentation Fault. Затем я поставил GC.disable наверх, и он работал нормально (пока я не заставлю выйти только через пару минут), но это было только для того, чтобы посмотреть, была ли это проблема сбора мусора, и это, кажется, первое создание объект времени, который вызывает проблему (выдает ошибку ошибки сегментации). Я знаю, что я не могу отключить сборку мусора для бесконечного цикла. Но как мне «почистить себя» с помощью рубина? Могу ли я как-нибудь освободить эти объекты времени в конце каждого цикла? Я видел сообщение о GC.start, но не мог понять, как это работает.

Также есть ли способ запустить мою программу и посмотреть, сколько оперативной памяти она использует? Я был бы признателен за любой совет, который кто-нибудь мог бы предложить мне здесь. (Включая рекомендации по общей архитектуре системы контроля солнечной выходной мощности, которую я описал в начале!)

Я уже получил большую выгоду от просмотра всех постов здесь в моем путешествии до сих пор, и я заранее благодарю вас!

Ответы [ 2 ]

3 голосов
/ 12 мая 2011

Чтобы запустить сборку мусора, просто вызовите GC.start в конце вашего цикла.Все, что может быть собрано мусором, будет собрано мусором.

С учетом сказанного, если вы действительно хотите, чтобы бесконечный цикл выполнял что-то каждую минуту (или 15 минут) вместо сравнения времени и новых минут и секунд,просто вызовите sleep внутри вашего бесконечного цикла.

loop do
  poll_inverters_and_update_db
  sleep 60
end

Поскольку вы упомянули, что используете Rails, вы также можете захотеть заглянуть в delayed_job для выполнения этого типа вещей,или просто настройте задачу cron для выполнения каждые n минут.

0 голосов
/ 12 мая 2011

Звучит как интересный проект.

Вам нужен только один объект Time за интервал, поскольку вы можете выполнять арифметические операции со временем.Например:

t0 = Time.new

while(1) do

  if ( Time.new - t0 >= 60 )    # test using one minute
     # poll inverters, update database
     t0 = Time.new
  end

end

Тогда вам не нужно беспокоиться о проблемах GC.

PS.+1 за использование delayed_job или другого способа поместить его в свой собственный поток, или cron, если вы можете запустить его как свой собственный процесс, поскольку подобный цикл или использование sleep () заблокирует все остальное.

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