[Ruby] Re: [Ruby] определения переменной в C
Eugene Scripnik
Eugene.Scripnik at itgrp.net
Tue Nov 5 13:14:41 MSK 2002
Tuesday, November 5, 2002, 11:40:54 AM, you wrote:
KA> Hi 2 all!
KA> Пишу модуль для Ruby на Си и никак не могу побороть одну вещь.Мне нужно
KA> создать класс,который изначально не имеет методов и переменных.Когда
KA> создается класс ruby в Cи, то обычно юзаются ф-ции: Data_Make_Struct и
KA> Data_Wrap_Struct, но им нужно передавать какой-то тип:
KA> obj = Data_Make_Struct(klass, struct st,0, free_p, p); // вместо struct
KA> st можно поставить и char или еще че-нить.Но мне нужно создать класс без
KA> всякой внутренних данных, т.е. без 'struct st' и че-нить подобного.
KA> Плюс ко всему у меня этот класс бужет иметь всего один экземпляр.Мне
KA> Александр Боковой предлагал определить сразу переменную и доопределять
KA> методы:
KA> static VALUE fc_video(obj)
KA> {
KA> return rb_iv_get(obj,"video");
KA> }
KA> void Init_freecraft(void)
KA> {
KA> VALUE vFreeCraft = rb_newobj();
KA> VALUE vVideo = rb_newobj();
KA> OBJSETUP(vFreeCraft,rb_cClass,0); // или OBJSETUP(vFreeCraft,rb_cObject,
KA> T_CLASS);
KA> OBJSETUP(vVideo,rb_cClass,0); // или flag = T_CLASS
KA> rb_define_variable("$FreeCraft", &vFreeCraft);
KA> rb_iv_set(vFreeCraft,"video",vVideo);
KA> rb_define_method(vFreeCraft, "video", fc_video, 0); // тут-то мы падает
KA> в корку
KA> }
KA> падение происходит на ф-ии st_insert() в rb_add_method(),вызываемый из
KA> rb_define_method() из-за того,что RCLASS(vFreeCraft)->m_tbl равен нулю.
KA> Как это можно ещё сделать?
Насколько я понимаю, ты пытаешься добавить метод video для обьекта
$FreeCraft. Но есть одна деталь, rb_define_method добавляет
instance_method, то есть метод для экземпляра класса (то что получится
после SomeClass.new). А $FreeCraft не является классом - это готовый
объект. С API для добавления метода к объекту я не знаю. Вместо этого
предлагаю немного иной вариант реализации. Вначале создаем некий класс
не доступный глобально, потом добавляем в него метод, а потом создаем
экземпляр этого класса:
void Init_freecraft(void) {
// создаем класс
VALUE cFreeCraft = rb_define_class("FreeCraftClass", rb_cObject);
// либо VALUE cFreeCraft = rb_class_new(rb_cObject);
// приклеиваем к нему новый метод
rb_define_method(cFreeCraft, "video", fc_video, 0);
// создаем экземпляр класса
VALUE vFreeCraft = rb_class_new_instance(0, 0, cFreeCraft);
// создаем глобальную переменную
rb_define_variable("$FreeCraft", &vFreeCraft);
rb_iv_set(vFreeCraft,"video",vVideo);
}
Код не тестировался.
--
Best regards,
Eugene [team Enticla] [IT Group] mailto:Eugene.Scripnik at itgrp.net
More information about the Ruby
mailing list