NODE_MATCH 系
ノードは3種類ありますが、要するにどれも =~ です。基本は、単純に =~ メソッドを呼ぶだけです。
case NODE_MATCH: case NODE_MATCH2: case NODE_MATCH3:{ ... 思いっきり略 ... COMPILE(recv, "reciever", node->nd_recv); COMPILE(val, "value", node->nd_value); ... 思いっきり略 ... ADD_SEQ(ret, recv); ADD_SEQ(ret, val); ADD_SEND(ret, nd_line(node), ID2SYM(idEqTilde), INT2FIX(1));
ただし、るびま で解説されている最適化が入ることがあります。idEqTilde を send する代わりに、「=~が再定義されていなければ、正規表現マッチ処理をする。再定義されていれば諦めてsendする」という意味の opt_regexpmatch 命令を使うという最適化です。Ruby では正規表現のマッチは非常によく使われるので、メソッド呼び出しのコストを回避する価値があるというわけです。
こちらがその最適化版を生成するコード
if (iseq->compile_data->option->specialized_instruction) { /* TODO: detect by node */ if (recv->last == recv->anchor.next && INSN_OF(recv->last) == BIN(putobject) && nd_type(node) == NODE_MATCH2) { ADD_SEQ(ret, val); ADD_INSN1(ret, nd_line(node), opt_regexpmatch1, OPERAND_AT(recv->last, 0)); } else { ADD_SEQ(ret, recv); ADD_SEQ(ret, val); ADD_INSN(ret, nd_line(node), opt_regexpmatch2); } }
使われてる正規表現がリテラルなら、opt_regexpmatch1。そうでなければ opt_regexpmatch1 と、さらに細かく分かれています。