メタプログラミングRuby 4章メモ
https://scrapbox.io/files/6599eda8173c1e00254bf9dc.png
ブロックがテーマ。
ブロックの復習
メソッドを呼び出す時にのみ定義できる
yieldを使うとコールバックできる
単体では実行できない
code:ruby
def my_method
x = "Hello" # メソッド内でローカル変数xを定義
yield("World")
end
x = "Goodbye"
my_method do |y|
puts x + y # GoodbyeWorld
end
メソッドの中にあるxはブロックからでは見えない
束縛 (binding) = 変数の宣言と使用の間の関係。
クロージャとは、プログラミング言語の機能・仕様の一つで、あるコードブロック内で定義された関数などが、そのブロックをスコープとする変数などを参照できること。
スコープゲート
スコープはどんどん変わり、Rubyでは変わると前のスコープは破棄される
そもそもスコープを定義できる場所
クラス定義
モジュール定義
メソッド
この3つのキーワードがスコープゲートとして振る舞う。
メソッドだけ実行された時のみスコープを持つ。
code:ruby
top_var = 1
MyClass = Class.new do
p top_var # スコープを超えた上で「1」が出る
define_method: :my_method do
p top_var # スコープを超えた上で「1」が出る
end
end
スコープゲートをメソッド呼び出しにしたことで、他のスコープの変数が見えるようになった。
この技をフラットスコープという。
わかりやすくいうと、普通のクラスやメソッド定義でスコープを自由に変えられることを学んだ。
instance_eval
オブジェクトの今テキストでブロックを評価する。
code: ruby
class MyClass
def initialize
@my_var = "Hello, world!"
end
end
my_instance = MyClass.new
my_instance.instance_eval do
end
つまりオブジェクトの中に入ることができる(カプセル化の破壊)
Procとlambda
違い1:returnの挙動
code: ruby
def test_proc
p = Proc.new { return 10 }
result = p.call
return result * 2 # 実行されない
end
def test_lambda
l = lambda { return 10 }
result = l.call
return result * 2 # 実行される
end
puts test_lambda # => 20