2015-04-16 1 views
3

я в настоящее время с помощью функции MongoDB курсора ToArray() для преобразования результатов базы данных в массив:Альтернативы MongoDB cursor.toArray() в node.js

run = true; 
count = 0; 
var start = process.hrtime(); 
db.collection.find({}, {limit: 2000}).toArray(function(err, docs){ 
    var diff = process.hrtime(start); 
    run = false; 
    socket.emit('result', { 
    result: docs, 
    time: diff[0] * 1000 + diff[1]/1000000, 
    ticks: count 
    }); 
    if(err) console.log(err); 
}); 

Эта операция занимает около 7 мс на моем компьютере. Если я удалю функцию .toArray(), то операция займет около 0,15 мс. Конечно, это не сработает, потому что мне нужно переслать данные, но мне интересно, что делает функция, так как она занимает так много времени? Каждый документ в базе данных состоит из четырех чисел.

В конце концов, я надеюсь запустить это на гораздо меньшем процессоре, таком как Raspberry Pi, и здесь операция, когда он извлекает 500 документов из базы данных и преобразует их в массив, занимает около 230 мс. Мне это очень нравится. Или я просто ожидаю слишком многого?

Есть ли альтернативные способы получения данных из базы данных без использования toArray()?

Еще одна вещь, которую я заметил, заключается в том, что приложение Node заметно замедляется при получении результатов базы данных. Я создал простую функцию интервала, который должен увеличить значение счетчика каждые 1 мс:

setInterval(function(){ 
    if(run) count++; 
}, 1); 

Я бы тогда ожидать, что значение счетчика будет почти таким же, как время, но в течение времени 16 мс на моем компьютере значение счета было 3 или 4. На малине Pi значение счета никогда не увеличивалось. Что такое использование процессора? Монитор сказал мне, что мой компьютер использует 27% процессор, а Raspberry Pi использует 92% процессор и 11% RAM, когда его просят повторно выполнять запрос базы данных.

Я знаю, что было много вопросов. Любую помощь или объяснения очень ценят. Я все еще новичок в Node и MongoDB.

ответ

6

db.collection.find() возвращает курсор, а не результаты, и открытие курсора довольно быстро.

После того, как вы начнете чтение курсора (с помощью .toArray() или путем обхода его с помощью .each() или .next()), фактические документы передаются из базы данных для вашего клиента. Эта операция занимает большую часть времени.

Я сомневаюсь, что использование .each()/.next() (вместо .toArray(), которое под капотом использует один из этих двух) значительно улучшит производительность, но вы всегда можете попробовать (кто знает). Поскольку .toArray() будет читать все в памяти, это может быть полезно, хотя это не похоже на то, что ваш набор данных такой большой.

Я действительно считаю, что MongoDB на малине Pi (esp a Model 1) не будет работать хорошо. Если вы слишком сильно не зависите от особенностей запросов MongoDB, вам следует рассмотреть возможность использования альтернативного хранилища данных. Возможно, даже хранилище в памяти (500 документов, умноженное на 4 числа, не похоже на то, что требуется большая ОЗУ).

+0

Спасибо за ваш быстрый ответ. Мне было очень ясно. Я попытался использовать .each(), но это было на самом деле немного медленнее. Ожидается ли, что приложение Node замедляется, когда данные передаются из базы данных? – KMK

+1

@KMK для небольших размеров документа, даже массивы данных большого объема не должны существенно замедлять работу вашего приложения. По моему опыту, большинство замедление произойдет в синтаксическом анализе BSON (что является синхронной операцией). С невысокой платформой это может стать узким местом. – robertklep