From 3ce5d89c206a54cbf32032674c9edf6f649e95f6 Mon Sep 17 00:00:00 2001 From: Jeremy Evans Date: Sat, 19 Apr 2025 23:47:36 -0700 Subject: [PATCH] [ruby/pp] Avoid an array allocation per element in list passed to seplist The array allocation was because the keyword splat expression is not recognized as safe by the compiler. Also avoid unnecessary >= method call per element. This uses a private constant to avoid unnecessary work at runtime. I assume the only reason this code is needed is because v may end with a ruby2_keywords hash that we do not want to treat as keywords. This issue was found by the performance warning in Ruby feature 21274. https://github.com/ruby/pp/commit/3bf6df0e5c --- lib/pp.rb | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/lib/pp.rb b/lib/pp.rb index 332062164d..d86bfb9119 100644 --- a/lib/pp.rb +++ b/lib/pp.rb @@ -276,15 +276,20 @@ class PP < PrettyPrint def seplist(list, sep=nil, iter_method=:each) # :yield: element sep ||= lambda { comma_breakable } first = true + kwsplat = EMPTY_HASH list.__send__(iter_method) {|*v| if first first = false else sep.call end - RUBY_VERSION >= "3.0" ? yield(*v, **{}) : yield(*v) + kwsplat ? yield(*v, **kwsplat) : yield(*v) } end + EMPTY_HASH = if RUBY_VERSION >= "3.0" + {}.freeze + end + private_constant :EMPTY_HASH # A present standard failsafe for pretty printing any given Object def pp_object(obj)