一、全局变量
window是全局变量(浏览器的叫法),EMCAScript规定全局变量是global。
window 是一个哈希表,有很多属性。
window的属性就是全局变量。
全局变量分成两种:
1.一种是 ECMAScript 规定的
- global.parseInt
- global.parseFloat
- global.Number
- global.String
- global.Boolean
- global.Object
2.一种是浏览器自己加的属性 - window.alert
- window.prompt
- window.comfirm
- window.console.log
- window.console.dir
- window.document
- window.document.createElement
- window.document.getElementById
二、简单类型和对象的区别
举例:1 与 new Number(1)
1是基本数据类型1(数值),存在stack(栈)内存里;
new Number(1)是通过New操作符创建了一个数值对象,存在Heap内存里;
为什么(1).toString() 可以输出数值1的字符串形式并且不报错?
因为在执行"(1).toString()" 时,其实是先把数据1包装成了一个temp对象(字符串对象),然后调用其原型链中的toString属性,在一行代码执行后,这个临时对象就被摧毁。
三、原型
为了节省内存空间,所以有了原型(即共用属性)
所有对象的原型:Object.prototype
每一个对象的 proto 存储这个「公用属性组成的对象」的地址。
重要公式:
var 对象 = new 构造函数()
对象.proto === 构造函数.prototype
四、原型链与继承
举例,
a=new Array()
a.push() //实例属性,因为a的类是Array,push方法是从Array中得到的。不是继承。
a.valueOf() //“继承”了Object的属性
继承的实质是:两次的原型搜索。
五、如何实现继承
简单来说,能造出一个【对象】的东西,就叫做“类”。
比如,下面的Human函数就是一个类,
给Human类一个共有属性
再写一个更具体的类,“Human”里面的“Man“
Man类
现在,我们来实现”继承“,让Man的_proto_指向Human.prototype,从而拥有run属性。另外,让Man拥有一个属性name
目标
Human.call(this,name) 将this(new的时候,this指Man实例)传进去,让this.name等于传进去的name。
如何实现
注意:IE不支持上面第二句的写法,须换成:
var f=function(){}
f.prototype=Human.prototype
Man.prototype=new f()
现在,我们来验证一下man每一层的原型链:
成功实现继承
从内存的角度来剖析:
关于继承的一张很重要的图
继承的两种写法:
- ES5:
function Human(name){
this.name = name
}
Human.prototype.run = function(){
console.log("我叫"+this.name+",我在跑")
return undefined
}
function Man(name){
Human.call(this, name)
this.gender = '男'
}
var f = function(){}
f.prototype = Human.prototype
Man.prototype = new f()
Man.prototype.fight = function(){
console.log('糊你熊脸')
}
ES 6 写法:
class Human{
constructor(name){
this.name = name
}
run(){
console.log("我叫"+this.name+",我在跑")
return undefined
}
}
class Man extends Human{
constructor(name){
super(name)
this.gender = '男'
}
fight(){
console.log('糊你熊脸')
}
}
网友评论