るびきちです。
久しぶりに拡張ライブラリを作ることになりました(^^;;
Cの文字列を破壊的に変更する関数をRubyでwrapするとき、
こんなコードはいけないのでしょうか?
README.EXT.jpでは
「文字列の中身は参照するだけで、直接変更しないことです」
と書いてありますが、動いてます。
直接変更するというのは、
* s = "abc"; RSTRING(s)->ptr = s; のようにポインタを変更することなのか、
((-これは明らかに危なっかしい気はします-))
* RSTRING(s)->ptr[0]='X'; のようにポインタを変えないで破壊的な動作をする
ことなのか
の両方を指しているのでしょうか?
/* 文字列を破壊的に変更 */
void test2(char *s){
if(*s) *s = 'X';
}
VALUE _test2(VALUE self, VALUE s){
char *_s;
switch(TYPE(s)){
case T_STRING:
/* 正しく動くようだけどこんなことしていいのかな? */
_s = RSTRING(s)->ptr;
test2(_s);
return Qtrue;
default:
rb_raise(rb_eTypeError, "invalid type");
return Qfalse;
}
}
void Init_blastest(){
rb_define_method(rb_cObject, "test2", _test2, 1);
}
################ テストスクリプト
#!/usr/bin/env ruby
s = "hoge"
test2 s
puts s # => "Xoge"
るびきち☆
http://voo.to/ruby/ ←Ruby大衆化計画(笑)