Деструкторы без классов - PullRequest
2 голосов
/ 27 марта 2012

Предположим, у меня есть функция, которая возвращает замыкание:

sub generator
{

   my $resource = get_resource();
   my $do_thing = sub
   {
     $resource->do_something();
   }

  return $do_thing;
}

# new lexical scope
{
   my $make_something_happen = generator();

   &$make_something_happen();
}

Я хотел бы быть в состоянии гарантировать, что когда $make_something_happe n будет удален из области, я смогу вызвать несколько $resource->cleanup();

Конечно, если бы у меня был класс, я мог бы сделать это с деструктором, но это кажется немного тяжелым для того, что я хочу сделать. На самом деле это не «объект» в смысле моделирования объекта, это просто функциональная вещь, которая должна выполнить некоторый код при запуске и непосредственно перед смертью.

Как бы я сделал это в Perl (и, из любопытства, поддерживает ли какой-либо язык эту идею)?

Ответы [ 2 ]

5 голосов
/ 27 марта 2012

Я бы просто использовал класс для этого.Благослови ссылку на подпрограмму и продолжай использовать ее, как и ты.get_resource затем использует этот класс.Так как я не знаю, как это выглядит, я оставлю это на ваше усмотрение, чтобы интегрировать это:

 package Gozer {
      sub new {
         my( $class, $subref );
         bless $subref, $class;
         }

      sub DESTROY {
         ...; #cleanup
         }
      }

Если каждая вещь может иметь свою собственную очистку, я бы использовал класс для группировки дваКод ссылки:

 package Gozer {
      sub new {
         my( $class, $subref, $cleanup );
         bless { run => $subref, cleanup => $cleanup }, $class;
         }

      sub DESTROY {
         $_[0]{cleanup}();
         }
      }

В Perl я не думаю, что это тяжеловес.Система объектов просто прикрепляет ярлыки к ссылкам.Не каждому объекту нужно что-то моделировать, так что это идеальный объект.

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

0 голосов
/ 03 апреля 2012

Мне кажется, я понимаю ваш вопрос.В моем случае я хочу:
* Глобальная переменная, которая может быть установлена ​​в любой точке во время выполнения сценария
* Для сохранения прав до конца срока действия сценария
* Явная очистка.

Похоже, я могу сделать это, определив блок END;Он будет запущен "как можно позже".Вы должны быть в состоянии сделать ваш $ resource-> cleanup ();там, наверху.

Подробнее здесь: http://perldoc.perl.org/perlmod.html#BEGIN%2c-UNITCHECK%2c-CHECK%2c-INIT-and-END

Программа на этой странице имеет код.

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