ジェネリックも怖くない!TypeScriptでkeyof演算子を使いこなすための完全ガイド
TypeScript クラスのプロパティの種類を取得する keyof 演算子
例
class Person {
name: string;
age: number;
}
const person: Person = { name: "John Doe", age: 30 };
type PersonPropertyType = keyof Person; // "name" | "age"
const personName: PersonPropertyType = "name"; // personName は "name" になる
const personAge: PersonPropertyType = "age"; // personAge は "age" になる
この例では、Person
クラスには name
と age
という 2 つのプロパティがあります。keyof Person
は、これらのプロパティの名前の型である PersonPropertyType
という新しい型を作成します。
personName
と personAge
という変数は、それぞれ PersonPropertyType
型に設定されています。これは、personName
は "name"
にのみ割り当てることができ、personAge
は "age"
にのみ割り当てることができることを意味します。
ユースケース
keyof
演算子は、ジェネリック プログラミングや、プロパティ名に基づいて値にアクセスする場合に役立ちます。
例 1: ジェネリック プログラミング
function getProperty<T, K extends keyof T>(obj: T, key: K): T[K] {
return obj[key];
}
const person: Person = { name: "John Doe", age: 30 };
const name: string = getProperty(person, "name"); // name は "John Doe" になる
const age: number = getProperty(person, "age"); // age は 30 になる
この例では、getProperty
関数は、オブジェクトのプロパティ名に基づいて値を取得する汎用関数です。keyof T
型は、T
型のプロパティの名前の型を表します。
例 2: プロパティ名に基づいて値にアクセスする
class Person {
private name: string;
private age: number;
getName(): string {
return this.name;
}
getAge(): number {
return this.age;
}
}
const person: Person = new Person();
person.name = "John Doe";
person.age = 30;
const name: string = person["name"]; // name は "John Doe" になる
const age: number = person["age"]; // age は 30 になる
この例では、Person
クラスは、name
と age
という 2 つのプロパティをカプセル化しています。これらのプロパティに直接アクセスするには、[]
演算子を使用してプロパティ名を指定する必要があります。
注意事項
keyof
演算子は、プロパティの名前の型を取得します。プロパティの値の型を取得するには、typeof
演算子を使用する必要があります。keyof
演算子は、プライベート プロパティを含むすべてのプロパティの名前を取得します。プライベート プロパティにアクセスするには、[]
演算子を使用する必要があります。
keyof
演算子は、TypeScript クラスのプロパティの名前の型を取得するための便利なツールです。ジェネリック プログラミングや、プロパティ名に基づいて値にアクセスする場合に役立ちます。
TypeScript クラスのプロパティの種類を取得する keyof 演算子 - サンプルコード
例 1: 基本的な使用法
class Person {
name: string;
age: number;
}
type PersonPropertyType = keyof Person; // "name" | "age"
const person: Person = { name: "John Doe", age: 30 };
const personName: PersonPropertyType = "name"; // personName は "name" になる
const personAge: PersonPropertyType = "age"; // personAge は "age" になる
console.log(personName); // "name" を出力
console.log(personAge); // "age" を出力
例 2: ジェネリック プログラミング
function getProperty<T, K extends keyof T>(obj: T, key: K): T[K] {
return obj[key];
}
const person: Person = { name: "John Doe", age: 30 };
const name: string = getProperty(person, "name"); // name は "John Doe" になる
const age: number = getProperty(person, "age"); // age は 30 になる
console.log(name); // "John Doe" を出力
console.log(age); // 30 を出力
例 3: プロパティ名に基づいて値にアクセスする
class Person {
private name: string;
private age: number;
getName(): string {
return this.name;
}
getAge(): number {
return this.age;
}
}
const person: Person = new Person();
person.name = "John Doe";
person.age = 30;
const name: string = person["name"]; // name は "John Doe" になる
const age: number = person["age"]; // age は 30 になる
console.log(name); // "John Doe" を出力
console.log(age); // 30 を出力
例 4: インデックス型
type User = {
[key: string]: any;
};
const user: User = { name: "John Doe", age: 30, city: "New York" };
type UserPropertyType = keyof User; // "name" | "age" | "city" | ...
const userName: UserPropertyType = "name"; // userName は "name" になる
const userAge: UserPropertyType = "age"; // userAge は "age" になる
const userCity: UserPropertyType = "city"; // userCity は "city" になる
console.log(userName); // "name" を出力
console.log(userAge); // "age" を出力
console.log(userCity); // "city" を出力
この例は、keyof
演算子をインデックス型で使用する方法を示しています。インデックス型は、オブジェクトのキーの型を表すために使用されます。
これらの例は、keyof
演算子の基本的な使用方法を示しています。この演算子は、TypeScript でより強力で柔軟なコードを書くために使用できる強力なツールです。
TypeScript クラスのプロパティの種類を取得するその他の方法
型アサーション
as
キーワードを使用して、変数に型をアサートすることができます。これは、keyof
演算子よりも簡潔な方法ですが、型安全性を保証するものではありません。
class Person {
name: string;
age: number;
}
const person: Person = { name: "John Doe", age: 30 };
const personName: string = person.name as keyof Person; // personName は "name" になる
const personAge: number = person.age as keyof Person; // personAge は "age" になる
型推論
TypeScript の型推論機能を使用して、プロパティの種類を推論することができます。これは、keyof
演算子を使用するよりも簡潔な方法ですが、常に正確な結果が得られるとは限りません。
class Person {
name: string;
age: number;
}
const person: Person = { name: "John Doe", age: 30 };
const personName: string = person.name; // personName は "name" になる
const personAge: number = person.age; // personAge は "age" になる
ジェネリック型を使用して、プロパティの種類を動的に取得することができます。これは、より複雑なシナリオで役立ちますが、理解するのがより難しい場合があります。
interface Property<T, K extends keyof T> {
(obj: T, key: K): T[K];
}
const getProperty: Property<Person, keyof Person> = (obj, key) => obj[key];
const person: Person = { name: "John Doe", age: 30 };
const name: string = getProperty(person, "name"); // name は "John Doe" になる
const age: number = getProperty(person, "age"); // age は 30 になる
カスタム型ガードを使用して、プロパティの種類を検証することができます。これは、型安全性を向上させるための良い方法ですが、コードが冗長になる可能性があります。
class Person {
name: string;
age: number;
}
function isPersonPropertyName(name: string): name is keyof Person {
return name === "name" || name === "age";
}
const person: Person = { name: "John Doe", age: 30 };
const personName: string | undefined = person.name as keyof Person; // personName は "name" になる
const personAge: number | undefined = person.age as keyof Person; // personAge は "age" になる
if (isPersonPropertyName(personName)) {
console.log(personName); // "John Doe" を出力
}
if (isPersonPropertyName(personAge)) {
console.log(personAge); // 30 を出力
}
これらの方法はそれぞれ長所と短所があるので、状況に応じて適切な方法を選択する必要があります。
keyof
演算子は、TypeScript クラスのプロパティの名前の型を取得するための最も一般的な方法です。- 型アサーション、型推論、ジェネリック型、カスタム型ガードなどの他の方法も使用できます。
- 状況に応じて適切な方法を選択することが重要です。
typescript