Changeset 331 for EcnlProtoTool/trunk/mruby-1.3.0/mrbgems/mruby-struct
- Timestamp:
- Jan 21, 2018, 12:10:09 AM (6 years ago)
- Location:
- EcnlProtoTool/trunk/mruby-1.3.0
- Files:
-
- 3 edited
- 1 moved
Legend:
- Unmodified
- Added
- Removed
-
EcnlProtoTool/trunk/mruby-1.3.0/mrbgems/mruby-struct/mrblib/struct.rb
r321 r331 83 83 alias to_s inspect 84 84 end 85 86 ## 87 # call-seq: 88 # hsh.dig(key,...) -> object 89 # 90 # Extracts the nested value specified by the sequence of <i>key</i> 91 # objects by calling +dig+ at each step, returning +nil+ if any 92 # intermediate step is +nil+. 93 # 94 def dig(idx,*args) 95 n = self[idx] 96 if args.size > 0 97 n&.dig(*args) 98 else 99 n 100 end 101 end 85 102 end 86 103 -
EcnlProtoTool/trunk/mruby-1.3.0/mrbgems/mruby-struct/src/struct.c
r321 r331 6 6 7 7 #include <string.h> 8 #include "mruby.h"9 #include "mruby/array.h"10 #include "mruby/string.h"11 #include "mruby/class.h"12 #include "mruby/variable.h"13 #include "mruby/hash.h"14 #include "mruby/range.h"8 #include <mruby.h> 9 #include <mruby/array.h> 10 #include <mruby/string.h> 11 #include <mruby/class.h> 12 #include <mruby/variable.h> 13 #include <mruby/hash.h> 14 #include <mruby/range.h> 15 15 16 16 #define RSTRUCT_LEN(st) mrb_ary_ptr(st)->len … … 62 62 } 63 63 if (RSTRUCT_LEN(s) != RARRAY_LEN(members)) { 64 mrb_raisef(mrb, E_TYPE_ERROR, 65 "struct size differs (%S required %S given)", 66 mrb_fixnum_value(RARRAY_LEN(members)), mrb_fixnum_value(RSTRUCT_LEN(s))); 64 if (RSTRUCT_LEN(s) == 0) { /* probably uninitialized */ 65 mrb_ary_resize(mrb, s, RARRAY_LEN(members)); 66 } 67 else { 68 mrb_raisef(mrb, E_TYPE_ERROR, 69 "struct size differs (%S required %S given)", 70 mrb_fixnum_value(RARRAY_LEN(members)), mrb_fixnum_value(RSTRUCT_LEN(s))); 71 } 67 72 } 68 73 return members; … … 80 85 } 81 86 87 static void 88 mrb_struct_modify(mrb_state *mrb, mrb_value strct) 89 { 90 if (MRB_FROZEN_P(mrb_basic_ptr(strct))) { 91 mrb_raise(mrb, E_RUNTIME_ERROR, "can't modify frozen struct"); 92 } 93 94 mrb_write_barrier(mrb, mrb_basic_ptr(strct)); 95 } 96 82 97 /* 15.2.18.4.6 */ 83 98 /* … … 99 114 } 100 115 101 static mrb_value 102 mrb_struct_getmember(mrb_state *mrb, mrb_value obj, mrb_sym id) 103 { 104 mrb_value members, slot, *ptr; 105 const mrb_value *ptr_members; 106 mrb_int i, len; 107 108 ptr = RSTRUCT_PTR(obj); 109 members = struct_members(mrb, obj); 110 ptr_members = RARRAY_PTR(members); 111 slot = mrb_symbol_value(id); 112 len = RARRAY_LEN(members); 113 for (i=0; i<len; i++) { 114 if (mrb_obj_equal(mrb, ptr_members[i], slot)) { 115 return ptr[i]; 116 } 117 } 118 mrb_raisef(mrb, E_INDEX_ERROR, "'%S' is not a struct member", mrb_sym2str(mrb, id)); 119 return mrb_nil_value(); /* not reached */ 120 } 116 static mrb_value struct_aref_sym(mrb_state *mrb, mrb_value obj, mrb_sym id); 121 117 122 118 static mrb_value 123 119 mrb_struct_ref(mrb_state *mrb, mrb_value obj) 124 120 { 125 return mrb_struct_getmember(mrb, obj, mrb->c->ci->mid); 126 } 127 128 static mrb_value mrb_struct_ref0(mrb_state* mrb, mrb_value obj) {return RSTRUCT_PTR(obj)[0];} 129 static mrb_value mrb_struct_ref1(mrb_state* mrb, mrb_value obj) {return RSTRUCT_PTR(obj)[1];} 130 static mrb_value mrb_struct_ref2(mrb_state* mrb, mrb_value obj) {return RSTRUCT_PTR(obj)[2];} 131 static mrb_value mrb_struct_ref3(mrb_state* mrb, mrb_value obj) {return RSTRUCT_PTR(obj)[3];} 132 static mrb_value mrb_struct_ref4(mrb_state* mrb, mrb_value obj) {return RSTRUCT_PTR(obj)[4];} 133 static mrb_value mrb_struct_ref5(mrb_state* mrb, mrb_value obj) {return RSTRUCT_PTR(obj)[5];} 134 static mrb_value mrb_struct_ref6(mrb_state* mrb, mrb_value obj) {return RSTRUCT_PTR(obj)[6];} 135 static mrb_value mrb_struct_ref7(mrb_state* mrb, mrb_value obj) {return RSTRUCT_PTR(obj)[7];} 136 static mrb_value mrb_struct_ref8(mrb_state* mrb, mrb_value obj) {return RSTRUCT_PTR(obj)[8];} 137 static mrb_value mrb_struct_ref9(mrb_state* mrb, mrb_value obj) {return RSTRUCT_PTR(obj)[9];} 138 139 #define numberof(array) (int)(sizeof(array) / sizeof((array)[0])) 140 #define N_REF_FUNC numberof(ref_func) 141 142 static const mrb_func_t ref_func[] = { 143 mrb_struct_ref0, 144 mrb_struct_ref1, 145 mrb_struct_ref2, 146 mrb_struct_ref3, 147 mrb_struct_ref4, 148 mrb_struct_ref5, 149 mrb_struct_ref6, 150 mrb_struct_ref7, 151 mrb_struct_ref8, 152 mrb_struct_ref9, 153 }; 121 return struct_aref_sym(mrb, obj, mrb->c->ci->mid); 122 } 154 123 155 124 static mrb_sym … … 172 141 } 173 142 174 static mrb_value 175 mrb_struct_set(mrb_state *mrb, mrb_value obj, mrb_value val) 176 { 143 static mrb_value mrb_struct_aset_sym(mrb_state *mrb, mrb_value s, mrb_sym id, mrb_value val); 144 145 static mrb_value 146 mrb_struct_set_m(mrb_state *mrb, mrb_value obj) 147 { 148 mrb_value val; 149 177 150 const char *name; 178 mrb_int i, len,slen;151 mrb_int slen; 179 152 mrb_sym mid; 180 mrb_value members, slot, *ptr; 181 const mrb_value *ptr_members;153 154 mrb_get_args(mrb, "o", &val); 182 155 183 156 /* get base id */ … … 185 158 mid = mrb_intern(mrb, name, slen-1); /* omit last "=" */ 186 159 187 members = struct_members(mrb, obj); 188 ptr_members = RARRAY_PTR(members); 189 len = RARRAY_LEN(members); 190 ptr = RSTRUCT_PTR(obj); 191 for (i=0; i<len; i++) { 192 slot = ptr_members[i]; 193 if (mrb_symbol(slot) == mid) { 194 return ptr[i] = val; 195 } 196 } 197 mrb_raisef(mrb, E_INDEX_ERROR, "'%S' is not a struct member", mrb_sym2str(mrb, mid)); 198 return mrb_nil_value(); /* not reached */ 199 } 200 201 static mrb_value 202 mrb_struct_set_m(mrb_state *mrb, mrb_value obj) 203 { 204 mrb_value val; 205 206 mrb_get_args(mrb, "o", &val); 207 return mrb_struct_set(mrb, obj, val); 160 return mrb_struct_aset_sym(mrb, obj, mid, val); 208 161 } 209 162 … … 235 188 236 189 if (is_local_id(mrb, name) || is_const_id(mrb, name)) { 237 if (i < N_REF_FUNC) { 238 mrb_define_method_id(mrb, c, id, ref_func[i], MRB_ARGS_NONE()); 239 } 240 else { 241 mrb_define_method_id(mrb, c, id, mrb_struct_ref, MRB_ARGS_NONE()); 242 } 190 mrb_define_method_id(mrb, c, id, mrb_struct_ref, MRB_ARGS_NONE()); 243 191 mrb_define_method_id(mrb, c, mrb_id_attrset(mrb, id), mrb_struct_set_m, MRB_ARGS_REQ(1)); 244 192 mrb_gc_arena_restore(mrb, ai); … … 266 214 if (mrb_const_defined_at(mrb, mrb_obj_value(klass), id)) { 267 215 mrb_warn(mrb, "redefining constant Struct::%S", name); 268 /* ?rb_mod_remove_const(klass, mrb_sym2name(mrb, id)); */216 mrb_const_remove(mrb, mrb_obj_value(klass), id); 269 217 } 270 218 c = mrb_define_class_under(mrb, klass, RSTRING_PTR(name), klass); … … 336 284 else { 337 285 if (argc > 0) name = argv[0]; 338 if (argc > 1) rest = argv[1]; 339 if (mrb_array_p(rest)) { 340 if (!mrb_nil_p(name) && mrb_symbol_p(name)) { 341 /* 1stArgument:symbol -> name=nil rest=argv[0]-[n] */ 342 mrb_ary_unshift(mrb, rest, name); 343 name = mrb_nil_value(); 344 } 345 } 346 else { 347 pargv = &argv[1]; 348 argcnt = argc-1; 349 if (!mrb_nil_p(name) && mrb_symbol_p(name)) { 350 /* 1stArgument:symbol -> name=nil rest=argv[0]-[n] */ 351 name = mrb_nil_value(); 352 pargv = &argv[0]; 353 argcnt++; 354 } 355 rest = mrb_ary_new_from_values(mrb, argcnt, pargv); 356 } 286 pargv = &argv[1]; 287 argcnt = argc-1; 288 if (!mrb_nil_p(name) && mrb_symbol_p(name)) { 289 /* 1stArgument:symbol -> name=nil rest=argv[0]-[n] */ 290 name = mrb_nil_value(); 291 pargv = &argv[0]; 292 argcnt++; 293 } 294 rest = mrb_ary_new_from_values(mrb, argcnt, pargv); 357 295 for (i=0; i<RARRAY_LEN(rest); i++) { 358 296 id = mrb_obj_to_sym(mrb, RARRAY_PTR(rest)[i]); … … 360 298 } 361 299 } 362 st = make_struct(mrb, name, rest, struct_class(mrb));300 st = make_struct(mrb, name, rest, mrb_class_ptr(klass)); 363 301 if (!mrb_nil_p(b)) { 364 mrb_yield_with_class(mrb, b, 1, &st, st, mrb_class_ptr( klass));302 mrb_yield_with_class(mrb, b, 1, &st, st, mrb_class_ptr(st)); 365 303 } 366 304 … … 419 357 { 420 358 mrb_value s; 421 mrb_int i, len;422 359 423 360 mrb_get_args(mrb, "o", &s); … … 430 367 mrb_raise(mrb, E_TYPE_ERROR, "corrupted struct"); 431 368 } 432 if (RSTRUCT_LEN(copy) != RSTRUCT_LEN(s)) { 433 mrb_raise(mrb, E_TYPE_ERROR, "struct size mismatch"); 434 } 435 len = RSTRUCT_LEN(copy); 436 for (i = 0; i < len; i++) { 437 mrb_ary_set(mrb, copy, i, RSTRUCT_PTR(s)[i]); 438 } 369 mrb_ary_replace(mrb, copy, s); 439 370 return copy; 440 371 } 441 372 442 373 static mrb_value 443 struct_aref_sym(mrb_state *mrb, mrb_value s, mrb_sym id)444 { 445 mrb_value *ptr, members;374 struct_aref_sym(mrb_state *mrb, mrb_value obj, mrb_sym id) 375 { 376 mrb_value members, *ptr; 446 377 const mrb_value *ptr_members; 447 378 mrb_int i, len; 448 379 449 ptr = RSTRUCT_PTR(s); 450 members = struct_members(mrb, s); 380 members = struct_members(mrb, obj); 451 381 ptr_members = RARRAY_PTR(members); 452 382 len = RARRAY_LEN(members); 383 ptr = RSTRUCT_PTR(obj); 453 384 for (i=0; i<len; i++) { 454 if (mrb_symbol(ptr_members[i]) == id) { 385 mrb_value slot = ptr_members[i]; 386 if (mrb_symbol_p(slot) && mrb_symbol(slot) == id) { 455 387 return ptr[i]; 456 388 } 457 389 } 458 mrb_raisef(mrb, E_INDEX_ERROR, " no member '%S' in struct", mrb_sym2str(mrb, id));390 mrb_raisef(mrb, E_INDEX_ERROR, "'%S' is not a struct member", mrb_sym2str(mrb, id)); 459 391 return mrb_nil_value(); /* not reached */ 460 392 } … … 504 436 505 437 if (mrb_nil_p(sym)) { 506 mrb_ raisef(mrb, E_INDEX_ERROR, "no member '%S' in struct", idx);438 mrb_name_error(mrb, mrb_intern_str(mrb, idx), "no member '%S' in struct", idx); 507 439 } 508 440 idx = sym; … … 523 455 members = struct_members(mrb, s); 524 456 len = RARRAY_LEN(members); 525 if (RSTRUCT_LEN(s) != len) {526 mrb_raisef(mrb, E_TYPE_ERROR,527 "struct size differs (%S required %S given)",528 mrb_fixnum_value(len), mrb_fixnum_value(RSTRUCT_LEN(s)));529 }530 457 ptr = RSTRUCT_PTR(s); 531 458 ptr_members = RARRAY_PTR(members); 532 459 for (i=0; i<len; i++) { 533 460 if (mrb_symbol(ptr_members[i]) == id) { 461 mrb_struct_modify(mrb, s); 534 462 ptr[i] = val; 535 463 return val; 536 464 } 537 465 } 538 mrb_ raisef(mrb, E_INDEX_ERROR, "no member '%S' in struct", mrb_sym2str(mrb, id));466 mrb_name_error(mrb, id, "no member '%S' in struct", mrb_sym2str(mrb, id)); 539 467 return val; /* not reach */ 540 468 } … … 575 503 576 504 if (mrb_nil_p(sym)) { 577 mrb_ raisef(mrb, E_INDEX_ERROR, "no member '%S' in struct", idx);505 mrb_name_error(mrb, mrb_intern_str(mrb, idx), "no member '%S' in struct", idx); 578 506 } 579 507 idx = sym; … … 595 523 mrb_fixnum_value(i), mrb_fixnum_value(RSTRUCT_LEN(s))); 596 524 } 525 mrb_struct_modify(mrb, s); 597 526 return RSTRUCT_PTR(s)[i] = val; 598 527 } … … 720 649 mrb_int i; 721 650 722 members = struct_ s_members(mrb, mrb_class(mrb, self));651 members = struct_members(mrb, self); 723 652 ret = mrb_hash_new_capa(mrb, RARRAY_LEN(members)); 724 653 … … 761 690 struct RClass *st; 762 691 st = mrb_define_class(mrb, "Struct", mrb->object_class); 692 MRB_SET_INSTANCE_TT(st, MRB_TT_ARRAY); 763 693 764 694 mrb_define_class_method(mrb, st, "new", mrb_struct_s_def, MRB_ARGS_ANY()); /* 15.2.18.3.1 */ … … 777 707 mrb_define_method(mrb, st, "values", mrb_struct_to_a, MRB_ARGS_NONE()); 778 708 mrb_define_method(mrb, st, "to_h", mrb_struct_to_h, MRB_ARGS_NONE()); 779 mrb_define_method(mrb, st, "values_at", mrb_struct_values_at, MRB_ARGS_ NONE());709 mrb_define_method(mrb, st, "values_at", mrb_struct_values_at, MRB_ARGS_ANY()); 780 710 } 781 711 -
EcnlProtoTool/trunk/mruby-1.3.0/mrbgems/mruby-struct/test/struct.rb
r321 r331 3 3 4 4 assert('Struct', '15.2.18') do 5 Struct.class == Class5 assert_equal Class, Struct.class 6 6 end 7 7 8 8 assert('Struct.new', '15.2.18.3.1') do 9 9 c = Struct.new(:m1, :m2) 10 c.superclass == Struct and11 c.members == [:m1,:m2]10 assert_equal Struct, c.superclass 11 assert_equal [:m1, :m2], c.members 12 12 end 13 13 … … 15 15 assert('Struct.new', '15.2.18.3.1') do 16 16 c = Struct.new() 17 c.superclass == Struct and c.members == [] 17 assert_equal Struct, c.superclass 18 assert_equal [], c.members 18 19 end 19 20 … … 22 23 cc1 = c.new(1,2) 23 24 cc2 = c.new(1,2) 24 cc1 == cc2 25 assert_true cc1 == cc2 26 27 Struct.new(:m1, :m2) { def foo; end } 28 assert_raise(NoMethodError) { Struct.new(:m1).new.foo } 25 29 end 26 30 … … 28 32 c = Struct.new(:m1, :m2) 29 33 cc = c.new(1,2) 30 cc[:m1] == 1 and cc["m2"] == 2 34 assert_equal 1, cc[:m1] 35 assert_equal 2, cc["m2"] 36 assert_equal 1, cc[0] 37 assert_equal 2, cc[-1] 38 assert_raise(TypeError) { cc[[]] } 39 assert_raise(IndexError) { cc[2] } 40 assert_raise(NameError) { cc['tama'] } 31 41 end 32 42 … … 35 45 cc = c.new(1,2) 36 46 cc[:m1] = 3 37 cc[:m1] == 347 assert_equal 3, cc[:m1] 38 48 cc["m2"] = 3 39 49 assert_equal 3, cc["m2"] 50 cc[0] = 4 51 assert_equal 4, cc[0] 52 cc[-1] = 5 53 assert_equal 5, cc[-1] 40 54 assert_raise(TypeError) { cc[[]] = 3 } 55 assert_raise(IndexError) { cc[2] = 7 } 56 assert_raise(NameError) { cc['pochi'] = 8 } 41 57 end 42 58 … … 48 64 a << x 49 65 } 50 a [0] == 1 and a[1] == 266 assert_equal [1, 2], a 51 67 end 52 68 … … 58 74 a << [k,v] 59 75 } 60 a [0] == [:m1, 1] and a[1] == [:m2, 2]76 assert_equal [[:m1, 1], [:m2, 2]], a 61 77 end 62 78 63 79 assert('Struct#members', '15.2.18.4.6') do 64 80 c = Struct.new(:m1, :m2) 65 cc = c.new(1,2) 66 cc.members == [:m1,:m2] 81 assert_equal [:m1, :m2], c.new(1,2).members 67 82 end 68 83 69 84 assert('Struct#select', '15.2.18.4.7') do 70 85 c = Struct.new(:m1, :m2) 71 cc = c.new(1,2) 72 cc.select{|v| v % 2 == 0} == [2] 86 assert_equal([2]) { c.new(1,2).select{|v| v % 2 == 0} } 73 87 end 74 88 … … 101 115 end 102 116 117 assert('struct dup') do 118 c = Struct.new(:m1, :m2, :m3, :m4, :m5) 119 cc = c.new(1,2,3,4,5) 120 assert_nothing_raised { 121 assert_equal(cc, cc.dup) 122 } 123 end 124 103 125 assert('struct inspect') do 104 126 c = Struct.new(:m1, :m2, :m3, :m4, :m5) … … 130 152 assert_raise(IndexError) { a.values_at 2 } 131 153 end 154 155 assert("Struct#dig") do 156 a = Struct.new(:blue, :purple).new('aki', Struct.new(:red).new(1)) 157 assert_equal 'aki', a.dig(:blue) 158 assert_equal 1, a.dig(:purple, :red) 159 assert_equal 1, a.dig(1, 0) 160 end 161 162 assert("Struct.new removes existing constant") do 163 skip "redefining Struct with same name cause warnings" 164 begin 165 assert_not_equal Struct.new("Test", :a), Struct.new("Test", :a, :b) 166 ensure 167 Struct.remove_const :Test 168 end 169 end 170 171 assert("Struct#initialize_copy requires struct to be the same type") do 172 begin 173 Struct.new("Test", :a) 174 a = Struct::Test.new("a") 175 Struct.remove_const :Test 176 Struct.new("Test", :a, :b) 177 assert_raise(TypeError) do 178 a.initialize_copy(Struct::Test.new("a", "b")) 179 end 180 ensure 181 Struct.remove_const :Test 182 end 183 end 184 185 assert("Struct.new does not allow array") do 186 assert_raise(TypeError) do 187 Struct.new("Test", [:a]) 188 end 189 end 190 191 assert("Struct.new generates subclass of Struct") do 192 begin 193 original_struct = Struct 194 Struct = String 195 assert_equal original_struct, original_struct.new.superclass 196 ensure 197 Struct = original_struct 198 end 199 end 200 201 assert 'Struct#freeze' do 202 c = Struct.new :m 203 204 o = c.new 205 o.m = :test 206 assert_equal :test, o.m 207 208 o.freeze 209 assert_raise(RuntimeError) { o.m = :modify } 210 assert_raise(RuntimeError) { o[:m] = :modify } 211 assert_equal :test, o.m 212 end
Note:
See TracChangeset
for help on using the changeset viewer.