类的成分
- 成员方法
- 成员变量
- 构造器
- 代码块
- 内部类
面向对象的三大特性
封装 继承 多态
封装
- 可以提高安全性
- 可以实现代码的组件化
封装的规范:
-
建议成员变量都私有:private修饰
private修饰的方法,变量,构造器只能在本类中访问
-
提供成套的get/set方法暴漏成员变量的取值和赋值
小结:
封装的核心思想: 合理隐藏,合理暴漏
封装已经称为Java代码的风格,即使毫无意义也要按照封装的规范写代码
static关键字
之前我们定义了很多成员变量(name age sex) 其实我们只写了一次,但是发现每个对象都可以用,这说明Java中这些成员变量或方法是存在所属性的,有些事属于对象的, 有些事属于类本身的
Java是通过成员变量是否有static修饰来区分是类的还是对象的
static== 静态==修饰的成员(方法和变量)属于类本身的
按照有无static修饰,成员变量和成员方法可以分为:
成员变量:
-
静态成员变量(类变量):
有static修饰的成员变量也叫做类变量,属于类本身的,直接用类名访问即可
-
实例成员变量
无static修饰的成员变量,属于类的每个变量的,必须用类的对象来访问
成员方法:
-
静态方法:
有static修饰的成员方法称为静态方法,也叫做类方法,属于类本身的,直接用类名访问即可
-
实例方法:
无static修饰的成员方法称为实例方法,属于类对象的,必须用类的对象来访问
继承
子类可以继承父类的 实例方法 , 实例对象
子类不能继承父类的东西:
子类不能继承父类的构造器(没有争议)
有争议的观点(拓展):
子类是否可以继承父类的私有成员(私有成员变量 , 私有成员方法)?
我认为:可以继承,不能直接访问,但是可以暴力访问(反射)
子类是否可以继承父类的静态成员?
我认为:不可以继承,但是可以被共享(父类的静态成员只有一份属于类,只被加载一次)
继承 成员变量的访问特点:
就近原则: 子类有找子类,子类没有找父类
this关键字代表了当前对象的应用,可以用于访问当前对象的成员变量
super关键字代表了父类对象的用用,可以用于访问父类的成员变量
继承 成员方法的访问特点:
就近原则
继承 方法重写:
子类继承了父类,子类就有了父类的某个方法,但是子类觉得这个方法不好用或不能满足自己的需求,子类重写一个与父类申明一样的方法来覆盖父类的该方法,子类的这个方法就进行了重写
Java重写的校验注解: @override 方法一旦加入这个注解那就必须成功重写父类的方法,否则报错
@override: 可读性好, 安全, 优雅
重写要求:
-
重写的方法名称和参数列表必须和父类被重写方法一样
-
返回值类型要么和父类一样,要么比父类的返回值范围小
-
修饰符权限要么和父类一样,要么比父类的更大
-
申明抛出的异常要和父类一样或者范围更小
方法重写规范:
- 加上@override注解
- 建议"申明不变 , 重新实现"
子类对象可以使用super关键字调用父类被重写的方法
私有方法和静态方法都不能被重写
继承 构造器(构造方法)的特点:
- 子类构造器的第一行默认一定会先访问父类的无参数构造器,在执行自己的构造器
为什么子类构造器会先访问父类构造器?
- 子类构造器第一行默认有一个super(),来调用父类的无参数构造器,写不写都存在
- 子类继承了父类,子类就有了父类的属性和行为,当我们使用子类构造器初始化子类对象数据的时候,就必须先调用父类构造器初始化父类的属性和行为
super调用父类构造器 : 可以在子类构造器中使用super(…参数…)制定调用父类构造器,以便调用父类构造器初始化继承自父 类的数据
继承特点:
- 单继承: 一个类只能继承一个直接父类 (否则会出现类的二义性)
- 多层继承:一个类可以间接继承多个父类
- 一个类可以有多个子类
- 一个类要么直接继承了Object类,要么间接继承了Object类,Object类是Java中的祖宗类
引用类型
引用数据类型作为Java的数据类型,自然可以作为方法的参数类型和返回值类型
除了基本数据类型,都是引用数据类型
抽象类
什么是抽象类?
父类知道子类一定要完成某个功能,但是每个子类完成的情况不一样
子类以后也只会用自己重写的功能,那么父类的该功能就可以定义为抽象方法,子类重写调用自己的方法
抽象类可以有:有成员变量、成员方法、抽象方法
什么是抽象方法:
抽象方法:没有方法体,只有方法签名,必须用abstract修饰
拥有抽象方法的类必须定义为抽象类
抽象类: 必须用abstract修饰
作用: 为了被子类继承
继承了抽象类必须重写抽象类中的全部抽象方法,否则这个类也必须定义为抽象方法
抽象类的特征:
有得有失,除此之外类的成分他都具备
有的:得到了拥有抽象方法的能力
有事:失去了创建对象的能力(抽象类不能创建对象)
抽象类是否有构造器,抽象类是否可以创建对象,为什么?
答:抽象类作为类一定有构造器,而且抽象类必须有构造器。提供子类创建对象调用父类构造器使用的
抽象类虽然有构造器但是不能创建对象。反证法:抽象类的方法不能执行,因为抽象方法没有方法体
模板模式
在模板模式(Template Pattern)中,一个抽象类公开定义了执行它的方法的方式/模板。它的子类可以按需要重写方法实现,但调用将以抽象类中定义的方式进行。这种类型的设计模式属于行为型模式。
**意图:**定义一个操作中的算法的骨架,而将一些步骤延迟到子类中。模板方法使得子类可以不改变一个算法的结构即可重定义该算法的某些特定步骤。
使用场景: 1、有多个子类共有的方法,且逻辑相同。 2、重要的、复杂的方法,可以考虑作为模板方法。
**注意事项:**为防止恶意操作,一般模板方法都加上 final 关键词。
接口
jdk1.8之前
什么是接口:
- 接口是更加彻底的抽象,jdk1.8之前接口中只有抽象方法和常量
- 接口体现的是规范的思想,实现接口的子类必须重写玩接口的所有抽象方法
- 接口中抽象方法 public abstract 可以省略不写
- 接口中常量 public static final 可以省略不写
- 除此之外接口是没有其他成分
接口的实现
子类 继承 父类
实现类 实现 接口
类与类之间是单继承关系
实现类与接口之间是实现关系
接口与接口之间是多继承关系
类实现类的格式
修饰符 class 实现类名 implements 接口1,接口2~~~{ }
接口可以多实现
jdk1.8之后
1.8之前接口中只有抽象方法和常量
1.8之后新增三个方法
新增方法
- 默认方法:其实就是我们之前写的实例方法
- 必须加default修饰
- 默认会加public修饰
- 只能用接口的实现类对象调用
- 静态方法
- 可以直接加static修饰
- 默认会加public修饰
- 只能用接口的类名调用
- 私有方法
- 其实就是私有的实例方法。必须加private修饰
- 只能在本接口中被私有方法或默认方法调用
实现多接口注意事项
- 如果实现了多接口,多个接口中存在的多个重名的静态方法并不会冲突,因为只能通过各自方法名访问各自静态方法
- 当一个类继承一个父类有实现多个接口时,父类中的成员方法与接口中的默认方法重名,子类就近选择父类的成员方法
- 当一个类实现多个接口时,多个接口中有重名的默认方法,实现类必须重写这个方法
代码块
代码块按照有无static修饰分为静态代码块,实例代码块
-
静态代码块
-
格式 static {
}
必须有static修饰。属于类,会与类一起优先加载,而且自定触发执行一次!
-
用于在执行类的方法之前进行静态资源的初始化操作
-
-
实例代码块
-
格式 {
}
无static修饰,属于类的每个对象的,会与类的每一个对象一起加载,每次创建对象时,实例代码块就会触发执行一次
-
final关键字
final可以修饰 类、方法、对象、
final修饰类:类不能被继承
final修饰方法:方法不能被重写
final修饰变量:变量有且仅能被赋值一次