最近有位读者投简历去一家小公司面试时,和面试官聊了一个小时的并发编程,全程记录。面试时小心翼翼,如履薄冰,生怕说错一句话,错失良机,着急,面试紧张卡顿。不知道你有没有这个问题?_采访者:_你知道CAS吗?你能告诉我吗?_Me:_CAS(CompareAndSwap),比较并交换。整个AQS同步组件,Atomic原子类操作等都是基于CAS实现的,甚至在JDK1.8版本中ConcurrentHashMap也调整为CAS+synchronized。可以说CAS是整个JUC的基石。CAS的实现其实并不难。CAS中有3个参数:内存值V、旧期望值A、待更新值B。当且仅当内存值V的值等于旧的期望值A时,内存值V的值才会修改为B,否则什么都不做,是乐观锁。伪代码如下:_I:_然后举个AtomicInteger的例子,给面试官解释CAS的实现。_采访者:_CAS有没有漏洞?_Me:_CAS高效的解决了原子问题,但是还是有一些缺陷,主要体现在三个方面:1.循环时间过长:如果spinCAS长时间失效,会带来非常大的负载到CPU。开销,在JUC中,有些地方限制了CAS自旋的次数。2.只能保证一个共享变量原子操作:看了CAS的实现就知道这个只能针对一个共享变量。如果有多个共享变量,只能使用锁。或者您可以使用CAS将多个变量集成为一个变量。3、ABA问题:CAS需要检查运算值是否发生变化,没有变化就更新,但是有这样一种情况:如果一个值本来是A,变成B,然后又变成A,那么在CAS检查的时候,会发现没有变化,但本质上发生了变化。这就是所谓的ABA问题。ABA问题的解决方法是加版本号,即给每个变量加一个版本号,每变化一次就加1,即A->B->A,变成1A->2B->3A.比如在原子类中使用AtomicInteger会出现ABA问题,使用AtomicStampedReference就可以解决ABA问题。采访者:能谈谈轻量化锁吗?面试官:先说说你对synchronized的理解。面试官:什么是原子操作?面试官:Executors框架是什么?面试官:什么是阻塞队列?阻塞队列的实现原理是什么?如何使用阻塞队列实现生产者消费者模型?面试官:CycliBarriar和CountdownLatch有什么区别?面试官:Java中使用的线程调度算法是什么?我:...............................................总结面试时,先说话简而言之,面试官会知道你的水平。你用了很多东西,但是你不明白底层的原理。面试官一问,你就傻了……
