• R
    PERF: Improve performance of where when using an array of values · c3a2b54b
    Ryuta Kamizono 提交于
    This is a smaller alternative of performance improvement, without
    refactoring type casting mechanism #39009.
    
    This is relatively a smaller change (but about 40% faster than before),
    so I think this could be easier reviewed without discuss about
    refactoring type casting mechanism.
    
    This just makes `attribute.in(values)` less allocation from an array of
    casted nodes to one casted array node.
    
    ```ruby
    ids = (1..1000).each.map do |n|
      Post.create!.id
    end
    
    Benchmark.ips do |x|
      x.report("where with ids") do
        Post.where(id: ids).to_a
      end
    
      x.report("where with sanitize") do
        Post.where(ActiveRecord::Base.sanitize_sql(["id IN (?)", ids])).to_a
      end
    
      x.compare!
    end
    ```
    
    Before:
    
    ```
    Warming up --------------------------------------
          where with ids     7.000  i/100ms
     where with sanitize    13.000  i/100ms
    
    Calculating -------------------------------------
          where with ids     70.661  (± 5.7%) i/s -    357.000  in   5.072771s
     where with sanitize    130.993  (± 7.6%) i/s -    663.000  in   5.096085s
    
    Comparison:
     where with sanitize:      131.0 i/s
          where with ids:       70.7 i/s - 1.85x  slower
    ```
    
    After:
    
    ```
    Warming up --------------------------------------
          where with ids    10.000  i/100ms
     where with sanitize    13.000  i/100ms
    
    Calculating -------------------------------------
          where with ids     98.174  (± 7.1%) i/s -    490.000  in   5.012851s
     where with sanitize    132.289  (± 8.3%) i/s -    663.000  in   5.052728s
    
    Comparison:
     where with sanitize:      132.3 i/s
          where with ids:       98.2 i/s - 1.35x  slower
    ```
    c3a2b54b
predications.rb 5.9 KB