Rails создает одну запись VS создает несколько записей Разница в ПРОИЗВОДИТЕЛЬНОСТИ

Есть ли разница в скорости между этими методами? (ПОСТГРЕSQL)

Первый

products = [{...},{...},...]
products.each { |p|
  Product.create(p)
}

Второй

products = [{...},{...},...]
Product.create(products)

Оба метода для каждой записи делают два запроса:

1) INSERT INTO "products" VALUES (..)
2) UPDATE "products" SET "updated_at"...

"Есть ли разница в скорости" - это то, что можно мера (и точно знать)

Sergio Tulentsev 10.04.2019 11:59

но если я должен предположить, второй, по крайней мере, не медленнее. И это может быть намного быстрее (если все создания продукта будут выполняться в одном INSERT).

Sergio Tulentsev 10.04.2019 12:01

Кажется, в вашей модели определен обратный вызов, который вызывает второй запрос на обновление. На самом деле должен быть только один запрос на вставку. Это действительно не имеет ничего общего с первой частью вашего вопроса.

max 10.04.2019 13:56
Стоит ли изучать PHP в 2023-2024 годах?
Стоит ли изучать PHP в 2023-2024 годах?
Привет всем, сегодня я хочу высказать свои соображения по поводу вопроса, который я уже много раз получал в своем сообществе: "Стоит ли изучать PHP в...
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
В JavaScript одним из самых запутанных понятий является поведение ключевого слова "this" в стрелочной и обычной функциях.
Приемы CSS-макетирования - floats и Flexbox
Приемы CSS-макетирования - floats и Flexbox
Здравствуйте, друзья-студенты! Готовы совершенствовать свои навыки веб-дизайна? Сегодня в нашем путешествии мы рассмотрим приемы CSS-верстки - в...
Тестирование функциональных ngrx-эффектов в Angular 16 с помощью Jest
В системе управления состояниями ngrx, совместимой с Angular 16, появились функциональные эффекты. Это здорово и делает код определенно легче для...
Концепция локализации и ее применение в приложениях React ⚡️
Концепция локализации и ее применение в приложениях React ⚡️
Локализация - это процесс адаптации приложения к различным языкам и культурным требованиям. Это позволяет пользователям получить опыт, соответствующий...
Пользовательский скаляр GraphQL
Пользовательский скаляр GraphQL
Листовые узлы системы типов GraphQL называются скалярами. Достигнув скалярного типа, невозможно спуститься дальше по иерархии типов. Скалярный тип...
0
3
787
2
Перейти к ответу Данный вопрос помечен как решенный

Ответы 2

Между ними не должно быть практически никакой разницы в производительности.

Если вы отметите реализация, вы увидите, что если вы передаете массив .create, он выполняет итерацию по массиву и вызывает .create для каждого элемента в массиве.

module ActiveRecord
  module Persistence
    extend ActiveSupport::Concern
    module ClassMethods
      # ...
      def create(attributes = nil, &block)
        if attributes.is_a?(Array)
          attributes.collect { |attr| create(attr, &block) }
        else
          object = new(attributes, &block)
          object.save
          object
        end
      end
      # ...
   end
end

ActiveRecord на самом деле не реализует массовые вставки. Под этим я подразумеваю вставку нескольких строк в один оператор:

INSERT INTO products (name, description) VALUES ('Soap', '100% whale based.'),('Shampoo', '...') 

Что может быть быстрее на порядок при наличии достаточного количества записей.

Но вы можете написать свой собственный SQL для этого:

class Product
  def self.mass_insert(attributes)
    values = products.map("(#{attributes[:name]}, #{attributes[:description]})").join(',')
    self.connection.execute("INSERT INTO products (name, description) VALUES #{values}")
  end
end

Обратите внимание, что этот простой пример НЕ очищает ввод и уязвим для атаки с внедрением SQL.

Ответ принят как подходящий

Максимум прав. Это локальное решение.

Но я нашел activerecord-importдрагоценный камень, который делает то же самое - импортирует объемные объекты.

Другие вопросы по теме