Biểu tượng

Ký hiệu là một khái niệm tương đối mới ban đầu được đưa vào trong ES6. Ký hiệu nguyên gốc biểu thị một giá trị duy nhất không bao giờ xung đột với bất kỳ giá trị nào khác, bao gồm cả giá trị của các ký hiệu nguyên gốc khác. Hai chuỗi gốc tạo thành từ các ký tự giống nhau sẽ được đánh giá là nghiêm ngặt bằng:

String() === String()
> true

String( "My string." ) === String( "My string." );
> true

Tuy nhiên, không thể có hai ký hiệu được tạo bằng hàm Symbol() hoàn toàn ngang bằng:

Symbol() === Symbol()
> false

Trait này cho phép bạn sử dụng các ký hiệu làm khoá thuộc tính duy nhất trong một đối tượng, ngăn chặn xung đột với các khoá mà bất kỳ mã nào khác có thể thêm vào đối tượng đó.

const mySymbol = Symbol( "Desc" );

const myObject = {

}

myObject
> Object { Symbol("Desc"): "propSymbol" }

Có ba loại biểu tượng:

  • Biểu tượng được tạo bằng Symbol()
  • Các biểu tượng dùng chung được thiết lập và truy xuất từ sổ đăng ký biểu tượng chung bằng cách sử dụng Symbol.for()
  • "Những biểu tượng nổi tiếng" được xác định là các thuộc tính tĩnh trên đối tượng Symbol (Biểu tượng). Các ký hiệu này chứa phương thức nội bộ không thể vô tình ghi đè.

Symbol() chấp nhận nội dung mô tả (hoặc "tên biểu tượng") làm đối số không bắt buộc. Những nội dung mô tả này là nhãn mà con người đọc được để phục vụ cho mục đích gỡ lỗi và không ảnh hưởng đến tính duy nhất của kết quả. Mọi lệnh gọi đến Symbol đều trả về một giá trị biểu tượng hoàn toàn duy nhất, ngay cả khi nhiều lệnh gọi có giống hệt nhau mô tả:

Symbol( "My symbol." ) === Symbol( "My symbol." );
> false

Cũng giống như các kiểu dữ liệu gốc khác, biểu tượng sẽ kế thừa các phương thức và thuộc tính từ nguyên mẫu của chúng. Ví dụ: bạn có thể truy cập vào nội dung mô tả dưới dạng thuộc tính kế thừa của biểu tượng đã tạo:

let mySymbol = Symbol( "My symbol." );

mySymbol.description
> "My symbol."

Tuy nhiên, bạn không thể tạo biểu tượng bằng từ khoá new:

let mySymbol = new Symbol();

> Uncaught TypeError: Symbol is not a constructor

Ký hiệu không thể liệt kê được, nghĩa là không có các thuộc tính tượng trưng khi dùng các phương thức chuẩn để lặp lại các lượt chuyển đổi đó. getOwnPropertySymbols() phương thức cấp quyền truy cập vào các thuộc tính biểu tượng của một đối tượng.

Biểu tượng dùng chung

Phương thức Symbol.for() cố gắng tra cứu mọi ký hiệu hiện có trong sổ đăng ký biểu tượng chung trên toàn thời gian chạy với một chuỗi nhất định làm khoá và trả về ký hiệu khớp nếu tìm thấy một mã. Nếu không tìm thấy biểu tượng, Chrome sẽ tạo một biểu tượng bằng khoá được chỉ định và thêm khoá đó vào sổ đăng ký chung:

let sharedSymbol = Symbol.for( "My key." );

sharedSymbol === Symbol.for( "My key." )
> true

Các khoá này không trùng lặp chức năng với nội dung mô tả được chỉ định cho Dữ liệu gốc Symbol do tác giả tạo. Để truy cập một biểu tượng trong sổ đăng ký biểu tượng, trước tiên, bạn phải tạo tệp bằng for():

Symbol( "String" ) === Symbol( "String" );
> false

Symbol( "String" ) === Symbol().for( "String" );
> false

Symbol().for( "String" ) === Symbol().for( "String" );
> true

Để truy xuất khoá của bất kỳ biểu tượng nào trong sổ đăng ký biểu tượng, hãy sử dụng Symbol.keyFor():

let mySymbol = Symbol.for( "Key." );

Symbol.keyFor( mySymbol ) ;
> "Key."

"Phổ biến" ký hiệu

Ký hiệu phổ biến là các thuộc tính tĩnh của đối tượng Symbol, mỗi thuộc tính chính là một biểu tượng. Những ký hiệu nổi tiếng cung cấp khoá thuộc tính duy nhất cho truy cập và sửa đổi các phương thức tích hợp của JavaScript, đồng thời ngăn chặn để tránh bị ghi đè vô tình.

Symbol;
> function Symbol()
    asyncIterator: Symbol(Symbol.asyncIterator)
    for: function for()
    hasInstance: Symbol("Symbol.hasInstance")
    isConcatSpreadable: Symbol("Symbol.isConcatSpreadable")
    iterator: Symbol(Symbol.iterator)
    keyFor: function keyFor()
    length: 0
    match: Symbol("Symbol.match")
    matchAll: Symbol("Symbol.matchAll")
    name: "Symbol"
    prototype: Object { … }
    replace: Symbol("Symbol.replace")
    search: Symbol("Symbol.search")
    species: Symbol("Symbol.species")
    split: Symbol("Symbol.split")
    toPrimitive: Symbol("Symbol.toPrimitive")
    toStringTag: Symbol("Symbol.toStringTag")
    unscopables: Symbol("Symbol.unscopables")
    <prototype>: function ()

Vì ký hiệu là một tính năng đặc trưng của ES6, nên các giá trị tượng trưng này nhằm mục đích sử dụng làm "điểm mở rộng" dành cho nhà phát triển sửa đổi đoạn mã mà không gây ra vấn đề về khả năng tương thích ngược.

Các giá trị biểu tượng nổi tiếng thường được cách điệu bằng Tiền tố @@ hoặc được gói trong % để phân biệt khoá của chúng với nguyên mẫu có thể biến đổi. Ví dụ: @@match (hoặc %match%) là tham chiếu đến Symbol.match bất biến, chứ không phải String.prototype.match.

Kiểm tra kiến thức

Bạn có thể sử dụng new để tạo biểu tượng không?

Không

Câu nào sau đây mô tả biểu tượng "nổi tiếng"?

Thuộc tính tĩnh của đối tượng "Symbol"
Những biểu tượng mà bạn thường dùng
Khoá thuộc tính duy nhất để truy cập và sửa đổi tệp JavaScript phương thức tích hợp sẵn