33#include "mruby/array.h"
44#include "mruby/class.h"
55#include "mruby/string.h"
6+ #include "mruby/range.h"
67
78static mrb_value
89mrb_str_getbyte (mrb_state * mrb , mrb_value str )
@@ -18,6 +19,59 @@ mrb_str_getbyte(mrb_state *mrb, mrb_value str)
1819 return mrb_fixnum_value ((unsigned char )RSTRING_PTR (str )[pos ]);
1920}
2021
22+ static mrb_value
23+ mrb_str_setbyte (mrb_state * mrb , mrb_value str )
24+ {
25+ mrb_int pos , byte ;
26+ long len = RSTRING_LEN (str );
27+
28+ mrb_get_args (mrb , "ii" , & pos , & byte );
29+
30+ if (pos < - len || len <= pos )
31+ mrb_raisef (mrb , E_INDEX_ERROR , "index %S is out of array" , mrb_fixnum_value (pos ));
32+ if (pos < 0 )
33+ pos += len ;
34+
35+ mrb_str_modify (mrb , mrb_str_ptr (str ));
36+ byte &= 0xff ;
37+ RSTRING_PTR (str )[pos ] = byte ;
38+ return mrb_fixnum_value ((unsigned char )byte );
39+ }
40+
41+ static mrb_value
42+ mrb_str_byteslice (mrb_state * mrb , mrb_value str )
43+ {
44+ mrb_value a1 ;
45+ mrb_int len ;
46+ int argc ;
47+
48+ argc = mrb_get_args (mrb , "o|i" , & a1 , & len );
49+ if (argc == 2 ) {
50+ return mrb_str_substr (mrb , str , mrb_fixnum (a1 ), len );
51+ }
52+ switch (mrb_type (a1 )) {
53+ case MRB_TT_RANGE :
54+ {
55+ mrb_int beg ;
56+
57+ len = RSTRING_LEN (str );
58+ if (mrb_range_beg_len (mrb , a1 , & beg , & len , len )) {
59+ return mrb_str_substr (mrb , str , beg , len );
60+ }
61+ return mrb_nil_value ();
62+ }
63+ case MRB_TT_FLOAT :
64+ a1 = mrb_fixnum_value ((mrb_int )mrb_float (a1 ));
65+ /* fall through */
66+ case MRB_TT_FIXNUM :
67+ return mrb_str_substr (mrb , str , mrb_fixnum (a1 ), 1 );
68+ default :
69+ mrb_raise (mrb , E_TYPE_ERROR , "wrong type of argument" );
70+ }
71+ /* not reached */
72+ return mrb_nil_value ();
73+ }
74+
2175/*
2276 * call-seq:
2377 * str.swapcase! -> str or nil
@@ -375,6 +429,8 @@ mrb_mruby_string_ext_gem_init(mrb_state* mrb)
375429
376430 mrb_define_method (mrb , s , "dump" , mrb_str_dump , MRB_ARGS_NONE ());
377431 mrb_define_method (mrb , s , "getbyte" , mrb_str_getbyte , MRB_ARGS_REQ (1 ));
432+ mrb_define_method (mrb , s , "setbyte" , mrb_str_setbyte , MRB_ARGS_REQ (2 ));
433+ mrb_define_method (mrb , s , "byteslice" , mrb_str_byteslice , MRB_ARGS_REQ (1 )|MRB_ARGS_OPT (1 ));
378434 mrb_define_method (mrb , s , "swapcase!" , mrb_str_swapcase_bang , MRB_ARGS_NONE ());
379435 mrb_define_method (mrb , s , "swapcase" , mrb_str_swapcase , MRB_ARGS_NONE ());
380436 mrb_define_method (mrb , s , "concat" , mrb_str_concat2 , MRB_ARGS_REQ (1 ));
0 commit comments