tính cấu hình dường như deletable:Tại sao thuộc tính có thể định cấu hình này không thể xóa?
var o = {};
Object.defineProperty(o, 'prop', {
configurable: true,
value: 'val'
});
delete o.prop; // true
o.prop; // undefined
Nhưng nó không hoạt động trong trường hợp sau đây, ít nhất là trên Firefox và Chrome:
var form = document.createElement('form'),
input = document.createElement('input');
form.appendChild(input);
var elems = form.elements;
Object.getOwnPropertyDescriptor(form, 0)
.configurable; // true <────────────────────── !!!
delete elems[0]; // false │
elems[0]; // input │
(function(){ 'use strict'; // V
delete elems[0]; // TypeError: property 0 is non-configurable
})(); // and can't be deleted
Nhưng điều này dường như mâu thuẫn với spec.
Nhà điều hành delete
được định nghĩa như thế này:
Việc sản xuất UnaryExpression:
delete
UnaryExpression được đánh giá như sau:
- Hãy ref là kết quả của việc đánh giá UnaryExpression.
- [...]
- Nếu IsPropertyReference (ref) là đúng, sau đó
- Return kết quả của cách gọi [[Xóa]] phương pháp nội bộ về ToObject (GetBase (ref)) cung cấp GetReferencedName (ref) và IsStrictReference (ref) làm đối số .
Vì vậy, kết quả của việc sử dụng delete
phụ thuộc vào [[Xóa]]. Bây giờ chúng ta hãy xem những gì [[Xóa]] làm:
8.12.7 - [[Delete]] (P, Throw)
Khi [[Xóa]] phương pháp nội bộ của O được gọi với tài sản tên P và cờ Boolean Ném, các bước sau đây được thực hiện:
- Hãy desc là kết quả của cách gọi [[GetOw nProperty]] phương thức nội bộ của O với tên thuộc tính P.
- Nếu desc là undefined, sau đó trả lại đúng.
- Nếu desc.[[Cấu hình]] là đúng, sau đó
- Di chuyển tài sản riêng với tên P từ O.
- Trả lại đúng.
- khác nếu Ném, sau đó ném một TypeError ngoại lệ.
- Trả lại false.
Do đó, nếu thuộc tính được cấu hình, nó sẽ bị xóa.
Nhưng chờ đợi, có thể Object.getOwnPropertyDescritor
là một troll và nói rằng thuộc tính có thể định cấu hình, nhưng [[Configurable]] là false. Hãy xem:
15.2.3.3 - Object.getOwnPropertyDescriptor (O, P)
Khi getOwnPropertyDescriptor hàm được gọi, các bước sau đây được thực hiện:
- Nếu Type (O) không được đối tượng ném một TypeError ngoại lệ.
- Hãy để tên là ToString (P).
- Hãy desc là kết quả của cách gọi [[GetOwnProperty]] phương pháp nội bộ của O với lập luận tên.
- Trả lại kết quả gọi số FromPropertyDescriptor (desc).
Vì vậy, nó cũng sử dụng [[GetOwnProperty]], như [[Xóa]]. Có lẽ troll là FromPropertyDescriptor?
8.10.4 FromPropertyDescriptor (Desc)
Khi FromPropertyDescriptor hoạt động trừu tượng được gọi với mô tả tài sản quyết, các bước sau đây được thực hiện:
- Nếu quyết là không xác định, sau đó trở không xác định.
- Hãy obj thể là kết quả của việc tạo ra một đối tượng mới, nếu như bởi sự biểu hiện new Object() nơi Object là tiêu chuẩn được xây dựng trong constructor với tên đó.
- ...
- Gọi [[DefineOwnProperty]] phương pháp nội bộ của obj với đối số "
configurable
", Property Descriptor {[[Giá trị]]:. quyết [[Cấu hình]], [[Có thể ghi được ]]: đúng, [[Enumerable]]: đúng, [[Cấu hình]]: đúng}, và sai.- Trả lại obj.
Vì vậy, không, nó không phải là troll. Thuộc tính configurable
của bộ mô tả thuộc tính được đặt thành giá trị [[Có thể cấu hình]].
Làm cách nào để có thể xóa thuộc tính có thể định cấu hình?