Я совершенно не знаком с MongoDB и хотел сравнить производительность запросов модели данных NoSQL относительно ее счетчика реляционной базы данных. Я написал это в оболочке MongoDB
// Make 10 businesses
// Each business has 10 locations
// Each location has 10 departments
// Each department has 10 teams
// Each team has 100 employees
(new Array(10)).fill(0).forEach(_=>
db.businesses.insert({
"name":"Business Name",
"locations":(new Array(10)).fill(0).map(_=>({
"name":"Office Location",
"departments":(new Array(10)).fill(0).map(_=>({
"name":"Department",
"teams":(new Array(10)).fill(0).map(_=>({
"name":"Team Name",
"employees":(new Array(100)).fill(0).map(_=>({
"age":Math.floor(Math.random()*100)
}))
}))
}))
}))
})
);
Затем я попытался создать эквивалент MySQL, EXPLAIN SELECT age,name,(and a few other fields) FROM employees WHERE age >= 50 ORDER BY age DESCнаписав следующее утверждение:
db.businesses.aggregate([
{ $unwind: "$locations" },
{ $unwind: "$locations.departments" },
{ $unwind: "$locations.departments.teams" },
{ $unwind: "$locations.departments.teams.employees" },
{ $project: { _id: 0, age: "$locations.departments.teams.employees.age" } },
{ $match: { "age": { $gte: 50 }} },
{ $sort: {"age" : -1}}
]).explain("executionStats")
Результат был:
"errmsg": "Сортировка превысила лимит памяти в 104857600 байт, но не включила внешнюю сортировку. Отмена операции. Передайте allowDiskUse: true, чтобы включить.",
Поэтому я удалил предложение сортировки и попытался получить файл explain. Но результат был:
TypeError: db.busshops.aggregate (...). Объяснение не является функцией
Итак, мои вопросы:
В первую очередь, я хочу знать разницу в производительности по SELECT age FROM employees WHERE age >= 50 ORDER BY age DESCсравнению с агрегированным счетчиком запросов MongoDB. Это более или менее то же самое? Будет ли один из них существенно быстрее или производительнее другого?
В качестве альтернативы, как мне исправить мой запрос MongoDB, чтобы я мог получить подробную информацию о производительности для сравнения с моей частью счетчика запросов MySQL?
Сотрудники - это отдельные лица; таким образом, вы, вероятно, не захотите ageтак глубоко моделировать члена команды в богатой структуре отделов, локаций и команд. Прекрасно иметь отдельную employeesколлекцию и просто делать:
db.businesses.aggregate([
{$match: {"age": {$gt: 50} }}
,{$sort: {"age": -1} }
]);
Глубоко в вашей businessesколлекции вы можете иметь:
{ teams: [ {name: "T1", employees: [ "E1", "E34" ]} ] }
В качестве альтернативы попробуйте следующее:
db.businesses.aggregate([ your pipeline] ,{allowDiskUse:true});
OP имеет настройку 10 бизнес -> 10 мест -> 10 отделов -> 10 команд -> 100 emps. Первые 3 раскрутки создают 10000-кратный взрыв данных, а последний - 100-кратный. Мы можем уменьшить попадание, используя $filter:
db.businesses.aggregate([
{ $unwind: "$locations" },
{ $unwind: "$locations.departments" },
{ $unwind: "$locations.departments.teams" },
{$project: { XX: {$filter: {
input: "$locations.departments.teams.employees", as: "z", cond: {$gte: [ "$$z.age", 50] } }} }} ,{$unwind: "$XX"} ,{$sort: {"XX.age":-1}}])
Вам лучше перейти $matchк первому конвейеру, потому что структура агрегирования теряет индекс после первого конвейера, также я думаю, вам не нужно раскручивать эти массивы.
я смог получить результат за 1,5 секунды без каких-либо индексов, изменив запрос следующим образом:
db.businesses.aggregate([
{
$unwind: "$locations"
},
{
$unwind: "$locations.departments"
},
{
$unwind: "$locations.departments.teams"
},
{
$unwind: "$locations.departments.teams.employees"
},
{
$match: { "locations.departments.teams.employees.age": { $gte: 50
}
}
},
{
$project: { _id: 0, age: "$locations.departments.teams.employees.age"
}
},
{
$group: { _id: "$age"
}
},
{
$project: { _id: 0, age: "$_id"
}
},
{
$sort: {
"age": - 1
}
}
], {
explain: false
})
Есть еще один способ решить общую проблему, хотя вопрос OP - это не яблоки для яблок. Цель - найти всех возрастом> = 50 и отсортировать. Ниже приведен пример того, что «почти» делает это и также добавляет в него, loc,dept,teamесли вам интересно, как это тоже получить, но вы можете убрать строки, чтобы получить только emps. Теперь это не отсортировано, но можно утверждать, что механизм БД не собирается выполнять работу по сортировке лучше, чем клиент, и все данные в любом случае должны поступать по сети. А клиент может использовать более изощренные приемы кодирования, чтобы ageразобраться в поле и отсортировать его.
c = db.foo.aggregate([
{$project: {XX: {$map: {input: "$locations", as:"z", in: {$map: {input: "$$z.departments", as:"z2", in: {$map: {input: "$$z2.teams", as:"z3", in: {loc: "$$z.name", // remove if you want
dept: "$$z2.name", // remove if you want team: "$$z3.name", // remove if you want
emps: {$filter: {input: "$$z3.employees",
as: "z4",
cond: {$gt: [ "$$z4.age", 50] }
}}
}
}}
}}
}}
}}
]);
ages = [];
c.forEach(function(biz) {
biz['XX'].forEach(function(locs) {
locs.forEach(function(depts) {
depts.forEach(function(teams) {
teams['emps'].forEach(function(emp) {
ages.push(emp['age']);
});
});
});
});
});
print( ages.sort(function(a, b){return b-a}) );
99,98,97,96,95,94,92,92,84,81,78,77,76,72,71,67,66,65,65,64,63,62,62,61,59,59,57,57,57,56,55,54,52,51
На MacBook Pro с MongoDB 4.0 мы видим следующую коллекцию:
Collection Count AvgSize Unz Xz +Idx TotIdx Idx/doc
-------------------- ------- -------- -G--M------ --- ---- ---M------ -------
foo 10 2238682 22386820 4.0 0 16384 0
Учитывая случайный возраст от 0 до 100, неудивительно, что у каждого места / отдела / команды возраст> = 50 и что общее количество возвращаемых байтов составляет примерно половину. Обратите внимание, однако, что общее время для настройки агрегирования - не возврата всех байтов - составляет ~ 700 миллисекунд.
697 millis to agg; 0.697
found 10
tot bytes 11536558
Яна Дуггар открыто говорила о своих поисках любви. Вот все, что она сказала на эту тему и о своем пятилетнем окне для замужества.
Звезда «Чужестранки» Сэм Хьюэн недавно рассказал, что он возьмет со съемочной площадки, чтобы вспомнить Джейми Фрейзера, роль, которая сделала его звездой.
«She Loves You» была написана за час, записана за день и стала песней The Beatles с одним из лучших исполнений в их карьере.
У Долли Партон и ее бабушки Бесси были особые отношения. Бабушка Партон была очень больна, но это не мешало Долли разыгрывать ее.
Вы можете подумать, что дуб или гикори — прочные породы дерева, но когда речь идет о самой твердой древесине в мире, они даже близко не стоят.
Океан полон красоты, но он также скрывает одних из самых страшных морских существ на планете. Многие из этих животных скрываются глубоко под поверхностью океана, в тёмном, полном давления мире морских глубин.
Если вы сражаетесь с враждебными мобами или готовитесь к PvP-боям, знание лучших чар для мечей в Minecraft может дать вам серьёзное преимущество. Зачарование мечей позволяет наносить больше урона, увеличивать количество выпадающих мобов и продлевать срок службы меча.
Когда говорят о социалистических странах, часто представляют себе полный государственный контроль и отсутствие частной собственности. Но на практике социалистические экономики сильно различаются.
В «Детях» появится громкая камео и несколько разрушительных новостей
Утверждается, что этот RAV4 находится в отличном состоянии и готов к игре в музыкальные стулья.
На кадрах, снятых с дрона, видно, как пожарные изо всех сил пытаются потушить пламя.
«Глаза Ваканды» напрямую связаны с MCU, а также обновления о «Людях Икс '97», «Что, если...», «Сорвиголова» и многом другом.
Ава Гарднер была замужем за Микки Руни и Фрэнком Синтрой, и встречалась с несколькими другими голливудскими звездами. Вот взгляд назад на историю знакомств Авы Гарднер.
Джон Клиз женился на Дженнифер Уэйд в 2012 году. Вот все, что нужно знать о жене Джона Клиза, Дженнифер Уэйд.
Олимпийская чемпионка Эллисон Феликс вышла замуж за своего мужа Кеннета Фергюсона в 2018 году. Вот все, что нужно знать о муже Эллисон Феликс, Кеннете Фергюсоне.
Мена Сувари замужем за своим мужем Майклом Хоупом с 2018 года. Вот все, что нужно знать о муже Мены Сувари.
Это поражает меня Внезапно, как это часто бывает, Это снова и снова на полпути <Нет, не то, что в Тихом океане, ты темно-бордовый, то, что на карнавале> Каждый громкий заголовок…..
В 2022 году, с выпуском GPT-3, навыки письма, кажется, стали менее важными. С помощью ИИ люди с плохим письмом также могут генерировать качественный персонал.
В современном быстро меняющемся и конкурентном мире карьера играет важную роль в личностном росте, финансовой стабильности и общей удовлетворенности жизнью. Однако многие люди оказываются в безжалостном цикле застоя и неудовлетворенности, постепенно угасая в своей профессиональной жизни.
На прошлой неделе я заметил пресс-релиз, разосланный через PressGazette (новостной веб-сайт британских СМИ). В статье сообщалось, что Acast, скандинавская компания по размещению и рекламе подкастов, возглавит консорциум «вероятно, самых влиятельных» издателей подкастинга.