//1.3
let user = {
name: 'xx'.
get name() {
return this.name;
},
set name(value) {
this.name = value //這句話報錯了
}
};
user.name = "Peter"; //嘗試賦值的時候報錯Uncaught RangeError: Maximum call stack size exceeded
//解決方法
let user = {
_name:'xx',
get name() {
return this._name;
},
set name(value) {
this._name = value //設置一箇中轉變量
}
};
//1.4
class SetVar{
m=2;
set m(d){this.m=d}
}
let d=new SetVar();
d.m=99;//{m:99}
類方法之間不需要逗號分隔,加了會報錯
類的內部所有定義的方法,都是不可枚舉的(non-enumerable)。
class Point {
constructor(x, y) {
// ...
}
toString() {
// ...
}
}
Object.keys(Point.prototype)// []
類與模塊爲嚴格模式,不需要聲明 use strict;
類必須使用new調用,否則會報錯。這是它跟普通構造函數的一個主要區別,後者不用new也可以執行。
function m(){console.log(new.target===m)}
m()//false
new m()// true 通過這個可以強制函數通過new來調用
類不存在變量提升(hoist),這一點與 ES5 完全不同。
new Foo(); // ReferenceError
class Foo {}
方法多層嵌套,this指向問題解決
1.箭頭函數
2.重新賦值 如 let _t= this;
3.綁定this指向
class Logger {
constructor() {
this.printName = this.printName.bind(this);
}
// ...
}
基類默認構造方法
constructor() {}
派生類,默認構造函數
constructor(...args) {
super(...args);
}
//-------
class A {constructor(a){this.a=a;}};
class B extends A{}
new B(1)//{a:1}
派生類可以繼承父類的屬性與方法
類的實例化
調用 new 類名(參數a,b...),實際執行constructor構造方法,接收參數,實例化一個實例對象
類的所有實例共享一個原型對象 類名.prototype
繼承與覆蓋
class A {
x=1;
y(){}
z(){console.log('a')}
}
class B{
constructor(a){if(a){this.m=a;}}
m=2;
z(){console.log('b')}
}
let p= new B(9);//m值=9;
p.z();//'b' 覆蓋了父類的z方法
let p1= new B();// m值=2
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 Point {
// ...
}
typeof Point // "function" 類的數據類型就是函數
Point === Point.prototype.constructor // true 類本身就指向構造函數
類有prototype和__proto__ ,對象實例只有__proto__
function Foo(){}
let p= new Foo();
/*
p.__proto__===>Foo.prototype(其__proto__===>Object.prototype(其__proto__===>null))
Foo.prototype,Object.prototype,Function.prototype都是由構造函數創建的
自定義構造方法的__proto__=>Function.prototype(其__proto__==>Object.prototype)
見github 圖
*/