Я просто потратил значительную часть своего времени на то, чтобы попытаться реализовать решение Асии выше с объектными сравнениями, а не строгое равенство. Поэтому я решил поделиться этим здесь.
Допустим, вы расширили свой вопрос от userIds до полных пользователей. Вы хотите найти все документы, в которых каждый элемент в массиве users
присутствует в другом массиве пользователей: [{user: 1, group: 3}, {user: 2, group: 5},...]
Это не сработает: db.collection.find({"users":{"$not":{"$elemMatch":{"$nin":[{user: 1, group: 3},{user: 2, group: 5},...]}}}}})
, потому что $ nin работает только для строгого равенства. Поэтому нам нужно найти другой способ выражения «Не в массиве» для массивов объектов. И использование $where
слишком сильно замедлит запрос.
Решение:
db.collection.find({
"users": {
"$not": {
"$elemMatch": {
// if all of the OR-blocks are true, element is not in array
"$and": [{
// each OR-block == true if element != that user
"$or": [
"user": { "ne": 1 },
"group": { "ne": 3 }
]
}, {
"$or": [
"user": { "ne": 2 },
"group": { "ne": 5 }
]
}, {
// more users...
}]
}
}
}
})
Чтобы завершить логику: $ elemMatch соответствует всем документам, у которых есть пользователь, который не находится в массив. Таким образом, $ не будет соответствовать всем документам, в которых есть все пользователи в массиве.
Метод bbox
возвращает ограничивающий прямоугольник только для элементов холста. Если вы добавите метку на холст с помощью grid
, это не элементы холста. Вы должны использовать один из методов (create_line
, create_window
и т. Д.), Чтобы добавить объект на холст.
(Обратите внимание, что bbox
будет возвращать, покажет (0, 0, 0, 0), пока все, что добавлено на холст, фактически не будет видно на экране. Вам нужно сбросить область прокрутки либо после вызова update, либо в ожидании для чего-то вроде <Configure>
события.)