Лучшая производительность - временная таблица MySQL или чтение CSV-файла напрямую или что-то еще?

0

Ежедневно я получаю исходный файл csv, который имеет строки 250k и 40 столбцов. Его 290 МБ. Мне нужно будет отфильтровать его, потому что у него больше строк, чем мне нужно, и больше столбцов, чем мне нужно.

Для каждой строки, которая соответствует критериям фильтрации, мы хотим обновить ее в записи системы назначения 1 за раз, используя свой PHP API.

Каким будет наилучший подход для всего до вызова API (чтение/фильтрация/загрузка) для максимальной производительности?

  1. Итерация через каждую строку файла, решая, нужна ли мне эта строка, хватаю только те столбцы, которые мне нужны, а затем передаю их в API?

  2. Загрузка ВСЕХ записей во временную таблицу MySQL с использованием LOAD DATA INFILE. Затем запрос таблицы для строк и полей, которые я хочу, и итерации через набор результатов, передающий каждую запись в API?

Есть ли лучший вариант?

Спасибо!

Теги:
performance

2 ответа

0
  1. LOAD DATA, но скажите @dummy1, @dummy2 т.д. Для столбцов, которые вам не нужно сохранять. Это избавляет от лишних столбцов. Загрузите временную таблицу. (1 оператор SQL.)
  2. Производите очистку данных. (Некоторое количество операторов SQL, но без цикла, если это возможно.)
  3. Сделайте один INSERT INTO real_table SELECT... FROM tmp_table WHERE... чтобы отфильтровывать ненужные строки и копировать нужные в реальную таблицу. (1 оператор SQL.)

Вы не упомянули о необходимости шага 2. Некоторые вещи, которые могут вам понадобиться:

  • Вычисление одного столбца из другого (-ов).
  • Нормализация.
  • Синхронизация дат в правильном формате.

В одном проекте я сделал:

  • 1 Гб данных приходили в каждый час.
  • Загрузите временную таблицу.
  • Нормализовать несколько столбцов (2 SQL на столбец)
  • Некоторая другая обработка.
  • Обобщите данные примерно на 6 сводных таблиц. Пример: INSERT INTO summary SELECT a,b,COUNT(*),SUM(c) FROM tmp GROUP BY a,b; , Или INSERT ON DUPLICATE KEY UPDATE для обработки строк, уже существующих в summary.
  • Наконец, скопируйте нормализованные, очищенные данные в таблицу "real".
  • Весь процесс занял 7 минут.

Использовать ли MyISAM, InnoDB или MEMORY - вам нужно будет сравнить свой собственный случай. В таблице tmp индекс не требуется, так как каждый шаг обработки выполняет полное сканирование таблицы.

Таким образом, 0,3 ГБ каждые 24 часа - не должно быть пота.

0

Сначала мне нужно сделать предположение, большинство из 250 тыс. Строк перейдут в базу данных. Если только очень небольшой процент, то итерация по файлу и отправка всех строк в партии, безусловно, быстрее.

Различные конфигурации могут повлиять на оба подхода, но, в общем, говорить, второй подход лучше работает с меньшим количеством усилий по созданию сценариев.

Подход 1: хуже всего отправить каждую строку на сервер. Больше кругосветного путешествия и более мелких коммитов.

То, что вы можете улучшить здесь, - это отправить строки в пакетном режиме, возможно, несколько сотен. Вы увидите гораздо лучший результат.

Подход 2: MyISAM будет быстрее, чем InnoDB из-за всех накладных расходов и сложности ACID. Если MyISAM вам подходит, попробуйте сначала.

Для InnoDB существует лучший подход 3 (который на самом деле представляет собой сочетание подхода 1 и подхода 2). Поскольку InnoDB не блокирует таблицу, и вы можете попытаться одновременно импортировать несколько файлов, то есть отделить файлы CSV к нескольким файлам и выполнить загрузку данных из ваших сценариев. Не добавляйте автоматически ключ auto_increment в таблицу, чтобы избежать блокировки auto_inc.

Ещё вопросы

Сообщество Overcoder
Наверх
Меню