构造函数和new的关系之我见

众所周知,在创建特殊用处的实例时,构造函数发挥了很大的作用。

而且,构造函数必须靠new表达式配合使用。

相声中说:

三分逗,七分捧

同样,创建实例的过程中,其实发挥着更重要的作用的是new表达式。

如果没有new表达式,构造函数和普通函数无本质区别。

就像《食神》中说的那样:

根本就没有什么食神,或者说,人人都是食神。

所以,欢迎走进new的世界。

new的功能

如下构造函数:

function WangJianLin() {
  this.IQ = 180
}
WangJianLin.prototype.money = '1000亿'
var siCong = new WangJianLin()

console.log(siCong.IQ) // 180
console.log(siCong.money) // 1000亿

/*
*  这段代码,简单表现了WangJianLin和siCong的三个关系:
*  1. 让siCong出生。
*  2. 让siCong继承1000。
*  3. 让siCong的IQ为180。
*  4. 将siCong返还给国民。
*/

由此可以看出,构造函数用new实现了三个功能:

1.创建一个对象。
2.让它继承构造函数的属性库。
3.将构造函数的this指针替换成它,构造它。
4.返回这个对象。

自我实现_new函数

上述代码new WangJianLin()的作用,可用伪代码表示为:

new WangJianLin = {
    // 多么普通的生命
    var baby = {}
    // 先天继承:
    baby.__proto__ = WangJianLin.prototype
    // 后天调教:
    var boy = WangJianLin.call(baby)
    // 一个崭新的国民老公即将诞生!
    return typeof boy === 'object' ? boy : baby
}

创建一个_new函数来实现上述功能:

function _new(Fn) {
    var obj = {}
    obj.__proto__ = Fn.prototype
    var args = [...arguments].slice(1)
    var newObj = Fn.call(obj, ...args)
    return typeof newObj === 'object' ? newObj : obj
}
var siCong = _new(WangJianLin)

再说new和构造函数的关系

// 普通函数foo:
function foo() {
  var a = 1
}
// 构造函数Animal:
function Animal(name) {
  this.name = name
}

/*
* 1. 正常使用
* */
foo()
var dog = new Animal('哈士奇') // dog: {name: '哈士奇'}

/*
* 2. 反常使用
* */
var obj = new foo() // obj: {}
Animal('哈士奇')
console.log(window.name) // '哈士奇'。已经污染了全局。

/*
* 可见,所谓的普通函数可以当构造函数来用;
* 所谓的构造函数也可以当普通函数来用;
* 只是这种职能分配有悖常理。
* */

综上所述,new操作符和构造函数的关系,好比厕所和上厕所的关系。

构造函数要用new调用,就好比上厕所就应该去厕所一样。

但是,构造函数可以不用new调用吗?

当然可以,这就好比随地大小便,会污染全局环境。

new可以调用普通函数吗?

当然可以,这就好比你不上厕所,却可以留在厕所(传说中的占着茅坑不拉屎?)。

虽然有多种选择,但是我们还是提倡用new调用构造函数这种组合,

就好像我们提倡不要随地大小便一样。

参考自:深入理解 new 操作符

  • 2
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值