JavaScript的创世神话——统统源于对象

《圣经》里的第一章创世纪中个中有一段典范纪录天主是怎样制造人的。
神说:“我们要照着我们的笼统,根据我们的款式造人”。不约而同的是,JavaScript中好像也遵照着天主的旨意去制造顺序天下,统统皆对象的认知里背地是人间万物皆源于一个原型,一个一致的情势,一个柏拉图口中的理念……

JavaScript的编程艺术也由此归纳开来~~~

目次:
1.面向对象编程的一些开端思索
2.类与对象
3.组织函数constructor
3.1 new敕令
3.2 this关键字
3.3.原型对象
4.一些相干的要领

《JavaScript的创世神话——统统源于对象》

1.面向对象编程的一些开端思索

“面向对象编程”(Object Oriented Programming,缩写为OOP)本身是一种编程的头脑形式,它把天下的统统看做是对象的鸠合,天下的运转就是靠一个个对象分工、协作的效果。

有了这么一种宏观维度的编程认知,那末我们在编程时也就不会困在代码的死胡同了出不来。

给一段小代码做开端诠释:
我们在网页开辟中,常常要举行事宜绑定。

var btn = document.getElementById('button');
btn.addEventListener('click',function(){console.log('click me')})

初学时,笔者也是无意识的看到addEventListener()要领可以举行事宜绑定以完成点击特定元素后,就可以完成需求就没有再往深层次去想太多;

跟着进修的深切,在进入OOP的章节,我们就会发明“统统皆对象”这句话的深入性。

上面的代码中,btn本身就一个对象,点击时该对象将会挪用本身的要领addEventListener()去做事。

一个完全的诠释就是谁(对象)干了什么(要领),btn被点击时干了输出‘click me ’。

固然这只是个中一个案例,JS的编程中这类编程形式领悟一直,如:

//1、定义一个对象
var sheep = {
  color: white,
  echo: function(){
      console.log('mae~~~')
  }
} 
sheep.echo()
//这只羊发出mae的啼声

//2.设置对象的款式
$('.passage').css({
      width: '100px',
      color: 'pink'
  }
)
//这个名为passge的jquery对象被设置宽和色
......

总之,JavaScript的编程没法离开对象而独存

2.类与对象

说了那末久,假如连对象是什么都没一个清晰的界定,那末在编程过程当中照样存在隐约地带。

  • 什么是对象
    对象可以说是对实际事物的笼统,对象封装了属性和要领,属性值指的是对象的状况,要领指的是对象的行动。

比方,我们把NBA的巨星kobe笼统为javascript里的对象:

var kobe = {
    team: 'Los Angeles Lakers',
    position: 'shooting guard',
    ability :  function(){
        console.log('impress those who like basketball')
  }
}

实际天下的科比笼统为js中kobe这一对象,效能于洛杉矶湖人和位置是得分后卫是他的属性,才能是影响很多兴趣篮球的人是他的要领。

  • 什么是’类'(组织函数)

根据圣经的纪录,在第一章的创世纪中写道:“神根据着本身的笼统造人。”

实际天下的万物(对象)的演变不是平空降生的,它须要根据一个模板去组织出种种实例出来。

因而,类(组织函数)就是供应这么一种模板的‘对象’(函数本身在js中就是对象),它是对象的笼统

然则,js中并没有类的观点,而是经由过程组织函数替换了类的功用,为某一类的对象供应配合的属性和要领。

经由过程组织函数可以制造种种具有特定类的属性和要领的实例对象。

比方,定义一个篮球运动员的类(组织函数):

//定义一个类,该类包含了一个篮球运动员应有的属性和要领
var BasketballPlayer = function(){
   this.height = '180+',
   this.muscle = true,
   this.ability = function(){
        console.log('shooting and passing ')
    }
}

//由类(组织函数)制造出3个实例对象
var kobe = new BasketballPlayer();
var james =new BasketballPlayer();
var curry =new BasketballPlayer();

这里有个小问题,组织函数BasketballPlayer又是有谁组织出来呢?看了下面的代码便知~~~

BasketballPlayer instanceof Object//true
组织函数或者是函数在js中天生就是组织函数Object的实例

所以说,一切的实例对象都有类(组织函数)制造出来,而一切的组织函数都是由最为平常的类,即Object组织出来,故统统皆对象

【注】
类在js中表现为组织函数,为了正确起见,下面一致称为组织函数,我们只须要知道两者起到的作用是一致就行。

3.组织函数

前面我们相识到,人间万物(实例对象)都是根据特定的模板(类或组织函数)组织的,而一切的组织函数都是由最平常的组织函数Object组织的。

然则,我们也许看到下面的代码会发生这么一种迷惑:
1.组织函数中的Book的this是干吗的,有什么门道?
2.应用组织函数Book组织实例javascript时new起到什么作用
3.为何我组织出一个实例对象后,这个组织函数可以返回一个对象给我
总结成一句就是:在全部造物的过程当中,组织函数的运作机制是怎样的???

var Book = function(){
    this.material = 'paper';
    this.color = 'white';
    this.utility = function(){
       console.log('IQ+');
  }
    this.whoAmI = function(){
      console.log(this)
  }
}

var javascript = new Book()
  • this在组织函数的作用

    关键字this在js中显得十分主要,它在差别的运转环境(属性和要领的挪用者)指向的环境(对象)差别,也就是说this的指向是动态的,然则不管this的指向是谁,只需清晰属性和要领的挪用者是谁那末this就指向谁。

//在浏览器全局环境下,即window对象下
var print = function(){
      console.log(this)
 }
print()//this指向Window,由于这是Window对象挪用了print要领

//在特定对象的环境下
var o = {
    print: function(){
      console.log(this)
  }
}
o.print()//this指向o,由于这是o对象挪用print要领

因而,回到组织函数中的this来,当实行 var javascript = new Book()时,此时是javascript这个实例对象挪用了组织函数Book,函数内部的this指向javascript这一实例对象

javascript.whoAmI()//this此时指向javascript对象

【注】更多this的学问详见what’s this???

  • new敕令的道理

    接下来谈一谈new敕令的道理。

new敕令的作用,就是实行组织函数,返回一个实例对象

与一般的一般挪用函数差别,在函数实行前面附加new敕令,函数实行以下步骤:

1.建立一个空对象,作为将要返回的实例对象;

2.将这个空对象的原型``__proto__``指向组织函数的prototype属性以完成继续机制
3.将这个空对象赋值给函数内部的this关键字
4.最先实行组织函数内部的代码
  • 原型对象

    上面我们基础相识组织函数在制造实例对象时的部份运作机制,邃晓了this关键字和new敕令在组织实例时所起的作用。

如今有一个最最主要的疑问是实例对象究竟是怎样继续组织函数中设定好的属于该类的共有的属性和要领呢?

prototype object

JavaScript中每一个实例对象继续自另一个对象,后者被称为原型对象,原型对象上的属性和要领都能被派生对象同享,这就是JavaScript有名的继续机制的基础设想。

先上一段代码用于解说:

function Dog(name,color){
  this.name = name;
  this.color = color;
}

Dog.prototype.spark = function(){
    console.log('Wow~~~')
}
var tony = new Dog('tony','white')

1.经由过程组织函数Dog天生的实例对象tony,会自动为实例对象tony分派原型对象;

2.每一个组织函数都有一个prototype属性,该属性就是实例对象的原型对象

《JavaScript的创世神话——统统源于对象》

3.实例对象内部有一个__proto__属性,该属性在被组织函数一制造出来就指向组织函数的protype属性

《JavaScript的创世神话——统统源于对象》

这样一来,我们经由过程组织函数Dog中的原型对象prototype完成了实例对象tony对Dog的共有属性和要领的继续。

《JavaScript的创世神话——统统源于对象》

因而,我们可以得出的思索是,原型对象定义一切实例对象的共有的属性和要领,一切的实例对象不过是从原型对象衍生出的子对象,只不过在后来给它添加了特有的属性和要领罢了。

prototype chain

实例对象tony的__proto__指向组织函数Dog的prototype对象,因而继续了Dog中prototype的属性和要领;

而组织函数本身也存在__proto__指向更平常的函数(本质上也是对象)的prototype对象;

《JavaScript的创世神话——统统源于对象》

更进一步,该函数也存在__proto__指向最平常的组织函数Object的prototype对象

《JavaScript的创世神话——统统源于对象》

这类层层嵌套的关联构成一条原型链(prototype chain)。

一只名叫tony的狗,起首继续了组织函数Dog的原型对象,而Dog的原型对象中的__proto__有继续了函数的原型对象,函数对象中的__proto__有继续了Oject的原型对象。

这里再一次表现了组织函数Object的威力,一切的对象不过都是Object的衍生,均继续Object.prototype的属性和要领,越发深入表达“统统皆对象”的头脑。

4.一些相干的要领

  • instanceof 运算符
    instanceof运算符返回一个布尔值,示意指定对象是不是为某个组织函数的实例

tony instanceof Dog//true
or
Dog.prototype.isPrototypeOf(tony)//true
  • Object.getPrototypeOf()

Object.getPrototypeOf()返回一个对象的原型,这是猎取原型对象的规范要领

《JavaScript的创世神话——统统源于对象》

  • Object.setPrototypeOf()
    Object.setPrototypeOf

要领可认为现有对象设置原型,返回一个新对象,该要领接收两个参数,第一个是现有对象,第二个是原型对象。

var foo = { x:1 };
var bar = Object.setPrototypeOf({},foo)
bar.x === 1//true

我们之前以new敕令去构建实例对象,本质上就是把一个空对象的proto指向组织函数的prototype,然后在实例对象上实行组织函数

var  Person = function(){
    this.race = 'monkey'
};
var Asian = new Person();
//等价于
var Asian = Object.setPrototypeOf({},Person.prototype);
Person.call(Asian)
  • Object.create()
    Object.create要领用于从原型对象天生新的实例对象,可以替换new敕令

var  Person = {
    race: 'monkey'
}
var Asian = Object.create(Person)
//等价于
var Person = function(){
    this.race='monkey'
}
var Asian = new Person()
  • Object.isPrototypeOf()
    对象实例的isPrototypeOf要领,用来推断一个对象是不是是另一个对象的原型。

var obj1 = {};
var obj2 = Object.create(obj1);
obj1.isPrototypeOf(obj2)//true
  • Object.prototype.hasOwnProperty()
    对象实例的hasOwnProperty要领返回一个布尔值,用于推断某个属性定义在对象本身,照样定义在原型链上。

var o = {
  name:'teren'
}
o.hasOwnProperty('name')//true
o.hasOwnProperty('toString')//false
Object.getPrototypeOf(o).hasOwnProperty('toString')//true
参考文献:

阮一峰-JavaScript规范参考教程
饥人谷进修笔记

    原文作者:teren
    原文地址: https://segmentfault.com/a/1190000007811303
    本文转自网络文章,转载此文章仅为分享知识,如有侵权,请联系博主进行删除。
点赞