面试必刷!Java面向对象10道经典题 答对8道直接上岸!
面向对象的三大特性是什么?分别有什么作用?
三大特性:封装、继承、多态。
① 封装
将数据和操作数据的方法绑定在一起,通过访问修饰符隐藏内部实现细节,只暴露必要的接口。核心目的:高内聚、低耦合。例如将类的属性设为 private,提供 public 的 getter/setter 方法,可以在 setter 中加入校验逻辑而不影响调用方。
② 继承
子类通过extends关键字获得父类的属性和方法,实现代码复用和is-a 关系。Java 只支持单继承(一个类只能有一个直接父类),但支持多层继承。所有类默认继承 Object。
③ 多态
同一个行为具有多个不同表现形式或形态的能力。编译时多态(方法重载)和运行时多态(方法重写 + 父类引用指向子类对象)。核心条件:继承 + 重写 + 父类引用指向子类对象(向上转型)。
2
方法重载(Overload)和方法重写(Override)的区别?
对比维度 | 方法重载(Overload) | 方法重写(Override) |
|---|---|---|
发生位置 | 同一个类中 | 父子类之间 |
方法签名 | 方法名相同,参数列表不同 | 方法名、参数列表完全相同 |
返回类型 | 可以不同 | 相同或其子类(协变返回) |
访问修饰符 | 无限制 | 不能比父类更严格 |
异常 | 无限制 | 不能抛出比父类更宽泛的检查异常 |
绑定时机 | 编译时绑定 (静态多态) | 运行时绑定 (动态多态) |
关键记忆点:
重载——"同一个类,方法名相同参数不同";重写——"父子类,一模一样,子类修饰符不缩小、异常不扩大、返回值同或子"。注意:static 方法不能被重写(可以被隐藏),final/private 方法不能被重写。@Override 注解帮助编译器检查。
3
抽象类和接口有什么区别?(含 JDK8+ 新特性)
对比维度 | 抽象类 | 接口 |
|---|---|---|
关键字 | abstract class | interface |
继承 | 单继承 extends | 多实现 implements(支持多继承) |
构造方法 | 有 | 无 |
成员变量 | 无限制 | 只能 public static final 常量 |
普通方法 | 可以有具体方法 | JDK8+:default/static 方法;JDK9+:private 方法 |
设计理念 | is-a 关系,模板设计 | has-a / can-do 能力,行为规范 |
JDK8+ 接口新特性:
- default 方法:
有方法体,实现类可以直接用或重写。解决"接口增加方法,所有实现类都要改"的痛点。
- static 方法:
通过接口名直接调用,实现类不能继承。
- JDK9 private 方法:
抽取 default/static 方法中的公共代码。
4
面向过程和面向对象的区别是什么?
对比维度 | 面向过程(POP) | 面向对象(OOP) |
|---|---|---|
核心思想 | 以函数/过程为单位,自顶向下逐步细化 | 以对象为单位,数据+行为封装一体 |
数据与操作 | 分离 ,数据全局传递 | 绑定 在对象内,通过方法操作 |
代码复用 | 函数调用 | 继承、组合 |
扩展性 | 修改成本高,牵一发动全身 | 开闭原则,对扩展开放对修改关闭 |
代表语言 | C、Pascal | Java、C++、Python |
🔥 面试加分句:
面向过程强调"怎么做"(算法 + 数据结构),面向对象强调"谁来做"(对象 + 消息传递)。面向对象更符合人类思维习惯,适合大型复杂系统;面向过程适合简单、流程明确的场景。现代 Java 也融合了函数式编程(Lambda/Stream),并不是非此即彼。
点击下方小卡片免费获取Java资料Java资料https://mp.weixin.qq.com/s/iBmSycbmeTCSRNKJQ10EuA
5
多态的实现原理是什么?向上转型和向下转型有什么注意事项?
① 多态实现原理(JVM 层面)
- 编译时多态(重载):
编译器根据参数列表在编译阶段确定调用哪个方法——静态分派。
- 运行时多态(重写):
JVM 在运行期间通过动态分派,根据对象的实际类型(而非引用类型)查找方法表决定调用哪个方法。底层依赖虚方法表(vtable)。
② 向上转型(Upcasting)
子类对象赋值给父类引用:Animal a = new Cat();——自动、安全,但丢失了子类特有的方法。
③ 向下转型(Downcasting)
父类引用强转为子类类型:Cat c = (Cat) a;——必须显式强转,不安全,可能抛出ClassCastException。建议用instanceof先判断再转型。JDK16+ 支持模式匹配简化写法。
6
构造方法有哪些特点?构造方法能否被重写?
构造方法核心特点:
方法名必须与类名完全相同
- 没有返回类型
(连 void 都不能写)
用
new关键字调用,不能像普通方法那样直接调用如果不写,编译器自动提供无参默认构造方法
如果写了有参构造,默认无参构造不再自动生成,需要手动编写
子类构造方法的第一行默认都会调用 super()(父类无参构造),也可以显式指定 super(arg) 或 this(arg)
- 递归调用
构造方法是编译错误
🔥 关键结论:
构造方法不能被重写(Override),因为构造方法不属于类的成员方法,子类不会继承父类的构造方法。但构造方法可以被重载(Overload)——同一个类中可以有多个参数不同的构造方法。
7
this 和 super 关键字的作用和区别?
维度 | this | super |
|---|---|---|
指向 | 当前对象的引用 | 父类对象的引用 |
访问成员 | this.属性 / this.方法() | super.属性 / super.方法()(访问父类被覆盖的成员) |
构造方法 | this() 调用本类其他构造方法 | super() 调用父类构造方法 |
位置要求 | 构造方法第一行 | 构造方法第一行 |
互斥关系 | this() 和 super()不能同时出现 |
常见使用场景:
- this:
区分成员变量和局部变量(如构造方法中 this.name = name)、链式调用返回 this、构造方法间互相调用。
- super:
子类重写方法后仍想调用父类版本、子类构造中调用父类构造。
- static 方法中不能用 this 和 super
,因为没有实例上下文。
8
Java中有哪些内部类?各自的特点和使用场景?
类型 | 位置 | static | 场景 |
|---|---|---|---|
| 成员内部类 | 类中,方法外 | 可选 | 类与外部类强关联(如 Body.Heart) |
| 静态内部类 | 类中,方法外 + static | 必须 | 独立于外部类实例(如 Builder 模式、Map.Entry) |
| 局部内部类 | 方法/代码块内 | 不能 | 仅在某个方法中使用,作用域极小 |
| 匿名内部类 | 表达式/参数中 | 不能 | 一次性使用(如事件监听、Runnable、Comparator) |
🔥 面试核心要点:
- 成员内部类 vs 静态内部类:
前者持有外部类引用,后者不持有(不导致外部类无法 GC)。能用静态内部类尽量用静态。
- 匿名内部类:
只能访问final(或 effectively final)的局部变量。JDK8 后用 Lambda 代替更简洁。
- 权限:
内部类编译后生成单独的 .class 文件(如 Outer$Inner.class)。JVM 层面没有内部类概念,是编译器的语法糖。
9
Java四种访问修饰符的作用范围分别是什么?
修饰符 | 本类 | 同包子类 | 同包非子类 | 不同包子类 | 不同包非子类 |
|---|---|---|---|---|---|
| private | ✓ | ✗ | ✗ | ✗ | ✗ |
| default (无修饰) | ✓ | ✓ | ✓ | ✗ | ✗ |
| protected | ✓ | ✓ | ✓ | ✓ | ✗ |
| public | ✓ | ✓ | ✓ | ✓ | ✓ |
🔥 速记口诀(范围从小到大):
private → default → protected → public(私有、默认包级、保护子类、公开所有人)
别踩坑:
类(外部类)只能用public或默认修饰,不能用 private/protected。
接口的成员变量默认 public static final,方法默认 public abstract。
不同包子类中,protected 只能通过继承访问,不能通过父类实例访问。
10
深拷贝和浅拷贝有什么区别?Java中如何实现?
① 区别对比
维度 | 浅拷贝(Shallow Copy) | 深拷贝(Deep Copy) |
|---|---|---|
基本类型字段 | 复制值 | 复制值 |
引用类型字段 | 复制引用地址(共享同一对象) | 创建新对象 并递归复制 |
独立性 | 修改会互相影响(引用字段) | 完全独立 |
性能 | 快 | 慢(尤其嵌套深时) |
② 实现方式
- 浅拷贝:
实现
Cloneable接口,重写clone()调用super.clone()。 - 深拷贝:
方式一——clone() 中递归克隆引用字段;方式二——序列化/反序列化(推荐,无需递归处理,借助 ObjectOutputStream/ObjectInputStream 或 JSON 序列化工具如 Gson、Jackson);方式三——拷贝构造方法或工厂方法。
🔥 别踩坑:
Object 的 clone() 是protected native,需要实现 Cloneable 并重写为 public。
- 不实现 Cloneable 直接调用 clone() 会抛 CloneNotSupportedException
。
序列化深拷贝要求对象及其所有引用字段都实现
Serializable,且可能触发循环引用问题(注意 transient 字段)。集合框架中,Arrays.copyOf() / List.copyOf() 对元素是浅拷贝。
总结
面向对象是 Java 面试的必考板块,也是写高质量代码的基础。10道题目覆盖了:
- 三大特性:
封装、继承、多态(概念 + 原理)
- 方法:
重载 vs 重写、构造方法、this/super
- 设计:
抽象类 vs 接口(含 JDK8+)、面向过程 vs 面向对象
- 细节:
内部类、访问修饰符、深拷贝浅拷贝
由于篇幅有限,更多详情更有Java免费资料点击下方小卡片获取Java资料https://mp.weixin.qq.com/s/iBmSycbmeTCSRNKJQ10EuA
