TypeScriptのtypeof演算子

profile image

typeof演算子のJavaScriptとTypeScriptコンテキストでの違いと様々な活用方法

この記事は Jetbrains's Coding Agent Junie junie logoによって翻訳されました。誤訳があれば教えてください!

TypeScriptを使用していると、typeof演算子(JavaScriptにも存在する)によく出会います。TypeScriptでは、typeofは2つのコンテキストで使用されます。

  1. JavaScriptのランタイムtypeof演算子
  2. TypeScriptのタイプ演算子としてのtypeof

1. JavaScriptのランタイムtypeof演算子

typeofはオペランドのデータ型を表す文字列を返します。

jsx
let value = "hello";
console.log(typeof value); // "string"

let number = 32;
console.log(typeof number); // "number"

let func = () => {};
console.log(typeof func); // "function"

返される値は、JavaScriptの基本データ型(boolean, number, bigint, string, symbol, null, undefined)とfunction, objectです。

2. TypeScriptのタイプ演算子typeof

TypeScriptでは、typeoftypeコンテキストでも使用できます。この場合、役割が変わります。

tsx
const user = {
  name: "John",
  age: 30,
  isAdmin: true
};

const v_user = typeof user; // object
type User = typeof user;
// 結果:
// type User = {
//   name: string;
//   age: number;
//   isAdmin: boolean;
// }

上記の例のv_userconstキーワードで宣言された変数で使用されています。したがって、値が割り当てられる必要があるため、userのランタイム型を指す'object'を返します。しかし、typeキーワードの後に使用されるtypeofはTypeScriptの型を返します。

typeofは値から型を抽出する場合にのみ使用してください。すでに型であるものに使用すると、エラーが発生します。

tsx
// 誤った使用法
type MyString = string;
type Wrong = typeof MyString; // エラー!

// 正しい使用法
const myString = "hello";
type Correct = typeof myString; // string

typeofの活用

1. 配列からユニオン型を抽出

tsx
const colors = ["red", "green", "blue"] as const;
type Colors = typeof colors[number];
// type Colors = "red" | "green" | "blue"

2. オブジェクト型の抽出

tsx
// without as const
const config = {
  endpoint: "api.example.com",
  port: 3000
};
type Config = typeof config;
// type Config = {
//   endpoint: string;
//   port: number;
// }

// with as const
const config = {
  endpoint: "api.example.com",
  port: 3000
} as const;
type Config = typeof config;
// type Config = {
//   readonly endpoint: "api.example.com";
//   readonly port: 3000;
// }

as constと一緒に使用すると、readonlyが付いて抽出されます。

3. 関数型の抽出

ユーティリティ型ReturnTypeParametersを活用して、関数のパラメータと戻り値の型を抽出できます。

tsx
function createUser(name: string, age: number) {
  return { id: Date.now(), name, age };
}

type User = ReturnType<typeof createUser>;
// type User = {
//   id: number;
//   name: string;
//   age: number;
// }

type Param = Parameters<typeof createUser>
// type Param = {
//   name: string;
//   age: number;
// }

🔎 参照

❤️ 0
🔥 0
😎 0
⭐️ 0
🆒 0