Table des matières
Node.js est un programme à thread unique*
Méthode synchrone, exécutée dans le thread principal
La méthode asynchrone pbkdf2 ne s'exécute pas dans le thread principal
Requête HTTP
Event Loop
Maison interface Web js tutoriel Comment comprendre que Node.js n'est pas un programme entièrement monothread (une brève analyse)

Comment comprendre que Node.js n'est pas un programme entièrement monothread (une brève analyse)

Feb 08, 2022 pm 06:20 PM
node.js fil unique

Pourquoi disons-nous que Node.js n'est pas complètement monothread ? Comment comprendre ? L’article suivant en discutera avec vous, j’espère qu’il vous sera utile !

Comment comprendre que Node.js n'est pas un programme entièrement monothread (une brève analyse)

Je crois que tout le monde sait que node est un programme monothread qui utilise Event Loop pour obtenir plusieurs simultanéités. Malheureusement, ce n'est pas tout à fait exact.

Alors pourquoi Node.js n'est-il pas un programme entièrement monothread ?

Node.js est un programme à thread unique*

Toutes les boucles Javsacript, V8 et d'événements que nous avons nous-mêmes écrites s'exécutent dans le même thread, qui est le thread principal.

Hé, cela ne signifie-t-il pas que ce nœud est monothread ?

Mais peut-être que vous ne savez pas que ce nœud contient de nombreux modules avec du code C++ derrière eux.

Bien que le nœud n'expose pas les utilisateurs à l'autorisation de contrôler les threads, C++ peut utiliser le multi-threading.

Alors, quand node utilisera-t-il le multi-threading ?

  • Si une méthode de nœud appelle la méthode synchronisation de C++ en arrière-plan, tout s'exécutera dans le thread principal.

  • Si une méthode de nœud appelle la méthode asynchrone de C++ en arrière-plan, parfois elle ne s'exécute pas dans le thread principal.

Talk n'est pas cher, montre-moi le code

Méthode synchrone, exécutée dans le thread principal

Ici crypto Modules associés, beaucoup sont écrits en C++. Le programme suivant est une fonction de calcul de hachage, généralement utilisée pour stocker les mots de passe.

import { pbkdf2Sync } from "crypto";
const startTime = Date.now();
let index = 0;
for (index = 0; index < 3; index++) {
    pbkdf2Sync("secret", "salt", 100000, 64, "sha512");
    const endTime = Date.now();
    console.log(`${index} time, ${endTime - startTime}`);
}
const endTime = Date.now();
console.log(`in the end`);
Copier après la connexion

Temps de sortie,

0 time, 44 
1 time, 90
2 time, 134
in the end
Copier après la connexion

peut être vu que cela prend environ 45 ms à chaque fois et que le code est exécuté séquentiellement sur le thread principal.

Faites attention à qui est le résultat final ? Notez qu'un hachage prend ici environ 45 ms sur mon processeur.

La méthode asynchrone pbkdf2 ne s'exécute pas dans le thread principal

import { cpus } from "os";
import { pbkdf2 } from "crypto";
console.log(cpus().length);
let startTime = console.time("time-main-end");
for (let index = 0; index < 4; index++) {
    startTime = console.time(`time-${index}`);
    pbkdf2("secret", `salt${index}`, 100000, 64, "sha512", (err, derivedKey) => {
        if (err) throw err;
        console.timeEnd(`time-${index}`);
    });
}
console.timeEnd("time-main-end");
Copier après la connexion

Le temps de sortie,

time-main-end: 0.31ms
time-2: 45.646ms
time-0: 46.055ms
time-3: 46.846ms
time-1: 47.159ms
Copier après la connexion

Comme vous pouvez le voir ici, le thread principal se termine plus tôt, mais chaque temps de calcul est de 45 ms. Le processeur calcule le hachage. Le temps est de 45 ms. Le nœud ici utilise définitivement plusieurs threads pour le calcul du hachage.

Si je change le nombre d'appels ici à 10, alors le temps est le suivant. Vous pouvez voir qu'à mesure que le nombre de cœurs de processeur est utilisé, le temps augmente également. Une fois de plus, il est prouvé que le nœud utilise définitivement plusieurs threads pour le calcul du hachage.

time-main-end: 0.451ms
time-1: 44.977ms
time-2: 46.069ms
time-3: 50.033ms
time-0: 51.381ms
time-5: 96.429ms // 注意这里,从第五次时间开始增加了
time-7: 101.61ms
time-4: 113.535ms
time-6: 121.429ms
time-9: 151.035ms
time-8: 152.585ms
Copier après la connexion

Bien qu'il soit prouvé ici que le multi-threading est définitivement activé sur le nœud. Mais il y a un petit problème ? Le processeur de mon ordinateur est AMD R5-5600U, doté de 6 cœurs et 12 threads. Mais pourquoi le temps augmente-t-il à partir de la cinquième fois ? Le nœud n’utilise pas pleinement mon processeur ?

Quelle est la raison ?

Node utilise un pool de threads prédéfini. La taille par défaut de ce pool de threads est 4.

export UV_THREADPOOL_SIZE=6

Regardons un exemple,

Requête HTTP

import { request } from "https";
const options = {
  hostname: "www.baidu.com",
  port: 443,
  path: "/img/PC_7ac6a6d319ba4ae29b38e5e4280e9122.png",
  method: "GET",
};

let startTime = console.time(`main`);

for (let index = 0; index < 15; index++) {
  startTime = console.time(`time-${index}`);
  const req = request(options, (res) => {
    console.log(`statusCode: ${res.statusCode}`);
    console.timeEnd(`time-${index}`);
    res.on("data", (d) => {
      // process.stdout.write(d);
    });
  });

  req.on("error", (error) => {
    console.error(error);
  });

  req.end();
}

console.timeEnd("main");
Copier après la connexion
main: 13.927ms
time-2: 83.247ms
time-4: 89.641ms
time-3: 91.497ms
time-12: 91.661ms
time-5: 94.677ms
.....
time-8: 134.026ms
time-1: 143.906ms
time-13: 140.914ms
time-10: 144.088ms
Copier après la connexion

Le programme principal ici est Cela s'est également terminé plus tôt. Ici, j'ai lancé la requête http pour télécharger des images 15 fois. Le temps nécessaire n'a pas augmenté de façon exponentielle et ne semblait pas être limité par le pool de threads/le processeur.

Pourquoi ? ? Node utilise-t-il un pool de threads ?

Si la méthode C++ asynchrone derrière Node, elle essaiera d'abord de voir s'il existe un support asynchrone du noyau. Par exemple, veuillez utiliser epoll (Linux) pour le réseau ici. Si le noyau ne fournit pas de méthode asynchrone, Node. utilisera son propre pool de threads. .

Ainsi, bien que la requête http soit asynchrone, elle est implémentée par le noyau lorsque le noyau est terminé, C++ en sera informé et C++ notifiera au thread principal de gérer le rappel.

Alors, quelles méthodes asynchrones dans Node utilisent le pool de threads ? Lesquels ne le feront pas ?

  • Native Kernal Async

    • Client serveur TCP/UDP
    • Unix Domain Sockets (IPC)
    • pipes
    • dns.resolveXXX
    • tty input (stdin etc)
    • Signaux Unix
    • Processus enfant
  • Thread pool

    • fs.*
    • dns.lookup
    • pipe (edge ​​​​case)

C'est également le point d'entrée pour la plupart des optimisations de nœuds.

Mais comment ceux-ci se combinent-ils avec la boucle d'événement la plus importante ?

Event Loop

Je pense que tout le monde connaît très bien Event Loop. La boucle d'événements est comme un distributeur.

  • Si elle rencontre un programme javascript ordinaire ou un rappel, elle est transmise à V8 pour traitement.

  • Si vous rencontrez une méthode synchronisée écrite en C++, remettez-la en C++ et exécutez-la sur le thread principal.

  • Si vous rencontrez une méthode asynchrone, le verso est écrit en C++. S'il existe un support asynchrone du noyau, transmettez-le du thread principal au noyau pour traitement.

  • Si elle est asynchronele dos de la méthode est écrit en C++ S'il n'y a pas de support asynchrone par le noyau, elle est transmise du thread principal au pool de threads.

  • Le pool de threads et le noyau renverront les résultats à la boucle d'événements. Si un rappel javascript est enregistré, il sera transmis à la V8 pour traitement.

Ensuite, le cycle continue jusqu'à ce qu'il n'y ait plus rien à traiter.

Donc, Node n'est pas exactement un programme monothread.

Pour plus de connaissances sur les nœuds, veuillez visiter : tutoriel Nodejs !

Ce qui précède est le contenu détaillé de. pour plus d'informations, suivez d'autres articles connexes sur le site Web de PHP en chinois!

Déclaration de ce site Web
Le contenu de cet article est volontairement contribué par les internautes et les droits d'auteur appartiennent à l'auteur original. Ce site n'assume aucune responsabilité légale correspondante. Si vous trouvez un contenu suspecté de plagiat ou de contrefaçon, veuillez contacter admin@php.cn

Outils d'IA chauds

Undresser.AI Undress

Undresser.AI Undress

Application basée sur l'IA pour créer des photos de nu réalistes

AI Clothes Remover

AI Clothes Remover

Outil d'IA en ligne pour supprimer les vêtements des photos.

Undress AI Tool

Undress AI Tool

Images de déshabillage gratuites

Clothoff.io

Clothoff.io

Dissolvant de vêtements AI

Video Face Swap

Video Face Swap

Échangez les visages dans n'importe quelle vidéo sans effort grâce à notre outil d'échange de visage AI entièrement gratuit !

Outils chauds

Bloc-notes++7.3.1

Bloc-notes++7.3.1

Éditeur de code facile à utiliser et gratuit

SublimeText3 version chinoise

SublimeText3 version chinoise

Version chinoise, très simple à utiliser

Envoyer Studio 13.0.1

Envoyer Studio 13.0.1

Puissant environnement de développement intégré PHP

Dreamweaver CS6

Dreamweaver CS6

Outils de développement Web visuel

SublimeText3 version Mac

SublimeText3 version Mac

Logiciel d'édition de code au niveau de Dieu (SublimeText3)

Explication graphique détaillée de la mémoire et du GC du moteur Node V8 Explication graphique détaillée de la mémoire et du GC du moteur Node V8 Mar 29, 2023 pm 06:02 PM

Cet article vous donnera une compréhension approfondie de la mémoire et du garbage collector (GC) du moteur NodeJS V8. J'espère qu'il vous sera utile !

Un article pour parler du contrôle de la mémoire dans Node Un article pour parler du contrôle de la mémoire dans Node Apr 26, 2023 pm 05:37 PM

Le service Node construit sur une base non bloquante et piloté par les événements présente l'avantage d'une faible consommation de mémoire et est très adapté à la gestion de requêtes réseau massives. Dans le contexte de demandes massives, les questions liées au « contrôle de la mémoire » doivent être prises en compte. 1. Le mécanisme de récupération de place du V8 et les limitations de mémoire Js sont contrôlés par la machine de récupération de place

Parlons de la façon de choisir la meilleure image Docker Node.js ? Parlons de la façon de choisir la meilleure image Docker Node.js ? Dec 13, 2022 pm 08:00 PM

Le choix d'une image Docker pour Node peut sembler trivial, mais la taille et les vulnérabilités potentielles de l'image peuvent avoir un impact significatif sur votre processus CI/CD et votre sécurité. Alors, comment choisir la meilleure image Docker Node.js ?

Parlons en profondeur du module File dans Node Parlons en profondeur du module File dans Node Apr 24, 2023 pm 05:49 PM

Le module de fichiers est une encapsulation des opérations de fichiers sous-jacentes, telles que l'ajout de lecture/écriture/ouverture/fermeture/suppression de fichiers, etc. La plus grande caractéristique du module de fichiers est que toutes les méthodes fournissent deux versions de **synchrone** et ** asynchrone**, with Les méthodes avec le suffixe sync sont toutes des méthodes de synchronisation, et celles qui n'en ont pas sont toutes des méthodes hétérogènes.

Node.js 19 est officiellement sorti, parlons de ses 6 fonctionnalités majeures ! Node.js 19 est officiellement sorti, parlons de ses 6 fonctionnalités majeures ! Nov 16, 2022 pm 08:34 PM

Node 19 est officiellement publié. Cet article vous donnera une explication détaillée des 6 fonctionnalités majeures de Node.js 19. J'espère qu'il vous sera utile !

Parlons du mécanisme GC (garbage collection) dans Node.js Parlons du mécanisme GC (garbage collection) dans Node.js Nov 29, 2022 pm 08:44 PM

Comment Node.js fait-il le GC (garbage collection) ? L’article suivant vous guidera à travers cela.

Parlons de la boucle d'événements dans Node Parlons de la boucle d'événements dans Node Apr 11, 2023 pm 07:08 PM

La boucle d'événements est un élément fondamental de Node.js et permet une programmation asynchrone en garantissant que le thread principal n'est pas bloqué. Comprendre la boucle d'événements est crucial pour créer des applications efficaces. L'article suivant vous donnera une compréhension approfondie de la boucle d'événements dans Node. J'espère qu'il vous sera utile !

Que dois-je faire si le nœud ne peut pas utiliser la commande npm ? Que dois-je faire si le nœud ne peut pas utiliser la commande npm ? Feb 08, 2023 am 10:09 AM

La raison pour laquelle le nœud ne peut pas utiliser la commande npm est que les variables d'environnement ne sont pas configurées correctement. La solution est la suivante : 1. Ouvrez "Propriétés système" ; 2. Recherchez "Variables d'environnement" -> "Variables système", puis modifiez l'environnement. variables ; 3. Recherchez l'emplacement du dossier nodejs ; 4. Cliquez sur "OK".

See all articles