FE-DSHUI / DSHUI

前端王者小分队读书会
4 stars 1 forks source link

《你不知道的JavaScript 下卷》 ——2020-02-04 #38

Open sworlife opened 3 years ago

sworlife commented 3 years ago

js 底层对象 1 js 对象 2

函数与对象

JavaScript 专门为函数对象预留了私有字段机制,并规定了抽象的函数对象和构造器对象的概念。 函数对象的定义:具有 [[call]] 私有字段的对象; 构造器对象的定义:具有 [[construct]] 私有字段的对象。 因此任何对象只要实现 [[call]] ,那它就是一个函数;实现了 [[construct]] 就是一个构造器。

使用 function 语法或者 Function 构造器创建的对象来说,必定同时包含了 [[call]] 和 [[construct]] 私有字段,并且 [[call]] 和 [[construct]] 它们执行同一段代码。

[[construct]] 的执行过程大致如下:

[[construct]] 的规则造成一个有趣的现象,如果构造器返回新的对象,那么 new 创建的新对象将只能被构造器访问,在一定程度上实现“私有”。

function cls(){
    this.a = 100;
    return {
        getValue:() => this.a
    }
}
var o = new cls;
o.getValue(); //100
//a 在外面永远无法访问到

而对于宿主和内置对象来说,[[call]] 和 [[construct]] 表现出的行为效果却并不相同。

// 内置对象 Date 作为构造器调用返回新对象,作为函数调用,则返回字符串
console.log(new Date); // 1
console.log(Date())
// 浏览器宿主环境中的 Image 构造器根本不允许被作为函数调用
console.log(new Image); 
console.log(Image());// 抛出错误
// String、Number、Boolean 则产生类型转换的效果

ES6 之后 => 语法创建的函数只包含 [[call]],没有 [[construct]] 私有字段。