2009-09-27 2 views
0

У меня есть метод, который возвращает объект File. Мне нужно знать, когда файл закрывается. Это не так просто, как переписывание метода close. Метод close не вызывается, если файл закрыт деструктором.Как ruby ​​может обеспечить обратный вызов, когда файл закрыт?

Он должен работать так:

def something 
    get_lock_on_file 
    file File.new("foobar") 
    file.on_close { release_lock_on_file } 
    file 
end 

Как реализовать файл # ON_CLOSE (& блок)?

+0

Позволяет ли Ruby переопределять деструктор? – luiscubal

+0

Можете ли вы поделиться некоторым кодом? – khelll

+1

@luiscubal: Ruby не имеет деструкторов. –

ответ

2

Боюсь, что вы ничего не можете сделать. Если метод File#close не вызывается, то, скорее всего, файл фактически будет автоматически закрыт операционной системой, когда интерпретатор Ruby выйдет. Другими словами: в то время, когда файл закрыт, интерпретатор Ruby (или, по крайней мере, ваша программа) давно ушел, поэтому просто невозможно сообщить о вашей программе.

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

  • перекрывая метода, File объекта,
  • установки собственных финализаций и
  • установки at_exit обработчика.

Однако все они имеют свои проблемы: метод не может быть вызван. Финализатор запускается только тогда, когда объект собирает мусор, что может быть намного позже, чем вы ожидаете (и если у вас никогда не закончится память, сборщик мусора никогда не запустится, и финализатор никогда не будет вызван). И даже обработчик at_exit не может работать, если сбой интерпретатора.

3

Определение что-то вроде этого ...

def something 
    get_lock_on_file 
    yield file 
    release_lock_on_file 
end 

.. и использовать его так:

something do |file| 
    ... 
end 

Wrap выход с блока на обработку ошибок, если вам это нужно.

+0

Мой метод должен вернуть файл. – johannes

+0

add: файл перед окончанием def что-то – khelll