面向过程:面向过程就是分析出解决问题需要的步骤,然后用函数把这些步骤一个个实现,使用的时候依次调用。面向过程的核心是解决问题的过程。
面向对象:面向对象就是把需要解决的问题分解成一个个对象,建立对象不是为了实现一个步骤,而是为了描述每个对象在解决问题中的行为,面向对象的核心是对象。
1、模块化更深,封装性强。
2、更容易实现复杂的业务逻辑。
3、更易维护、易复用、易扩展。
1、封装性:对象是属性(静态特征)和行为(动态特征)的结合体(封装体)。
2、继承性:父类(基类)的属性和行为可以派生到子类中。子类不需要重复定义。
3、多态性:同一个消息传递给不同的对象,得到的结果不同。
类:事物分为具体的事物和抽象的事物,当我们脑中出现“书”这个词的时候,可以大致想象到书的基本样貌特征,这个过程就是抽象,抽象出来的结果,就是类。
也就是说,类是具有相同属性和行为的对象的抽象。
对象:而当我们拿起手里的一本真实存在的书的时候,这本书有自己的书名、作者、页数等信息,像这种具体的事物,就是对象。
也就是说,对象是类的实例(类的具体体现)。
class关键字:用来定义一个类,在类中可以定义constructor()构造方法,用来初始化对象的成员。
定义类的方法:
class 类名 { constructor([参数]) { //构造方法:用来初始化对象的成员 //方法体; } }
示例:
class Student { //使用class关键字定义类 constructor(na, a) { //构造方法:用来初始化对象的成员 this.name = na; this.age = a; } }
其中,“this.name”中的name是对象的属性
语法为:
var 对象名 = new 类名([参数]);
示例:假设之前已经定义了一个Person类,里面有name属性,用以下的方法就可以创建对象并访问
// 利用类创建对象 var p1 = new Person('张三');// 创建p1对象 var p2 = new Person('李四');// 创建p2对象 console.log(p1.name);// 访问p1对象的name属性 console.log(p2.name); // 访问p2对象的name属性
对象成员(包括属性和方法)的访问,语法如下:
对象名.属性名
或者:
对象名.方法名([参数])
注意:在ES6中constructor构造方法不能显式调用
在下面的例子中定义了一个Say()方法,并对方法进行了调用
示例:
class Person {//定义一个Person类 constructor(name) { this.name = name;//初始化对象的成员 } say() { // 在类中定义一个say()方法 console.log("你好,我叫" + this.name); } } var p1 = new Person("橘猫吃不胖"); p1.say();
结果为:你好,我叫橘猫吃不胖
继承:在JavaScript中,继承用来表示两个类之间的关系,子类可以继承父类的一些属性和方法,在继承以后还可以增加自己独有的属性和方法。
父类:又称为基类或超类,被继承的类
子类:又称为派生类,由父类派生来的类
继承的实现:extends
语法为:
class 子类名 extends 父类名 { constructor() { } //其他的成员方法 }
示例:定义父类和子类
// 先准备一个父类 class Father { constructor() { } money() { console.log(100); } } // 子类继承父类 class Son extends Father { }
调用父类中的方法:
// 创建子类对象 var son = new Son(); son.money();
结果为:100
super关键字:super关键字用于访问和调用对象在父类上的方法,可以调用父类的构造方法,也可以调用父类的普通方法。也就是说,uper关键字代表父类,用来访问和调用父类的成员。
调用父类的构造方法:在子类的构造方法中调用父类的构造方法。 在继承中,创建子类对象时必须先调用父类的构造方法,然后再调用子类的构造方法,并且父类构造方法的调用必须是子类构造方法中第一条语句。
调用父类的构造方法语法:
super([参数]);
调用父类的普通方法:
super.方法名([参数])
示例:在子类中添加特有的方法
class Father {//定义一个父类 constructor(x, y) {//初始话对象的成员 this.x = x; this.y = y; } sum() {//定义一个方法 console.log(this.x + this.y); } } class Son extends Father {//子类Son继承父类Father constructor(x, y) { super(x, y); // super必须在子类的this之前调用 this.x = x; this.y = y; } subtract() {// 定义一个子类特有的方法 console.log(this.x - this.y); } } var son = new Son(5, 3);//实例化对象 son.sum(); // 输出结果:8 son.subtract(); // 输出结果:2
结果为:8 2
实例成员:对象成员
静态成员:所有对象共享的成员,不属于某个具体的对象,又称为类成员
ES6中访问:
类名.成员名
ES5中访问:
构造方法名.成员名
在ES5中定义类:通过构造函数实现
示例:
function Student(name, age) { //构造函数,建议首字母大写,Student可以看作类 this.name = name; this.age = age; }
创建类的对象:
var s1 = new Student("张三", 19);
设计雇员Employee类,记录雇员的情况,包括姓名、年薪、受雇时间,要求定义MyDate类作为受雇时间,其中包括工作的年、月、日,并用相应的方法(构造方法、显示信息的方法)对Employee类进行设置。
class MyDate {//定义MyData类作为受雇时间 constructor(year, month, date) {//年、月、日 //初始化对象的成员 this.year = year; this.month = month; this.date = date; } show() {//构造显示受雇时间的方法 console.log(this.year + "年" + this.month + "月" + this.date + "日") } } class Employee {//定义雇员类 constructor(name, salary, workDate) {//姓名、薪资、受雇时间 this.name = name; this.salary = salary; this.workDate = workDate; } disp() {//构造显示姓名、年薪、受雇时间的方法 console.log("姓名:" + this.name); console.log("年薪:" + this.salary); console.log("受雇时间:"); this.workDate.show() } } var work1 = new MyDate(2021, 6, 15);//创建受雇时间对象 var e1 = new Employee("周瑜", 400000, work1);//创建雇员对象 e1.disp();