TypeScriptのOptional Parametersとnull/undefinedの使い方を徹底解説

TypeScriptは、JavaScriptに型システムを追加した言語であり、コードの予測可能性と堅牢性を向上させることができます。その中でも、Optional Parameters(オプショナルパラメーター)やnull/undefinedの扱いは非常に重要なテーマです。オプショナルパラメーターを使用することで、関数呼び出し時に特定の引数が省略可能となり、コードの柔軟性が高まります。また、nullとundefinedはどちらも値が存在しない状態を表しますが、それぞれ異なる意味を持ち、状況に応じて使い分ける必要があります。本記事では、TypeScriptにおけるこれらの機能の使い方を詳しく解説し、具体的なコード例や実践的な方法を通して、その効果的な利用方法を紹介します。

目次
  1. オプショナルパラメーターとは?
  2. オプショナルパラメーターの定義方法
  3. nullとundefinedの違い
    1. undefinedとは?
    2. nullとは?
    3. nullとundefinedの使い分け
  4. Optional Parametersとundefinedの関係
    1. undefinedが使われる理由
    2. オプショナルパラメーターとundefinedの扱い方
  5. nullを使うべき場面とその理由
    1. 意図的に値がないことを示す場面
    2. nullを使う理由
    3. nullの適用例
  6. nullチェックの実装方法
    1. 基本的なnullチェック
    2. 厳密等価演算子(===)の使用
    3. 早期リターンを使ったnullチェック
    4. オプショナルチェイニングを使った安全なアクセス
    5. Nullish Coalescingを使ったデフォルト値の設定
  7. Optional Chainingの使い方
    1. Optional Chainingの基本的な使い方
    2. ネストされたオブジェクトのアクセス
    3. 関数呼び出しにおけるOptional Chaining
    4. 配列やプロパティへの安全なアクセス
    5. Optional ChainingとNullish Coalescingの組み合わせ
  8. nullish coalescing演算子の利用方法
    1. 基本的な利用方法
    2. nullish coalescingと論理OR演算子(||)との違い
    3. オプショナルパラメーターとnullish coalescing
    4. ネストされたプロパティとnullish coalescing
    5. 実践例: フォーム入力のデフォルト値設定
  9. nullとundefinedのトラブルシューティング
    1. 1. 未定義の値を使用するエラー
    2. 2. 関数が`undefined`の状態で呼び出されるエラー
    3. 3. nullやundefinedによる条件分岐の不具合
    4. 4. null/undefinedの手動チェック忘れによるエラー
    5. 5. デフォルト値の設定忘れによるエラー
  10. 演習問題
    1. 問題1: オプショナルパラメーターの利用
    2. 問題2: Optional Chainingを使用したネストされたオブジェクトのアクセス
    3. 問題3: Nullish Coalescingを使用したデフォルト値の設定
    4. 問題4: nullチェックを使った安全なデータ処理
  11. まとめ

オプショナルパラメーターとは?


オプショナルパラメーターとは、関数に渡す引数が必須ではなく、呼び出し側で指定しなくても問題ないパラメーターのことを指します。JavaScriptでは、関数の引数にデフォルト値を設定することで、オプショナルパラメーターのような動作を実現できますが、TypeScriptではその機能が型として正式にサポートされています。

オプショナルパラメーターを使用することで、関数を呼び出す際に柔軟な引数の指定が可能となり、使い勝手が向上します。関数の定義内で「?」を付けることで、その引数がオプションであることを示します。この機能により、必要な引数と省略可能な引数を区別しやすくなり、コードの可読性やメンテナンス性が向上します。

オプショナルパラメーターの定義方法


TypeScriptでオプショナルパラメーターを定義する方法は非常にシンプルです。関数の引数に「?」を付けることで、その引数がオプションであることを示します。オプショナルパラメーターは、必須の引数の後に定義され、関数を呼び出す際に引数が指定されない場合、自動的にundefinedが代入されます。

以下は、オプショナルパラメーターを使用した関数の例です。

function greet(name: string, age?: number): string {
  if (age !== undefined) {
    return `Hello, my name is ${name} and I am ${age} years old.`;
  } else {
    return `Hello, my name is ${name}.`;
  }
}

console.log(greet("Alice")); // "Hello, my name is Alice."
console.log(greet("Bob", 30)); // "Hello, my name is Bob and I am 30 years old."

この例では、ageはオプショナルパラメーターとして定義されています。greet関数を呼び出す際に、ageを指定してもしなくても機能します。未指定の場合にはundefinedとして扱われ、コード内でその処理を分けています。

オプショナルパラメーターを使用する際のポイントは以下の通りです:

  • 必須パラメーターはオプショナルパラメーターより前に配置する必要があります。
  • オプショナルパラメーターは、指定されなかった場合、undefinedとして扱われます。
  • 関数内でパラメーターが未定義の場合にどう対処するかをしっかりと検討することが重要です。

nullとundefinedの違い


TypeScriptでは、nullundefinedの両方が「値がない」ことを表しますが、これらには明確な違いがあります。それぞれの特徴や使いどころを理解しておくことで、より安全で直感的なコードを書くことができます。

undefinedとは?


undefinedは、変数が宣言されたものの、値が割り当てられていない状態を表します。JavaScriptでは、関数が明示的な値を返さない場合や、オプショナルパラメーターが指定されなかった場合、自動的にundefinedが返されます。

let x: number | undefined;
console.log(x); // undefined

この例では、xは宣言されましたが、値が代入されていないためundefinedとなっています。

nullとは?


nullは、開発者が意図的に「値が存在しない」ことを示すために使用する特殊な値です。undefinedが「何も設定されていない」状態を表すのに対して、nullは「明示的に空である」ことを表現するために使います。

let y: number | null = null;
console.log(y); // null

この例では、ynullが代入されており、値が存在しないことを明示的に示しています。

nullとundefinedの使い分け


undefinedはシステムによって自動的に設定されることが多いのに対して、nullは開発者が明示的に設定します。たとえば、APIのレスポンスでデータが存在しない場合、nullを返すことが一般的です。一方で、変数やパラメーターが未定義の場合は、undefinedが使用されます。

  • undefined: 値がまだ割り当てられていない状態を自動的に示す。
  • null: 値が存在しないことを明示的に示す。

この2つを適切に使い分けることで、コードの意図を明確に伝え、バグを防ぐことができます。

Optional Parametersとundefinedの関係


TypeScriptにおいて、オプショナルパラメーター(Optional Parameters)は、関数が呼び出された際に引数が渡されなかった場合、自動的にundefinedが代入される仕組みになっています。これは、関数の柔軟性を高め、引数が省略されることを想定した設計が容易になるためです。

undefinedが使われる理由


オプショナルパラメーターに対して値が渡されない場合にundefinedが使われる理由は、TypeScriptの型システムがundefinedを「値が存在しない状態」として扱うためです。これにより、関数内部で「その値が定義されているかどうか」を簡単にチェックでき、未定義の値に対して適切な処理を行うことが可能です。

以下はオプショナルパラメーターが未指定の場合にundefinedが使われる例です。

function displayInfo(name: string, age?: number) {
  if (age === undefined) {
    console.log(`${name}の年齢は指定されていません。`);
  } else {
    console.log(`${name}の年齢は${age}歳です。`);
  }
}

displayInfo("Alice"); // "Aliceの年齢は指定されていません。"
displayInfo("Bob", 25); // "Bobの年齢は25歳です。"

この例では、ageというオプショナルパラメーターが指定されていない場合、undefinedとして扱われ、関数内部で条件分岐により適切なメッセージが表示されます。TypeScriptでは、未定義の値を直接扱うため、undefinedを用いることでコードの予測可能性が向上します。

オプショナルパラメーターとundefinedの扱い方


オプショナルパラメーターを使用する際、undefinedを直接チェックすることで、未定義の状態に対して適切な動作を実装できます。また、デフォルト値を指定することで、undefinedのケースに対応することも可能です。

function greet(name: string, age: number = 30) {
  console.log(`${name} is ${age} years old.`);
}

greet("Charlie"); // "Charlie is 30 years old."

この例では、ageが指定されなかった場合、デフォルトで30が使用されます。このように、オプショナルパラメーターとundefinedをうまく活用することで、関数の使い勝手と安全性を向上させることができます。

nullを使うべき場面とその理由


nullは、開発者が明示的に「値が存在しない」ことを示すために使用されます。undefinedが「システムやプログラムによって自動的に未定義にされた状態」であるのに対し、nullは「意図的に設定された値がない状態」を意味します。この違いを踏まえ、nullを適切に使う場面を理解することが重要です。

意図的に値がないことを示す場面


nullを使用するべき典型的な場面は、意図的に「データが存在しない」ことを示したい場合です。例えば、データベースクエリの結果がない場合や、オブジェクトのプロパティが意図的に初期化されていないことを表す際にnullを使います。これは、将来的にデータが存在する可能性があるが、現時点では存在しないことを明示するのに役立ちます。

let userData: { name: string; age: number | null } = { name: "Alice", age: null };
console.log(userData.age); // null

この例では、agenullとして設定されています。これは、ユーザーの年齢データが現時点では存在しないことを意味していますが、将来的に値が設定される可能性があることを表現しています。

nullを使う理由


nullを使う理由はいくつかありますが、主な理由は以下の通りです。

  • 意図的な空データの表現: nullを使うことで、値が存在しないことを意図的に示すことができ、システムや他の開発者にその意味を明確に伝えます。
  • 予期的なデータの欠如: データが存在しないことが正常な状態である場合、nullを使用することで、その状態が意図的であることを表現できます。たとえば、APIレスポンスでオプションのフィールドが存在しない場合にnullを返すことは一般的です。
  • エラーハンドリングの明確化: undefinedは多くの場合、予期しないエラーの原因となる可能性がありますが、nullはその状態が意図されたものであることを明示するため、エラーハンドリングが容易になります。

nullの適用例


例えば、Webフォームの入力フィールドで、ユーザーが任意の項目を空欄にした場合、その値をnullとして扱うことが適切です。これは、未入力が許容される状態であることを示すためです。

function submitForm(name: string, age: number | null) {
  if (age === null) {
    console.log(`${name}の年齢は未入力です。`);
  } else {
    console.log(`${name}は${age}歳です。`);
  }
}

submitForm("Bob", null); // "Bobの年齢は未入力です。"

このように、nullは「値が意図的に存在しない」という状況を正しく伝える手段として使われ、特定の状況においては非常に有効です。undefinedとは異なる明確な意味を持つため、適切な場面で使うことが推奨されます。

nullチェックの実装方法


TypeScriptでは、nullundefinedが原因で予期しないエラーが発生することを避けるために、これらの値を正しくチェックすることが非常に重要です。特に、値が確実に存在するかどうかを確認せずに操作すると、ランタイムエラーが発生するリスクがあります。ここでは、nullのチェック方法とその実装例について解説します。

基本的なnullチェック


nullのチェックは、通常、条件分岐を使って実装します。最も一般的な方法は、if文を使用して値がnullであるかどうかを確認することです。

function printAge(age: number | null) {
  if (age === null) {
    console.log("年齢が設定されていません。");
  } else {
    console.log(`年齢は${age}歳です。`);
  }
}

printAge(null); // "年齢が設定されていません。"
printAge(25);   // "年齢は25歳です。"

このように、agenullかどうかを明示的に確認し、適切に処理を行います。この方法により、null値が関数やメソッドに渡されたときに適切な対応が可能です。

厳密等価演算子(===)の使用


nullundefinedを区別するために、厳密等価演算子===を使用することが推奨されます。==(緩い等価演算子)では、nullundefinedが等価と見なされるため、予期しない結果を引き起こす可能性があります。

let value: number | null = null;

if (value === null) {
  console.log("値はnullです。");
}

この方法では、nullのみが対象となり、undefinedとは区別されます。

早期リターンを使ったnullチェック


複数の処理を行う関数の場合、早期にnullをチェックして、値がnullならその時点で処理を中断する方法があります。これにより、コードの可読性が向上し、エラーを未然に防ぐことができます。

function processUserData(userData: { name: string; age: number | null }) {
  if (userData.age === null) {
    console.log("ユーザーの年齢が不明です。");
    return;
  }

  // 年齢が存在する場合の処理
  console.log(`${userData.name}は${userData.age}歳です。`);
}

この方法では、nullのケースを早期に処理し、それ以降の処理に移らないようにしています。

オプショナルチェイニングを使った安全なアクセス


TypeScriptでは、オプショナルチェイニング(?.)を使用することで、nullまたはundefinedであってもエラーを発生させずにプロパティにアクセスすることができます。これにより、コードがより安全で簡潔になります。

let person: { name: string; age?: number | null } = { name: "Alice" };

console.log(person.age?.toString() ?? "年齢が設定されていません。");
// "年齢が設定されていません。" と表示されます。

この例では、person.agenullまたはundefinedである場合、チェイニングが自動的に処理され、エラーを回避します。

Nullish Coalescingを使ったデフォルト値の設定


nullundefinedの値に対してデフォルト値を設定するには、nullish coalescing演算子(??)を使うことができます。この演算子は、値がnullまたはundefinedの場合にだけデフォルト値を使用します。

function getUserAge(age: number | null) {
  return age ?? 18; // ageがnullまたはundefinedなら18を返す
}

console.log(getUserAge(null)); // 18
console.log(getUserAge(25));   // 25

この演算子を使うことで、nullundefinedに対して安全にデフォルト値を提供し、コードを簡潔に保つことができます。

以上のように、TypeScriptではnullを扱う際にさまざまなチェック方法があります。それぞれの方法を理解し、適切に使い分けることで、予期しないエラーを回避し、コードの安全性を向上させることができます。

Optional Chainingの使い方


TypeScriptにおけるOptional Chaining(オプショナルチェイニング)は、オブジェクトやプロパティがnullまたはundefinedである場合に、エラーを発生させずに安全にアクセスするための強力な構文です。この機能を使うことで、深くネストされたオブジェクトに対しても、値の存在を確認しながらコードをシンプルに記述することが可能です。

Optional Chainingの基本的な使い方


Optional Chainingは、プロパティアクセスや関数呼び出しの際に?.を使うことで動作します。もしそのプロパティがnullundefinedであれば、通常のプロパティアクセスとは異なり、エラーが発生せず、undefinedが返されます。

以下の例を見てみましょう。

let user: { name?: string; age?: number } = { name: "Alice" };

console.log(user.name?.toUpperCase()); // "ALICE"
console.log(user.age?.toString()); // undefined

この例では、user.nameが存在するため、toUpperCase()が呼び出されますが、user.ageは未定義なので、undefinedが返され、エラーは発生しません。

ネストされたオブジェクトのアクセス


Optional Chainingは、オブジェクトが深くネストされている場合に特に役立ちます。通常、ネストされたオブジェクトを安全にアクセスするには複数のif文を使って存在確認を行いますが、Optional Chainingを使うことで、コードを簡潔に保つことができます。

let user: { address?: { city?: string } } = { address: { city: "Tokyo" } };

console.log(user.address?.city); // "Tokyo"
console.log(user.address?.postalCode); // undefined

ここでは、user.addressが存在する場合にのみcityプロパティにアクセスしています。また、postalCodeが存在しないため、undefinedが返されますが、エラーは発生しません。

関数呼び出しにおけるOptional Chaining


Optional Chainingは、関数が存在するかどうかを確認したうえで実行する際にも使用できます。関数がnullまたはundefinedである可能性がある場合、?.()を使って安全に関数を呼び出すことができます。

let person: { greet?: () => void } = { greet: () => console.log("Hello!") };

person.greet?.(); // "Hello!"
person.unknownFunction?.(); // エラーなしで無視される

この例では、greet関数が存在する場合にのみ呼び出されます。unknownFunctionが存在しないため、その関数呼び出しは無視され、エラーが発生しません。

配列やプロパティへの安全なアクセス


配列の要素にOptional Chainingを適用することで、存在しないインデックスにアクセスしてもエラーを回避できます。また、プロパティアクセスでも同様に安全なチェックが行われます。

let users: { name?: string }[] = [{ name: "Alice" }, {}];

console.log(users[0]?.name); // "Alice"
console.log(users[1]?.name); // undefined
console.log(users[2]?.name); // undefined

この例では、配列内のusers[0]は存在するため、nameプロパティにアクセスできますが、users[1]およびusers[2]のいずれもnameが存在しないため、undefinedが返されます。

Optional ChainingとNullish Coalescingの組み合わせ


Optional Chainingは、Nullish Coalescing(??)と組み合わせることで、より強力なエラーハンドリングが可能です。nullundefinedの値に対してデフォルト値を提供する場合、これらを一緒に使うことで、簡潔で安全なコードが書けます。

let user: { name?: string; age?: number } = { name: "Bob" };

let userName = user.name?.toUpperCase() ?? "名前未設定";
console.log(userName); // "BOB"

let userAge = user.age ?? 18;
console.log(userAge); // 18

このように、Optional Chainingで安全にプロパティにアクセスしつつ、nullundefinedの場合には??を使ってデフォルト値を提供することで、柔軟でエラーフリーなコードを実現できます。

Optional Chainingを使うことで、TypeScriptのコードはより安全で簡潔になり、特にnullundefinedが関与するシチュエーションでのエラーを大幅に減らすことができます。

nullish coalescing演算子の利用方法


Nullish Coalescing(ヌリッシュ・コアレッシング)演算子(??)は、TypeScriptにおいてnullまたはundefinedが現れたときに、デフォルト値を指定できる便利な構文です。??は、nullundefinedに対してのみ反応し、それ以外の「偽の値」(例えば、0や空文字""など)には反応しません。これにより、デフォルト値を安全に設定しながら、予期しないデータ損失を防ぐことができます。

基本的な利用方法


Nullish Coalescingは、値がnullまたはundefinedである場合に、指定されたデフォルト値を返す仕組みです。これを利用することで、デフォルト値を手軽に設定でき、nullundefinedが混在するコードでも安心して扱えます。

以下の例では、変数がnullまたはundefinedの場合に、デフォルトの値を返す方法を示しています。

let input: string | null = null;
let output = input ?? "デフォルト値";
console.log(output); // "デフォルト値"

この例では、inputnullなので、??の右側にあるデフォルト値「デフォルト値」が返されます。

nullish coalescingと論理OR演算子(||)との違い


??は、nullundefinedのみを対象にするのに対し、論理OR演算子(||)は、false0""などの「偽の値」全体に反応します。したがって、0や空文字などが有効な値として扱われる場合、??を使用する方が適切です。

以下は、??||の違いを示す例です。

let count = 0;

console.log(count || 10); // 10
console.log(count ?? 10); // 0

count0のとき、論理OR演算子||0を「偽の値」として扱い、右側の10を返します。しかし、??nullundefinedのみを対象とするため、count0の場合でも0をそのまま返します。これにより、意図しないデータの上書きを防ぐことができます。

オプショナルパラメーターとnullish coalescing


Nullish Coalescingは、オプショナルパラメーターにデフォルト値を設定する際にもよく使われます。オプショナルパラメーターがundefinedであった場合、デフォルト値を返すことで、関数の動作が安定します。

function greet(name?: string) {
  let userName = name ?? "ゲスト";
  console.log(`こんにちは、${userName}さん!`);
}

greet(); // "こんにちは、ゲストさん!"
greet("Alice"); // "こんにちは、Aliceさん!"

この例では、nameが指定されなかった場合(つまり、undefinedの場合)、??を使って"ゲスト"というデフォルト値が設定されます。これにより、オプショナルパラメーターを使った関数でもエラーや予期しない動作を避けることができます。

ネストされたプロパティとnullish coalescing


Optional Chainingと組み合わせて、ネストされたオブジェクトのプロパティに対してもnullundefinedを安全に扱うことができます。これにより、深くネストされたプロパティを扱う際も、より安全かつ簡潔にコーディングできます。

let user: { profile?: { name?: string } } = {};

let userName = user.profile?.name ?? "匿名ユーザー";
console.log(userName); // "匿名ユーザー"

この例では、user.profile?.nameが存在しない場合にundefinedが返され、"匿名ユーザー"が代わりに使用されます。Optional Chaining(?.)とNullish Coalescing(??)を組み合わせることで、ネストされたオブジェクトの値を安全にアクセスしながら、デフォルト値を提供できます。

実践例: フォーム入力のデフォルト値設定


フォームの入力データにおいて、ユーザーが特定のフィールドを空のままにして送信した場合、nullish coalescingを使ってデフォルト値を設定できます。

function submitForm(input: { name?: string; age?: number }) {
  let name = input.name ?? "名無し";
  let age = input.age ?? 18;

  console.log(`名前: ${name}, 年齢: ${age}`);
}

submitForm({}); // "名前: 名無し, 年齢: 18"
submitForm({ name: "Alice", age: 25 }); // "名前: Alice, 年齢: 25"

この例では、inputオブジェクトのnameageが指定されなかった場合、nullish coalescingを使ってデフォルト値を提供しています。

Nullish Coalescing演算子を使用することで、nullundefinedに対する柔軟かつ安全なデフォルト値の設定が可能になり、より堅牢なコードを実現することができます。

nullとundefinedのトラブルシューティング


TypeScriptの開発では、nullundefinedに関連するエラーは非常によく発生します。これらの値は、存在しないデータや未定義の変数を意味しますが、それらを適切に扱わないと、実行時エラーや予期しない動作を引き起こす可能性があります。このセクションでは、nullundefinedによる一般的なトラブルとその解決策を紹介します。

1. 未定義の値を使用するエラー


TypeScriptで最も一般的なエラーの1つは、未定義の変数やプロパティにアクセスしようとして発生するエラーです。たとえば、変数がundefinedである場合にプロパティを参照しようとすると、ランタイムエラーが発生します。

let user: { name?: string } = {};
console.log(user.name.toUpperCase()); // エラー: Cannot read property 'toUpperCase' of undefined

この例では、user.nameが未定義のため、toUpperCaseを呼び出すことができずエラーが発生します。

解決策: Optional Chainingの使用


Optional Chaining(?.)を使用することで、nullundefinedのチェックを自動化し、エラーを防止できます。

let user: { name?: string } = {};
console.log(user.name?.toUpperCase()); // undefinedが返され、エラーは発生しない

これにより、nameが未定義の場合はエラーが発生せず、undefinedが返されます。

2. 関数が`undefined`の状態で呼び出されるエラー


TypeScriptでは、関数が定義されていない状態で呼び出そうとするとエラーが発生します。このような状況は、オプショナルな関数プロパティや条件付きのコールバック関数を扱う際によく見られます。

let obj: { greet?: () => void } = {};
obj.greet(); // エラー: Cannot read property 'greet' of undefined

この例では、greetが存在しないため、エラーが発生します。

解決策: Optional Chainingで関数を安全に呼び出す


Optional Chainingを使用して、関数が存在する場合にのみ実行されるようにすることで、エラーを回避できます。

let obj: { greet?: () => void } = {};
obj.greet?.(); // エラーは発生せず、何も実行されない

この方法により、関数が未定義でも安全にスキップされます。

3. nullやundefinedによる条件分岐の不具合


nullundefinedを適切に扱わないと、条件分岐が意図通りに動作しないことがあります。例えば、nullundefinedが偽の値として扱われるため、false0と混同されることがあります。

let value: number | null = 0;
if (!value) {
  console.log("値がありません。"); // 実際には0があるが、"値がありません"と表示される
}

この例では、value0であってもfalseとして評価されてしまいます。

解決策: Nullish Coalescingの使用


nullundefinedのみをチェックするためには、??(Nullish Coalescing演算子)を使うと効果的です。

let value: number | null = 0;
console.log(value ?? "値がありません。"); // 0と表示され、nullやundefinedの場合のみ"値がありません"と表示される

??を使用することで、nullundefinedの場合にのみデフォルト値が使われ、0falseなどの値が適切に扱われます。

4. null/undefinedの手動チェック忘れによるエラー


TypeScriptでは、nullundefinedが含まれる可能性がある変数に対してチェックを行わないと、実行時エラーが発生することがあります。特に、strictNullChecksオプションを無効にしている場合、チェックを忘れたことで意図しないエラーが発生しやすくなります。

let num: number | null = null;
console.log(num.toFixed(2)); // エラー: Cannot read property 'toFixed' of null

この例では、numnullであるにもかかわらず、そのプロパティにアクセスしようとしてエラーが発生します。

解決策: 明示的なnullチェック


明示的にnullundefinedをチェックしてから処理を進めることで、エラーを防ぎます。

let num: number | null = null;
if (num !== null) {
  console.log(num.toFixed(2));
} else {
  console.log("数値が存在しません。");
}

この方法により、nullチェックが明確に行われ、エラーが回避されます。

5. デフォルト値の設定忘れによるエラー


nullundefinedが関数の引数に渡された場合、意図しない動作やエラーが発生することがあります。特に、オプショナルな引数が省略された場合には注意が必要です。

function displayMessage(message?: string) {
  console.log(message.toUpperCase()); // エラー: Cannot read property 'toUpperCase' of undefined
}

displayMessage(); // 引数が省略されているためエラーが発生

解決策: デフォルト値を指定


関数の引数にデフォルト値を設定することで、undefinedの場合でも安全に動作するようにします。

function displayMessage(message: string = "デフォルトメッセージ") {
  console.log(message.toUpperCase());
}

displayMessage(); // "デフォルトメッセージ"

このように、デフォルト値を指定することで、引数が省略されても安全に処理できます。

TypeScriptでnullundefinedによるトラブルを防ぐためには、Optional Chaining、Nullish Coalescing、明示的なチェック、デフォルト値の設定など、さまざまなツールや方法を活用することが重要です。これにより、エラーの少ない、より堅牢なコードを実現できます。

演習問題


これまでに学んだTypeScriptでのオプショナルパラメーター、null/undefinedの取り扱い方、そしてOptional ChainingやNullish Coalescingを活用するために、以下の演習問題を通して理解を深めましょう。

問題1: オプショナルパラメーターの利用


次の関数createUserを実装してください。ageパラメーターはオプショナルです。ageが指定されなかった場合はデフォルトで18歳を設定し、nameageをログに出力してください。

function createUser(name: string, age?: number): void {
  // ここに実装を追加
}

createUser("Alice"); // "Alice is 18 years old."
createUser("Bob", 25); // "Bob is 25 years old."

解答例

function createUser(name: string, age: number = 18): void {
  console.log(`${name} is ${age} years old.`);
}

問題2: Optional Chainingを使用したネストされたオブジェクトのアクセス


次のコードで、personオブジェクトのaddressプロパティが存在する場合はcityを、存在しない場合は"住所未設定"と出力する関数printCityを実装してください。

let person: { address?: { city?: string } } = { address: { city: "Tokyo" } };

function printCity(person: { address?: { city?: string } }) {
  // ここに実装を追加
}

printCity(person); // "Tokyo"
printCity({}); // "住所未設定"

解答例

function printCity(person: { address?: { city?: string } }) {
  console.log(person.address?.city ?? "住所未設定");
}

問題3: Nullish Coalescingを使用したデフォルト値の設定


次の関数getDiscountedPriceを実装してください。discountパラメーターはオプショナルで、指定されていない場合は10%の割引を適用します。

function getDiscountedPrice(price: number, discount?: number): number {
  // ここに実装を追加
}

console.log(getDiscountedPrice(100)); // 90
console.log(getDiscountedPrice(200, 20)); // 160

解答例

function getDiscountedPrice(price: number, discount?: number): number {
  let finalDiscount = discount ?? 10;
  return price - (price * finalDiscount) / 100;
}

問題4: nullチェックを使った安全なデータ処理


次のコードで、dataオブジェクトのvalueプロパティがnullの場合、「データがありません」を、値が存在する場合はその値を出力する関数printValueを実装してください。

let data: { value: number | null } = { value: null };

function printValue(data: { value: number | null }) {
  // ここに実装を追加
}

printValue(data); // "データがありません"
data.value = 42;
printValue(data); // "42"

解答例

function printValue(data: { value: number | null }) {
  if (data.value === null) {
    console.log("データがありません");
  } else {
    console.log(data.value);
  }
}

これらの演習問題に取り組むことで、オプショナルパラメーターやnull/undefinedの処理、Optional Chaining、Nullish Coalescingの実践的な使い方を深く理解できるでしょう。

まとめ


本記事では、TypeScriptにおけるオプショナルパラメーターとnull/undefinedの扱い方について詳しく解説しました。オプショナルパラメーターを使うことで、柔軟な関数定義が可能になり、Optional ChainingやNullish Coalescingを活用することで、安全にnullundefinedを扱えるようになります。これらの機能を適切に活用することで、エラーを回避し、堅牢でメンテナンスしやすいコードを作成することができます。

コメント

コメントする

目次
  1. オプショナルパラメーターとは?
  2. オプショナルパラメーターの定義方法
  3. nullとundefinedの違い
    1. undefinedとは?
    2. nullとは?
    3. nullとundefinedの使い分け
  4. Optional Parametersとundefinedの関係
    1. undefinedが使われる理由
    2. オプショナルパラメーターとundefinedの扱い方
  5. nullを使うべき場面とその理由
    1. 意図的に値がないことを示す場面
    2. nullを使う理由
    3. nullの適用例
  6. nullチェックの実装方法
    1. 基本的なnullチェック
    2. 厳密等価演算子(===)の使用
    3. 早期リターンを使ったnullチェック
    4. オプショナルチェイニングを使った安全なアクセス
    5. Nullish Coalescingを使ったデフォルト値の設定
  7. Optional Chainingの使い方
    1. Optional Chainingの基本的な使い方
    2. ネストされたオブジェクトのアクセス
    3. 関数呼び出しにおけるOptional Chaining
    4. 配列やプロパティへの安全なアクセス
    5. Optional ChainingとNullish Coalescingの組み合わせ
  8. nullish coalescing演算子の利用方法
    1. 基本的な利用方法
    2. nullish coalescingと論理OR演算子(||)との違い
    3. オプショナルパラメーターとnullish coalescing
    4. ネストされたプロパティとnullish coalescing
    5. 実践例: フォーム入力のデフォルト値設定
  9. nullとundefinedのトラブルシューティング
    1. 1. 未定義の値を使用するエラー
    2. 2. 関数が`undefined`の状態で呼び出されるエラー
    3. 3. nullやundefinedによる条件分岐の不具合
    4. 4. null/undefinedの手動チェック忘れによるエラー
    5. 5. デフォルト値の設定忘れによるエラー
  10. 演習問題
    1. 問題1: オプショナルパラメーターの利用
    2. 問題2: Optional Chainingを使用したネストされたオブジェクトのアクセス
    3. 問題3: Nullish Coalescingを使用したデフォルト値の設定
    4. 問題4: nullチェックを使った安全なデータ処理
  11. まとめ