Почему значения, которые я извлекаю из массива ruby ​​в расширение c, неверны? - PullRequest
4 голосов
/ 23 июня 2011

Этот метод просто проверяет, что я могу правильно видеть элементы массива ruby.

static VALUE 
print_cards(self) 
  VALUE self;
{
    VALUE cards;
    int i;

    cards = rb_ivar_get(self, rb_intern("@cards"));
    VALUE *ary_ptr = RARRAY_PTR(cards);
    int ary_length = RARRAY_LEN(cards);

    for(i=0; i< ary_length; i++)
        printf("%d\n", ary_ptr[i]);

  return Qnil;
}

void Init_ev() {
    rb_eval_string("require './lib/ev/pair_counter'");
    VALUE PairCounter = rb_path2class("EV::PairCounter");
    rb_define_method(PairCounter, "print_cards", print_cards, 0);
}

Но когда я использую метод, элементы массива неверны.Странно то, что не похоже, что я получаю какую-то адресную информацию, поскольку размер напечатанного числа примерно соответствует размеру числа в массиве ruby.Числа также совпадают каждый раз, когда я создаю новый объект и запускаю print_cards.

ruby-1.9.2-p180 :001 > p = EV::PairCounter.new   #=> #<EV::PairCounter:0x000001046a10f8 @pairs={}, @cards=[]>
ruby-1.9.2-p180 :002 > p.add_card(1)   #=> 1
ruby-1.9.2-p180 :003 > p.print_cards
3                                      #=> nil
ruby-1.9.2-p180 :004 > p.add_card(5)   #=> 2
ruby-1.9.2-p180 :005 > p.add_card(88)   #=> 3
ruby-1.9.2-p180 :006 > p
=> #<EV::PairCounter:0x000001046a10f8 @pairs={1=>1, 5=>1, 88=>1}, @cards=[1, 5, 88]>
ruby-1.9.2-p180 :007 > p.print_cards
3
11
177                 

Ответы [ 2 ]

6 голосов
/ 23 июня 2011

Мне нужно было использовать

printf("%d\n", NUM2INT(ary_ptr[i]));
0 голосов
/ 09 марта 2012

rb_ary_entry - это безопасный способ получить содержимое из массива Ruby. К ним нет доступа, как к обычным массивам C.

Похоже, что связан с этим вопросом: https://stackoverflow.com/a/9619163/486990

...