Java核心面试题解惑(高频完整版+详细实战答案)_第1页
Java核心面试题解惑(高频完整版+详细实战答案)_第2页
Java核心面试题解惑(高频完整版+详细实战答案)_第3页
Java核心面试题解惑(高频完整版+详细实战答案)_第4页
Java核心面试题解惑(高频完整版+详细实战答案)_第5页
已阅读5页,还剩4页未读, 继续免费阅读

下载本文档

版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领

文档简介

Java核心面试题解惑(高频完整版+详细实战答案)本文整理互联网企业高频Java面试题,覆盖Java基础、集合框架、JVM、多线程、Spring核心、数据库、微服务基础等核心考点,所有答案均贴合实际开发场景,摒弃书本化空洞表述,适配初中级开发面试场景。一、Java基础核心面试题1.JDK、JRE、JVM的区别与联系?详细答案:三者是层层包含的关系,范围从大到小依次是JDK>JRE>JVM。JVM是Java虚拟机,是Java程序运行的核心载体,只负责解析执行class字节码文件,不包含任何开发工具,是Java跨平台的核心(一次编译、到处运行)。不同操作系统对应不同版本的JVM。JRE是Java运行环境,包含JVM+Java核心类库(IO、集合、基础工具类等)。只安装JRE可以运行编译好的Java程序,但无法开发、编译代码,普通用户运行Java软件只需安装JRE。JDK是Java开发工具包,包含JRE+开发必备工具(javac编译器、java运行命令、jar打包工具、调试工具等)。开发人员必须安装JDK,才能完成代码编写、编译、调试、打包等全套操作。2.==和equals()的区别?详细答案:核心区别:==比较的是内存地址,equals()比较的是内容(重写后)1、基本数据类型:只能用==,比较的是变量的实际数值;2、引用数据类型:==比较两个对象在堆内存中的地址,判断是否是同一个对象;3、equals()是Object类的原生方法,原生逻辑和==一致,也是比较地址。但String、Integer、自定义实体类都会重写该方法,重写后不再比较地址,而是比较对象的实际内容、属性值是否相同。实战场景:判断字符串内容一致必须用equals,判断两个对象是否为同一对象用==。3.String、StringBuilder、StringBuffer的区别?详细答案:1、可变性:String是不可变字符串,每次拼接、修改都会生成新的字符串对象,频繁操作会产生大量垃圾对象;StringBuilder和StringBuffer是可变字符串,直接修改原对象,不会新建对象。2、线程安全:StringBuffer所有方法都加了synchronized锁,线程安全,适合多线程场景;StringBuilder无锁,线程不安全,性能更高;String不可变,天然线程安全。3、性能:单线程下StringBuilder>StringBuffer>String。实战规范:日常字符串拼接优先用StringBuilder;多线程共享字符串操作用StringBuffer;固定不变的字符串常量直接用String。4.final、finally、finalize的区别?详细答案:1、final:是修饰符,用于修饰变量、方法、类。final变量不可二次赋值;final方法不可重写;final类不可被继承。2、finally:是异常处理关键字,搭配try-catch使用。无论代码是否抛出异常、是否return,finally中的代码最终都会执行,常用于释放资源(关闭流、关闭数据库连接)。3、finalize():是Object类的废弃方法,JDK9之后已废弃。原本作用是GC回收对象前触发,用于手动清理资源,但执行时机不确定、无法保证调用,开发中绝对不使用。5.接口和抽象类的区别?详细答案:1、继承规则:抽象类只能单继承;接口可以多实现,解决了单继承的局限性。2、成员修饰:抽象类可以有普通成员变量、构造方法、静态方法、抽象方法、普通方法;接口(JDK8前)只能有常量和抽象方法,JDK8支持默认方法、静态方法,JDK9支持私有方法,无构造方法。3、设计思想:抽象类是模板复用,描述一类事物的共性特征;接口是行为规范,描述对象具备的能力。4、使用场景:需要复用代码、统一父类结构用抽象类;需要定义行为标准、实现多能力扩展用接口。二、Java集合框架面试题1.ArrayList和LinkedList的区别?详细答案:1、底层结构:ArrayList基于动态数组实现;LinkedList基于双向链表实现。2、查询效率:ArrayList支持随机访问,通过下标直接定位元素,查询速度极快;LinkedList只能从头节点遍历查询,效率极低。3、增删效率:ArrayList增删元素需要移动数组元素、扩容缩容,首尾以外位置增删效率低;LinkedList只需修改节点指针,无需移动元素,频繁增删场景效率更高。4、内存占用:ArrayList会预留冗余容量,存在内存浪费;LinkedList每个节点包含数据和前后指针,单个元素内存占用更大。实战选型:查多改少用ArrayList,增删频繁用LinkedList,日常开发90%场景优先ArrayList。2.HashMap的底层原理?JDK1.7和JDK1.8的区别?详细答案:HashMap底层是数组+链表+红黑树的哈希表结构,用于存储键值对,基于哈希算法实现高效存取,允许key、value为null,线程不安全。JDK1.7与JDK1.8核心区别:1、数据结构:1.7只有数组+链表;1.8新增红黑树,链表长度超过8且数组容量大于64时,链表转为红黑树,降低查询时间复杂度。2、哈希算法:1.7扰动次数多,计算复杂;1.8简化哈希扰动,性能更高。3、扩容机制:1.7扩容时链表元素会倒置,多线程下容易出现死循环;1.8保留原有节点顺序,规避了扩容死循环问题。4、插入方式:1.7头插法;1.8尾插法。3.HashMap为什么线程不安全?怎么解决?详细答案:HashMap所有方法无同步锁,多线程并发场景下会出现数据覆盖、丢失、死循环、数据不一致等问题。1、并发put:多个线程同时添加元素,会发生哈希碰撞,导致数据覆盖、元素丢失;2、JDK1.7并发扩容:链表倒置会形成环形链表,触发死循环,导致CPU飙升。线程安全解决方案:1、Hashtable:全表锁,并发性能极差,基本废弃;2、Collections.synchronizedMap:封装HashMap,方法加锁,性能一般;3、ConcurrentHashMap:分段锁(1.7)/CAS+synchronized锁(1.8),并发性能最优,生产环境首选。4.HashSet的底层原理?详细答案:HashSet底层直接依托HashMap实现,源码中HashSet内部维护一个HashMap对象。HashSet存储的元素,作为HashMap的key存入,而HashMap的value统一存储一个静态常量空对象。所以HashSet去重逻辑和HashMapkey去重一致:先判断hashCode,再判断equals,两者都相同则判定为重复元素,无法存入。注意:自定义对象存入HashSet去重,必须同时重写hashCode和equals方法,否则会出现去重失效。三、JVM与内存机制面试题1.JVM内存区域划分?各自作用?详细答案:JVM运行时数据区分为5个区域,线程私有3个、线程共享2个:线程私有(随线程创建销毁):1、程序计数器:记录当前线程执行的字节码行号,是唯一一个无内存溢出的区域,用于线程切换后恢复执行位置;2、虚拟机栈:存储方法栈帧(局部变量、操作数栈、方法返回值等),方法调用即入栈,执行结束即出栈,栈内存溢出会抛出StackOverflowError;3、本地方法栈:作用和虚拟机栈一致,专门为JVM调用的native本地方法服务。线程共享(随JVM启动销毁):1、堆内存:JVM最大内存区域,所有对象、数组都在堆中分配,是GC垃圾回收的主要区域,内存溢出抛出OOM;2、方法区:存储类信息、常量、静态变量、即时编译代码等,JDK1.8后方法区改为元空间,使用本地内存,不再占用JVM堆内存。2.堆内存的分代模型?GC回收机制?详细答案:JVM堆内存分为新生代、老年代,永久代/元空间不属于堆内存。1、新生代:占堆内存1/3,分为Eden区、FromSurvivor、ToSurvivor(8:1:1),存放新建的短期存活对象。对象频繁创建销毁,触发MinorGC(轻量GC),速度快。2、老年代:占堆内存2/3,存放长期存活对象、大对象。对象存活率高,极少GC,触发FullGC(全局GC),速度慢、耗时久,生产环境要尽量避免。对象晋升规则:新生代对象经过15次GC仍存活,晋升到老年代;大对象直接进入老年代。3.什么是OOM?常见OOM场景及解决方案?详细答案:OOM即内存溢出,指JVM没有足够内存分配给新对象,且GC后仍无法释放空闲内存,导致程序崩溃。常见场景:1、堆OOM:大量创建对象、集合无限add、静态集合持有对象不释放;2、栈OOM:递归死循环、方法嵌套调用过深;3、元空间OOM:动态生成大量类、频繁热部署。解决方案:排查代码内存泄漏、优化集合使用、终止无效递归、合理调整JVM内存参数、使用内存分析工具定位问题。四、多线程面试题1.线程和进程的区别?详细答案:1、进程是操作系统资源分配的最小单位,线程是CPU调度的最小单位;2、进程相互独立,拥有独立的内存空间,一个进程崩溃不影响其他进程;线程共享所在进程的内存资源,一个线程异常崩溃,整个进程可能崩溃;3、进程创建、销毁开销极大;线程开销极小,切换速度快;4、一个进程包含多个线程,至少有一个主线程。2.synchronized和Lock的区别?详细答案:1、底层层面:synchronized是JVM原生关键字,底层依赖虚拟机指令实现;Lock是Java接口,基于代码层面实现锁机制;2、锁类型:synchronized是隐式锁,自动加锁、自动释放锁;Lock是显式锁,需要手动lock()加锁、unlock()释放锁;3、锁特性:synchronized不可中断、无法超时、非公平锁;Lock可中断、可设置超时时间、可实现公平/非公平锁、可绑定多个条件;4、性能:低并发下两者性能接近,高并发下Lock性能更优;实战选型:简单同步场景用synchronized,高并发、需要灵活锁机制场景用ReentrantLock。3.线程的生命周期有哪些状态?详细答案:Java线程一共6种状态:1、NEW:新建状态,线程对象创建,未调用start();2、RUNNABLE:就绪+运行状态,等待CPU调度或正在执行;3、BLOCKED:阻塞状态,等待获取synchronized锁;6、TERMINATED:终止状态,线程执行完毕或异常退出。五、Spring核心面试题1.SpringIOC的原理和作用?详细答案:IOC即控制反转,是Spring的核心思想。传统开发中程序员主动new对象创建实例,控制权在程序代码;IOC将对象的创建、管理、依赖注入的控制权交给Spring容器,实现控制权反转。核心作用:1、解耦:彻底消除代码硬依赖,无需手动new对象,降低模块耦合度;2、统一管理:Spring容器统一管理所有Bean的生命周期、实例化、销毁;3、支持依赖注入:自动完成属性赋值、依赖装配,简化开发;4、便于扩展:配合AOP、事务、拦截器等功能,实现统一增强。2.SpringAOP的原理和应用场景?详细答案:AOP即面向切面编程,基于动态代理机制,在不修改原有业务代码的前提下,对方法进行前置、后置、异常、环绕增强,实现业务逻辑与通用逻辑分离。底层机制:目标类有接口用JDK动态代理,无接口用CGLIB字节码增强代理。常用场景:统一日志记录、权限校验、事务控制、接口限流、性能监控、缓存处理。3.SpringBean的生命周期?详细答案:1、实例化:Spring容器根据配置创建Bean对象实例;2、属性填充:自动完成依赖注入,给Bean属性赋值;3、初始化前置处理:执行BeanPostProcessor前置增强方法;4、初始化:执行InitializingBean、自定义init-method初始化方法;5、初始化后置处理:执行BeanPostProcessor后置增强方法;6、销毁:容器关闭时,执行DisposableBean、自定义destroy-method销毁方法。六、数据库与MyBatis面试题1.MySQL索引的分类及底层原理?详细答案:常用索引分类:主键索引、唯一索引、普通索引、联合索引、全文索引。MySQLInnoDB引擎索引底层基于B+树实现,相比B树,B+树所有数据都存储在叶子节点,非叶子节点只存索引键,磁盘IO更少、查询效率更高,且叶子节点双向链表串联,适配范围查询。核心特性:遵循最左前缀匹配原则,联合索引查询必须匹配左侧字段,否则索引失效。2.什么是SQL注入?如何防止?详细答案:SQL注入是用户通过输入恶意SQL语句,拼接进后台执行的SQL中,篡改查询逻辑,实现越权查询、删除数据等恶意操作。解决方案:1、杜绝字符串拼接SQL,统一使用预编译SQL(MyBatis#{}占位符);2、#{}会自动参数预编译、转义,有效防止注入,${}直接字符串拼接,存在注入风险,禁止用于普通参数;3、增加参数校验、过滤特

温馨提示

  • 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
  • 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
  • 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
  • 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
  • 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
  • 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
  • 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。

最新文档

评论

0/150

提交评论