Уведомление об уничтожении объекта в Ruby - PullRequest
16 голосов
/ 01 октября 2008

Я написал собственную модель Rails. Эта модель поддерживается фактически сервером, а не таблицей базы данных (поэтому она не наследуется от ActiveRecord::Base). Чтобы получить запрашиваемую информацию с сервера, я открываю к нему SSH-соединение. Поскольку rails не использует объект повторно, для каждого полученного запроса будет создан новый объект, а также новое SSH-соединение с сервером. Чтобы уменьшить нагрузку на сервер, я хочу закрыть SSH-соединение до того, как объект модели будет собирать мусор. Мне интересно, предоставляет ли ruby ​​механизм уведомления, чтобы сообщить объекту, что он будет уничтожен? Если это так, я мог бы использовать это уведомление, чтобы знать, когда закрывать соединения SSH. Если нет, мне нужно будет сделать это вручную, когда я узнаю, что закончил с объектом.

Если мне нужно позаботиться об этом вручную, могу ли я явно уничтожить объект? Или лучшее, что я могу сделать, это object = nil?

Ответы [ 2 ]

21 голосов
/ 01 октября 2008

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

Другими словами, с точки зрения вашей программы, объект никогда не будет уничтожен или уничтожен. По этим причинам вам следует переосмыслить проблему (это не редкость - освобождение ресурсов, когда объект больше не нужен), чтобы он соответствовал парадигме Ruby.

Установка объекта на nil дает подсказку сборщику мусора, но не обязательно немедленно уничтожает его.

Однако, если вам нужно, чтобы сборщик мусора справился с этим, тогда читайте дальше.

Нет прямой поддержки деструктора, но вы можете заставить его вызывать функцию финализатора , когда он уничтожен.

Согласно http://pleac.sourceforge.net/pleac_ruby/classesetc.html сборка мусора может не выполняться, если она содержит ссылку на исходный объект, поэтому должен быть метод класса, а не метод экземпляра.

class MyClass
    def initialize
        ObjectSpace.define_finalizer(self,
                                     self.class.method(:finalize).to_proc)
    end
    def MyClass.finalize(id)
        puts "Object #{id} dying at #{Time.new}"
    end
end
0 голосов
/ 23 июля 2016

Я разместил решение здесь в другом потоке StackOverflow, который реализует Ruby способом, похожим на менеджер контекста Python. Со стороны клиента уничтожение неявное.

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