From 71ffcaf08256c94866cf1e79f3779c85b90fa5bb Mon Sep 17 00:00:00 2001 From: Jean Boussier Date: Wed, 16 Oct 2024 12:01:21 +0200 Subject: [PATCH] Speedup AttributeSet#deep_dup MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit `Hash#deep_dup` is slower because it has to check if the keys are mutable. In this case we know keys are all frozen strings so we can use `transform_values` to skip dealing with keys. Benchmark: https://gist.github.com/casperisfine/ae56bec1e7eecbff3a696b367e2bafa2 Before: ``` ruby 3.4.0preview2 (2024-10-07 master 32c733f57b) +YJIT +PRISM [arm64-darwin23] Warming up -------------------------------------- ActiveRecord 6.113k i/100ms Calculating ------------------------------------- ActiveRecord 61.941k (± 1.6%) i/s (16.14 μs/i) - 311.763k in 5.034628s ``` After: ``` ruby 3.4.0preview2 (2024-10-07 master 32c733f57b) +YJIT +PRISM [arm64-darwin23] Warming up -------------------------------------- ActiveRecord 7.323k i/100ms Calculating ------------------------------------- ActiveRecord 73.195k (± 1.0%) i/s (13.66 μs/i) - 366.150k in 5.002894s ``` --- activemodel/lib/active_model/attribute_set.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/activemodel/lib/active_model/attribute_set.rb b/activemodel/lib/active_model/attribute_set.rb index 94c7fcd7ec7b3..3d418ee973315 100644 --- a/activemodel/lib/active_model/attribute_set.rb +++ b/activemodel/lib/active_model/attribute_set.rb @@ -71,7 +71,7 @@ def freeze end def deep_dup - AttributeSet.new(attributes.deep_dup) + AttributeSet.new(attributes.transform_values(&:deep_dup)) end def initialize_dup(_)