JavaScript ファクトリ関数

概要: このチュートリアルでは、オブジェクトを返す関数であるJavaScriptファクトリ関数について学習します。

JavaScriptにおけるファクトリ関数の紹介

ファクトリ関数は、新しいオブジェクトを返す関数です。 以下は、person1という名前のpersonオブジェクトを作成します。

let person1 = {
  firstName: 'John',
  lastName: 'Doe',
  getFullName() {
    return this.firstName + ' ' + this.lastName;
  },
};

console.log(person1.getFullName());Code language: JavaScript (javascript)

出力

John Doe

person1オブジェクトには、firstNamelastNameの2つのプロパティと、フルネームを返すgetFullName()という1つのメソッドがあります。

person2という別の同様のオブジェクトを作成する必要があるとします。コードを次のように複製できます。

let person2 = {
  firstName: 'Jane',
  lastName: 'Doe',
  getFullName() {
    return this.firstName + ' ' + this.lastName;
  },
};

console.log(person2.getFullName());Code language: JavaScript (javascript)

出力

Jane Doe

この例では、person1person2オブジェクトは同じプロパティとメソッドを持っています。

問題は、作成したいオブジェクトが多くなるほど、重複コードが多くなることです。

同じコードを何度もコピーすることを避けるために、personオブジェクトを作成する関数を定義できます。

function createPerson(firstName, lastName) {
  return {
    firstName: firstName,
    lastName: lastName,
    getFullName() {
      return firstName + ' ' + lastName;
    },
  };
}Code language: JavaScript (javascript)

関数が新しいオブジェクトを作成して返す場合、それはファクトリ関数と呼ばれます。createPerson()は、新しいpersonオブジェクトを返すため、ファクトリ関数です。

以下は、createPerson()ファクトリ関数を使用して、2つのオブジェクトperson1person2を作成する方法を示しています。

function createPerson(firstName, lastName) {
  return {
    firstName: firstName,
    lastName: lastName,
    getFullName() {
      return firstName + ' ' + lastName;
    },
  };
}

let person1 = createPerson('John', 'Doe');
let person2 = createPerson('Jane', 'Doe');

console.log(person1.getFullName());
console.log(person2.getFullName());Code language: JavaScript (javascript)

ファクトリ関数を使用することで、コードを複製することなく、任意の数のpersonオブジェクトを作成できます。

オブジェクトを作成すると、JavaScriptエンジンはそのオブジェクトにメモリを割り当てます。多くのpersonオブジェクトを作成する場合、JavaScriptエンジンはこれらのオブジェクトを格納するために多くのメモリ空間を必要とします。

しかし、各personオブジェクトには、同じgetFullName()メソッドのコピーが含まれています。これは効率的なメモリ管理ではありません。

すべてのオブジェクトで同じgetFullName()関数を複製することを避けるために、personオブジェクトからgetFullName()メソッドを削除できます。

function createPerson(firstName, lastName) {
    return {
        firstName: firstName,
        lastName: lastName
    }
}Code language: JavaScript (javascript)

そして、このメソッドを別のオブジェクトに移動します。

var personActions = {
  getFullName() {
    return this.firstName + ' ' + this.lastName;
  },
};Code language: JavaScript (javascript)

そして、personオブジェクトでgetFullName()メソッドを呼び出す前に、personActionsオブジェクトのメソッドを次のようにpersonオブジェクトに割り当てることができます。

let person1 = createPerson('John', 'Doe');
let person2 = createPerson('Jane', 'Doe');

person1.getFullName = personActions.getFullName;
person2.getFullName = personActions.getFullName;

console.log(person1.getFullName());
console.log(person2.getFullName());Code language: JavaScript (javascript)

オブジェクトに多くのメソッドがある場合、このアプローチはスケーラブルではありません。なぜなら、個別に手動で割り当てる必要があるからです。これが、Object.create()メソッドが登場する理由です。

Object.create()メソッド

Object.create()メソッドは、既存のオブジェクトを新しいオブジェクトのプロトタイプとして使用して、新しいオブジェクトを作成します。

Object.create(proto, [propertiesObject])Code language: CSS (css)

そのため、次のようにObject.create()を使用できます。

var personActions = {
  getFullName() {
    return this.firstName + ' ' + this.lastName;
  },
};

function createPerson(firstName, lastName) {
  let person = Object.create(personActions);
  person.firstName = firstName;
  person.lastName = lastName;
  return person;
}Code language: JavaScript (javascript)

これで、personオブジェクトを作成し、personActionsオブジェクトのメソッドを呼び出すことができます。

let person1 = createPerson('John', 'Doe');
let person2 = createPerson('Jane', 'Doe');

console.log(person1.getFullName());
console.log(person2.getFullName());
Code language: JavaScript (javascript)

コードは完璧に機能します。しかし、実際には、ファクトリ関数をめったに使用しません。代わりに、クラスまたはコンストラクタ/プロトタイプパターンを使用します。

まとめ

  • ファクトリ関数は、新しいオブジェクトを返す関数です。
  • 既存のオブジェクトをプロトタイプとして使用してオブジェクトを作成するには、Object.create()を使用します。
このチュートリアルは役に立ちましたか?