C拡張メソッドを使用して新しいruby配列を作成していますが、RARRAY_LENが設定されていません。私は何か間違ったことをしていますか?
long int max = 4;
VALUE rAry;
rAry = rb_ary_new2(max);
printf("allocated: %lu\n", RARRAY_LEN(rAry));
出力:
allocated: 0
C拡張メソッドを使用して新しいruby配列を作成していますが、RARRAY_LENが設定されていません。私は何か間違ったことをしていますか?
long int max = 4;
VALUE rAry;
rAry = rb_ary_new2(max);
printf("allocated: %lu\n", RARRAY_LEN(rAry));
出力:
allocated: 0
array.c
(Ruby 1.8.6)
から:#define RARRAY_LEN(s) (RARRAY(s)->len)
RARRAY(s)->len
と同じArray#length
です。
rb_ary_new2(4)
と同じではありませんArray.new(4)
。
VALUE
rb_ary_new2(len)
long len;
{
return ary_new(rb_cArray, len);
}
VALUE
rb_ary_new()
{
return rb_ary_new2(ARY_DEFAULT_SIZE);
}
ARY_DEFAULT_SIZE
として定義され16
ます。
配列にメモリを割り当てるだけですが、データを入力しません。動的にサイズを変更する必要がないように、配列の最終的なサイズがわかっている場合に使用します。
あなたの意図に使用したいものはrb_ary_new3
またはrb_ary_new4
です。
Ruby のプログラミング: The Pragmatic Programmer's Guideから:
VALUE rb_ary_new3(long length, ...")
Array
指定された長さ の new を返し、残りの引数が取り込まれます。
VALUE rb_ary_new4(long length, VALUE *values")
Array
指定された長さ の new を返し、C 配列の値が取り込まれます。
これらの関数では、各要素に値を指定する必要があることに注意してください。rAry = rb_ary_new3(4, Qnil, Qnil, Qnil, Qnil)
したがって、次のようなことを行う必要がありますArray.new(4)
。より少ない引数を指定すると、Ruby で奇妙な動作が発生します。(例外はありません - 無効なオブジェクトを取得したにもかかわらずです。)
どうやら rb_ary_store(obj, index, val) を使用して RARRAY_LEN をインクリメントする必要があるようです。非常に重要なメソッドが基本的に文書化されていないのは奇妙です。