1.面向对象三大特征
1.封装:将某个具体的功能封装在对象中,只对外部暴露指定接口,外界在使用的时候,只考虑接口怎么用,不用考虑内部怎么实现(函数的封装,api)
2.继承:一个函数拥有其他对象的属性和方法
3.多态:一个对象在不同情况下的多种状态
//示例:饲养员给动物喂食物
//动物
function Animal ( name ) {
this.name = name;
};
//猫
let cat = new Animal('猫咪');
cat.eat = function ( food ) {
console.log ( "喵喵猫" + "我吃了" + food );
};
//狗
let dog = new Animal('小狗狗');
dog.eat = function ( food ) {
console.log ( "汪汪汪" + "我吃了" + food );
};
//饲养员
function Person ( name ) {
this.name = name;
};
Person.prototype.work = function (animal,food ) {
//animal接收一个由Anmiaml构造函数生成的实例化对象,调用它的eat方法
//同一对象表现出来不同的状态,就叫做多态
animal.eat(food);
};
let p1 = new Person('酸奶');
p1.work(cat, '饼干');
p1.work(dog, '翔');
//继承:让一个对象拥有另一个对象的属性和方法
//父对象
let father = {
house : {
address:'武汉天地',
price : 10000000
},
car:{
brand:'劳斯莱斯幻影',
price:8000000
}
}
//子对象构造函数
function Son(name,age){
this.name = name
this.age = age
}
//默认原型
Son.prototype.eat = function(){
console.log('吃东西')
}
/* 替换原型继承: 把父对象作为子对象构造函数的原型*/
Son.prototype = father
let son1 = new Son('大哥',30)
let son2 = new Son('二哥',20)
console.log(son1,son2)
2.原型链
1.原型链:每一个对象都有原型,原型本身又是对象,所以原型又有原型,以此类推形成一个链式结构,称为原型链
2.对象访问原型链中的成员规则:就近原则
- 当访问一个对象的成员变量时,会首先访问它自身的成员变量,如果有则访问。没有则在原型中寻找,能找到就访问,不能找到则继续往原型的原型中寻找,以此类推,如果找到原型链的顶端还是找不到,则程序报错:
xxx is not a function
//1.构造函数
function Person(name,age){
this.name = name;
this.age = age;
};
//2.原型对象
Person.prototype.sayHi = function(){
console.log('人生若只如初见,何事秋风悲画扇');
};
Person.prototype.type = '哺乳动物';
//3.实例化对象
let p1 = new Person('又又',18);
console.log(p1);
//请说出以下代码执行结果
console.log(p1.name);//又又 p1自己有name属性
console.log(p1.type);//哺乳动物 p1自己没有type,但是p1的原型有
console.log(p1.hobby);//undefined p1自己没有hobby,原型也没有
p1.sayHi();// 人生若只如初见,何事秋风悲画扇 p1自己没有这个方法,原型有
// p1.eat();//报错 xxx is not defined p1自己没有这个方法,原型也没有
//为什么不报错? p1自己没有这个方法,原型也没有这个方法,但是原型的原型有
p1.toString();
//查看p1的原型链
console.log(p1.__proto__.constructor);//Person
console.log(p1.__proto__ === Person.prototype);//true
//查看p1的原型的原型
console.log(p1.__proto__.__proto__.constructor);//Object
console.log(p1.__proto__.__proto__ === Object.prototype);//true
//查看p1的原型的原型的原型
console.log(p1.__proto__.__proto__.__proto__);//null
3.原型链详解
-
1.通过查看Array的原型链
- 了解构造函数的原型本身是一个对象,只要是对象就有原型
-
2.通过查看Date的原型链
- 学会举一反三,所有的内置对象(Math Array 基本包装类型等)的原型链都是一样的,最终都指向Object
-
3.通过查看String的原型链:了解这里的String值得是内置对象String(是一个基本包装类型),其他的Number、Boolean原型链和String是一样的
- 只有对象才有原型,这里一定要把基本数据类型string、number、boolean,和基本包装类型(特殊的引用类型对象)String、Number、Boolean区分开来,不要搞混淆
1.Array的原型链
2.Date的原型链
3.String对象原型链
4.Dom数对象原型链
5.instanceof运算符
- nstanceof语法:
对象instanceof构造函数 - 作用:检测构造函数的原型prototype在不在这个对象的原型链上
//1.示例
let arr = [10,20,30];
//数组原型链 arr->Arr.prototype->Object.prototype->null
console.log ( arr instanceof Array );//true
console.log ( arr instanceof Object );//true
//2.示例
//根据instanceof语法:左边Function表示对象,右边Function表示构造函数
//Function原型链 Function对象->Function.prototype->Object.prototype->null
console.log ( Function instanceof Function );//true
console.log ( Function instanceof Object );//true
//3.示例
//根据instanceof语法:左边Object表示对象,右边Object表示构造函数
//Object原型链 Object对象->Function.prototype->Object.prototype->null
console.log ( Object instanceof Object );//true
console.log ( Object instanceof Function );//true