持续的意思和操作,es6学学笔记12

类继承:

三番七遍的含义和操作

Class基本语法

接轨的主见在于,充份利用原来就有类的功效,在其幼功上来扩展来定义新的类。

先天学习了面向对象的世襲意义和有个别操作,继承,分为父类和子类,父类的某些公共数据都足以让子类举行应用,而私有化的数量,子类将不能够使用。Class
Person()与class Man(Person)那样正是Class Man(Person)是Class
Person的子类,父类Class
Person中的公共数据,都能够让子类进行应用,等于是将父类的数额赋值给子类,通过内部存款和储蓄器地址实行三回九转,世袭还会有多三番一回,多个父类能够被三个子类世襲,收缩了代码的重复使用,使代码更加的精简。

概述

JavaScript语言的看法格局是因而构造函数,定义并生成新对象。下边是一个例证。

function Point(x,y){
  this.x = x;
  this.y = y;
}

Point.prototype.toString = function () {
  return '(' + this.x + ', ' + this.y + ')';
};

地方这种写法跟守旧的面向对象语言(比方C++和Java卡塔尔差距一点都不小,相当的轻易让新学习那门语言的程序猿以为纳闷。

ES6提供了更宛如古板语言的写法,引进了Class(类卡塔 尔(英语:State of Qatar)这几个概念,作为靶子的模版。通过class根本字,能够定义类。基本上,ES6的class能够当作只是贰个语法糖,它的多边功效,ES5都足以造成,新的class写法只是让对象原型的写法越发分明、更像面向对象编制程序的语法而已。上面的代码用ES6的“类”改写,便是底下那样。

//定义类
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其一至关心器重要字,直接把函数定义放进去了就足以了。别的,方法之间无需逗号分隔,加了会报错。

构造函数的prototype天性,在ES6的“类”上边继续存在。事实上,类的享有办法都定义在类的prototype本性上边

class Point {
  constructor(){
    // ...
  }

  toString(){
    // ...
  }

  toValue(){
    // ...
  }
}

// 等同于

Point.prototype = {
  toString(){},
  toValue(){}
};

在类的实例上边调用方法,其实正是调用原型上的办法。

class B {}
let b = new B();

b.constructor === B.prototype.constructor // true

类的在那之中有着定义的法门,都以成千成万的(non-enumerable卡塔尔国。

 

后续是面向对象的一个要命重大的特征,通过贰个档案的次序对另三个体系的连续,能够使代码重复利用,同一时间也压实了代码的功效上的扩张,继承的语法使用Class,在Python中,一切皆对象,都足以向来或许直接的去继续(object卡塔 尔(英语:State of Qatar)对象

constructor方法

constructor艺术是类的暗许方法,通过new命令生成对象实例时,自动调用该形式。叁个类必得有constructor方法,倘诺未有显式定义,叁个空的constructor主意会被暗中同意加多。

constructor艺术暗中同意再次来到实例对象(即this卡塔尔,完全能够钦命再次来到其它二个对象。

class Foo {
  constructor() {
    return Object.create(null);
  }
}

new Foo() instanceof Foo
// false

上边代码中,constructor函数重回三个全新的指标,结果产生实例对象不是Foo类的实例。

Parent Class(父类)
与 Child Class(子类):

父类,就是被一而再一连的类,称为父类,基类,超类。子类是持续了父类的类,称为子类,可能派生类。子类从父类世襲公共的品质和公共措施,不能继续私有化的数量,子类能够继续父类,父类还是能三回九转三番两次父类。三个子类能够同一时候继续几个父类,同理能够运用三个父类的国有性质和国有艺术,假若父类中冒出相通的性质和办法的话,使用_mro_来查看优先继承权,世袭中父类尽量不要用重新的天性和办法。

类的实例对象

生成类的实例对象的写法,与ES5截然豆蔻梢头致,也是运用new命令。如若忘记加上new,像函数这样调用Class,将会报错。

// 报错
var point = Point(2, 3);

// 正确
var point = new Point(2, 3);

与ES5同意气风发,实例的性格除非显式定义在其自己(即定义在this指标上卡塔尔国,不然都以概念在原型上(即定义在class上)。

与ES5一样,类的兼具实例分享二个原型对象。

那也象征,可以透超过实际例的__proto__属性为Class增加措施。

var p1 = new Point(2,3);
var p2 = new Point(3,2);

p1.__proto__.printName = function () { return 'Oops' };

p1.printName() // "Oops"
p2.printName() // "Oops"

var p3 = new Point(4,2);
p3.printName() // "Oops"

地点代码在p1的原型上增加了贰个printName方法,由于p1的原型正是p2的原型,因此p2也得以调用那些法子。况兼,今后新建的实例p3也得以调用这几个措施。那象征,使用实例的__proto__质量改写原型,必需风度翩翩对风华正茂稳重,不引入应用,因为那会改造Class的原本定义,影响到持有实例。

被接续的类称为父类,世襲的类称为子类,一个父类,能够有八个子类;

子类是三回九转父类的,可是子类也足以再度定义父类的留存的方法,那称之为重写,重写浮现了子类的独立性还应该有可变性,也称之为(多态卡塔 尔(英语:State of Qatar),方法重写有三个标准1:世袭的关联。2:父类存在的主意。3:子类重新定义

name属性

鉴于精气神儿上,ES6的Class只是ES5的构造函数的生机勃勃层包装,所以函数的累累特点都被Class世袭,富含name属性。

class Point {}
Point.name // "Point"

name属性总是回到紧跟在class重视字背后的类名。

子类,风度翩翩旦延续父类,就具有了父类的脾性与措施,依照要求能够开展增加和删除改。

自家对后续的驾驭便是,父类中的方法和总体性有众多,不过子类只关心要求的诀窍和性质,父类中寄存的类似都是有些集体的情节,升高代码的复用性,子类能够随即世襲父类中的公共艺术和剧情。

Class表达式

与函数相通,Class也足以使用表明式的款式定义。

const MyClass = class Me {
  getClassName() {
    return Me.name;
  }
};

地方代码应用表明式定义了三个类。须求注意的是,这些类的名字是MyClass而不是MeMe只在Class的内部代码可用,指代当前类。

let inst = new MyClass();
inst.getClassName() // Me
Me.name // ReferenceError: Me is not defined

上面代码表示,Me只在Class内部有定义。

风姿洒脱旦Class内部没用到的话,可以差不离Me,相当于能够写成上边包车型地铁方式。

const MyClass = class { /* ... */ };

运用Class表达式,能够写出当下施行的Class。

let person = new class {
  constructor(name) {
    this.name = name;
  }

  sayName() {
    console.log(this.name);
  }
}('张三');

person.sayName(); // "张三"

上面代码中,person是叁个及时施行的Class的实例。

这种做法的根本收益之黄金时代正是代码重用。

后续有几点注意:

不设有变量提高

Class不设有变量提高(hoist卡塔 尔(英语:State of Qatar),那一点与ES5一心分歧。

new Foo(); // ReferenceError
class Foo {}

地点代码中,Foo类使用在前,定义在后,那样会报错,因为ES6不会把变量注脚提高到代码底部。这种规定的开始和结果与下文要提到的接二连三有关,必得保证子类在父类之后定义。

 

1.私局地属性,无法透过对象直接待上访谈,不过足以因而艺术来访谈。

Class的继承

演示代码1:

2.私片段艺术,不能够通过对象直接待上访谈。

主导用法

Class之间能够经过extends关键字兑现持续,那比ES5的通过修正原型链达成三回九转,要明晰和福利广大。

class ColorPoint extends Point {}

上边代码定义了四个ColorPoint类,该类通过extends关键字,继承了Point类的有着属性和措施。可是由于还未有配备任何代码,所以那多少个类完全等同,等于复制了三个Point类。下面,我们在ColorPoint在那之中加上代码。

class ColorPoint extends Point {
  constructor(x, y, color) {
    super(x, y); // 调用父类的constructor(x, y)
    this.color = color;
  }

  toString() {
    return this.color + ' ' + super.toString(); // 调用父类的toString()
  }
}

上边代码中,constructor方法和toString方法之中,都现身了super至关重要字,它在这里间代表父类的构造函数,用来新建父类的this对象。

子类必得在constructor办法中调用super方法,要不然新建实例时会报错。这是因为子类未有团结的this对象,而是继续父类的this对象,然后对其展开加工。若果不调用super措施,子类就得不到this对象。

class Point { /* ... */ }

class ColorPoint extends Point {
  constructor() {
  }
}

let cp = new ColorPoint(); // ReferenceError

地点代码中,ColorPoint世袭了父类Point,可是它的构造函数未有调用super格局,导致新建实例时报错

#*_*coding:utf-8*_*

class perent_class(object):
    def __init__(self,name):
        self.name = name

    def printName(self):
        print('你的名字是:'+self.name)


class child_class(perent_class):
    def __init__(self,name,age):
        super(child_class,self).__init__(name) #初始化类super()函数返回类对象
        self.age = age


if __name__=="__main__":
    child_class('xzdylyh','25').printName()

3.私有的属性,方法不会被子类世襲,也不能够被访谈。

类的prototype属性和__proto__属性

超过四分之二浏览器的ES5落实之中,每叁个指标都有__proto__属性,指向对应的构造函数的prototype属性。Class作为构造函数的语法糖,同不时间有prototype属性和__proto__质量,因而同期存在两条世袭链。

(1)子类的__proto__质量,表示构造函数的持续,总是指向父类。

(2)子类prototype属性的__proto__品质,表示方法的存在延续,总是指向父类的prototype属性。

class A {
}

class B extends A {
}

B.__proto__ === A // true
B.prototype.__proto__ === A.prototype // true

地点代码中,子类B__proto__属性指向父类A,子类Bprototype属性的__proto__质量指向父类Aprototype属性。

那般的结果是因为,类的继续是遵照上边包车型大巴形式达成的。

class A {
}

class B {
}

// B的实例继承A的实例
Object.setPrototypeOf(B.prototype, A.prototype);

// B继承A的静态属性
Object.setPrototypeOf(B, A);

输出

4.貌似景况下,私有的性质,方法都以不对外宣布的,往往用来做内部的政工,起到平安的左右和遵守

Object.getPrototypeOf()

Object.getPrototypeOf艺术能够用来从子类上收获父类。

Object.getPrototypeOf(ColorPoint) === Point
// true

因此,能够运用这几个主意推断,多少个类是还是不是继续了另贰个类。

C:Python27python.exe D:/weixin/temp/temp.py
你的名字是:xzdylyh

Process finished with exit code 0

�������rz�+��

super关键字

super这么些重中之重字,有三种用法,含义不相同。

(1)作为函数调用时(即super(...args)),super表示父类的构造函数。

(2)作为对象调用时(即super.propsuper.method()),super意味着父类。注意,那个时候super即能够引用父类实例的习性和章程,也足以援用父类的静态方法。

 

 

原生构造函数的三番两次

原生构造函数是指语言内置的构造函数,平日用来生成数据结构。ECMAScript的原生构造函数大概有下边这个。

  • Boolean()
  • Number()
  • String()
  • Array()
  • Date()
  • Function()
  • RegExp()
  • Error()
  • Object()

以前,那个原生构造函数是爱莫能助持续的,ES6同意继续原生构造函数定义子类,因为ES6是先新建父类的实例对象this,然后再用子类的构造函数修饰this,使得父类的享有行为都得以三番三遍。下边是三个世袭Array的例子。

class MyArray extends Array {
  constructor(...args) {
    super(...args);
  }
}

var arr = new MyArray();
arr[0] = 12;
arr.length // 1

arr.length = 0;
arr[0] // undefined

地点代码定义了叁个MyArray类,继承了Array构造函数,因而就能够从MyArray生成数组的实例。这意味,ES6得以自定义原生数据结构(举例Array、String等卡塔尔的子类,那是ES5不可能到位的。

地点那个事例也表达,extends根本字既可以够用来世襲类,仍然是能够用来持续原生的构造函数。由此得以在原生数据结构的根基上,定义自个儿的数据结构。

当子类与父类下方法同样时,子类会覆盖父类的法门内容;其实这便是生龙活虎种重写,也是黄金年代种多态。

Class的静态方法

类相当于实例的原型,全部在类中定义的办法,都会被实例世袭。假使在三个办法前,加上static器重字,就表示该方法不会被实例世袭,而是一贯通过类来调用,那就叫做“静态方法”。

class Foo {
  static classMethod() {
    return 'hello';
  }
}

Foo.classMethod() // 'hello'

var foo = new Foo();
foo.classMethod()
// TypeError: undefined is not a function

上边代码中,Foo类的classMethod主意前有static重在字,注明该办法是三个静态方法,能够一贯在Foo类上调用(Foo.classMethod()卡塔尔,并非在Foo类的实例上调用。若是在实例上调用静态方法,会抛出三个不当,表示荒诞不经该措施。

父类的静态方法,能够被子类世袭。

class Foo {
  static classMethod() {
    return 'hello';
  }
}

class Bar extends Foo {
}

Bar.classMethod(); // 'hello'

地点代码中,父类Foo有叁个静态方法,子类Bar能够调用这么些形式。

静态方法也是足以从super指标上调用的。

new.target属性

new是从构造函数生成实例的命令。ES6为new一声令下引进了二个new.target属性,(在构造函数中卡塔尔国重回new指令成效于的卓殊构造函数。要是构造函数不是透过new指令调用的,new.target会返回undefined,因而那特性情能够用来分明构造函数是怎么调用的。

 

发表评论

电子邮件地址不会被公开。 必填项已用*标注