JAVA三年面试总结,金九银十,你准备好了吗?

三次握手的原因?

三次握手TCP协议建立连接的过程。
原因或目的是为了证明客户端和服务端都有发送和接收的能力。

原理
第一次:客户端发送SYN包给服务端
第二次:服务端接收后在SYN包中的序列号+1 (即SYN+ACK包) 发送给客户端
第三次:客户端收到服务端的SYN包后,在SYN包中的序列号+1后 (ACK包) 发送给服务端

为啥四次挥手?

四次挥手是TCP释放连接的过程。
原因:客户端和服务端会各自发送1次和回复1次,共4次

tcp/udp分别的应用场景?

tcp准确度高,适用于文件传输,电子邮件等场景
udp效率比较高,适用于直播,网络语音等场景

Java

ArrayList和LinkedList的区别、扩容机制以及底层实现

ArrayList基于数组实现,由于使用下标查询,所以查询比较快,增删数据会移动数据,所以增删略慢
扩容:数组是定长的,ArrayList是通过复制到新的数组来实现动态扩容。默认长度10,扩容1.5倍

LinkedList基于双向链表实现,插入元素只记录前一个元素和后一个元素,所以插入比较快。
不需要扩容。

ArrayList和LinkedList的线程安全解决办法?

  1. Collections.synchronizedList(new LinkedList<Object>())和Collections.synchronizedList(new ArrayList<Object>())
  2. Vector : 基于数组+synchronized
  3. CopyOnWriteArrayList、ConcurrentLinkedQueue

Set为什么不可重复?

set是无序不可重复的,底层使用了map, 比较key值来判断是否重复

Set怎么实现有序?

HashSet是无序的,
但是LinkedHashSet能保证元素添加的顺序,TreeSet能保证元素自然的顺序
如果想要自定义排序规则:
1.使用TreeSet存储
2.TreeSet内的元素需要实现Comparable接口,重写compareTo方法自定义排序规则。

HashMap、ConcurrentHashMap、HashTable的原理和区别?

HashMap的介绍
HashMap在JAVA8之后的结构是:数组(默认16个)+单向链表+红黑树
数组的每个元素对应一条链表,存储的是那条链表的头节点
数据存入的时候,对key做hash运算,计算出在数组中的下标,并存入该下标元素对应的链表中
当链表的长度超过8后转化为红黑树,当红黑树的元素少于6后转化为链表
扩容触发条件:HashMap的长度>容量加载因子(160.75),
扩容大小:2倍

区别
HashMap线程不安全,key可以为null,HashTable和ConcurrentHashMap线程安全,key不可以为null
HashTable使用数据+链表的结构,并加synchronize锁保证线程安全,
ConcurrentHashMap在HashMap的基础上使用了CAS+synchronize来保证线程安全。
HashTable锁住整个对象,效率偏低。ConcurrentHashMap只锁住数组的每个元素,锁的粒度更细,效率较高。

sleep和wait的区别?

1.sleep()是 Thread类的方法,wait()是 Object类中定义的方法
2.sleep()方法可以在任何地方使用,wait方法只能在 synchronized方法或synchronized块中使用
3.sleep()不会释放锁,wait()会。

什么是线程安全?

在多个线程操作访问某一个方法时,对资源的更改操作不会产生问题
实现方法:
1.synchronized:自动加锁释放锁
2.ReentrantLock:手动加锁释放锁
3.如果是集群结构,需要使用分布式锁

线程越多越好吗,为什么?

1.根据系统配置有关,
2.以一核为例,多线程其实是竞争一个线程的执行权,交替执行

有几种线程池,线程池的好处,哪些核心参数?

Java通过Executors提供四种线程池
1.newCachedThreadPool 创建一个可缓存线程池,可灵活回收空闲线程,若无可回收,则新建线程
2.newFixedThreadPool 创建一个定长线程池,可控制线程最大并发数,超出的线程会在队列中等待
3.newScheduledThreadPool 创建一个定长线程池,支持定时及周期性任务执行
4.newSingleThreadExecutor 创建一个单线程化的线程池,它只会用唯一的工作线程来执行任务

线程池的好处:使用线程池可以减少在创建和销毁线程的消耗,并提高线程的可管理性,且提供队列以及拒绝策略等功能。

核心参数
1.corePoolSize 线程池中核心线程的数量
2.maximumPoolSize 线程池中最大线程数量
3.keepAliveTime 非核心线程的最大空闲时间
4.workQueue 线程池中的任务队列
5.handler 拒绝策略

什么情况会触发拒绝策略?

当线程池的核心线程数+任务缓存队列已满并且线程池中的线程数目达到最大线程数量

ThreadLocal的使用场景?

ThreadLocal是线程之间互相隔离的变量,我们用ThreadLocal维护本线程的simpleDateFormat。

自己写一个String类,包名也是java.lang会是怎样?

手写的String类无效,会被真正的String覆盖。
而且在手写的String类中写个方法并调用,会报错:Stirng 没有该方法。

java类的周期可分为:加载,连接(验证、准备、解析),初始化、使用、卸载
其中类加载时候的机制:JVM有四个类加载器:
1.启动类加载器(Bootstrap ClassLoader):加载核心包
2.扩展类加载器(Extension ClassLoader):加载扩展包
3.应用程序类加载器(Application ClassLoader):加载我们写的程序和引用的jar包
4.自定义加载器(Custom ClassLoader):加载自定义的包

类的加载的时候会按照上面的顺序,至下而上的检查有没有被加载,然后至上而下的加载,由于java自身的String 优先 被启动类加载器加载,所以手写的java.lang.String 无效。
以上也是类加载的双亲委派机制

讲讲JVM内存模型?

堆,元空间,本地方法栈,虚拟机栈,程序计数器 (前面两个线程共享)
程序计数器:记录程序执行时的行数
虚拟机栈:存储对象的引用,8种基础类型,局部变量表,操作栈,动态链接,方法出口等信息
堆:存储对象实例
元空间:存储类的信息、方法、属性、常量、静态变量、常量池
本地方栈:存储native方法的信息

讲讲垃圾回收机制和算法?

垃圾回收机制:
一般情况下,一个对象创建后存在堆内存中年轻代的伊甸区,年轻代分为伊甸区和两个幸存区,对象经过回收从伊甸区移动到幸存区,再经历N次回收后,最终存活的对象移动到老年代。

垃圾回收算法:
年轻代使用的垃圾回收算法是复制算法,原因是年轻代大部分被回收,只需要复制少量存活的对象
老年代使用的垃圾回收算法是标记清除算法和标记整理算法。

垃圾回收触发条件
伊甸区满了触发Minor GC ,对年轻代回收
老年代满了触发Full GC ,对整个对内存回收

JVM调优目的:减少Full GC

什么对象会被认为是垃圾并回收掉?

1.引用计数算法:对象被引用的个数为0的会被回收
2.可达性算法:与引用链的无关联的对象会被回收

排序方法有哪些?

1.选择排序
2.冒泡排序
3.快速排序
4.选择排序
5.插入排序

数据结构有哪些

数组(Array):含有下标
栈(Stack):先进后出
队列(Queue):先进先出
链表(Linked List):手拉手
树(Tree):倒挂的树,有根节点和叶子节点这样式的。
散列表(Hash):key和value
堆(Heap):
图(Graph):

数据库

事务的隔离级别以及每个级别的会引发的问题?

事务隔离级别 脏读 不可重复 幻读
未提交读 发生 发生 发生
未提交读 避免 发生 发生
可重复读 避免 避免 发生
串行化 避免 避免 避免

建一个索引,使用Like查询,左右两边都加%。索引会起作用吗?为什么?

这个不会起作用,只有在左边没有%的情况下才会起作用。
原因后面补充

最左匹配原则的成因?

最左匹配的原则:MySQL执行sql时候在where后面字段从左到右匹配索引,遇到范围查询就停止,=和in可以乱序。
最左匹配的成因:联合索引是多个字段共同组成的B+tree结构,最左边的字段在树的最上边,按照顺序自上而下分布,而查询树结构就是从树的根节点往下查询。

什么是覆盖索引?

查询语句的索引起作用了,并且查询的字段也是索引本身的字段
就是覆盖索引,可避免回表查询。
执行计划时:Extra:Using index

那什么是回表?

和覆盖索引相反,查询的字段除了索引字段还有其他字段。
mysql查询完索引树后再回到表里,把其他字段查出来。
执行计划时:Extra:Using index condition

聚合索引和非聚合索引的区别?

主键索引是聚合索引,其他索引是非聚合索引
聚合索引叶子节点存储整条记录,非聚合索引叶子节点存储的是主键指针。

一条sql执行经历了什么?

首先MySQL会去检查这条语句有没有缓存的数据,有就结束了,没有开始检查语法,然后选择用哪些个索引,最后使用选择搜索引擎( InnoDB 还是 MyISAM)去执行。

expain怎么用?

explain叫执行计划,是mysql检验sql语句效率的工具,用法是直接加在sql语句的前面去执行。
我主要是看执行后的两个值 typeExtra
当type的值是index或all的时候,表示需要优化了
当Extra的值是Using filesort 或 Using temporary 表示需要优化了

遇到 Using temporary 和 Using filesort怎么优化?

Using temporary是使用到了临时表,常发生在order by 和group by 的语句中
Using filesort 使用了文件排序,即在内存和磁盘中排序
给 order by 或 group by 后面的字段加索引

什么是乐观锁和悲观锁?

乐观锁和悲观锁并发控制的两种思路
乐观锁:更新的时候校验更新前查到的数据是不是最新的,实现方法:CAS机制和版本号机制
悲观锁:更新前锁住数据,不让其他线程查询和更新,等到更新完成后,再释放锁。实现方法:加锁:数据库加锁select ... for update,代码加锁synchronized

数据库多大的时候需要分表?

分别为纵向分表和横向分表
纵向分表:一张表根据字段的活跃度不同为多张表,经常查询的放在一张表这样。
横向分表:数据量大的时候需要数据横向切割,分布在几张结构相同的表中,避免一张表过大,查询太慢,一般mysql在单表1000万的时候就需要了,这个还和服务器的配置、MySQL的性能、表结构的设计,索引的创建,查询的语句有关系。

ElasticSearch为什么比mysql 快?

ElasticSearch使用的倒排索引技术,MySQL使用的索引结构是B+tree。

怎么解决ElasticSearch 深分页问题?

ElasticSearch 在大数据量分页的时候,最后面的数据查询很慢(5万条以后),可以使用scroll滚动的方式去查询,根据每次查询得到的scroll_id去进行下次查询,类似于游标,和redis的scan命令查询差不多。
弊端,只能上一页下一页查询,不能跳页查询。

spring 和 mybatis

spring MVC 和sping boot 的区别?

spring MVC是spring 框架的一个模块,使用的MVC思想,M代表对象(Model),V代表页面(view),C代表(控制器)controller
在一定程度上封装并简化了原生的Servlet的WEB应用的开发。

spring boot是spring 框架的一个自动配置的完整开发包,简化了spring MVC在搭建web应用时的繁琐的各种配置,比如:视图解析器的配置、注入bean的扫描路径的配置等,它的特点是约定大于配置,很多配置都已经默认配置好了。
sping boot内嵌了tomcat,打包默认是jar包。

spring bean作用域?

singleton :IOC容器中只有一个
prototype:IOC容器中有多个
request:有效期是一次请求
session:有效期是一次会话
global session:有效期是一次启动

讲讲springboot如何实现自动装配的?

主要是springboot启动类上面的@SpringBootApplication注解的作用,它是一个复合注解
里面的@SpringBootConfiguration标记当前的类是配置类
@ComponentScan注解用来指定需要注入到IOC容器的包的路径
@EnableAutoConfiguration注解用来指定需要装配的类的配置文件
最后通过动态代理来实现自动装配。

BeanFactory 和FactoryBean 的区别?

日后更新

spring怎么解决循环依赖的问题?

循环依赖是多个类互相引用,分为构造依赖和属性循环依赖,
spring用三级缓存来解决属性循环依赖,详情日后更新。

AOP 的实现原理,什么情况下使用JDBC 的代理?

AOP是基于动态代理实现的,
如果目标类是接口,则用 jDKProxy来实现,否则用cglib
JDKProxy:通过ava的内部反射机制实现
cgib:以继承的方式动态生成目标类的代理,借助ASM实现

Spring中使用到的设计模式?

日后更新

懒汉模式和饿汉模式的区别?

懒汉模式:在实例化的时候初始化。
饿汉模式:在类加载时时候初始化。

mybatis什么时候使用${}?

#{}是预编译时候充当占位符的一种方式,可以防止sql注入。
${}是直接拼接sql,一般在表示字段名或表名的时候使用。from ${表名} ,order by ${字段名}

mybatis嵌套查询和嵌套结果有什么区别?

都是发生在结果映射的<resultMap>标签里。
都有嵌套的关系,对象嵌套对象用<association>标签,对象嵌套集合使用<collection>标签。
嵌套查询 是在嵌套的标签使用select="xxx"关联另一条查询语句,再次查询,有N+1问题。
嵌套结果 是将查询的结果自动映射到<resultMap>标签的嵌套关系中。

怎么使用mybatis的二级缓存?

1.在mybais配置文件中开启二级缓存
2.在相应的mapper.xml中加上cache标签。

中间件等

nginx 的负载均衡方式有哪些?

1.轮询
2.配置权重
3.根据IP做hash算法,同一个IP进同一个服务器
4.同一个url进入同一个服务器

redis为什么快?

运行在内存、数据结构简单、IO多路复用

redis有几种数据类型

8种,常用的5种:string、list、hash、set、sorted、set
3种不常见的bitmap(位图)、hyperloglog(不精准去重计数器)、Geo(地理信息定位)

redis的使用场景?

用作缓存,存储经常查询的数据,缓解数据库的压力
存储短信验证码,定时失效
利用redis的过期提醒,实现订单自动过期[《订单自动过期方案》
利用setnx命令实现分布式锁

缓存穿透、击穿、雪崩的成因和解决方案?

缓存击穿:热点key失效,此时大流量进来,请求穿过redis直接访问数据库。
解决方案:热点key的有效期设置永久。

缓存穿透:请求一个不存在的数据,redis没有就去查数据库,反反复复。
解决方案
1.将不存在的数据在redis中设置默认值并有有效期。弊端:如果有恶意攻击,会存大量的默认值。
2.布隆过滤器,弊端:有一定的误差。

缓存雪崩:有大量的key同时失效。
解决方案:key的有效期在一定范围内随机一点。

redis的更新策略?

修改数据:先操作数据库,再删除redis中的key
删除数据:先操作数据库,再删除redis中的key

redis 的持久化?

redis的持久化有两种,AOF和RDB。
AOF是全量的,RDB是增量的。

redis 哨兵的工作原理?

日后更新

怎么防止消息的丢失和重复?

我的项目用的RabbitMQ,消息丢失是使用消息队列会遇到的问题。往往由于网络抖动或服务宕机产生。
一般会发生在三个地方,1.生产者到消息队列,2.消息队列,3.消息队列到消费者。
生产者到消息队列防止消息丢失可以开启RabbitMQ接收到消息会应答的 confirm 模式,
消息队列开启持久化到数据库,可以避免宕机后消息丢失。
消费者也是通过一个手动应答的方式告诉RabbitMQ是否真正消费。

消息重复:对消费消息的方法加锁,并对消息的唯一性做判断。

分布式锁的实现方式有哪些?

redis的setnx :多个线程对一个key去set值,如果不存在key就会设置成功,否则set失败,set成功的就相当于拿到了锁,就可以处理某方法。处理完成删除key,即释放锁。
需要对key设置有效期,避免发生得到锁的线程发生意外,不能释放锁。

zookeeper的临时顺序节点:多个线程对某个持久化节点设置临时顺序节点,这些临时顺序节点是按照创建时间排序的,第一个创建节点的线程就相当于拿到了锁,处理完逻辑后删除第一个节点,第二个变成了第一个就拿到了锁这样..

服务注册与发现的实现原理?

服务注册于发现是微服务架构中服务之间调用的组件,常见的有Eureka、Nacos、Zookeeper
可以简单的想象成一个list,服务注册就相当于将服务的信息存储list,服务发现就相当于查询list,如果某个服务挂了,就从这个list中删除或标记为失效,可以通过组件向各服务发送心跳来确定服务是否正常。

spring cloud 的核心组件有哪些?

Eureka:服务注册于发现。
Feign:根据注解和选择的机器,拼接请求 url 地址,发起请求。
Ribbon:实现负载均衡。
Hystrix:熔断器,实现了不同服务调用的隔离,防止一个服务出现异常,拖垮整个服务链路,避免了服务雪崩的问题。
Zuul:网关管理,由 Zuul 网关转发请求给对应的服务,后端服务的总入口。

下面分享我这些年总结的一些Java后端架构以及面试资料,希望能帮助到还在努力奋斗的码农们。

(1)观看零基础学习视频

看视频学习是最快捷也是最有效果的方式,跟着视频中老师的思路,首先学习Java语法基础,再到框架,从基础到深入,还是很容易入门的。至于视频,网络上实际上有一大堆,我这边是学长给我的珍藏版,应该是搜索不到,如果你需要,当然我也可以免费分享给你。

(2)阅读前辈一些书籍和笔记

当有自己的理解能力的时候,会去阅读一些前辈整理的书籍或者手写的笔记资料,这些笔记详细记载了他们对一些技术点的理解,这些理解是比较独到,可以学到不一样的思路。

书籍和笔记

资料【获取方式】

关注+转发后,私信回复【Java】即可获取!

重要的事情说三遍,关注+转发、关注+转发、关注+转发,然后私信,才可以拿到哦!

©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 204,445评论 6 478
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 85,889评论 2 381
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 151,047评论 0 337
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 54,760评论 1 276
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 63,745评论 5 367
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 48,638评论 1 281
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 38,011评论 3 398
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 36,669评论 0 258
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 40,923评论 1 299
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,655评论 2 321
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 37,740评论 1 330
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 33,406评论 4 320
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 38,995评论 3 307
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 29,961评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 31,197评论 1 260
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 45,023评论 2 350
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 42,483评论 2 342