12. 用三个线程按顺序循环打印 abc 三个字母,比如 abcabcabc。
public class PrintABC { public static Boolean isThreadA = true; public static Boolean isThreadB = false; public static Boolean isThreadC = false; public static void main(String[] args) { final PrintABC abc = new PrintABC(); new Thread(new Runnable() { public void run() { for (int i = 0; i < 10; i++) { synchronized (abc) { while(!isThreadA) { try { abc.wait(); } catch (InterruptedException e) { // TODO Auto-generated catch block e.printStackTrace(); } } System.out.print("A"); isThreadA = false; isThreadB = true; isThreadC = false; abc.notifyAll(); } } } }).start(); new Thread(new Runnable() { public void run() { for (int i = 0; i < 10; i++) { synchronized (abc) { while(!isThreadB) { try { abc.wait(); } catch (InterruptedException e) { // TODO Auto-generated catch block e.printStackTrace(); } } System.out.print("B"); isThreadA = false; isThreadB = false; isThreadC = true; abc.notifyAll(); } } } }).start(); new Thread(new Runnable() { public void run() { for (int i = 0; i < 10; i++) { synchronized (abc) { while(!isThreadC) { try { abc.wait(); } catch (InterruptedException e) { // TODO Auto-generated catch block e.printStackTrace(); } } System.out.print("C"); isThreadA = true; isThreadB = false; isThreadC = false; abc.notifyAll(); } } } }).start(); } }
13. ThreadLocal 用过么,用途是什么,原理是什么,用的时候要注意什么。
14. 如果让你实现一个并发安全的链表,你会怎么做。
聊聊高并发(三十二)实现一个基于链表的无锁Set集合_ITer_ZC的专栏-CSDN博客
15. 有哪些无锁数据结构,他们实现的原理是什么。
ConcurrentLikedQueue是一个适用于高并发场景下的队列,通过无锁(CAS)的方式,实现了高并发状态下的高性能, 通常ConcurrentLikedQueue性能好于BlockingQueue。
ConcurrentLinkedQueue的其他方法:
peek():获取表头元素但不移除队列的头,如果队列为空则返回null。
remove(Object obj):移除队列已存在的元素,返回true,如果元素不存在,返回false。 add(E e):将指定元素插入队列末尾,成功返回true,失败返回false(此方法非线程安全的方法,不推荐使用)。
注意:
虽然ConcurrentLinkedQueue的性能很好,但是在调用size()方法的时候,会遍历一遍集合,对性能损害较大,执行很慢,最好用isEmpty()方法。
ConcurrentLinkedQueue不允许插入null元素,会抛出空指针异常。
ConcurrentLinkedQueue是无界的,所以使用时,一定要注意内存溢出的问题。即对并发不是很大中等的情况下使用,不然占用内存过多或者溢出,对程序的性能影响很大
16. 讲讲 java 同步机制的 wait 和 notify。
17. 多线程如果线程挂住了怎么办。
18. countdowlatch 和 cyclicbarrier的内部原理和用法,以及相互之间的差别。
1.CountDownLatch减计数,CyclicBarrier加计数。 2.CountDownLatch是一次性的,CyclicBarrier可以重用。 应用场景 对于CountDownLatch来说,重点是那个“一个线程”, 是它在等待, 而另外那N的线程在把“某个事情”做完之后可以继续等待,可以终止。 对于CyclicBarrier来说,重点是那N个线程,他们之间任何一个没有完成,所有的线程都必须等待。
19. 使用 synchronized 修饰静态方法和非静态方法有什么区别。
所有的非静态同步方法用的都是同一把锁——实例对象本身,也就是说如果一个实例对象的非静态同步方法获取锁后, 该实例对象的其他非静态同步方法必须等待获取锁的方法释放锁后才能获取锁, 可是别的实例对象的非静态同步方法因为跟该实例对象的非静态同步方法用的是不同的锁, 所以毋须等待该实例对象已获取锁的非静态同步方法释放锁就可以获取他们自己的锁。 而所有的静态同步方法用的也是同一把锁——类对象本身,这两把锁是两个不同的对象, 所以静态同步方法与非静态同步方法之间是不会有竞态条件的。但是一旦一个静态同步方法获取锁后, 其他的静态同步方法都必须等待该方法释放锁后才能获取锁,而不管是同一个实例对象的静态同步方法之间, 还是不同的实例对象的静态同步方法之间,只要它们同一个类的实例对象!
20. 简述 ConcurrentLinkedQueue 和 LinkedBlockingQueue 的用处和不同之处。
LinkedBlockingQueue 一个由链接节点支持的可选有界阻塞队列。
ConcurrentLinkedQueue 通过compare and swap(简称CAS)协议的方式,来保证多线程情况下数据的安全,不加锁,主要使用了Java中的要使用了Java中的sun.misc.Unsafe类来实现
21. 导致线程死锁的原因?怎么解除线程死锁。
一、导致线程死锁的原因 两个不同的线程加锁的顺序不一样 二、怎么解除线程死锁 1.加锁过期时限,当一个线程持有锁的时间达到一定值时,wait释放锁,等待一段随机的时间再重试 2.当几个线程都要访问共享资源A、B、C时,保证使每个线程都按照同样的顺序去访问它们,比如都先访问A,在访问B和C。
22. 非常多个线程(可能是不同机器),相互之间需要等待协调,才能完成某种工作,问怎么设计这种协调方案。
CountDownLatch,CyclicBarrier
23. 正确使用 Volatile 变量
正确使用 volatile 变量的条件
您只能在有限的一些情形下使用 volatile 变量替代锁。要使 volatile 变量提供理想的线程安全,必须同时满足下面两个条件:
1对变量的写操作不依赖于当前值。
2该变量没有包含在具有其他变量的不变式中。
并发编程之 Java 内存模型 + volatile 关键字 + Happen-Before 规则_击水三千里的专栏-CSDN博客
24. BIO,NIO与AIO的区别
Java BIO :在JDK1.4出来之前,我们建立网络连接的时候采用BIO模式,需要先在服务端启动一个 ServerSocket,然后在客户端启动Socket来对服务端进行通信,默认情况下服务端需要对每个请求建立一堆线 程等待请求,而客户端发送请求后,先咨询服务端是否有线程相应,如果没有则会一直等待或者遭到拒绝请求, 如果有的话,客户端会线程会等待请求结束后才继续执行。 Java NIO : 同步非阻塞,服务器实现模式为一个请求一个线程,即客户端发送的连接请求都会注册到多路复用 器上,多路复用器轮询到连接有I/O请求时才启动一个线程进行处理。 Java AIO(NIO.2) : 异步非阻塞,NIO不同,当进行读写操作时,只须直接调用API的read或write方法即可, 这两种方法均为异步的。 NIO方式适用于连接数目多且连接比较短(轻操作)的架构,比如聊天服务器,并发局限于应用中,编程比较复 杂,JDK1.4开始支持。 AIO方式使用于连接数目多且连接比较长(重操作)的架构,比如相册服务器,充分调用OS参与并发操作,编程比 较复杂,JDK7开始支持
25.synchronized和reentrantlock异同
相同点
都实现了多线程同步和内存可见性语义
都是可重入锁
不同点
实现机制不同 synchronized通过java对象头锁标记和Monitor对象实现 reentrantlock通过CAS、
ASQ(AbstractQueuedSynchronizer)和locksupport(用于阻塞和解除阻塞)实现 synchronized依赖jvm内
存模型保证包含共享变量的多线程内存可见性 reentrantlock通过ASQ的volatile state保证包含共享变量的多
线程内存可见性
使用方式不同 synchronized可以修饰实例方法(锁住实例对象)、静态方法(锁住类对象)、代码块(显示指定
锁对象) reentrantlock显示调用trylock()/lock()方法,需要在finally块中释放锁
功能丰富程度不同 reentrantlock提供有限时间等候锁(设置过期时间)、可中断锁(lockInterruptibly)、
condition(提供await、signal等方法)等丰富语义 reentrantlock提供公平锁和非公平锁实现
synchronized是非公平锁,不可设置等待时间、不可被中断(interrupted),
26.公平锁和非公平锁
公平锁:
获取不到锁的时候,会自动加入队列,等待线程释放后,队列的第一个线程获取锁
非公平锁:
获取不到锁的时候,会自动加入队列,等待线程释放锁后所有等待的线程同时去竞争
27.为什么Java中 wait 方法需要在 synchronized 的方法中调用?
1) Java 会抛出 IllegalMonitorStateException,如果我们不调用来自同步上下文的wait(),notify()或者notifyAll()方法。
2) 如果我们不在同步方法或块中调用它们就可能存在wait()和 notify()之间的竞态条件。由于竞态条件,没有获取到锁,我们可能会丢失通知,如果我们使用缓冲区或只使用一个元素,生产线程将永远等待,你的程序将挂起
1、submit有返回值,而execute没有
submit它的功能是提交指定的任务去执行并且返回Future对象,即执行的结果
2、submit方便Exception处理
意思就是如果你在你的task里会抛出checked或者unchecked exception,而你又希望外面的调用者能够感知这些exception并做出及时的处理,那么就需要用到submit,通过捕获Future.get抛出的异常。
TCP 与 HTTP
1. http/1.0、http/1.1和http2.0有什么区别
在http1.0中,当建立连接后,客户端发送一个请求,服务器端返回一个信息后就关闭连接, 当浏览器下次请求的时候又要建立连接,显然这种不断建立连接的方式,会造成很多问题。 在http1.1中,引入了持续连接的概念,通过这种连接,浏览器可以建立一个连接之后, 发送请求并得到返回信息,然后继续发送请求再次等到返回信息,也就是说客户端可以连续发送多个请求,而不用等待每一个响应的到来。 在http/2.0中,支持多路复用技术,同一个连接并发处理多个请求(NIO),http/1.1可以通过建立多个TCP解决
2. TCP 三次握手和四次挥手的流程,为什么断开连接要4次,如果握手只有两次,会出现什么。
知识铺垫
TCP看似复杂,其实可以归纳为以下5种报文
(1)SYN
(2)Data (唯一携带用户数据)
(3)FIN
(4)Reset
(5)ACK
- 其中1、2、3分别为建立连接、数据传输、断开连接,这三种报文对方接收到一定要ACK确认,为何要确认,因为这就是可靠传输的依赖的机制。如果对方在超时时间内不确认,发送方会一直重传,直到对方确认为止、或到达重传上限次数而Reset连接。
- 4、5 为重置连接报文、确认ACK报文,这两种报文对方接收到要ACK确认吧?不需要!自然发送方也不会重传这2种类型的报文。
为何Reset报文不需要ACK确认?
因为发送Reset报文的一端,在发送完这个报文之后,和该TCP Session有关的内存结构体瞬间全部释放,无论对方收到或没有收到,关系并不大。
- 如果对方收到Reset报文,也会释放该TCP Session 的相关内存结构体。
- 如果对方没有收到Reset 报文,可能会继续发送让接收方弹射出Reset报文的报文,到最后对方一样会收到Reset 报文,并最终释放内存。
为何ACK报文不需要ACK确认?
这里的ACK报文,是指没有携带任何数据的裸ACK报文,对方收到这样的ACK报文,自然也不需要ACK。
否则,对方为了ACK己方的ACK,那己方收到对方的ACK,也要ACK对方的ACK,这就是一个死循环,永无止息。所以为了避免这个死循环,一律不允许ACK对方的裸ACK报文。
TCP连接建立过程:
1、客户端向服务器发送SYN,其中seq=x。
2、服务器收到SYN报文段后,发送SYN+ACK,其中seq=y,确认号=x+1。
3、客户端收到SYN+ACK报文段后,发送ACK,确认号=y+1。服务器收到ACK报文段后,连接建立。
TCP连接断开过程:
1、客户端TCP模块在收到应用程序的通知后,发送FIN,seq=x。
2、服务器收到FIN报文段,发送ACK,确认号=x+1,并且通知应用程序客户端关闭了连接。客户端收到ACK报文段。
3、服务器端的应用程序通知TCP关闭连接,服务器端TCP发送FIN+ACK,seq=y,确认号=x+1(此时服务端已经断开连接)。
4、客户端收到FIN+ACK报文段后,发送ACK,确认号y+1。服务器收到ACK报文段后,连接断开。
为什么TCP建立连接不是四次握手?
- A 发送SYN 报文给B,这是第一次报文交互。
- B发送ACK确认A的SYN报文,这是第二次报文交互
- B发送自己的SYN报文给A,这是第三次报文交互
- A需要ACK确认B的SYN报文,这是第四次报文交互
以上的演绎没有问题,但是报文2、3为何要分开发送呢?增加了延迟不说,同时还白白浪费了网络的带宽
为什么断开连接要4次,如果握手只有两次,会出现什么?
为什么不把断开连接的第二步,第三步合在一起进行呢?
因为,第二步中,服务器端通知应用程序并获得反馈信息可能需要可观的时间,这可能涉及人机交互操作,也可能服务器应用层暂时还不想关闭连接。第二步结束后,服务器还可以继续通过这条连接发送数据给客户端,客户端已经不能发送数据了,但是仍然可以回复ACK。第二步中服务器立即发送确认是为了防止客户端重传FIN报文。
3. TIME_WAIT 和 CLOSE_WAIT 的区别。
CLOSE_WAIT:等待关闭,是被动关闭连接形成的,也就是第二次挥手时产生的状态。也就是当对方close一个SOCKET后发送FIN报文给自己,系统会回应一个ACK报文给对方,此时进入CLOSE_WAIT状态。接着,我们需要考虑的事情是查看是否还有数据发送给对方,如果没有就可以close这个链接,发送FIN给对方,也既关闭连接。所以在CLOSE_WAIT状态时,需要查看自己是否需要关闭连接。
TIME_WAIT:是主动关闭连接方形成的,表示收到了对方的FIN报文,并发送ACK报文,等待2MSL(Maximum Segment Lifetime:报文最大生存时间)约4分钟时间后进入CLOSE状态。主要是防止最后一个ACK丢失(之最后一个客户端ack),由于TIME_WAIT等待时间较长,因此server端尽量减少关闭。
4. 说说你知道的几种 HTTP 响应码,比如 200, 302, 404。
200 OK:表示客户端请求成功。 301 redirect: 301 代表永久性转移(Permanently Moved) 302 redirect: 302 代表暂时性转移(Temporarily Moved ) 400 Bad Request 语义有误,不能被当前服务器理解。 401 Unauthorized 当前请求需要用户验证。 403 Forbidden 服务器收到消息,但是拒绝提供服务。 404 Not Found 请求资源不存在。 408 Request Timeout 请求超时,客户端没有在服务器预备等待的时间内完成发送。 500 Internal Server Error 服务器发生不可预期的错误。 503 Server Unavailable 由于临时的服务器维护或过载,服务器当前不能处理请求,此状况知识临时的,可恢 复
5. 当你用浏览器打开一个链接的时候,计算机做了哪些工作步骤。
域名解析--> 发起TCP的3次握手 --> 建立TCP连接后发起http请求 --> 服务器响应http请求--> 浏览器得到html代码 --> 浏览器解析html代码,并请求html代码中的资源(如js、css、图片等) --> 浏览器对页面进行渲染呈现给用户
6. TCP/IP 如何保证可靠性,说说 TCP 头的结构。
7. 如何避免浏览器缓存。
无法被浏览器缓存的请求:
HTTP信息头中包含Cache-Control:no-cache,pragma:no-cache,或Cache-Control:max-age=0等告诉浏览器不用缓存的请求
需要根据Cookie,认证信息等决定输入内容的动态请求是不能被缓存的
经过HTTPS安全加密的请求(有人也经过测试发现,ie其实在头部加入Cache-Control:max-age信息,firefox在头部加入Cache-Control:Public之后,能够对HTTPS的资源进行缓存,参考《HTTPS的七个误解》)
POST请求无法被缓存
HTTP响应头中不包含Last-Modified/Etag,也不包含Cache-Control/Expires的请求无法被缓存
8. 简述 Http 请求 get 和 post 的区别以及数据包格式。
GET提交,请求的数据会附在URL之后(就是把数据放置在HTTP协议头<request-line>中 POST提交:把提交的数据放置在是HTTP包的包体<request-body>中
9. 简述 HTTP 请求的报文格式。
一个HTTP请求报文由请求行(request line)、请求头部(header)、空行和请求数据4个部分组成
10. HTTPS 的加密方式是什么,讲讲整个加密解密流程。
HTTPS其实是有两部分组成:HTTP + SSL / TLS,也就是在HTTP上又加了一层处理加密信息的模块。服务端和客户端的信息传输都会通过TLS进行加密,所以传输的数据都是加密后的数据
1. 客户端发起HTTPS请求
2. 服务端的配置
采用HTTPS协议的服务器必须要有一套数字证书,可以自己制作,也可以向组织申请
3. 传送证书
这个证书其实就是公钥,只是包含了很多信息,如证书的颁发机构,过期时间等等。
4. 客户端解析证书
这部分工作是有客户端的TLS来完成的,首先会验证公钥是否有效,比如颁发机构,过期时间等等,如果发现异常,则会弹出一个警告框,提示证书存在问题。如果证书没有问题,那么就生成一个随机值(私匙)。然后用证书对该随机值进行加密。就好像上面说的,把随机值用锁头锁起来,这样除非有钥匙,不然看不到被锁住的内容。
5. 传送加密信息
这部分传送的是用证书加密后的随机值,目的就是让服务端得到这个随机值,以后客户端和服务端的通信就可以通过这个随机值来进行加密解密了。
6. 服务段解密信息
服务端用私钥解密后,得到了客户端传过来的随机值(私钥),然后把内容通过该值进行对称加密。所谓对称加密就是,将信息和私钥通过某种算法混合在一起,这样除非知道私钥,不然无法获取内容,而正好客户端和服务端都知道这个私钥,所以只要加密算法够彪悍,私钥够复杂,数据就够安全。
7. 传输加密后的信息
这部分信息是服务端用私钥加密后的信息,可以在客户端被还原。
8. 客户端解密信息
客户端用之前生成的私钥解密服务端传过来的信息,于是获取了解密后的内容。整个过程第三方即使监听到了数据,也
11.对称加密和非对称加密
12.TCP与UDP的区别是什么
1.基于连接与无连接;
2.对系统资源的要求(TCP较多,UDP少);
3.UDP程序结构较简单;
4.流模式与数据报模式 ;
5.TCP保证数据正确性,UDP可能丢包,TCP保证数据顺序,UDP不保证。
UDP应用场景:
1.面向数据报方式
2.网络数据大多为短消息
3.拥有大量Client
4.对数据安全性无特殊要求
5.网络负担非常重,但对响应速度要求高
架构设计与分布式
1. 常见的缓存策略有哪些,你们项目中用到了什么缓存系统,如何设计的。
2. 用 java 自己实现一个 LRU。
3. 分布式集群下如何做到唯一序列号。
4. 设计一个秒杀系统,30 分钟没付款就自动关闭交易。
5. 如何使用 redis 和 zookeeper 实现分布式锁?有什么区别优缺点,分别适用什么场景。
Redis 的分布式锁而言,它有以下缺点:
它获取锁的方式简单粗暴,获取不到锁直接不断尝试获取锁,比较消耗性能。
另外来说的话,Redis 的设计定位决定了它的数据并不是强一致性的,在某些极端情况下,可能会出现问题。锁的模型不够健壮
对于 ZK 分布式锁而言:
ZK 天生设计定位就是分布式协调,强一致性。锁的模型健壮、简单易用、适合做分布式锁。
如果获取不到锁,只需要添加一个监听器就可以了,不用一直轮询,性能消耗较小。
但是 ZK 也有其缺点:如果有较多的客户端频繁的申请加锁、释放锁,对于 ZK 集群的压力会比较大。
6. 如果有人恶意创建非法连接,怎么解决。
7. 分布式事务:XA,2PC,3PC,TCC
XA协议
XA则规范了TM与RM之间的通信接口,在TM与多个RM之间形成一个双向通信桥梁,从而在多个数据库资源下保证ACID四个特性。目前知名的数据库,如Oracle, DB2,mysql等,都是实现了XA接口的,都可以作为RM。
2PC
在处理分布式事务时分为两个阶段:voting(投票阶段,有的地方会叫做prepare阶段)和commit阶段。
3PC
协议在协调者和参与者中都引入 超时机制,并且把两阶段提交协议的第一个阶段拆分成了两步:询问,然后再锁资源,最后真正提交。三阶段提交的三个阶段分别为:can_commit,pre_commit,do_commit。
2PC和3PC的区别:
相对于2PC,3PC主要解决的单点故障问题,并减少阻塞。一旦参与者无法及时收到来自协调者的信息之后,他会默认执行commit。而不会一直持有事务资源并处于阻塞状态。无论是二阶段提交还是三阶段提交都无法彻底解决分布式的一致性问题。世上只有一种一致性算法,那就是Paxos,所有其他一致性算法都是Paxos算法的不完整版
TCC
Try阶段:完成所有业务检查(一致性),预留业务资源(准隔离性)
Confirm阶段:确认执行业务操作,不做任何业务检查, 只使用Try阶段预留的业务资源。要满足幂等性。
Cancel阶段:取消Try阶段预留的业务资源。
TCC与XA两阶段提交二者之间的对比 :
TCC是业务的分布式事务,最终一致性,不会出现长事务的锁风险,try是本地事务,锁定资源后就提交事务,confirm/cancel也是本地事务,可以直接提交事务,所以多个短事务不会出现长事务的风险。
8. 什么是一致性 hash。
假设:我们增加了一台缓存服务器,那么缓存服务器的数量就由4台变成了5台。那么原本hash(a.png) % 4 = 2 的公式就变成了hash(a.png) % 5 = ? , 可想而知这个结果肯定不是2的,这种情况带来的结果就是当服务器数量变动时,所有缓存的位置都要发生改变!换句话说,当服务器数量发生改变时,所有缓存在一定时间内是失效的,当应用无法从缓存中获取数据时,则会向后端数据库请求数据。
一致性Hash算法也是使用取模的方法,只是,刚才描述的取模法是对服务器的数量进行取模,而一致性Hash算法是对2^32取模。一致性Hash算法对于节点的增减都只需重定位环空间中的一小部分数据,具有较好的容错性和可扩展性。
想要深入理解可以看:
9. 什么是 restful,讲讲你理解的 restful。
10. 如何设计建立和保持 100w 的长连接。
11. 如何防止缓存雪崩。
12. 解释什么是 MESI 协议(缓存一致性)。
13. 说说你知道的几种 HASH 算法,简单的也可以。
14. 什么是 paxos 算法。
15. 什么是 zab 协议。
整个ZAB协议主要包括消息广播和崩溃恢复两个过程,进一步可以分为三个阶段,分别是:
发现 Discovery
同步 Synchronization
广播 Broadcast
组成ZAB协议的每一个分布式进程,都会循环执行这三个阶段,将这样一个循环称为一个主进程周期。
16. 一个在线文档系统,文档可以被编辑,如何防止多人同时对同一份文档进行编辑更新。
17. 线上系统突然变得异常缓慢,你如何查找问题。
18. 说说你平时用到的设计模式。
19. Dubbo 的原理,数据怎么流转的,怎么实现集群,负载均衡,服务注册和发现。重试转发,快速失败的策略是怎样的。
20. 一次 RPC 请求的流程是什么。
21. 异步模式的用途和意义。
22. 缓存数据过期后的更新如何设计。
23. 编程中自己都怎么考虑一些设计原则的,比如开闭原则,以及在工作中的应用。
24. 设计一个社交网站中的“私信”功能,要求高并发、可扩展等等。画一下架构图。
25. MVC 模式,即常见的 MVC 框架。
26. 聊了下曾经参与设计的服务器架构。
27. 应用服务器怎么监控性能,各种方式的区别。
28. 如何设计一套高并发支付方案,架构如何设计。
29. 如何实现负载均衡,有哪些算法可以实现。
30. Zookeeper 的用途,选举的原理是什么。
31. Mybatis 的底层实现原理。
MyBatis底层就是JDBC 所以他的核心就是配置文件 : 1:全局配置文件 (配置数据源 事务运行时信息) 2:映射文件(执行statement的相关信息,包括SQL语句,输入参数,输出结果) MyBatis把全局配置文件加载到内容中 构建出SqlSessionFactory ,这个工厂的作用相当于生产对象 生产SqlSession。 SqlSession :它是一个面向程序员的接口,可以操作数据库。 接口有一个默认实现DefaultSqlSession。 在SqlSession 中有一个executor 执行器。 SqlSession 本身不能操作数据库 需要通过这个执行器去操 作。有2个实现 一个叫做基本执行器,还有一个缓存执行器 (默认)。 MappedStatement:封装了执行Statement信息,包括SQL语句 输入参数,输出结果。由它去操作数 据库。 输入输出参数类型: 1:基本类型 2:自定义类型 3:hashmap 根据源码:看到Sqlsession内部并不能直接操作数据库。而是利用内部的一个执行器去操作数据库。执行器执行 的时候会去执行MappedStatement 到最后才去真正执行数据库。
32. 请思考一个方案,设计一个可以控制缓存总体大小的自动适应的本地缓存。
33. 请思考一个方案,实现分布式环境下的 countDownLatch。
34. 后台系统怎么防止请求重复提交。
用隐藏表单记录token属性。当提交表单后,应用程序会比较隐藏域中的值和Session域中的标志号(比较比较之后会清除当前用户Session中的token),如果相同就处理表单数,如果不相同就会忽略表单请求同时生成新的token存入Session中。当重复提交表单时,当前Session域中会不存在相应的表单标识号。
35. 如何看待缓存的使用(本地缓存,集中式缓存),简述本地缓存和集中式缓存和优缺点。本地缓存在并发使用时的注意事项。
36. 描述一个服务从发布到被消费的详细过程。
37. 讲讲你理解的服务治理。
38. 如何做到接口的幂等性。
接口幂等性,只要保证接口内的逻辑不涉及接口外的对象状态累积或变迁即可。 譬如说需求是: 当用户点击赞同时,将答案的赞同数量+1。 改为: 当用户点击赞同时,确保答案赞同表中存在一条记录,用户、答案。 赞同数量由答案赞同表统计出来
39.集群部署时的分布式session如何实现?
(1)tomcat + redis
(2)spring session + redis
(3)RedisSession jar包
40.如果让你设计一个消息中间件,你会怎么做?
生产消费模型以及核心数据结构
可以先允许数据写入内存作为一个缓冲,然后每隔几秒再把数据刷入磁盘文件中,数据写入磁盘文件之后,是不是要有相应的一些metadata来标识这个数据的offset偏移量,和内置的唯一id。一个queue里的数据,是会均匀分配给消费者的各个实例