零碎点java经验
0 上线文切换为什么会增加开销?
线程上下文切换:主动切换,被动切换; 主动切换指的是通过线程间通信,去决定线程在满足条件下是否需要阻塞或执行;而被动切换是指时间片用完了,cpu需要给其它线程让出执行权,可能是“跨进程的”。
如何优化线程切换带来的性能消耗呢?
1 减少锁的资源竞争减小(rl rrl sync)锁影响的代码块大小,而且编译器在检测时也会做: “锁消除”,“锁增粗优化”。
2 在使用sync加wait以及notify和notifyAll时,尽量避免使用notifyAll,因为notifyAll会唤醒所有线程,在一次让没有拿到执行权的线程进行了一次线程状态切换。 我们可以使用ReentranLock+condition来进行操作,condition可以更加精准的唤醒线程。
1 删减库存时可以使用基于version的乐观锁,而且update时需要where条件使用id(主键或者唯一索引)进行查询,否则会变成表锁。
2 内部类引用外面的变量,为什么不能修改?
原因是内部类在编译以后会生成一个新的class文件,而在原来的主类中引用了这个类,并通过构造函数或指定的函数,将参数传入的,并存到了内部类的全局变量中。
这种情况下即使是对内部类变量赋值了对外面的变量仍然不起作用,这一样会导致内外不一致,毫无意义。
3 HashMap 原理
(1)数组和链表的结构
(2)Hash算法,高16位无符号右移动16位,与原hashcode做异或运算,这样会让hashcode重复概率降低
(3)node对象一般情况下放在“newhashcode与数组长度减一的按位与运算值”索引位置上,发生hash碰撞以后则以第一个元素为头节点构建链表(最长为6)
(4)hashmap的初始长度为1<<4,负载因子为0.75f,一旦数据量超过75%以后,就会扩容重新计算每个数据应该出现的位置。
(5)扩容计算原则,如果没有链表则直接hashcode&table.length按位与计算,确定位置;
---如果发现有链表的情况则根据 hashcode&oldCap(旧的链表长度)==0 则原位置不动,如果计算结果不为0则保存在“原索引值+扩容长度”为索引位置进行存储
(6)而且在1.8版本有”高低位链表”的概念,而且不会出现1.7版本的链表倒置问题,以低位置链表为例,从第一个node开始即为loHead和loTail,每向后遍历出一个节点则将引用指向loTail.next
(7)长度超过8个转换为平衡二叉树,小于6个则转回链表。
4 HashMap 初始为什么是16?
进行&运算的时候是与16-1进行运算,而15的各个位上都是1,运算时会减少hash碰撞的概率。因为与1运算比较公平,结果是1,结果是0的情况各占50%
5 Hashmap线程不安全表现在哪?
(1) 可能会丢数据:当发生hash碰撞后,A线程获得到了某链表的最后一个位置,这时候时间片轮转,B线程也获得到相同的位置并插入值成功,这时A恢复运行,继续插入操作会覆盖B的值。
(2)只有老的1.7版本会get时死循环无法读取数据(链表倒置所导致):A线程执行到链表节点重新分配位置时A挂起,B开始执行并完成resize方法;因为1.7中扩容时,链表重新分配存储位置会导致链表倒置,那B线程已经执行完毕,现在A继续执行,则会将原有已经转置的链表在转制回去,但此时已经收尾的节点已经链接,变成了环形链表。如图说明:
第一次倒置:

线程A再次启动时第二次倒置:

6 StringBuilder 为什么线程不安全?
(1)StringBuilder的内部维护了两个共享变量,一个是char数组用来放置即将要拼接的字符,另一个count用来记录当前的总字符长度,那么在append方法中 count += len; 是线程不安全的,完全可以导致count并发时长度算错。
(2)在char数组扩容的时候,可以导致数组越界异常。

7 红黑树,内幕?
红黑树是一种自平衡的二叉查找树
它具有以下5个性质:
1、节点颜色必须是红色或者黑色
2、根节点是黑色
3、每个叶子节点(NIL节点、空节点)是黑色的
4、每个红色节点的两个子节点都是黑色
5、从任一节点到每个叶子的所有路径都包含数目相同的黑色节点
8 long和double在64位机器上没有原子操作?
因为线程栈的基本单位是32位的slot,这也是为什么栈中只能存储基本类型而不能存储对象的原因,64位的机器要使用两个slot进行存储,所以存在多线程并发问题。
8 线程的5种状态?
1)新建状态
2)等待状态
3)计时等待状态
4)运行态
5)锁态
6)终止状态

9 java 在重写equals方法的时候为什么要重写hashCode方法
默认情况下,hashCode返回的是内存对象的地址。equals方法本身就是先去对比内存地址,如果仅仅重写了equals方法而不重写hashCode,很可能导致对象本身各个属性是相同的,但由于hashCode不同而导致最终返回false。

浙公网安备 33010602011771号