Показать сообщение отдельно
  #12 (permalink)  
Старый 29.01.2010, 17:28
Профессор
Отправить личное сообщение для Dmitry A. Soshnikov Посмотреть профиль Найти все сообщения от Dmitry A. Soshnikov
 
Регистрация: 25.02.2008
Сообщений: 707

Сообщение от x-yuri
а можно увидеть, как эта функция на Ruby выглядела бы?
Ну, для начала общий пример (из Википедии):

# ruby
def foo
  f = Proc.new { return "return from foo from inside proc" }
  f.call # control leaves foo here
  return "return from foo"
end

def bar
  f = lambda { return "return from lambda" }
  f.call # control does not leave bar here
  return "return from bar"
end

puts foo # prints "return from foo from inside proc"
puts bar # prints "return from bar"


Замыкания, порождаемые Proc.new - при return-e могут завершать контекст, в котором были порождены.

Замыкания, порождаемые функцией lambda - не могут.

Касаемо массива, метода .each и фунарга - я проверил, в версии 1.8.6 - и lambda, почему-то, завершает порождаемый контекст. В версии 1.9.1. это исправлено:

def test1
  fn = lambda {|x| return x}
  [1, 2, 3].each(&fn) # процедура передаётся с амперсандом
  return nil
end

def test2
  fn = Proc.new {|x| return x}
  [1, 2, 3].each &fn # скобки вызова - опциональны
  return nil
end

puts test1 # 1 - в 1.8.6, nil (правильно) - в 1.9.1
puts test2 # 1 - правильно


Есть ещё третий способ создать замыкание в Ruby - это блок кода (который можно преобразовать в процедуру). Различные методы (типа .each) как раз и используются с этими блоками кода.

def test3
  [1, 2, 3].each {|x| return x} # сразу описываем блок кода
  nil # слово return - тоже опциональное
end

puts test3 # 1 - при использовании блока, тоже выход из порождающего контекста
__________________
Тонкости ECMAScript

Последний раз редактировалось Dmitry A. Soshnikov, 30.01.2010 в 12:23.
Ответить с цитированием