Enumerable
の再実装やってると正解が見たくなる
仲間で集まって Ruby の Enumerable
のメソッドを再実装する遊びをよくやっているんだけど、書いたら答え合わせがしたくなる。そういうときは CRuby の実装 を見るのが一番なんだけど、Cが読めないとかなり辛い。
例: Enumerable#collect
の CRuby の実装(?)
enum.c
static VALUE
enum_collect(VALUE obj)
{
VALUE ary;
int min_argc, max_argc;
RETURN_SIZED_ENUMERATOR(obj, 0, 0, enum_size);
ary = rb_ary_new();
min_argc = rb_block_min_max_arity(&max_argc);
rb_lambda_call(obj, id_each, 0, 0, collect_i, min_argc, max_argc, ary);
return ary;
}
なにか別の関数(collect_i
?)を呼び出してるっぽいことくらいしかわからない…
TruffleRuby はわりと Ruby でかかれてる
いろいろ有名な処理系を見たら、 Oracle の TruflleRuby の Enumerable
実装が Ruby で書かれているのでとっつきやすかった。
src/main/ruby/truffleruby/core/enumerable.rb
def collect
if block_given?
ary = []
each do |*o|
ary << yield(*o)
end
ary
else
to_enum(:collect) { enumerator_size }
end
end
oracle/truffleruby src/main/ruby/truffleruby/core/enumerable.rb より
読める!読めるぞ!