三大特征
封装、继承、多态
封装
封装是将数据和方法组合在一个单元中
限制对内部实现的直接访问(私有化属性+get/set)
保证了属性、方法的安全 减少了代码的耦合性
使代码易于维护与调试
继承
继承是指一个类(子类)可以继承另一个类(父类)的属性和方法
避免重复编写相似的代码,减少了代码的冗余
提高代码的可维护性和可扩展性
实现代码的层次化组织,使得类之间的关系更加清晰
多态
多态是指同一个操作或方法可以具有不同的行为方式
子类对象指向父类引用
提高了代码的灵活性与可扩展性
自己的理解:创建的引用本质为父类。若子类对其父类方法进行重写,则调用子类重写后的方法,而非父类的方法。当前引用只能调用父类存在的属性及方法,不能调用子类的属性与方法(除重写),可以调用子类重写父类的方法
类与对象
类 对象的模板或蓝图,它定义了对象的属性和行为
类可以看作是一个抽象的概念,描述了对象的共同特征和行为对象 类的实例化结果,是类的具体实体
对象具有类定义的属性和行为,并可以通过调用类中的方法来实现特定的功能类是对象的抽象:类描述了对象的共同特征和行为,是对象的抽象概念。
它定义了对象的属性和方法,但并没有具体的数据和状态对象是类的实例:对象是类的具体实例化结果,它具有类定义的属性和行为。
通过创建对象,可以使用类中定义的属性和方法
属性
成员变量 静态变量 局部变量 常量
方法
含义:方法是一段可重复使用的代码块,用于执行特定的任务
成员方法
静态方法
使用static关键字修饰的方法
可以通过类名直接调用,无需创建类的实例
不能访问成员变量,只能访问静态变量和调用其他静态方法
静态代码块中只能调用外部静态属性与静态方法
自己理解:在运行主方法时,JVM加载时会先扫描主方法所在类中是否有静态代码块,执行静态代码块内容,然后扫描其他调用类中是否存在静态代码块,再执行构造方法
每个类都有构造方法
构造方法没有返回类型
构造方法的名称必须与类同名,一个类可以有多个构造方法
如果没有显式地为类定义构造方法,Java 编译器将会为该类提供一个默认构造方法
在创建一个对象的时候,至少要调用一个构造方法
在没有有参构造的情况下,无参构造系统会默认实现(如果类中编写了有参构造,最好把无参构造写上)抽象方法
在抽象类或接口中声明但没有具体实现的方法
只有方法签名而没有方法体
必须在子类中实现或者在实现接口的类中重写
访问修饰符
访问修饰符 | 本类 | 本包 | 其他包子类 | 其他包 |
---|---|---|---|---|
private | OK | |||
默认的 | OK | OK | ||
protected | OK | OK | OK | |
public | Ok | OK | OK | Ok |
重写
含义:在子类中将父类的方法重新写一遍
应用场景:父类方法不满足子类需求时就考虑在子类中重写
条件
- 在子类中重写父类的方法
- 返回值、方法名、参数列表必须一致
- 访问修饰符不能比父类的更加严格
- 子类在重写方法时可以抛出与父类方法相同的异常,或者不抛出任何异常
- 子类方法抛出的异常不能比父类方法抛出的异常更多,可以是相同的异常或其子类异常
重载
含义:方法与方法之间的关系
应用场景:编写多个方法,方法功能大致一致,细节实现不一致,就考虑使用重载
条件
在同一个类中
方法名相同
参数列表不一致
返回值类型可以不同
修饰访问修饰符可以不同
可以抛出不同的异常,或者在方法中不抛出异常
this
含义:代表当前对象的引用 作用
访问成员变量:this.variableName
调用当前对象的方法:this.methodName()
显式的调用构造函数: this(arguments)
区分成员变量和局部变量:成员变量和局部变量名称相同时,使用"this"关键字明确指定访问成员变量
传递当前对象: methodName(this) 将当前对象当作参数传递
super
含义:用于引用父类(超类)的成员,包括实例变量、方法和构造函数 作用
调用父类构造函数:super(arguments)这种情况下,构造函数的调用必须作为构造函数的第一条语句
访问父类方法或成员变量:super.methodName() super.variableName
解决方法或变量的重名:当子类中存在与父类同名的方法或变量时,可以使用"super"关键字来区分访问的是父类的成员还是子类的成员
"super"和"this"的区别:"super"关键字用于引用父类的成员,而"this"关键字用于引用当前对象的成员
final
含义:表示不可更改或不可继承的特性
常量存放在常量池中,项目结束时才会销毁
final类:用"final"修饰的类是不可继承的,即不能有子类
final方法:用"final"修饰的方法是不可重写的,即子类无法覆盖该方法
final变量:用"final"修饰的变量是不可改变的,即其值在初始化后不能再被修改。一旦赋予初始值后,该变量将成为常量(可以先定义,后面再赋值,但只能赋值一次)
Object
含义:基类、超类,所有类的父类,每个类都直接或间接地继承自Object类 常用方法
toString():用于返回对象的字符串表示
equals():用于比较对象的相等性
hashCode():用于返回对象的哈希码
getClass():用于返回对象所属的类的Class对象
finalize():用于在对象被垃圾回收之前执行清理操作
抽象类
含义:一种不能直接实例化的类,它用于被其他类继承并提供一些通用的抽象方法和成员变量
抽象类可以包含抽象方法,即没有具体实现的方法
子类必须实现(重写)抽象方法
抽象类不一定有抽象方法,有抽象方法必须是抽象类
若抽象类的子类为抽象类,可以不重写父抽象类的方法
若抽象类的子类非抽象类,必须重写父类及父类的父类的抽象方法
接口
含义: Java 中一种抽象的引用类型,用于定义一组抽象方法和常量(接口是一种特殊的抽象类)
注意
- 接口中只能有抽象方法与常量
- JDK1.8新特性,接口中添加默认(default)和静态(static)方法
- 接口中属性默认使用public static final修饰
- 接口中方法默认使用public abstract修饰
Java中为单继承多实现(即:可实现多个接口,只能继承一个父类)
对象转型
含义:将一个对象的类型转换为另一个类型
向上转型:指将一个子类对象转换为其父类类型或者接口类型的过程(安全),隐式,实现多态 向下转型:指将一个父类对象或接口类型的对象转换为其子类类型的过程(不安全),显式,强转
内部类
含义:在一个类(外部类)中声明另一个类(内部类)
应用场景
B类对象只在A类中使用,则可将B类设计成A类的内部类
B类的对象只在A类中使用,并且B类使用到A类所有的属性,就可以将B类设置为A类的成员内部类
B类的对象只在A类中使用,并且B类使用到A类静态的属性,就可以将B类设置为A类的静态内部类
B类的对象只在I1接口中使用,就可以将B类设置为I1接口的接口内部类
B类的对象只在A类的method方法中使用,就可以将B类设置为A类method方法中的局部内部类
抽线类的子类或者接口的实现类只new了一次对象,就可以使用匿名内部类
特点
内部类可以直接访问外部类的私有成员(属性与方法)
内部类可以拥有自己的成员变量和方法,并且可以像外部类一样被实例化和调用
内部类可以被继承,也可以实现接口
注意:public修饰的类名必须和文件名一致
成员内部类
定义在外部类的成员位置上,与外部类的实例相关联,可以访问外部类的成员
成员内部类中可以调用外部类所有的属性(包括被保护的及私有的)静态内部类
定义在外部类的成员位置上,使用static关键字修饰,与外部类的实例无关,可以直接通过外部类名访问
静态内部类只能调用外部类的静态属性(常量与变量、final修饰的变量)静态内部类为什么不能调用外部类的成员变量?
因为创建静态内部类是不需要创建外部类对象 所以外部类的成员变量不会再内存中得到体现,就自然调用不了接口内部类
定义在接口中的成员位置
接口中默认添加public static修饰,其实相当于静态内部类局部内部类
定义在代码块中的类,作用域仅限于所在的代码块
JDK1.8:局部内部类使用到了外部类的局部变量时,该变量自动转换为常量为什么局部内部类调用外部类的局部变量时,局部变量会变为常量?
因为局部内部类对象有可能传输给外界,把外部类的局部变量设置为常量后,常量的生命周期就更长了,在外界的局部内部类的对象也能调用匿名内部类
没有显式的类定义,直接在创建对象的地方定义,并重写父类或接口的方法