Подтвердить что ты не робот

Как эффективно удалять документы по запросу в монго?

У меня есть запрос, который выбирает документы для удаления. Прямо сейчас я удаляю их вручную, как это (используя python):

for id in mycoll.find(query, fields={}):
  mycoll.remove(id)

Это не очень эффективно. Есть ли лучший способ?

ИЗМЕНИТЬ

Хорошо, я должен извиниться за то, что забыл упомянуть подробности запроса, потому что это имеет значение. Вот полный код python:

def reduce_duplicates(mydb, max_group_size):
  # 1. Count the group sizes
  res = mydb.static.map_reduce(jstrMeasureGroupMap, jstrMeasureGroupReduce, 'filter_scratch', full_response = True)
  # 2. For each entry from the filter scratch collection having count > max_group_size
  deleteFindArgs = {'fields': {}, 'sort': [('test_date', ASCENDING)]}
  for entry in mydb.filter_scratch.find({'value': {'$gt': max_group_size}}):
    key = entry['_id']
    group_size = int(entry['value'])
    # 2b. query the original collection by the entry key, order it by test_date ascending, limit to the group size minus max_group_size.
    for id in mydb.static.find(key, limit = group_size - max_group_size, **deleteFindArgs):
      mydb.static.remove(id)
  return res['counts']['input']

Итак, что он делает? Это уменьшает количество дубликатов ключей до максимально max_group_size за каждое значение ключа, оставляя только самые новые записи. Он работает следующим образом:

  • MR данные в пары (key, count).
  • Итерации по всем парам с помощью count > max_group_size
  • Запросить данные key, сортируя его по возрастанию по метке времени (самая старая первая) и ограничивая результат count - max_group_size самыми старыми записями
  • Удалить каждую найденную запись.

Как вы можете видеть, это выполняет задачу сокращения дубликатов до максимально N новейших записей. Итак, последние два шага foreach-found-remove, и это важная деталь моего вопроса, которая меняет все, и я должен был быть более конкретным об этом - извините.

Теперь о команде удаления remove. Он принимает запрос, но мой включает сортировку и ограничение. Могу ли я сделать это с удалением? Ну, я пробовал:

mydb.static.find(key, limit = group_size - max_group_size, sort=[('test_date', ASCENDING)])

Эта попытка терпит неудачу. Кроме того, кажется, винт mongo.Observe:

C:\dev\poc\SDR>python FilterOoklaData.py
bad offset:0 accessing file: /data/db/ookla.0 - consider repairing database

Излишне говорить, что подход foreach-found-remove работает и дает ожидаемые результаты.

Теперь, надеюсь, я предоставил достаточный контекст и (надеюсь) восстановил утраченную честь.

4b9b3361

Ответ 1

Вы можете использовать запрос для удаления всех соответствующих документов

var query = {name: 'John'};
db.collection.remove(query);

Будьте осторожны, однако, если количество документов, соответствующих документам, велико, ваша база данных может быть менее отзывчивой. Часто рекомендуется удалять документы в небольших кусках.

Скажем, у вас есть 100k документов для удаления из коллекции. Лучше выполнить 100 запросов, которые удаляют 1k документов каждый, кроме 1 запроса, который удаляет все 100k документов.

Ответ 2

Вы можете удалить его непосредственно с использованием языка сценариев MongoDB:

db.mycoll.remove({_id:'your_id_here'});

Ответ 3

Будет ли deleteMany() более эффективным? Недавно я обнаружил, что remove() довольно медленный для 6-миллиметровых документов в коллекции данных 100 м. Документация на (https://docs.mongodb.com/manual/reference/method/db.collection.deleteMany)

db.collection.deleteMany(
   <filter>,
   {
      writeConcern: <document>,
      collation: <document>
   }
)

Ответ 4

Запустите этот запрос в cmd

db.users.remove({ "_id": ObjectId ( "5a5f1c472ce1070e11fde4af" )});

Если вы используете node.js, напишите этот код

User.remove({ _id: req.body.id },, function(err){...});