aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--benchmark/string_dup.yml7
-rw-r--r--string.c13
2 files changed, 20 insertions, 0 deletions
diff --git a/benchmark/string_dup.yml b/benchmark/string_dup.yml
new file mode 100644
index 0000000000..90793f9f2a
--- /dev/null
+++ b/benchmark/string_dup.yml
@@ -0,0 +1,7 @@
+prelude: |
+ # frozen_string_literal: true
+benchmark:
+ uplus: |
+ +"A"
+ dup: |
+ "A".dup
diff --git a/string.c b/string.c
index 41641c67e8..2f69ab1adb 100644
--- a/string.c
+++ b/string.c
@@ -1770,6 +1770,18 @@ rb_str_dup(VALUE str)
return str_duplicate(rb_obj_class(str), str);
}
+/* :nodoc: */
+VALUE
+rb_str_dup_m(VALUE str)
+{
+ if (LIKELY(BARE_STRING_P(str))) {
+ return str_duplicate(rb_obj_class(str), str);
+ }
+ else {
+ return rb_obj_dup(str);
+ }
+}
+
VALUE
rb_str_resurrect(VALUE str)
{
@@ -12084,6 +12096,7 @@ Init_String(void)
rb_define_method(rb_cString, "freeze", rb_str_freeze, 0);
rb_define_method(rb_cString, "+@", str_uplus, 0);
rb_define_method(rb_cString, "-@", str_uminus, 0);
+ rb_define_method(rb_cString, "dup", rb_str_dup_m, 0);
rb_define_alias(rb_cString, "dedup", "-@");
rb_define_method(rb_cString, "to_i", rb_str_to_i, -1);