Цикл событий Node js: Безопасный цикл и разница Python - PullRequest
0 голосов
/ 28 июня 2018

Работая над проектом для моего приложения Express, я написал рекурсивный метод, который извлекает данные из некоторого вложенного объекта JSON. Грубо говоря, метод выглядит так:

# The depth of the fields is up to 3-4 levels, so no stack overflow danger.

  _recursiveFindFieldName: function(someJSONStruct, nestedFieldList) {

if (nestedFieldList.length === 0) {
  return someJSONStruct;
}

fields = someJSONStruct['fields'];
for (var i=0; i < fields.length; i++) {
  subField = fields[i];
  if (subField['fieldName'] === nestedFieldList[0]) {
    return this._recursiveFindFieldName(subField, nestedFieldList.splice(1));
  }
}
return null;

Теперь я называю этот метод одним из моих обратных вызовов, утверждая data = _recursiveFindFieldName(someJSON, fieldPathList);. Однако один из друзей, который просматривал мой код, отметил, что этот метод, будучи рекурсивным и повторяющимся по потенциально большой структуре JSON, может блокировать цикл обработки событий и препятствовать тому, чтобы Express обслуживал другие запросы.

Хотя это имеет смысл, я не уверен, стоит ли мне когда-либо беспокоиться о задачах, синхронных с ЦП (в отличие от ввода-вывода). По крайней мере, интуитивно это выглядит не очень просто.

Я пытался использовать этот источник , чтобы лучше понять, как работает цикл обработки событий, и был очень удивлен, увидев, что следующий код приводит к сбою моего локального узла REPL.

for (var i = 0; i < 10000000; i++) {
  console.log('hi:', i);
}

Я не уверен, почему это происходит, в отличие от Python (который также работает в однопоточном режиме и легко выполняет задачу печати), и относится ли это к моему случаю, который не связан с вводом-выводом операции.

1 Ответ

0 голосов
/ 28 июня 2018

Во-первых, измеряет производительность вашего существующего кода: вероятно, это не узкое место с самого начала.

Если предполагаемое узкое место действительно допустимо, вы можете создать асинхронное дополнение Node C ++ , которое может обрабатывать весь большой двоичный объект JSON с помощью uv_queue_work() в отдельном потоке вне цикла событий JavaScript. и затем верните весь результат обратно в JavaScript, используя обещание.

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

Что касается вашего console.log () вопроса: в Node иногда stdio является синхронным, а иногда нет: см. это обсуждение . Если вы работаете в системе POSIX, она работает синхронно, и вы пишете достаточно данных, чтобы заполнить канал и заблокировать цикл событий, который запутывается там до следующего события. Я не уверен в деталях того, почему это вызывает сбой, но, надеюсь, это начало ответа на ваш вопрос.

...