Các kiểu dữ liệu nguyên thủy trong TypeScript

Bảng sau đây minh họa các kiểu dữ liệu nguyên thủy trong TypeScript:

Tên Miêu tả
string Đại diện cho dữ liệu văn bản
number Đại diện cho các giá trị số
boolean Có giá trị truefalse
null Có một giá trị: null
undefined Có một giá trị: undefined. Nó là một giá trị mặc định của một biến chưa được khởi tạo (gán giá trị)
symbol Đại diện cho một giá trị hằng số duy nhất

Kiểu số trong TypeScript

Tất cả các số trong TypeScript đều là giá trị dấu phẩy động hoặc số nguyên lớn. Các số dấu phẩy động có kiểu number trong khi các số nguyên lớn có kiểu bigint.

Kiểu dữ liệu number

Sau đây là cách khai báo một biến chứa giá trị dấu phẩy động:

let price: number;

Hoặc bạn có thể khởi tạo giá trị cho biến price như sau:

let price = 9.95;

Như trong JavaScript, TypeScript hỗ trợ các ký tự số cho các ký tự thập phân, thập lục phân, nhị phân và bát phân:

Số thập phân

Sau đây là một số số thập phân:

let counter: number = 0;
let x: number = 100, 
    y: number = 200;

Số nhị phân

Số nhị phân sử dụng số 0 đứng đầu theo sau là chữ b hoặc B, ví dụ : 0b hoặc 0B:

let bin = 0b100;
let anotherBin: number = 0B010;
Lưu ý rằng chữ số sau 0b hoặc 0B phải là 0 hoặc 1.

Số bát phân

Một số bát phân bắt đầu bằng số 0, tiếp sau là chữ cái o (kể từ ES2015) 0o. Các chữ số sau 0o là các số trong phạm vi 0 đến 7:

let octal: number = 0o10;

Số thập lục phân

Số thập lục phân bắt đầu bằng số 0, theo sau là chữ x hoặc X (0x hoặc 0X). Sau 0x phải là các số từ 0123456789 và các ký tự ABCDEF (0123456789ABCDEF). Ví dụ:

let hexadecimal: number = 0x5F1A;
JavaScript có kiểu dữ liệu Number (với chữ cái N viết hoa) đề cập đến đối tượng không nguyên thủy. Bạn không nên sử dụng kiểu Number này trong TypeScript.

Kiểu dữ liệu bigint

Các số nguyên lớn đại diện cho các số nguyên lớn hơn 253  - 1. Một số nguyên lớn có ký tự n ở cuối số nguyên như sau:

let big: bigint = 9007199254740991n;

Kiểu chuỗi trong TypeScript

Giống như JavaScript, TypeScript sử dụng dấu ngoặc kép (") hoặc dấu ngoặc đơn (') để bao quanh các ký tự chuỗi:

let firstName: string = 'John';
let title: string = "Web Developer";

TypeScript cũng hỗ trợ các chuỗi mẫu sử dụng dấu backtick (`) để bao quanh các ký tự.

Các chuỗi mẫu cho phép bạn tạo chuỗi nhiều dòng và cung cấp các tính năng nội suy chuỗi.

Ví dụ sau đây cho thấy cách tạo chuỗi nhiều dòng bằng cách sử dụng dấu backtick (`):

let description = `This TypeScript string can 
span multiple 
lines
`;

Nội suy chuỗi cho phép bạn nhúng các biến vào chuỗi như sau:

let firstName: string = `John`;
let title: string = `Web Developer`;
let profile: string = `I'm ${firstName}. 
I'm a ${title}`;

console.log(profile);

Đây là kết quả đầu ra:

I'm John. 
I'm a Web Developer.

Kiểu boolean trong TypeScript

Kiểu boolean trong TypeScript cho phép hai giá trị: truefalse. Đây là một trong những kiểu nguyên thủy trong TypeScript. Ví dụ:

let pending: boolean;
pending = true;
// after a while
// ..
pending = false;

JavaScript có kiểu Boolean tham chiếu đến đối tượng không nguyên thủy. Kiểu Boolean viết hoa chữ B, đó là khác biệt so với các kiểu boolean trong TypeScript.

Bạn nên tránh sử dụng kiểu Boolean này.

Kiểu void trong TypeScript

Kiểu void trong TypeScript đại diện cho không có bất kỳ giá trị nào cả. Nó giống như đối lập của kiểu any trong TypeScript.

Thông thường, bạn sử dụng kiểu void làm kiểu trả về của các hàm không trả về giá trị. Ví dụ:

function log(message): void {
    console.log(messsage);
}

Một best practice là sử dụng kiểu void làm kiểu trả về của một hàm hoặc một phương thức không trả về bất kỳ giá trị nào. Bằng cách này, bạn có thể đạt được những lợi ích sau:

  • Cải thiện độ rõ ràng của mã: bạn không cần phải đọc toàn bộ nội dung hàm để xem liệu nó có trả về bất kỳ thứ gì hay không.
  • Đảm bảo kiểu an toàn: bạn sẽ không bao giờ gán hàm có kiểu void cho một biến.

Lưu ý rằng nếu bạn sử dụng kiểu void cho một biến, bạn chỉ có thể gán undefined cho biến đó. Trong trường hợp này, kiểu void không hữu ích. Ví dụ:

let useless: void = undefined;
useless = 1; // error

Nếu cờ --strictNullChecks không được chỉ định, bạn có thể gán giá trị null cho useless.

useless = null; // OK if --strictNullChecks is not specified

Kiểu never trong TypeScript

Kiểu never trong TypeScript là một kiểu không chứa giá trị. Do đó, bạn không thể gán bất kỳ giá trị nào cho biến có kiểu never.

Thông thường, bạn sử dụng kiểu never để đại diện cho kiểu trả về của một hàm luôn tạo ra lỗi. Ví dụ:

function raiseError(message: string): never {
    throw new Error(message);
}

Kiểu trả về của hàm sau được suy ra là kiểu never:

function reject() { 
   return raiseError('Rejected');
}

Nếu bạn có một biểu thức hàm chứa một vòng lặp không xác định, thì kiểu trả về của nó cũng là kiểu never. Ví dụ:

let loop = function forever() {
    while (true) {
        console.log('Hello');
    }
}

Trong ví dụ này, kiểu kiểu trả về của hàm forever()never.

Nếu bạn thấy rằng kiểu trả về của một hàm là never, thì bạn nên đảm bảo rằng nó không phải là những gì bạn định làm.

Các biến cũng có thể nhận được kiểu never khi bạn thu hẹp kiểu của nó bằng một bộ bảo vệ kiểu dữ liệu không bao giờ có thể đúng.

Ví dụ: không có kiểu never, hàm sau đây gây ra lỗi vì không phải tất cả các đường dẫn mã đều trả về một giá trị.

function fn(a: string | number): boolean {
  if (typeof a === "string") {
    return true;
  } else if (typeof a === "number") {
    return false;
  }   
}

Để làm cho mã hợp lệ, bạn có thể trả về một hàm có kiểu trả về là kiểu never.

function fn(a: string | number): boolean {
  if (typeof a === "string") {
    return true;
  } else if (typeof a === "number") {
    return false;
  }  
  // make the function valid
  return neverOccur();
}

let neverOccur = () => {
   throw new Error('Never!');
}

Kiểu kết hợp trong TypeScript

Đôi khi, bạn sẽ gặp phải một hàm yêu cầu tham số là một số hoặc một chuỗi. Ví dụ:

function add(a: any, b: any) {
    if (typeof a === 'number' && typeof b === 'number') {
        return a + b;
    }
    if (typeof a === 'string' && typeof b === 'string') {
        return a.concat(b);
    }
    throw new Error('Parameters must be numbers or strings');
}

Trong ví dụ này, hàm add() sẽ tính tổng các tham số của nó nếu chúng là số.

Trong trường hợp các tham số là chuỗi, hàm add() sẽ nối chúng thành một chuỗi duy nhất.

Nếu các tham số không phải là số hoặc chuỗi, thì hàm add() sẽ tạo ra một lỗi.

Vấn đề với các tham số của hàm add() là các tham số của nó có kiểu any. Nó có nghĩa là bạn có thể gọi hàm với các đối số không phải là số hoặc chuỗi, TypeScript sẽ ổn với nó.

Mã này sẽ được biên dịch thành công nhưng gây ra lỗi khi chạy:

add(true, false);

Để giải quyết vấn đề này, bạn có thể sử dụng kiểu kết hợp trong TypeScript. Kiểu kết hợp cho phép bạn kết hợp nhiều kiểu dữ liệu thành một kiểu dữ liệu.

Ví dụ, biến sau có kiểu number hoặc string:

let result: number | string;
result = 10; // OK
result = 'Hi'; // also OK
result = false; // a boolean value, not OK

Một kiểu kết hợp mô tả một giá trị có thể là một trong một số kiểu dữ liệu, không chỉ dừng lại ở hai mà có thể có nhiều kiểu dữ liệu. Ví dụ: kiểu number | string | boolean thì giá trị có thể là một số, một chuỗi hoặc một boolean.

Quay lại ví dụ về hàm add(), bạn có thể thay đổi kiểu dữ liệu của các tham số từ kiểu any thành kiểu kết hợp như sau:

function add(a: number | string, b: number | string) {
    if (typeof a === 'number' && typeof b === 'number') {
        return a + b;
    }
    if (typeof a === 'string' && typeof b === 'string') {
        return a.concat(b);
    }
    throw new Error('Parameters must be numbers or strings');
}

Bí danh kiểu trong TypeScript

Bí danh kiểu (Type Alias) cho phép bạn tạo tên mới cho một kiểu hiện có. Sau đây là cú pháp của bí danh kiểu:

type alias = existingType;

Kiểu hiện có có thể là bất kỳ kiểu dữ liệu TypeScript hợp lệ nào.

Ví dụ sau sử dụng bí danh kiểu cho kiểu chuỗi:

type chars = string;
let messsage: chars; // same as string type

Bí danh kiểu rất hữu ích khi tạo bí danh cho các kiểu kết hợp. Ví dụ:

type alphanumeric = string | number;
let input: alphanumeric;
input = 100; // valid
input = 'Hi'; // valid
input = false; // Compiler error

Kiểu ký tự chuỗi trong TypeScript

Các kiểu ký tự chuỗi (String Literal Type) cho phép bạn định nghĩa một kiểu dữ liệu chỉ chấp nhận ký tự chuỗi được chỉ định.

Phần sau định nghĩa một kiểu ký tự chuỗi chấp nhận một chuỗi ký tự 'click':

let click: 'click';

click là một kiểu ký tự chuỗi chỉ chấp nhận chuỗi ký tự 'click'. Nếu bạn gán chuỗi 'click' cho chuỗi ký tự click sẽ hợp lệ:

click = 'click'; // valid

Tuy nhiên, khi bạn gán một chuỗi bất kỳ khác cho click, trình biên dịch TypeScript sẽ xuất hiện lỗi. Ví dụ:

click = 'dblclick'; // compiler error

Lỗi:

Type '"dblclick"' is not assignable to type '"click"'.

Kiểu ký tự chuỗi rất hữu ích để giới hạn giá trị chuỗi có thể có trong một biến.

Có thể sử dụng kiểu kết hợp để kết hợp các kiểu chuỗi ký tự để định nghĩa một tập hợp hữu hạn các giá trị chuỗi ký tự cho một biến như sau:

let mouseEvent: 'click' | 'dblclick' | 'mouseup' | 'mousedown';
mouseEvent = 'click'; // valid
mouseEvent = 'dblclick'; // valid
mouseEvent = 'mouseup'; // valid
mouseEvent = 'mousedown'; // valid
mouseEvent = 'mouseover'; // compiler error

Nếu bạn sử dụng kiểu ký tự chuỗi ở nhiều nơi, chúng sẽ rất dài dòng.

Để tránh điều này, bạn có thể sử dụng bí danh kiểu. Ví dụ:

type MouseEvent: 'click' | 'dblclick' | 'mouseup' | 'mousedown';
let mouseEvent: MouseEvent;
mouseEvent = 'click'; // valid
mouseEvent = 'dblclick'; // valid
mouseEvent = 'mouseup'; // valid
mouseEvent = 'mousedown'; // valid
mouseEvent = 'mouseover'; // compiler error

let anotherEvent: MouseEvent;

Tóm lược

  • Tất cả các số trong TypeScript đều là giá trị dấu phẩy động có kiểu dữ liệu number hoặc các số nguyên lớn có kiểu dữ liệu bigint.
  • Tránh sử dụng kiểu dữ liệu Number của JavaScript trong TypeScript.
  • Trong TypeScript, tất cả các chuỗi đều có kiểu string.
  • Giống như JavaScript, TypeScript sử dụng dấu ngoặc kép ("), dấu nháy đơn (') vàdấu backtick (`) để bao quanh các ký tự chuỗi.
  • Sử dụng kiểu void làm kiểu trả về của các hàm không trả về bất kỳ giá trị nào.
  • Kiểu never trong TypeScript không chứa giá trị.
  • Kiểu never đại diện cho kiểu trả về của một hàm luôn ném một lỗi hoặc một chức năng có chứa một vòng lặp vô hạn.
  • Kiểu kết hợp trong TypeScript cho phép bạn lưu trữ giá trị của một hoặc nhiều kiểu dữ liệu cung cấp trong một biến.
  • Sử dụng bí danh kiểu để định nghĩa tên mới cho các kiểu hiện có.
  • Kiểu ký tự chuỗi TypeScript xác định kiểu chấp nhận ký tự chuỗi được chỉ định.
  • Sử dụng kiểu ký tự chuỗi (String Literal Type) với kiểu kết hợp và bí danh kiểu để định nghĩa kiểu dữ liệu chấp nhận một tập hợp hữu hạn các ký tự chuỗi.
TypeScript
Bài Viết Liên Quan:
Namespace trong TypeScript
Trung Nguyen 14/10/2021
Namespace trong TypeScript

Namespace được sử dụng để nhóm logic các chức năng. Namespace có thể bao gồm các interface, lớp, hàm và biến để hỗ trợ một nhóm các chức năng liên quan.

Từ khóa readonly và static trong TypeScript
Trung Nguyen 13/10/2021
Từ khóa readonly và static trong TypeScript

Trong hướng dẫn này bạn sẽ tìm hiểu về từ khóa readonly, static và cách sử dụng chúng trong TypeScript.

Từ khóa kiểm soát truy cập trong TypeScript
Trung Nguyen 12/10/2021
Từ khóa kiểm soát truy cập trong TypeScript

TypeScript có ba từ khóa kiểm soát quyền truy cập: public, private và protected để kiểm soát khả năng hiển thị của các thành phần dữ liệu của nó.

Abstract Class trong TypeScript
Trung Nguyen 11/10/2021
Abstract Class trong TypeScript

Định nghĩa một abstract class trong TypeScript bằng cách sử dụng từ khóa abstract. Abstract class chủ yếu được sử dụng để các lớp khác kế thừa từ chúng. Chúng ta không thể tạo một thể hiện của một abstract class.