Как Ruby работает с именем этого метода, чтобы не конфликтовать с
защищенное ключевое слово, помечающее блокировку (например, если… конец)?
При использовании def
синтаксический анализатор предполагает, что ниже следует идентификатор (символ сортов), разделенный паренсом или пробелом. Вы не можете динамически назначать имена методов с помощью def (без использования какой-либо формы eval
).
define_method(:end){}
принимает символ (или строку), поэтому здесь нет проблем с использованием зарезервированного слова.
Но методы нельзя вызывать с неявным получателем, как это обычно делается внутри класса:
# ok
class Foo
def end
end
def test
# not ambiguous
self.end
end
end
# syntax error, unexpected keyword_end, expecting end-of-input
class Bar
def end
end
def test
end
end
end
Вы можете вызвать метод с явным получателем:
Foo.new.end
Или используйте динамический вызов с send
или call
.
class Foo
def end
end
def test
send(:end)
method(:end).call
end
end
Вы также можете использовать ключевые слова в именах переменных (@end), class (@@ end) и глобальных ($ end), поскольку сигил сообщает парсеру, что мы имеем дело с переменной, но не для локальных переменных, которые имеют без сигил.