From f02b261c8beb0cea7cc27f7a3fcef43a7900fde0 Mon Sep 17 00:00:00 2001 From: matz Date: Wed, 20 Sep 2006 04:18:25 +0000 Subject: * string.c (sym_eql): fail early to gain performance. * string.c (sym_hash): cache hash value in aux.shared if possible. * gc.c (rb_obj_id): no need to treat symbols specially. * lib/fileutils.rb (FileUtils::FileUtils): singleton_methods() no longer return an array of strings, but of symbols. * lib/delegate.rb (DelegateClass): ditto. git-svn-id: http://svn.ruby-lang.org/repos/ruby/trunk@10971 b2dd03c8-39d4-4d8f-98ff-823fe69b080e --- string.c | 46 ++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 46 insertions(+) (limited to 'string.c') diff --git a/string.c b/string.c index 63d4b298d..41661ba64 100644 --- a/string.c +++ b/string.c @@ -535,6 +535,8 @@ void rb_str_associate(VALUE str, VALUE add) { if (STR_ASSOC_P(str)) { + /* sanity check */ + if (OBJ_FROZEN(str)) rb_error_frozen("string"); /* already associated */ rb_ary_concat(RSTRING(str)->as.heap.aux.shared, add); } @@ -554,6 +556,7 @@ VALUE rb_str_associated(VALUE str) { if (STR_ASSOC_P(str)) { + if (OBJ_FROZEN(str)) return Qfalse; return RSTRING(str)->as.heap.aux.shared; } return Qfalse; @@ -4440,6 +4443,47 @@ sym_equal(VALUE sym1, VALUE sym2) return rb_str_equal(sym1, sym2); } +/* + * call-seq: + * sym.eql?(other) => true or false + * + * Two symbols are equal if they are exactly same symbols. + */ + +static VALUE +sym_eql(VALUE sym1, VALUE sym2) +{ + if (sym1 == sym2) return Qtrue; + if (SYMBOL_P(sym2)) return Qfalse; + return rb_str_eql(sym1, sym2); +} + +/* + * call-seq: + * sym.hash => fixnum + * + * Return a hash based on the symbol's length and content. + */ +static VALUE +sym_hash(VALUE sym) +{ + int h; + VALUE hval; + + if (STR_SHARED_P(sym)) { + /* if a symbol has shared value, that's a hash value. */ + return RSTRING(sym)->as.heap.aux.shared; + } + h = rb_str_hash(sym); + hval = INT2FIX(h); + if (!STR_EMBED_P(sym)) { + FL_SET(sym, STR_ASSOC); + RSTRING(sym)->as.heap.aux.shared = hval; + } + return hval; +} + + /* * call-seq: * sym.to_i => fixnum @@ -4721,6 +4765,8 @@ Init_String(void) rb_define_singleton_method(rb_cSymbol, "intern", rb_sym_s_intern, 1); rb_define_method(rb_cSymbol, "==", sym_equal, 1); + rb_define_method(rb_cSymbol, "eql?", sym_eql, 1); + rb_define_method(rb_cSymbol, "hash", sym_hash, 0); rb_define_method(rb_cSymbol, "to_i", sym_to_i, 0); rb_define_method(rb_cSymbol, "inspect", sym_inspect, 0); rb_define_method(rb_cSymbol, "to_s", sym_to_s, 0); -- cgit