class的基本操作方法

JavaScript语言中,生成实例对象的传统方法是通过构造函数

function Point(x,y){
    this.x = x;
    this.y = y;
}
Point.prototype.toString = function(){
    return '(' + this.x + ', ' + this.y + ')';
};
var p = new Point(1,2);
 

基本上,ES6的class可以看作只是一个语法糖,它的绝大部分功能,ES5都可以做到,新的class写法只是让对象原型的写法更加清晰、更像面向对象编程的语法而已。上面的代码用ES6的class改写。

//定义类
class Point{
    constructor(x,y){
        this.x = x;
        this.y = y;
    }
    toString(){
        return '(' + this.x + ', ' + this.y + ')';
    }
}

  

 

上面代码定义了一个类,可以看到里面有一个constructor方法,这就是构造方法,而this关键字则代表实例对象。也就是说ES5的构造函数point,对应ES6的point类的构造方法。
Point类除了构造方法,还定义了一个toString方法。注意,定义类的方法的时候,前面不需要加上function这个关键字,直接把函数定义放进去就可以了。另外,方法之间不需要逗号分割,加了会报错。
ES6的类,完全可以看作构造函数的另一种写法。

class Point{
    //...
}
typeof Point//function
Point === Point.prototype.constructor//true;

  上面代码表明,类的数据类型就是函数,类本身就指向构造函数。

使用的时候,也就是直接对类使用new命令,跟构造函数的用法完全一致。

class Bar{
    doStuff(){
        console.log('stuff');
    }
}
var b = new Bar();
b.doStuff();

  

 

构造函数的prototype属性,在ES6的类上面继续存在。事实上,类的所有方法都定义在类的prototype属性上面。

class Point{
    constructor(){}
    toString(){}
    toValue(){}
}
//等同于
Point.prototype = {
    constructor(){},
    toString(){},
    toValue(){},
}
 

在类的实例上面调用方法,其实就是调用原型上的方法。

class B{}
let b = new B{};
b.constructor === B.prototype.constructor;
 

上面代码中,b是B类的实例,它的constructor方法就是B类原型的constructor方法。
由于类的方法都定义在prototype对象上面,所以类的新方法可以添加在prototype对象上面。Object.assign方法可以很方便地一次向类添加多个方法。

class Point{

constructor(){}

}
Object.assign(Point.prototype,{

 
toString(){},
toValue(){} 

})

prototype对象的constructor属性,直接指向类的本身,这与ES5的行为是一致的。

Point.prototype.constructor === Point//true.

另外,类的内部所有定义的方法,都是不可枚举的。

class Point{
    constructor(x,y){}
    toString(){}
}
Object.keys(Point.prototype);
Object.getOwnPropertyName(Point.prototype);

  

 

上面代码中,toString方法是Point类内部定义的方法,它是不可枚举的。这一点与ES5的行为不一致。

 
var Point = function(x,y){}
Point.prototype.toString=function(){}
Object.keys(Point.prototype);
//["toString"]
Obejct.getOwnPtopertyName(Point.prototype)
//["constructor","toString"]

上面代码采用ES5的写法,toString方法就是可枚举的。
类的属性名,可以采用表达式。

 
let methodName = 'getArea';
class Square{
    constructor(length){}
    [methodName](){}
}

Square类的方法名getArea,是从表达式得到的。

原文地址:https://segmentfault.com/a/1190000017212581

posted @ 2018-12-08 08:41  Mahmud(مەھمۇد)  阅读(403)  评论(0编辑  收藏  举报