[JavaScript] Constructor pattern trong lập trình hướng đối tượng

Trong các ngôn ngữ lập trình hướng đối tượng, một constructor là một phương thức đặc biệt sử dụng để khởi tạo một object dựa trên một class. Trong JavaScript, khi mà mọi thứ gần như đều là một đối tượng, thì chúng ta rất thường xuyên phải sử dụng đến object constructor.

Object constructor được sử dụng để khởi tạo nên một object riêng biệt. Nó có 2 chức năng chính đó là tạo nên object để sử dụng sau đó, cũng như nó cũng có thể nhận vào các đối số để thiết lập các giá trị thuộc tính cho object được khởi tạo.

1. Các cách tạo một đối tượng

Có 3 cách tạo nên một object trong JavaScript

//Khởi tạo một object và là một object rộng 

var object = {};

var object = Object.create(Object.prototype);

var object = new Object();

Ở ví dụ hàm khởi tạo object sử dụng từ khóa new, có thể sẽ tạo nên một object có giá trị cụ thể nếu như truyền tham số khi khởi tạo hoặc không có tham số truyền vào thì nó sẽ tạo nên một object rỗng và trả lại.

Vì vậy đối với lập trình hướng đối tượng JavaScript, cách đơn giản nhất để tạo mới một object là sử dụng function kết hợp với từ khoá new. Bên trong hàm khởi tạo này, từ khoá this dùng để chỉ tới đối tượng mới. Thông thường, hàm khởi tạo được viết hoa chữ cái đầu tiên, dùng để phân biệt với các hàm số thông thường. Sau đây, tìm hiểu về một vài Constructor Pattern trong JavaScript.

2. Constructor Pattern cơ bản

function Person(name, age){
     this.name = name;
     this.age = age;
     this.information = function(){
           return this.name + " is " + this.age + " years old";
     };
}

var father = new Person("Manh", 30);
var mother = new Person("Thang", 25);

console.log(father.information()); // Manh is 30 years old
console.log(mother.information()); // Thang is 25 years old

Ở ví dụ trên, ta khởi tạo Person sẽ có 2 thuộc tính name, age và có một phương thức information dùng để in thông tin của đối tượng Person. Tuy nhiên, ở cách trên có nhược điểm là khó để kế thừa và khi mỗi đối tượng khác sử dụng thì phải định nghĩa lại phương thức information. Để khắc phục nhược điểm trên thì có thể sử dụng Contructor Pattern với Prototypes.

3. Constructor Pattern với Prototypes

Trong JavaScript, mọi object trong đó gồm có cả function đều tồn tại thuộc tính prototype – cũng là một object. Khi sử dụng hàm khởi tạo để tạo mới một object, mọi thuộc tính trong prototype đều được kế thừ cho các đối tượng mới.

function Person(name, age){
     this.name = name;
     this.age = age;
}
Person.prototype.information = function(){
     return this.name + " is " + this.age + " years old";
}

var father = new Person("Manh", 30);
var mother = new Person("Thang", 25);

console.log(father.information()); // Manh is 30 years old
console.log(mother.information()); // Thang is 25 years old

4. Constructor Pattern với từ khóa class

Sử dụng class cho phép khởi tạo đối tượng mới một cách trực quan, và gần với khái niệm class trong các ngôn ngữ lập trình khác như C++, Java,…

Một điểm khác giữa class và function là function thuộc dạng hoisting, còn class thì không. Nghĩa là bạn có thể sử dụng hàm số trước khi khai báo hàm. Trong khi nếu bạn sử dụng class trước khi khai báo class thì bạn sẽ nhận được thông báo lỗi ReferenceError.

class Person {
     constructor(name, age){
         this.name = name;
         this.age = age;
     }

     information(){
          return this.name + " is " + this.age + " years old";
     };
}

var father = new Person("Manh", 30);
var mother = new Person("Thang", 25);

console.log(father.information()); // Manh is 30 years old
console.log(mother.information()); // Thang is 25 years old

Trong class, có một hàm duy nhất và đặc biệt là constructor, đây là hàm khởi tạo của class. Trong hàm này bạn có thể định nghĩa các thuộc tính (nameage) giống như sử dụng function và phương thức (information). Ngoài ra, bạn có thể định nghĩa các gettersetter và các hàm static.