Interface trong TypeScript
1. Interface là gì?
Trong TypeScript, interface là một cấu trúc khai báo các tiêu chuẩn. Các lớp được dẫn xuất (derived) từ một interface phải tuân thủ các tiêu chuẩn do interface đặt ra.
Không có khái niệm interface trong JavaScript, vì vậy trình biên dịch TypeScript không chuyển đổi các interface sang JavaScript. Interface được sử dụng như một công cụ để kiểm tra các kiểu trong chương trình.
TypeScript sử dụng từ khoá interface cho việc định nghĩa một interface. Interface có thể bao gồm các trường (field), các property và các phương thức (method).
interface Greeting {
name: string;
sayHello(friendName:string): string; // A method
sayBye: (friendName: string) => string; // A arrow method
}
Trong ví dụ trên, Greeting là một interface nó bao gồm 1 trường (field) và 2 phương thức.
- name: Một trường (field) với kiểu dữ liệu là string.
- sayHello: Một phương thức thông thường với một tham số kiểu string, và trả về một string.
- sayBye: Một phương thức Lambda với một tham số kiểu string, và trả về một string. (Phương thức Lambda cũng còn được gọi là các phương thức mũi tên).
2. Interface là một kiểu dữ liệu
Interface là một kiểu dữ liệu, và bạn có thể tạo ra các đối tượng một cách trực tiếp, các đối tượng được tạo ra phải thi hành (implements) tất cả các trường, các property và các phương thức được khai báo trong interface.
Để đơn giản hãy xem ví dụ:
interface_ex1.ts
interface Greeting {
name: string;
sayHello(friendName: string): string; // A method
sayBye: (friendName: string) => string; // A arrow method
}
function interface_ex1_test() {
// Create an object:
var enPerson1: Greeting = {
name: "John",
sayHello: function (friendName: string): string {
return "Hello " + friendName;
},
sayBye: function (friendName: string): string {
return "Good Bye";
}
};
// Create an object
var vnPerson1: Greeting = {
name: "Tran",
sayHello: function (friendName: string): string {
return "Xin Chao " + friendName;
},
sayBye: function (friendName: string): string {
return "Tam biet " + friendName;
}
};
// Test objects:
console.log(enPerson1.name); // John
console.log(enPerson1.sayHello("Tom")); // Hello Tom
console.log(vnPerson1.name); // Tran
console.log(vnPerson1.sayBye("Jerry")); // Tam Biet Jerry
}
interface_ex1_test(); // Call the function.
Output:
John
Hello Tom
Tran
Tam biet Jerry
Khi tạo một đối tượng trực tiếp từ một interface bạn phải tuân thủ quy tắc Key-Value. Điều này có nghĩa là tất cả các thành viên trong đối tượng này đều được viết theo quy tắc Key-Value (Khoá và giá trị).
// Create an object:
var enPerson1: Greeting = {
name: "John",
sayHello: function (friendName: string): string {
return "Hello " + friendName;
},
sayBye: function (friendName: string): string {
return "Good Bye";
}
};
3. Trường tuỳ chọn
Trong TypeScript, các trường của một interface có thể được định nghĩa như một tuỳ chọn, điều này có nghĩa là lớp hoặc đối tượng thi hành interface này có thể bỏ qua chúng.
interface Interface_Name {
optional_field_name? data_type;
// Other fields and methods (If any)
}
Trong ví dụ dưới đây, trường empDept là một tuỳ chọn.
interface_optional_field_ex1.ts
interface IEmployee {
empCode: number;
empName: string;
empDept?: string;
}
function interface_optional_field_ex1_test() {
let tom: IEmployee = {
empCode: 1,
empName: "Tom"
}
let jerry: IEmployee = {
empCode: 2,
empName: "Jerry",
empDept: "IT"
}
console.log(" --- tom --- ");
console.log('tom.empName: ' + tom.empName); // Tom
console.log('tom.empDept: ' + tom.empDept); // undefined
console.log(" --- jerry --- ");
console.log('jerry.empName: ' + jerry.empName); // Jerry
console.log('jerry.empDept: ' + jerry.empDept); // IT
}
interface_optional_field_ex1_test(); // Call the function.
Output:
--- tom ---
tom.empName: Tom
tom.empDept: undefined
--- jerry ---
jerry.empName: Jerry
jerry.empDept: IT
4. Trường chỉ đọc (Read-only)
TypeScript cung cấp một cách để đánh dấu một trường là chỉ đọc (read only). Điều này có nghĩa là một khi trường được gán một giá trị, nó không thể thay đổi được!
Trong ví dụ dưới đây, trường SSN là chỉ đọc. Một khi nó được gán giá trị, bạn không thể gán giá trị khác cho nó, trình biên dịch sẽ thông báo lỗi nếu bạn vi phạm điều đó.
interface_readonly_field_ex1.ts
interface Citizen {
name: string;
readonly SSN: number;
}
function interface_readonly_field_ex1_test() {
let personObj: Citizen = {
SSN: 11111,
name: 'Tom'
};
personObj.name = 'Jerry'; // OK
personObj.SSN = 22222; // Compiler Error (!!!!!)
}
interface_readonly_field_ex1_test(); // Call the function.
5. Interface mở rộng từ các interface khác
Trong TypeScript, một interface có thể mở rộng (extends) từ một hoặc nhiều interface khác theo cú pháp:
interface C extends A, B {
// codes..
}
Ví dụ:
interface_extends_ex1.js
interface IAnimal {
name: string;
}
interface ICat extends IAnimal {
age: number;
move(): void;
}
function interface_extends_ex1_test() {
let tom = {
name: "Tom",
age: 3,
move: function () {
console.log("Moving...");
}
};
console.log(`Name: ${tom.name}`);
console.log(`Age: ${tom.age}`);
tom.move();
}
interface_extends_ex1_test(); // Call the function.
Output:
Name: Tom
Age: 3
Moving...
6. Thi hành các interface
Cũng giống như Java và C#. Interface trong TypeScript có thể được thi hành (implement) bởi một lớp. Về cơ bản, một lớp có thể thi hành một hoặc nhiều interface, và nó phải tuân thủ cấu trúc được định nghĩa bởi tất cả các interface đó.
- Classes
- Constructor trong TypeScript
7. Function-Type Interface
TypeScript cũng có khái niệm về Functional Interface như trong Java. Chúng ta tạm gọi nó là Function-Type Interface - Một interface chỉ có duy nhất một phương thức, và phương thức này không có tên, nó chỉ bao gồm các tham số và kiểu trả về. Function-Type Interface được sử dụng như một hàm, đôi khi nó cũng có các trường tuỳ chọn.
Cú pháp định nghĩa Functional Interface:
interface Interface_Name {
(param_name_1 data_type_1, param_name_n data_type_n): return_data_type;
}
Function-Type Interface là interface đặc biệt, nó được sử dụng như một hàm chứ không phải là một kiểu dữ liệu.Việc viết một interface mở rộng từ một Function-Type Interface là không có nhiều ý nghĩa.Hoặc việc viết một lớp thi hành một Function-Type Interface là không thể.
Ví dụ:
interface IFormatter {
(text:string) : number;
}
Functional interface được sử dụng như một hàm. Hãy xem ví dụ sau:
functional_interface_ex1.js
interface IFormatter {
(text:string) : number;
}
function functional_interface_ex1_test() {
var intFormatter: IFormatter = function(text:string): number {
return parseInt(text);
}
var floatFormatter: IFormatter = function(text:string): number {
return parseFloat(text);
}
var text:string = "2001.55";
var value1 = intFormatter(text); // Use as a function
console.log(value1); // 2001
var value2 = floatFormatter(text); // Use as a function
console.log(value2); // 2001.55
}
functional_interface_ex1_test(); // Call the function.
Output:
2001
2001.55
Function-Type Inteface có thể bao gồm các trường tuỳ chọn, hãy xem ví dụ:
functional_interface_ex2.ts
interface IFormatter {
(text:string) : number;
description? : string;
}
function functional_interface_ex2_test() {
var intFormatter: IFormatter = function(text:string): number {
return parseInt(text);
}
intFormatter.description = "Format a string to integer";
var text: string = "2001.55";
var result = intFormatter(text); // Use as a function
console.log(intFormatter.description); // Format a string to integer
console.log(result); // 2001
}
functional_interface_ex2_test(); // Call the function.
Output:
Format a string to integer
2001
8. Array-Type Interface
TypeScript cung cấp một loại interface để mô phỏng một mảng, nó được gọi nó là Array-Type Interface.
Cú pháp:
interface Interface_Name {
[index_name_1: index_data_type_1] : value_data_type;
[index_name_n: index_data_type_n] : value_data_type;
// Other properties and methods (If any) ...
}
Chú ý: index_data_type_1,..., index_data_type_n phải khác nhau, nếu không bạn sẽ nhận được một thông báo lỗi:Duplicate index signature for type 'xxx'
Ví dụ:
interface_array_ex1.ts
interface IEmployeeSalary {
[emp_name:string]:number; // emp_name --> salary
}
function interface_array_ex1_test() {
var salaryMap : IEmployeeSalary = {};
salaryMap["Tom"] = 2000;
salaryMap["Jerry"] = 1500;
salaryMap["Donald"] = 3000;
console.log(salaryMap["Jerry"]); // 1500
}
interface_array_ex1_test(); // Call the function.
Ví dụ: Một Array-Type Interface với index_data_type là number.
interface_array_ex2.ts
interface IFootballerArray {
[index:number]:string;
}
function interface_array_ex2_test() {
var footballerArray : IFootballerArray = ["Ronaldo", "Messi", "Pele"];
console.log(footballerArray[0]); // Ronaldo
console.log(footballerArray[1]); // Messi
footballerArray[0.5] = "<Funny>";
console.log(footballerArray[0.5]); // <Funny>
}
interface_array_ex2_test(); // Call the function.
Output:
Ronaldo
Messi
<Funny>
Ví dụ: Một Array-Type Interface với các trường và các phương thức:
interface_array_ex2b.ts
interface IFootballPlayerArray {
description: string;
someMethod(): string;
[index: number]: string;
}
function interface_array_ex2b_test() {
var footballerArray: IFootballPlayerArray = {
description: "Famous Football Players",
someMethod: function (): string {
return "Something";
}
}
footballerArray[0] = "Ronaldo";
footballerArray[1] = "Messi";
footballerArray[2] = "Pele";
footballerArray[0.5] = "<Funny>";
console.log(footballerArray.description); // Famous Football Players
console.log(footballerArray.someMethod()); // Something
console.log(" --- "); // ---
console.log(footballerArray[0]); // Ronaldo
console.log(footballerArray[1]); // Messi
console.log(footballerArray[0.5]); // <Funny>
}
interface_array_ex2b_test(); // Call the function.
Output:
Famous Football Players
Something
---
Ronaldo
Messi
<Funny>
Ví dụ: Một Array-Type Interface với 2 chiều chỉ số (2 dimensional indexes):
interface_array_2d_ex1.ts
interface IStaff {
[staff_id:number] : number; // staff_id --> salary
[staff_number:string] : number; // staff_number --> salary
}
function interface_array_2d_ex1_test() {
var staffArray : IStaff = {};
staffArray[100] = 2000;
staffArray[101] = 1500;
staffArray[102] = 3000;
staffArray["S-100"] = 2000;
staffArray["S-101"] = 1500;
staffArray["S-102"] = 3000;
console.log(staffArray[100]); // 2000
console.log(staffArray[102]); // 3000
console.log(" --- ");
console.log(staffArray["S-100"]); // 2000
console.log(staffArray["S-102"]); // 3000
}
interface_array_2d_ex1_test(); // Call the function.
Output:
2000
3000
---
2000
3000
Các hướng dẫn TypeScript
- Chạy ví dụ TypeScript đầu tiên của bạn trong Visual Studio Code
- Không gian tên (Namespace) trong TypeScript
- Module trong TypeScript
- Toán tử typeof trong TypeScript
- Biến (Variable) trong TypeScript
- Vòng lặp trong TypeScript
- Cài đặt TypeScript trên Windows
- Hướng dẫn và ví dụ hàm trong TypeScript
- Tuples trong TypeScript
- Interface trong TypeScript
- Mảng (Array) trong TypeScript
- Toán tử instanceof trong TypeScript
- Phương thức trong TypeScript
- Hướng dẫn và ví dụ TypeScript Closures
- Constructor trong TypeScript
- Property trong TypeScript
- Phân tích JSON trong TypeScript
- Phân tích JSON trong TypeScript với thư viện json2typescript
- Trình chuyển đổi mã nguồn (Transpiler) là gì?
Show More