Руководство по actionscript. часть 2, стр. 094
Если изменить нашу стратегию так, чтобы текущая цель удалялась в блоке fina 11 у, мы устраним ненужные команды в предыдущем коде:
public function attackEnemy (enemy:SpaceShiр):void { try {
setCurrentTarget(enemy): fireOnCurrentTarget( ): } finally { setCurrentTarget(nul1);
В модифицированной версии блок finally удаляет текущую цель независимо от того, возникло исключение или нет. Поскольку блок finally обрабатывает обе ситуации, у нас нет необходимости в блоке catch; мы можем просто позволить исключению автоматически подняться вверх к вызывающему методу.
Вы можете поинтересоваться, а зачем нам вообще нужен блок finally? Иными словами, почему нельзя просто использовать следующий код?
// Этот код выглядит подходящим, однако в нем существует проблема. // Сможете определить ее?
public function attackEnemy (enemy:SpaceShiр):void { setCurrentTarget(enemy); fireOnCurrentTarget( ); setCurrentTarget(nul1);
}
Запомните, что, когда генерируется исключение, управление программой передается в ближайший подходящий блок catch в стеке вызовов. Следовательно, если метод fir eOnCur rent Target ( ) генерирует исключение, управление передается в метод attackEnemy ( ), при этом обратно в метод fireOnCurrentTarget ( ) управление возвращено не будет и инструкция setCurrentTarget (null) останется невыполненной. Однако с помощью блока finally мы гарантируем, что инструкция setCurrentTarget (null) будет выполнена до того, как исключение поднимется вверх по иерархии объектов.
Пример метода attackEnemy ( ) отражает наиболее распространенное использование блока finally в многопоточных приложениях, в которых одновременно может выполняться сразу несколько фрагментов кода и которые разрабатываются с помощью таких языков программирования, как, например, Java. В языке Java следующая общая структура — обычное явление; она исключает возможность удаления объекта, выполняющего некую задачу, другим объектом в процессе выполнения текущей задачи:
// Установить состояние, обозначающее выполнение данным объектом текущей // задачи. Внешние объекты должны проверять состояние данного объекта перед // тем, как обратиться к нему или выполнить над ним какие-либо действия. doingSomething = true: try {
// Выполняем задачу. doSomething( ); } finally {
// Сбросить состояние, обозначающее выполнение текущей задачи (независимо // от того, возникло в процессе выполнения задачи исключение или нет). doingSomething = false:
}
В языке ActionScript приведенный код, управляющий состоянием объекта, на самом деле необязателен, поскольку разрабатываемые с помощью этого языка приложения являются однопоточными, следовательно, никакой внешний объект не сможет изменить состояние другого объекта, выполняющего некий метод. Таким образом, в языке ActionScript блок finally используется гораздо реже, чем в языках, применяемых для разработки многопоточных приложений. Тем не менее этот блок
можно использовать для организационных целей — помещать в него код, который выполняет очистку после выполнения другого кода.