aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--ChangeLog5
-rw-r--r--NEWS3
-rw-r--r--string.c22
-rw-r--r--test/ruby/test_symbol.rb15
4 files changed, 45 insertions, 0 deletions
diff --git a/ChangeLog b/ChangeLog
index df2aae8c20..eb20a73827 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,8 @@
+Wed Feb 26 01:29:27 2014 NARUSE, Yui <naruse@ruby-lang.org>
+
+ * string.c (sym_find): Add Symbol.find(str), which returns whether given
+ string is defined as symbol or not. [Feature #7854]
+
Tue Feb 25 22:52:02 2014 Kazuhiro NISHIYAMA <zn@mbf.nifty.com>
* ext/dl/dl.c (rb_dl_realloc): use NUM2SIZET instead of NUM2INT.
diff --git a/NEWS b/NEWS
index 12df4d201e..124e40aaf0 100644
--- a/NEWS
+++ b/NEWS
@@ -21,6 +21,9 @@ with all sufficient information, see the ChangeLog file.
* min_by
* max
* max_by
+* Symbol
+ * New methods
+ * Symbol.find(str) returns whether given string is defined as symbol or not.
=== Core classes compatibility issues (excluding feature bug fixes)
diff --git a/string.c b/string.c
index 4e30cb338a..1e26a25bb7 100644
--- a/string.c
+++ b/string.c
@@ -8231,6 +8231,27 @@ str_scrub_bang(int argc, VALUE *argv, VALUE str)
/*
* call-seq:
+ * Symbol.find(str) -> symbol or nil
+ *
+ * Return the related symbol if the symbol already exists.
+ * Return nil if not.
+ */
+
+static VALUE
+sym_find(VALUE dummy, VALUE sym)
+{
+ ID id = rb_check_id(&sym);
+
+ if (id) {
+ return ID2SYM(id);
+ }
+ else {
+ return Qnil;
+ }
+}
+
+/*
+ * call-seq:
* sym == obj -> true or false
*
* Equality---If <i>sym</i> and <i>obj</i> are exactly the same
@@ -8787,6 +8808,7 @@ Init_String(void)
rb_undef_alloc_func(rb_cSymbol);
rb_undef_method(CLASS_OF(rb_cSymbol), "new");
rb_define_singleton_method(rb_cSymbol, "all_symbols", rb_sym_all_symbols, 0); /* in parse.y */
+ rb_define_singleton_method(rb_cSymbol, "find", sym_find, 1);
rb_define_method(rb_cSymbol, "==", sym_equal, 1);
rb_define_method(rb_cSymbol, "===", sym_equal, 1);
diff --git a/test/ruby/test_symbol.rb b/test/ruby/test_symbol.rb
index 7f261b68bb..70358ea1bc 100644
--- a/test/ruby/test_symbol.rb
+++ b/test/ruby/test_symbol.rb
@@ -1,4 +1,5 @@
require 'test/unit'
+require_relative 'envutil'
class TestSymbol < Test::Unit::TestCase
# [ruby-core:3573]
@@ -206,4 +207,18 @@ class TestSymbol < Test::Unit::TestCase
assert_equal(true, "foo#{Time.now.to_i}".to_sym.frozen?)
assert_equal(true, :foo.to_sym.frozen?)
end
+
+ def test_sym_find
+ assert_separately(%w[--disable=gems], <<-"end;")
+ assert_equal :intern, Symbol.find("intern")
+ assert_raise(TypeError){ Symbol.find(true) }
+
+ str = "__noexistent__"
+ assert_equal nil, Symbol.find(str)
+ assert_equal nil, Symbol.find(str)
+ sym = str.intern
+ assert_equal str, sym.to_s
+ assert_equal sym, Symbol.find(str)
+ end;
+ end
end