面向对象
面向对象 vs 面向过程
- 面向过程
- 步骤清晰简单,第一步做什么,第二部做什么….
- 面向过程适合处理一些较为简单的问题
- 面向对象思想
- 物以类聚,分类的思维模式,思考问题首先会解决问题需要那些分类,然后对这些分类进行单独思考。最后,才对某个分类下的细节进行面向过程的探索。
- 面向对象适合处理复杂问题,适合处理需要多人协作的问题。
- 面向对象变成(Object-Oriented Programming, OOP)
- 面向对象变成的本质就是:以类的组织方式代码,以对象的组织(封装)数据
- 抽象
- 三大特性
- 封装
- 继承
- 多态
- 从认识论的角度考虑现有对象后有类。对象,是具体的食物。类,是抽象的,是对对象的抽象
-
方法调用
static 与类同时加载,而非static 在类实例化之后加载,因此非static无法被直接引用,需要通过new进行实例化
值传递
package com.java.Object;public class Value {public static void main(String[] args) {int a =1;System.out.println(a); // 1change(a);System.out.println(a); // 1}public static void change(int a) {a = 10;// return a;}}
package com.java.Object;// 对象,内存// 引用传递: 对象,本质还是值传递public class ObjValue {public static void main(String[] args) {Person person = new Person();System.out.println(person.name); // null\change(person);System.out.println(person.name); // xiaoyi}public static void change(Person person) {// person是一个对象; 它指向的是Person的实例person.name = "xiaoyi";}}// 定义一个Person类 有一个属性:nameclass Person {String name; // 默认值为null}
类与对象的关系
- 类是一种抽象的数据类型,它是对一类事物整体描述/定义,但并不能代表某一个具体的事物
- 动物、植物、手机、电脑…
- Person类、Pet类、Car类等,这些类都是用来描述/定义某一类具体事物应该具备的特点和行为
对象是抽象概念的具体实例
使用new关键字创建对象
- 使用new关键字创建对象的时候,除了分配内存空间之外,还会给创建好的对象 进行默认的初始化以及对类中的构造器调用
- 类中的构造器也称为构造方法,是在进行创建对象的时候必须调用的。并且构造器有以下两个特点:
- 必须和类的名字相同
- 必须没有返回值,也不能写void
- 构造器必须要掌握 ```java package com.xy.app;
public class Appliction { public static void main(String[] args) { // 类: 抽象的,需要实例化 // 类实例化之后会返回一个自己的对象 // student 对象就是一个Student类的具体事例 Student student = new Student(); student.name = “xyz”; student.age = 30; System.out.println(student.name); // xyz System.out.println(student.age); // 30
Student xiaoming = new Student();System.out.println(xiaoming.age);// 0System.out.println(xiaoming.name);// null}
}
<a name="FxA4g"></a>#### 构造器- 用来初始化- 一个类即使什么都不写,也会存在一个方法- 构造器也可以重载,根据传不传参数调用不同的构造器- "alt + insert"快速生成构造器(Idea)```javapackage com.xy.app;// java文件 ---> class文件public class Person {String name;// 一个显式定义的构造器// 实例化初始值// 使用new 关键字,本质是在调用构造器public Person() {this.name = "xyz";}}--------------------// 实例化Person person = new Person();
package com.xy.app;// java文件 ---> class文件public class Person {String name;public Person(String name) {this.name = name;}}-----------------------------// 实例化Person person = new Person("张飞");
实例化对象的内存调用
封装
- 该露的露,该藏的藏
- 程序设计追求“高内聚,低耦合”。高内聚就是类的内部数据操作细节自己完成,不允许外部干涉;低耦合:仅暴露少量的方法给外部
- 封装(数据的隐藏)
- 通常,应该禁止访问一个对象中的实际表示,而应通过接口来访问,这成为信息隐藏。
- 记住:属性私有,get/set ```java package com.xy.app;
public class Teacher { private String name; private int age;
public String getName() {return this.name;}public void setName(String name) {this.name = name;}public int getAge() {return age;}public void setAge(int age) {if(age > 120) {this.age = 0;}else if(age <= 0) {this.age = 0;}this.age = age;}
}
package com.xy.app;
public class Appliction { public static void main(String[] args) { Teacher teacher = new Teacher(); teacher.getName(); teacher.setName(“张山”); teacher.setAge(999); //防止不合法的年龄 } }
<a name="k05mK"></a>### 继承- 继承的本质是对某一批对象的抽象,从而实现对现实世界更好的建模- extends的意思是扩展。子类就是父类的扩展- Java中只有单类继承,没有多类继承- 继承是类和类的一种关系。除此之外类和类之间的关系还有依赖、组合、聚合等。- 继承关系的两个类,一个为子类(派生类),一个为父类(基类)。子类继承父类,使用关键字extends来表示1. object类2. super1. super调用父类的构造方法,必须在构造方法的第一个2. super必须只能出现在子类的方法或构造函数中3. super和this不能同时调用构造方法4. this:本身调用这个对象;super:代表父类对象的应用3. 重写- 子类重写父类的方法,与属性无关- 父类的引用指向了子类(父类 对象 = new 子类();)- 只能重写非静态方法(@Override)- 方法名和参数列表必须相同- 修饰符:范围可以扩大,但是没可以缩小 public > protected > Default > private- 抛出的异常:范围可以被缩小,但是不能扩大 classNotFoundException --> Exception(大)> 为什么需要重写:> 1. 父类的功能,子类并不一定需要,或不能满足子类的需求<a name="XtPhS"></a>### 多态- 即同一个方法可以根据发送对象的不同而采用多种不同的行为方式- 一个对象的实际类型是确定的,但可以指向对象的引用类型有很多- 多态存在的条件- 有继承关系- 子类重写父类的方法- 父类引用指向子类对象- 多态是方法的多态,属性没有多态- 强制类型转换:可以由父类强制转化为子类(高转低)> 1. static 方法: 属于类,它不属于实例> 2. final 常量> 3. private方法```java// 一个对象的实际类型是确定的// new Person();// 可以指向的引用类型就不确定了: 父类的引用指向子类Sudent s1 = new Student();Person s2 = new Student();Object s3 = new Student();// 对象能执行那些方法主要看左边的类型// 左边有的可以用,没有不可以用;如果子类没有重写父类的方法,执行父类的方法// 父类不能调用子类单独存在的方法
- instanceof(类型转换) 引用类型,判断一个对象是什么类型 ```java Object obj = new Student(); // Student 是Person的子类,Teacher也是Perosn的子类
System.out.println(obj instanceof Student); // true System.out.println(obj instanceof Person); // true System.out.println(obj instanceof Object); // true System.out.println(obj instanceof Teacher); // false System.out.println(obj instanceof String);// false
// 同级引用之间无法使用instanceof Student stu = new Student(); System.out.print(stu instanceof Teacher); // 编译不了
// 强制类型转换 Student stu1 = new Student();
((Person)stu1).test();
Person per = stu1;
per.text(); // 无法使用 子类转化为父类自动转化,但是可能会丢失自己本来的一些方法
- 作用- 方便方法的调用,减少重复的代码!简洁<a name="I55xO"></a>### 抽象类- abstract修饰符可以用来修饰方法,也可以用来修饰类;如果用来修饰方法,那么该方法就是抽象方法;如果修饰类,那么该类就是抽象类- 抽象类中没有抽象方法,但是抽象方法的类一定要声明为抽象类- 抽象类,不能使用new 关键字来创建对象,它只能由子类来继承- 抽象方法,只有方法的声明,没有方法的实现,它是用来给子类继承的- 子类继承抽象类,那么就必须要实现抽象类没有实现的抽象方法,否则该子类也要声明为抽象类<a name="bVDJ5"></a>### 接口(interface)- 普通类: 只有具体实现- 抽象类: 具体实现和规范(抽象方法)都有- 接口: 只有规范 (约束和实现分离:面向接口编程)- 接口就是规范,定义的是一组规则,体现了现实世界中“如果你是......你必须......”的思想。如果你是一个人,你必须有良心。如果是一台车,必须能跑,必须有发动机。- 接口的本质是契约,就像我们人间的法律一样,制定好后大家一起遵守- OO的精髓,是对对象的抽象,最能体现这一点的就是接口,为什么我们讨论设计模式都只针对具备了抽象能力的语言(比如c++,java,c#等),就是因为设计模式所研究的,实际上就是合理的抽象```javapackage com.xy.app;/*第一个接口*/public interface Inter {// 默认带有 public abstractvoid add(String name);void update(String name);void del(String name);void query(String name);}-----------------------package com.xy.app;/*第二个接口*/public interface Service {void get(String id);}-----------------------package com.xy.app;// 抽象类: extends// 类 可以实现接口 implements 接口// 实现了接口的类,就需要重写接口中的方法// 利用接口,实现继承public class Im implements Inter, Service{@Overridepublic void get(String name){}@Overridepublic void add(String name) {}@Overridepublic void update(String name) {}@Overridepublic void del(String name) {}@Overridepublic void query(String name) {}}
