2010-03-06 3 views
10

У меня есть скрипт для очистки веб-страниц, который получает новые данные раз в минуту, но в течение нескольких дней скрипт заканчивается использованием 200 МБ или более памяти, и я узнал, что это потому, что механизация сохраняет бесконечную историю браузера для функции .back().Как отключить историю в модуле механизации python?

Я смотрел в docstrings, и я нашел функцию clear_history() класса браузера, и каждый раз, когда я обновляю, я вызываю это, но я все равно получаю более 2-3 МБ памяти для каждого обновления страницы. Редактировать: Хм, похоже, что он продолжал делать то же самое после того, как я вызвал clear_history, до тех пор, пока не доберусь до использования памяти около 30 мб, затем он очистится до 10 мб или около того (что является базовым объемом памяти, программа запускается с) ... любым способом, чтобы заставить это поведение на более регулярной основе?

Как сохранить механизацию от хранения всей этой информации? Мне не нужно ничего хранить. Я бы хотел, чтобы мой скрипт python был ниже 15-мегабайтной памяти.

+0

Хороший вопрос - я использовал механизацию в потоковом сканере, и история заставляла программу поражать 1,5 ГБ памяти ... –

ответ

19

Вы можете передать аргумент history=whatever при создании экземпляра Browser; значение по умолчанию - None, что означает, что браузер фактически создает класс History (чтобы разрешить back и reload). Самый простой подход (даст исключение ошибок атрибута, если вы когда-нибудь перезвонить или перезагрузить):

class NoHistory(object): 
    def add(self, *a, **k): pass 
    def clear(self): pass 

b = mechanize.Browser(history=NoHistory()) 

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

Обратите внимание, что это изящное (хотя и недостаточно хорошо документированное;) использование шаблона проектирования инъекций зависимостей: в мире (bleah) «monkeypatching», ожидается, что клиентский код перезапишет b._history после того, как браузер будет создан , но с инъекцией зависимости вы просто проходите в объекте «история», вам хотите использовать. Я часто утверждал, что Dependency Injection может быть самым важным DP, которого не было в книге «банда 4»!).

+0

Это действительно должно быть частью стандартного кода механизации imho. Спасибо, тонна;) Я прибегал к использованию clear_history, импортировал модуль gc и форсировал сборку мусора, чтобы память не находилась под нагрузкой от 10 до 18 мб памяти, надеюсь, ваш метод позволит остальным относительно стабильным.) – ThantiK

+4

I «Конечно, механики-сопровождающие будут приветствовать крошечный патч, добавляющий« NoHistory »(в немного более сложной версии ;-) к их модулю' _mechanize.py'. Тем не менее, реальная проблема механизатора - это нехватка документов - является ли тривиальный 5-строчный класс частью кода или нет, действительно незначительный, по сравнению с тем, что вы не можете узнать об этом (нужно ли писать тривиальную 5 линий самостоятельно или нет ;-) кроме тщательного изучения источников! –

+0

Вау, Алекс, ты просто просветил меня. Раньше я слышал термин «monkeypatching» и вроде как пытался понять это. Это дает мне практический пример, но, просматривая мой код, я уже делал это сам! Мой класс переходит по умолчанию «Нет» для файла cookiejar и инициирует его, если другой не инициализирован и не передан уже. Благодаря тонну! – ThantiK

Смежные вопросы