js中的原型链
我们先来了解一下原型链中涉及到的知识的基本概念!
原型对象
1.原型是包含特定类型的所有实例共享的属性和方法。
2.原型对象的好处是,可以让所有实例对象共享它所包含的属性和方法。
3.每创建一个函数都会有一个prototype属性,这个属性是一个指针,指向一个对象(通过该构造函数创建实例对象的原型对象)。
注:所有对象的祖先级原型都为Object.prototype
构造函数
是一种特殊的方法。主要用来在创建对象时初始化对象, 即为对象成员变量赋初始值,总与new运算符一起使用在创建对象的语句中。
实例化对象
1.在面向对象的编程中,通常把用函数创建对象的过程称为实例化。
2.实例化对象就是创建对象的过程!
栈区与堆区
1.JavaScript中的内存也分为栈内存和堆内存。一般来说,栈内存中存放的是存储对象的地址,而堆内存中存放的是存储对象的具体内容。
2.(1)对于原始类型(基本类型)的值而言,其地址和具体内容都存在栈内存中;基本类型如果是全局的,也放在堆上。
(2)对于引用类型的值,其地址存在栈内存,其具体内容存在堆内存中。
而且,位于引用类型内的基本类型,也是放在堆上。
3.堆内存与栈内存是有区别的,栈内存运行效率比堆内存高,空间相对推内存来说较小,反之则是堆内存的特点。所以将构造简单的原始类型值放在栈内存中,将构造复杂的引用类型值放在堆中而不影响栈的效率。
画张原型图,深刻理解一下:
在上面这张原型图中,左边为栈区,右边为堆区;
为了理解原型,我们主要看一下堆区里面的东西。从上往下看:
所有的函数(普通函数和构造函数)在内存中都有两块,一块是它本身,另一块是它的原型
第一步:∵每一个对象的祖先级原型都为Object.prototype
∴画上Object B001及其原型Object.prototype B002
第二步:画一个构造函数Student及其原型
注:在每一个构造函数中都会有一个指针prototype指向原型,原型中也会有一个指针construcor指向构造函数,来证明两者之间的关系
第三步:实例化两个对象stu1,stu2
构造函数在进行实例化对象时,实例化的对象中会有一个属性__proto__指向构造函数的原型,从而方便调用父原型中的方法,即继承
重点理解一下 下面这几句话(实操为下面代码的第四、五、六、七步)
1.如果要调用实例化对象(stu1,stu2)中属性,会先在实例化对象中寻找;
2.如果找不到,就会通过__proto__去调用父原型中的属性;
3.如果父原型中也没有,就在通过__proto__去调用爷爷级原型中的属性;
4.以此类推,如果最终调用Object原型中也找不到,就会返回undefined。
举个例子,深入理解一下原型
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta http-equiv="X-UA-Compatible" content="ie=edge">
<title>原型</title>
</head>
<body>
<script>
//构造函数
function Student(){
this.name=name;
this.age= "age";
}
//实例化对象
var stu1=new Student();
var stu2=new Student();
console.log("学生1:",stu1.school);
console.log("学生2:",stu2.school);
//给原型中的学校定义一个属性
Student.prototype.school="山西农业大学";
console.log("学生1:",stu1.school);
console.log("学生2:",stu2.school);
//改变stu1中的属性值
stu1.school="太原理工大学";
console.log("学生1:",stu1.school);
console.log("学生2:",stu2.school);
</script>
</body>
</html>
分析一波:
1.创建了一个Student构造函数
2.实例化对象stu1,stu2
3.如果直接输出stu1,stu2的school属性,则会返回undefined
4.我们给构造函数Student的原型设置school=“山西农业大学”
5.再输出stu1,stu2的school属性,就会返会 山西农业大学
//第四步,第五步主要证明:在调用实例化对象中属性时,实例化对象中没有,则会调用父原型中的属性。
6.我们再去改变stu1中的school属性为"太原理工大学"
7.再去输出stu1,stu2的school属性,就会返回 学生1:太原理工大学
学生2:山西农业大学
从控制台查看输出结果为: