У меня есть большая таблица базы данных (~ 1 миллион записей), которая мне нужна для очистки дубликатов записей. Структура таблицы следующая:
|----|-------------|-----|-----|--------------------|
| id | relation_id | foo | bar | timestamp |
|----|-------------|-----|-----|--------------------|
| 1 | 1 |14.20|0.22 |2019-10-21 14:00:01 |
| 2 | 1 |14.20|0.22 |2019-10-21 14:00:01 |
| 3 | 1 |14.20|0.22 |2019-10-21 14:00:01 |
| 4 | 2 |10.36|0.75 |2019-10-21 14:00:01 |
| 5 | 2 |10.36|0.75 |2019-10-21 14:00:01 |
| 6 | 2 |10.36|0.75 |2019-10-21 14:00:01 |
|----|-------------|-----|-----|--------------------|
В соответствии с приведенным выше примером существует много записей, которые имеют одинаковую комбинацию значений relation_id
, foo
, bar
и * 1007. *. Мне нужно создать сценарий, который будет запускаться для определения уникальных значений, а затем удалять и дублировать ссылки. Поэтому я хотел бы получить что-то вроде:
|----|-------------|-----|-----|--------------------|
| id | relation_id | foo | bar | timestamp |
|----|-------------|-----|-----|--------------------|
| 1 | 1 |14.20|0.22 |2019-10-21 14:00:01 |
| 4 | 2 |10.36|0.75 |2019-10-21 14:00:01 |
|----|-------------|-----|-----|--------------------|
Я протестировал циклический просмотрrelation_id
(поскольку существует только 20 уникальных значений), а затем выполнить что-то вроде этого, чтобы создать коллекцию уникальных записей:
$unique = collect([]);
$collection = Model::where('relation_id', $relation_id)->chunk(100, function($items) use ($unique) {
$unique->push($items->unique()->values()->all());
});
После этого я планировал выполнить цикл по всей модели. записи и удалить, если элемент не был в коллекции $unique
. Примерно так:
Model::chunk(100, function($items) {
foreach ($items as $item) {
if(!$unique->contains('id', $item->id)){
$item->delete;
}
}
});
Моя проблема в том, что таблица базы данных настолько велика, что я не могу проверить, работает ли эта логика. Выполнение первой части вышеописанного сценария (для заполнения $unique
) для одного $relation_id
пробежало в течение 30 минут без результатов.
Я относительно уверен, что это не лучший подход кудаляйте дублирующиеся записи, так как мой подход требует нескольких запросов, которые, как я полагаю, могут быть оптимизированы (что крайне важно при работе с такой большой таблицей).
Итак, каков наиболее эффективный способ запроса таблицы базы данных? проверить уникальные записи (на основе нескольких столбцов) и удалить дублирующиеся записи?