ProgrammationDéveloppeur Frontend

Expliquez comment fonctionne le type de l'opérateur guard typeof en TypeScript, comment et pourquoi il est utilisé, et quelles sont ses limitations ?

Réussissez les entretiens avec l'assistant IA Hintsage

Réponse.

Historique de la question

En JavaScript, l'opérateur typeof est utilisé pour vérifier le type des valeurs primitives à l'exécution. TypeScript étend ce mécanisme et en fait une partie du système de restriction de types (type narrowing) à travers des protections de types (type guards). TypeScript utilise le résultat de l'opérateur typeof pour affiner le type d'une variable à l'intérieur d'un bloc de code, ce qui permet de décrire plus précisément la logique de la fonction, notamment lors de l'utilisation de types union.

Problème

Dans le JavaScript ordinaire, après avoir vérifié le type d'une valeur avec typeof, aucune garantie de type ne peut être donnée — le programmeur doit se souvenir de ce qui se passe à quel endroit du code. Cependant, dans TypeScript, la tâche est compliquée par la présence de différents types et de types union, et sans un affinement correct des types, il est facile de commettre une erreur, par exemple, en accédant à une méthode inexistante. De plus, l'opérateur a des limitations spécifiques : il ne « voit » que les types primitifs de base, par exemple, pour les tableaux et les objets, il renverra 'object'.

Solution

TypeScript permet de combiner l'opérateur typeof avec une analyse de types personnalisée pour restreindre le type d'une variable à l'intérieur d'un bloc de code. Cela augmente automatiquement la sécurité — le compilateur sait avec quel type le code travaille et suggère les propriétés et méthodes possibles.

Exemple de code :

function printId(id: number | string) { if (typeof id === 'string') { // Dans cette branche id: string console.log(id.toUpperCase()); } else { // Dans cette branche id: number console.log(id.toFixed(2)); } }

Caractéristiques clés :

  • Fonctionne uniquement avec des primitifs : 'string', 'number', 'boolean', 'symbol', 'undefined', 'object', 'function', 'bigint'.
  • Aide TypeScript à restreindre un type union à un primitif spécifique à l'intérieur d'un bloc de code.
  • Ne distingue pas les tableaux et les objets, renvoie toujours 'object' pour eux.

Questions pièges.

L'opérateur typeof peut-il identifier un tableau ?

Non, typeof pour un tableau et un objet renverra la même valeur — 'object'. Pour distinguer les tableaux, il est préférable d'utiliser la méthode Array.isArray().

Exemple de code :

const arr = [1, 2, 3]; console.log(typeof arr); // 'object' console.log(Array.isArray(arr)); // true

Peut-on distinguer null et objet avec typeof ?

Non, typeof null renvoie 'object', c'est une spécificité historique de JavaScript.

Exemple de code :

console.log(typeof null); // 'object'

Peut-on tester une classe utilisateur avec typeof ?

Non, pour les instances de classes, typeof renverra également 'object'. Pour cela, on utilise l'opérateur instanceof ou des fonctions de type guard personnalisées.

Exemple de code :

class User {} const u = new User(); console.log(typeof u); // 'object' console.log(u instanceof User); // true

Erreurs de type et anti-patterns

  • Utiliser typeof pour vérifier des structures de données complexes (par exemple, tableaux, null, objets).
  • Négliger d'utiliser les opérateurs instanceof et Array.isArray() pour un affinement de type plus précis.
  • Vérifier les types uniquement au niveau de l'exécution, en ignorant la vérification statique.

Exemple de la vie

Cas négatif

Un programmeur a écrit une fonction où il voulait vérifier si une valeur est un tableau à l'aide de typeof, et basé sur le résultat, appeler différentes méthodes.

Avantages :

  • Code simple à écrire.
  • Ne nécessite pas de fonctions supplémentaires.

Inconvénients :

  • La fonction échoue lors du passage d'un tableau : le tableau est perçu comme un objet, erreurs à l'exécution.

Cas positif

Utilisation de Array.isArray et combinaison avec un type guard.

Avantages :

  • Typage statique sécurisé.
  • Pas d'erreurs avec les types d'objets versus tableaux.

Inconvénients :

  • Il faut se souvenir des différents outils de type guard.