前言: java 面向对象中的知识可以说是整个 java 基础最核心的部分, 不知不觉已经学完快 2 个月了, 是时候复习一波了, 刚开始学习的时候被绕的很懵逼, 这次总结完毕之后有了很多新的感悟, 这就是所谓的每有会意, 便欣然忘食吧! 哈哈~
---------------------------------------------------------------------------------------------------------------------------------------------------------------------------->>>>华丽的分割线
1, 什么是类? 什么是对象?
简单来说, 类是抽象出某一类事物的行为和特征, 并进行的封装, 特征称之为属性, 行为称之为方法;
对象就是这一类的具体实例, 对象拥有这个类的所有属性和方法
举个例子:
所有的人是一个类, 人所具有的属性: 身高和体重..., 人具有的方法: 吃饭, 睡觉..
具体到某一个人是一个对象, 比如小明就是一个对象, 小明有身高, 体重, 可以吃饭, 可以睡觉..
java 编程思想中是这么描述对象的:
对象具有状态, 行为, 和标识. 这意味着每一个对象都可以拥有内部数据 (它们给出了该对象的状态) 和方法(它们产生行为), 并且每一个对象都可以与其他对象区分开来, 具体来说, 就是每一个对象在内存中都有一个唯一的地址.
2, 什么是面向对象? 为什么要面向对象?
官方话:
面向对象 (Object Oriented) 是一种新兴的程序设计方法, 或者是一种新的程序设计规范 (paradigm), 其基本思想是使用对象, 类, 继承, 封装, 多态等基本概念来进行程序设计. 从现实世界中客观存在的事物(即对象) 出发来构造软件系统, 并且在系统构造中尽可能运用人类的自然思维方式. 面向对象是为了解决系统的可维护性, 可扩展性, 可重用性....
我的理解:
首先, 面向对象是一种设计程序的方式, 是一种设计思想.
其次, 面向对象节省代码, 思路清晰, 便于扩展. 你所创建出的对象就是给你提供服务的.
3, 面向对象的三大特征:
一, 封装
封装是实现面向对象程序设计的第一步, 封装就是将属性和方法放在一个类中. 对外提供服务时尽可能的隐藏对象内部细节, 只保留有限的接口和方法;
封装的意义:
封装的意义在于保护或者防止代码 (数据) 被我们无意中破坏. 在面向对象程序设计中属性被看作是一个中心的元素并且和使用它的方法结合的很密切, 从而保护 它不被其它的方法意外的修改.
可以通过对类的成员设置一定的访问权限, 实现类中成员的信息隐藏.
private: 类中限定为 private 的成员, 只能被这个类本身访问. 如果一个类的构造方法声明为 private, 则其它类不能生成该类的一个实例.
default: 类中不加任何访问权限限定的成员属于缺省的 (default) 访问状态, 可以被这个类本身和同一个包中的类所访问.
protected: 类中限定为 protected 的成员, 可以被这个类本身, 它的子类 (包括同一个包中以及不同包中的子类) 和同一个包中的所有其他的类访问.
public: 类中限定为 public 的成员, 可以被所有的类访问.
二, 继承
Java 的类可以分为三类:
类: 使用 class 定义, 没有抽象方法
抽象类: 使用 abstract class 定义, 可以有也可以没有抽象方法
接口: 使用 inerface 定义, 只能有抽象方法,(也可以没有), 接口里的变量默认使用 public static final 修饰
在这三个类型之间存在如下关系:
类可以 extends: 类, 抽象类 (必须实现所有抽象方法), 但只能 extends 一个, 可以 implements 多个接口(必须实现所有接口方法)---> 单继承多实现
抽象类可以 extends: 类, 抽象类(可全部, 部分, 或者完全不实现父类抽象方法), 可以 implements 多个接口(可全部, 部分, 或者完全不实现接口方法)
一个接口可以继承多个接口
继承以后子类可以得到什么:
子类直接拥有父类非 private 的属性和方法
子类可以添加自己的属性和方法, 即对父类进行扩展
子类可以重写父类的方法
关于构造方法:
构造方法不能被继承, 子类可以通过 super()显式调用父类的构造方法
创建子类对象时, 编译器会自动调用父类的无参构造方法
如果父类没有定义无参构造方法, 子类必须在构造方法的第一行代码使用 super()显式调用
类默认拥有无参构造方法, 如果定义了其他有参构造方法, 则无参构造方法失效, 所以父类没有定义无参构造方法, 不是指父类没有写无参构造方法.
Java 中通过 super 来实现对父类成员的访问, super 用来引用当前对象的父类. super 的使用有三种情况:
访问父类被隐藏的成员变量
调用父类中被重写的方法
调用父类的构造函数
继承的意义:
代码重用是一点, 最重要的还是向上转型, 即父类的引用变量可以指向子类对象, 这是 Java 面向对象最重要特性多态的基础
三, 多态
在了解多态之前, 先了解以下几点:
什么是相同的方法:
一个方法可以由: 修饰符 + 返回值 + 方法名 + 参数 + throw 的异常 + 方法体 6 部分组成
其中只有方法名和参数是唯一性标识, 意即只要方法名和参数相同那他们就是相同的方法
所谓参数相同, 是指参数的个数, 类型, 顺序一致, 其中任何一项不同都是不同的方法
什么是重载:
重载是指一个类里面 (包括父类的方法) 存在方法名相同, 但是参数不一样的方法, 参数不同可以是不同的参数个数, 类型或顺序
如果仅仅是修饰符, 返回值, throw 的异常不同, 那这是 2 个相同的方法, 编译都通不过, 更不要说重载了
什么是重写:
子类中存在和父类相同的方法即为重写, 何谓相同方法请牢记前面的描述, 方法名和参数相同, 包括参数个数, 类型, 顺序
重写的规则:
子类不能覆盖父类 private 的方法, private 对子类不可见, 如果子类定义了一个和父类 private 方法相同的方法, 实为新增方法
重写方法的修饰符权限一定要大于或等于被重写方法的修饰符权限(public> protected> default> private)
重写抛出的异常需与父类相同或是父类异常的子类, 或者重写方法干脆不写 throws
重写方法的返回值必须与被重写方法一致, 否则编译报错
静态方法不能被重写为非静态方法, 否则编译出错
什么是多态?
同一操作作用于不同的对象, 可以产生不同的执行结果, 这就是多态性.
Java 的多态性体现在两个方面: 由方法重载实现的静态多态性 (编译时多态) 和方法重写实现的动态多态性(运行时多态).
编译时多态: 在编译阶段, 具体调用哪个被重载的方法, 编译器会根据参数的不同来调用相应的方法.
运行时多态: 当父类引用引用指向子类对象时, 被引用的对象的类型决定了调用谁的方法, 这个被调用的方法必须是在父类中定义过的, 也就是说被子类重写的方法
- class Animal {
- public void speak() {
- System.out.println("我是动物");
- }
- }
- class Dog extends Animal {
- public void speak() {
- System.out.println("汪汪...");
- }
- }
- class Cat extends Animal {
- public void speak() {
- System.out.println("喵喵...");
- }
- }
- public class Test {
- public static void main(String args[]) {
- Animal animal = new Dog();
- animal.speak(); // 汪汪...
- animal = new Cat();
- animal.speak();// 喵喵...
- }
- }
稍微复杂一点的案例:
- class Animal {
- public void speak1() {
- System.out.println("我是动物..");
- speak2();
- }
- public void speak2() {
- System.out.println("我是一只凶猛的动物");
- }
- }
- class Dog extends Animal {
- public void speak1(String name) {
- System.out.println("汪汪...");
- }
- public void speak2() {
- System.out.println("我是一只泰迪");
- }
- }
- public class Test {
- public static void main(String args[]) {
- Animal animal = new Dog();
- animal.speak1();
- // 我是动物..
- // 我是一只泰迪
- }
- }
来源: https://www.cnblogs.com/Kingram/p/9000705.html