Здравствуйте, Eugene Beschastnov, Вы писали:
EB>В качестве примера опишу два метода, один из которых вызывает другой с блоком в качестве параметра (всё, что в двойных кавычках — комментарии):
EB>EB>startingMethod "Здесь мы описываем создаваемый метод - указываем его имя и параметры.
EB> В данном случае имя метода - startingMethod, а параметров у него нету"
EB> | aBlock | "Здесь мы указываем, что у нас в методе используется локальная переменная aBlock"
EB> aBlock := [^123]. "Здесь мы присваиваем переменной aBlock блок, который возвращает число 123.
EB> ВАЖНО: блок здесь создаётся, но не выполняется."
EB> self methodThatWorksWithBlock: aBlock.
"Здесь мы вызываем у самого себя метод methodThatWorksWithBlock: с параметром aBlock"
EB>
EB>methodThatWorksWithBlock: aBlock
"Здесь мы описываем создаваемый метод - указываем его имя и параметры.
EB> В данном случае имя метода - methodThatWorksWithBlock: , и у метода есть один параметр - aBlock"
EB> | blockResult | "Здесь мы указываем, что у нас в методе используется локальная переменная blockResult"
EB> blockResult := aBlock value. "Здесь мы выполняем блок aBlock, пришедший нам в качестве параметра,
EB> а результат выполнения записываем в переменную blockResult.
EB> ВАЖНО: блок выполняется в том контекстве, где он было создан -
EB> т.е. в нашем случае в контексте метода startingMethod.
EB> При этом, если в блоке был выполнен оператор выхода из метода,
EB> то из метода value мы _не_ возвращаемся."
EB> ^blockResult "Возвращаем blockResult"
EB>
Спасибо, теперь я уверен, что понимаю всё правильно. Некоторые вопросы сразу сняты.
Но в таком случае может возникнуть куча проблем с тем, что пользователь не сообщив никак исполняющему методу выходит в другой метод: проектирование методов усложняется, нужно всё время помнить, что человек может передать возврат в исполняемом блоке, который ты никак не перехватишь.
Пожалуй всё. Мне даже понравилась такая возможность, её иногда нехватает.