基本写法
class myObj {
constructor(arg1,arg2){
this.arg1 = arg1;
this.arg2 = arg2; //这是该对象的属性,this指向myObj本身
} // 这是类的构造函数
myMethod () {
...doSomeThing
} //这是对象的方法
}
//调用时
let obj = new myObj(arg1,arg2) // 传入的arg1,arg2将自动绑定到构造函数的属性上
ES6的class语法基本上就是基于以前ES5构造函数的包装函数,也可以叫做语法糖,所有的功能都能用ES5做到,值得注意的是Class不存在变量提升,所以得先构造类,再进行类的实例化
再谈_proto_
和prototype
第一,从变量名就可以看出,一个是私有(不愿意公开)的变量,一个是显式的变量
所以_proto_
又叫隐式原型
,prototype
又叫显示原型
-
_proto_
隐式原型指向创建这个对象的函数(constructor)的prototype, 关键词 to the value of its constructor’s "prototype",所以由一个类实例出来的多个对象的_proto_
属性都是指向class
里构造函数的prototype属性的。
-
prototype
指向实例本身的prototype属性
个人理解
使用
_proto_
是为了实现方法的继承(children 全部 继承自同一个parent),而使用prototype
是为了实现属性的自定义(修改单个实例中的属性不会修改到所有的)
请仔细看下图
Class的继承
class a extends b {}
表示 a继承b (b是父,a是子)
class Human {
constructor (name,age) {
this.name = name // this指向Class 本身
this.age = age
} // constructor 就是构造函数
sayName () {
alert(this.name) // 调用对象里的属性
}
sayAge () {
alert(this.age)
}
}
//下面的Student继承自Human
class Student extends Human {
constructor (name,age,id){ //这里必须传入name,age 不然实例化出来的对象没法设置name和age
super(name,age) //调用父类中的 构造函数
this.id = id //自定义子类的属性
}
sayId () {
alert(this.id)
}
}
let yzy = new Student('yzy','23','1513011')
yzy.sayId() //1513011
yzy.sayName() //yzy
yzy.sayAge() // 23
值得注意的是必须在构造函数里面调用super
关键词,因为子类里面没有创建this
,必须得调用父类的this
并做加工才能实现继承。如果不调用super方法,子类就没有this对象
关注原型链
如上图代码有
Student._proto_
=== Human // true
Student.prototype._proto_
=== Human.prototype //true
getter和setter
getter
和setter
关键字可以对某个属性设置存值和取值函数,例如
class myGetSet {
constructor() {
this.props = 'default'
}
get getProp() {
return 'getter:' + this.props
}
set setProp(val) {
this.props = val
console.log('set:' + val)
}
}
get/set
是关键字
getProp
函数返回了对象的props属性值
setProp
函数可以传参数设置props的值
至于get/set的好处
可以参考
http://stackoverflow.com/questions/1568091/why-use-getters-and-setters 英文
https://www.zhihu.com/question/21401198 中文(知乎)
具体总结以下几点
- 可以在存值和取值的时候增加其他功能(验证,计算值处理,算数表达式等)
- 可以保持外部接口不变的情况下,修改内部存储方式和逻辑
- 任意管理变量的生命周期和内存存储方式
- 提供一个debug接口
- 能在读写数据的时候下断点
- 允许继承者改变语义
- getter和setter可以有不同的访问级别
(部分摘自知乎)
静态属性和静态方法
静态的方法是绑定在类
上面的,不会被实例
继承,也就是说实例调用不到静态方法,静态方法的this
是指向类本身
,所以可以直接通过类调用。静态属性的定义也基本如此。