集合:
LinkedList:
数据结构:双向列表
查询时间复杂度:O(n),插入时间复杂度:O(1)
扩容:每次添加1个节点
ArrayList:
数据结构:数组
查询时间复杂度:O(1),插入时间复杂度:O(n)
扩容:每次扩展1.5倍容量
零拷贝:
1、减少用户态和内核态对CPU的竞争,减少上下文切换
2、用户应用程序可以避开操作系统直接访问硬件存储
3、避免操作系统内核缓存区之间进行数据拷贝操作
4、数据传输尽量让DMA来做
系统函数read()和write()
优化一:read()修改为mmap()。优点:减少一次copy。缺点:mmap()出错后,进程会被终端
优化二:使用sendfile,减少数据拷贝的次数,减少上下文切换,数据传送始终只发生在kernel space
优化三:使用sendfile,利用硬件技术,减少kernel space的数据拷贝。数据拷贝时,页缓存的数据位置和长度发送给socket缓存。数据拷贝时,直接从硬件地址获取
HashMap:
容量扩容:超过hash因子(0.75)后,需要进行扩容,将数据扩大2倍
并发访问,容量变化时,会出现并发问题
JDK1.7版本及之前的版本:
实现方式:位桶 + 链表,使用链表处理冲突(拉链发)
JDK1.8版本及之后的版本:
实现方式:位桶 + 链表 + 红黑树,当链表长度超过阈值(8)时,将链表转换为红黑树
ConcurrentHashMap:
JDK1.7版本及之前的版本:
实现方式:分段锁(继承ReentrantLock),对每个分段进行加锁。每个分段就是一个HashEntry。HashEntry中的数据结构:数组+链表
JDK1.8版本及之后的版本:
实现方式:
取消分段锁(),直接采用transient volatile HashEntry<K, V>[] table保存数据,采用table数组元素作为锁,从而实现了对每一行数据进行加锁,并发控制使用
Synchronized和CAS操作。
数组 + 单项链表 + 红黑树
Hash冲突解决方法:
1、开放地址法
2、再哈希
3、链地址法
4、建立公共溢出区
TheadLocal:
实现方式:静态内部类TheadLocalMap维护一个数组table
内存泄漏:
原因:key是弱引用,value是强引用。线程退出后,value才能被回收。
解决方法:调用set()、get()或remove() 方法清除value值
ThreadLocal和Synchronized的区别:
Synchronized是通过线程等待,牺牲时间来解决访问冲突
ThreadLocal是通过每个线程单独一份存储空间,牺牲空间来解决冲突,具有线程隔离的效果
需求:主线程生成的变量需要传递到子线程中进行使用
解决方法:InheritableThreadLocal