Java06:面向对象编程
六、面向对象编程
(一)什么是面向对象
*OOP:面向对象编程(Object-Oriented Programming)
-
面向过程思想:
- 步骤清晰简单,第一步做什么、第二步做什么
- 适合处理一些简单的问题
-
面向对象思想:
- 物以类聚,分类的思维方式,思考解决问题所需要的分类,再对分类进行单独思考。最后,才对某个分类下的细节进行面向过程的思索。
- 适合处理复杂的问题,适合处理需要多人协作的问题。
- 为了从宏观上把握复杂事物,从整体上合理分析,我们需要用面向对象的思路来分析整个系统。但是,具体到微观操作,仍然需要面向过程的思路去处理。
-
面向对象编程的本质:抽象。以类的方式组织代码,以对象的方式封装数据。
-
三大特性:
- 封装
- 继承
- 多态
(二)02-03回顾方法的定义与调用
-
方法的定义:
- 修饰符
- 返回类型
- break:跳出当前循环
- return:返回值并结束方法
- 方法名:注意命名规范(驼峰),见名知意
- 参数列表:注意 可变长参数
- 异常抛出:保留
-
方法的调用:
- 静态方法
- 静态方法只能调用静态方法
- 非静态方法只能调用非静态方法
- 非静态方法
- 形参和实参
- 值传递和引用传递
- this关键字
- 静态方法
(三)04类与对象的创建
- 类与对象的关系:
- 类是一种抽象的数据类型,他是对某一类事物的具体描述/定义,但是不能代表某一个具体的事物。
- 动物、植物、手机、电脑
- Person类、Pet类、Car类等,只描述某一类具体事物应该具备的特点和行为
- 对象是抽象概念的具体事例
- 张三就是Person类的一个具体实例(对象)
- 能够体现出特点,展示出功能的就是具体的实例
- 类是一种抽象的数据类型,他是对某一类事物的具体描述/定义,但是不能代表某一个具体的事物。
- 使用new关键字创建对象
类名 对象名(标识符) = new 类名();
this.属性;//可调用当前文件中的类
- 注意事项:
- 一个包只留一个main方法用来执行程序、
类里尽量不留main方法
- 类应该是抽象的概念,所以应该谨慎赋予默认值
(四)05 构造器详解
*构造器必须要掌握,别名构造方法
-
构造器的特点:
-
和类名相同
-
public 类名(形参){ 赋值语句; } -
不能写返回值
-
-
作用:
-
使用new关键字,本质是在调用构造器
-
用来初始化值
-
-
注意点:
- 定义有参构造器之后,如果想使用无参构造器,必须重写一个无参的构造器
- alt +insert : 快捷键生成构造器
(五)06 创建对象内存分析
类只是一个模板,每次new一个对象,会分配不同的栈空间、堆空间,因此同一类的不同对象是不同的。
(六)07 简单小结类与对象
-
类与对象:
- 类是一个模板,是抽象的
- 对象是一个实例,是具体的,有参数的
-
方法的定义与调用:
-
对象的引用:
- 引用类型(其他)与基本类型(8个)
- 对象是通过引用来操作的:
- 对象的名字压入栈----->对象的值存入堆
-
属性:别名字段/成员变量
-
默认初始化的值:
- 数字: 0 0.0
- char: u0000
- boolean:false
- 引用:null
-
属性的定义:
修饰符 属性类型 属性名 = 属性值;
-
-
对象的创建和使用:
- 使用new 关键字+构造器创建对象
- 对象的属性: 对象名.属性名
- 对象的方法: 对象名.方法名(形参)
-
类:
- 属性:静态的特征
- 方法:动态的行为
-
Java三大特征:
- 封装
- 继承
- 多态
(七)08 封装详解
- 封装的内涵:
- 该露的露,该藏的藏:高内聚,低耦合。高内聚就是类的内部数据操作细节自己完成,不允许外部干涉。低耦合:仅暴露少量的方法给外部使用。
- 数据的隐藏:通常,应该禁止直接访问一个对象中数据的实际表示,而应该通过操作接口来访问,这称为信息隐藏
- 属性私有,get/set
- 封装的意义:
- 提高程序的安全性,保护数据
- 隐藏代码的实现细节
- 统一接口
- 提高系统的可维护性
(八)09 什么是继承
- 本质:对某一批类的抽象,从而实现对现实世界更好的建模。
- 关键字:extends,扩展。子类是父类的扩展。
修饰符 class 子类名 extends 父类名{
}
- 注意事项:
- 继承是类和类之间的一种关系。
- 继承关系:子类继承父类,用关键字extends表示
- 子类可以继承父类的方法和属性(public)
- JAVA中类只有单继承。(一个儿子只有一个爸爸,一个爸爸能有多个儿子)
- 在java中,所有的类,都默认直接或间接继承Object类
*修饰符种类:
- public
- protected
- default
- priva
(九)10 super详解
-
super关键字作用:
- 调用父类的方法,而不是调用子类的方法
-
注意事项:
-
new子类时:先进行父类的无参构造,再进行子类的无参构造(父类的无参构造必须在子类构造器的第一行)
-
super只能出现在子类的方法或构造方法中
-
super和this 不同同时调用构造方法
-
使用super时,必须保证父类有无参构造器,否则要显式构造父类如下:
-
父类私有的方法无法通过super调用
super(形式参数);//必须在子类构造器的第一行
-
-
super与this的区别:
- 代表的对象不同:
- this:正在调用着的对象(关键字所在的对象)
- super:代表父类对象
- 前提条件:
- this:在对象中即可调用,无需继承
- super:只有在继承了父类的子类中才能使用
- 构造方法:
- this():当前类的构造
- super():父类的构造
- 代表的对象不同:
(十)11 方法重写
- 定义:
- 存在于子类的方法之中,形参相同,方法名相同,但实现与同名的父类的方法不一样的功能(方法体不同).
- 快捷键:Alt+Insert,选择override(重写)
- 为什么需要重写:
- 父类的功能,子类不一定需要或者不能满足子类的需求.
-
注意事项:
- 方法重写必须用在非静态方法中
- 出现方法重写,IDEA中会有↑↓箭头提示
- 重写是方法的重写,和属性无关
- 静态方法的调用只和定义的数据类型有关(左值),方法不能重写;
-
前提条件:
-
要有继承关系,子类重写父类的方法
-
方法名必须相同
-
参数列表必须相同
-
修饰符要求:调用范围可以扩大,但不能缩小
public>Protected>Default>private -
抛出的异常:范围可以被缩小,但不能扩大
ClassNotFoundException < Exception
-
(十一)12 什么是多态
-
定义:
-
同一个方法可以根据发送对象的不同,采取不同的行为方式.即一个对象的实际类型时确定的,但可以指向对象的引用类型有很多.
-
动态编译:类型在执行时确定
-
eg.
-
子类只当父类用
father类 对象名 = new son类();
-
-
-
多态存在的条件:
- 有继承关系
- 子类重写父类的方法
- 父类引用指向子类对象
-
注意事项:
- 多态是方法的多态,属性没有多态性.
- 对象能执行的方法,看对象定义的类型(左值)
- 父类型可以指向子类,但不能调用子类独有的方法
- 没有联系的(非父类与子类)类型之间转换:报错,ClassCastException!
-
不存在多态的情况:
- static 方法名:当做类处理,不属于任何实例
- final 类型名 常量名:存入流量池,类型确定
- private 方法:
(十二)instanceof和类型转换
-
instanceof 关键字
- 作用:
判断一个对象是什么类型,即用来测试一个对象是否为一个类的实例.
- 用法:
boolean result = 对象名 instanceof 类名;//返回值为布尔值, //当 obj 为 Class 的对象,或者是其直接或间接子类,返回true //否则返回true- 注意事项:
- 将对象与没有父子关系的类型进行比较,会直接报错
-
引用类型转换
- 注意事项:
- 父类引用可以指向子类的对象
- 子类转换成父类:向上转型(自动类型转换)
- 父类转换成子类:向下转型(必须强制类型转换)
- 注意事项:
(十三)14 static关键字详解
-
定义:
- static是一个修饰符,用于修饰类的成员方法、类的成员变量,另外可以编写static代码块来优化程序性能;
- 被static关键字修饰的方法或者变量不需要依赖于对象来进行访问,只要类被加载了,就可以通过类名去进行访问
-
注意事项:
- 非静态方法可以调用静态方法,反之不行.这和加载顺序有关
- 被static修饰的静态方法可以被继承,但被final修饰的方法不可以被继承.
-
相关知识:
-
匿名代码块
-
静态代码块
-
构造器
-
eg
{ //匿名代码块 } static{ //静态代码块,只执行一次 } public 类名{ //构造器 } -
执行顺序:
- 1静态代码块(只执行1次)
- 2匿名代码块(每次new对象执行1次)
- 3构造器(每次new对象执行1次)
-
(十四)15 抽象类
-
定义:
-
abstract是一个修饰符
-
abstract修饰的类称为抽象类;
-
abstract修饰的方法称为抽象方法;
-
-
注意事项:
- 不能new抽象类,只能靠子类去实现它,是一个约束
- 抽象类中可以写普通的方法
- 抽象方法必须卸载抽象类中
-
抽象的本质:约束
-
思考题:
-
抽象类不能new对象,那么抽象类存在构造器(构造函数)吗?
- 存在,抽象类的构造函数用来初始化抽象类的一些字段,而这一切都在抽象类的派生类实例化之前发生。
- 由于抽象类的构造函数在实例化派生类之前发生,所以,可以在这个阶段初始化抽象类字段或执行其它与子类相关的代码。
-
抽象类的存在意义?
-
利于代码的维护和重用.抽象类往往用来表征对问题领域进行分析、设计中得出的抽象概念,是对一系列看上去不同,但是本质上相同的具体概念的抽象。
-
比如本科和研究生可以抽象成学生,他们有相同的属性和方法。这样当你对其中某个类进行修改时会受到父类的限制,这样就会提醒开发人员有些东西不能进行随意修改,这样可以对比较重要的东西进行统一的限制,也算是一种保护,对维护会有很大的帮助。
-
-
(十五)16 接口的定义与实现
-
如何理解接口:
- 接口是一种规范,定义的是一组规则.对应现实世界中"如果你是...则必须能..."的思想.(即在接口中无法写方法)
- 比如你是汽车,则必须能跑;如果你是天使,则必须会飞
- 接口的本质是契约,和现实中的法律一样,制定好后就必须遵守
- 面向对象的精髓,是 对对象的抽象,接口最能体现这一点.
-
对比类与接口:
- 普通类:只有具体实现
- 抽象类:具体实现和规范(抽象方法)都有!
- 接口:只有规范
-
接口的作用:
-
起约束作用,让不同的人按一定的规范编写程序
-
科研定义一些方法,让不同的人实现
-
接口中的方法默认被public abstract修饰
-
接口中的值认被public static final修饰,当做常量
-
接口不能被实例化,接口中没有构造方法
-
implements可以实现多个接口,实现类似于多继承的功能
-
implements关键字强制要求重写接口中的方法,从抽象→具体.
class Student extends Youngster,Person{ //编译不通过 } class StudentImpl implements Youngster,Person{ //实现Youngster和Person中的抽象方法后,才可以通过编译 }
-

浙公网安备 33010602011771号