- 线程安全的理解?
- 守护线程的理解?
- threadlocal的底层原理
- 并发、并行与串行之间的区别?
- Java死锁应如何避免?-√ Java死锁由四个因素导致:
- 资源是互斥资源 每次仅可由单个线程持有
- 在获得所有资源之前,线程自身不释放已持有资源
- 所需资源在其他线程上,且不可被剥夺
- 循环依赖,A持有B所需资源,B持有A所需资源
- 线程池底层工作原理-√
- 线程池中阻塞队列的作用?线程池为何先添加队列而不是先创建线程-√
- ReentrantLock中的公平锁与非公平锁的底层实现
- ReentrantLock的tryLock()与lock()区别
线程安全说的是,当多个线程并发访问互斥资源时,读写互斥资源的代码逻辑能正常处理,获得正确结果,不会互相干扰的情况。
守护线程是与普通线程相区分的概念,用户一般使用的就是普通线程,普通线程有自身独立的生命周期,而守护线程的生命周期取决于普通线程,只有当所有相关的普通线程都结束时,守护线程才会结束。
守护线程是为所有普通线程提供服务的线程
threadlocal:在线程里面多保存了一份map结构,由于变量存在线程内部,从而保证不同线程互相不干扰。
现在大多数用的都是线程池,由于线程都是复用的,而threadlocal往线程里面添加了一个map,因此,需要代码里面手动回收移除threadlocal保存的数据,否则,线程一直复用,数据量会一直累加至OOM。
并行:多条处理流同时执行,例如多端口同时工作,多条线路同时传送数据
串行:多条处理流排队执行。
并发:例如微机系统上有多个进程存活,从宏观上,多个进程上同时工作,是个并行的流程,但是,从微观底层上来看,多个进程是由CPU通过时间片轮转,逐个调度执行的,是个串行的流程,这个就是并发。
num:线程数量
当有任务需求时,
当num<poolSize时,优先创建线程
当num>poolSize时,且queue没满时,将任务添加到队列中排队
当maxpoolsize>num>poolSize时,且queue已满时,增加线程处理任务
当maxpoolsize==num,且queue已满时,不再新增线程,会按照handler所指定策略处理新任务。
同时会检查,是否有线程的空闲时间大于keepalivetime,如果有,终止对应线程
阻塞队列可以通过阻塞保留那些想要入队的任务;阻塞队列自带阻塞和唤醒功能,不需要一直占有CPU资源。
因为创建新线程需要获取全局锁,影响其他线程的效率,且线程数量不足有可能是临时性不足,因此,优先排队等待。
加锁[竞争锁]:
公平锁:新线程直接进入到队列
非公平锁:先直接竞争锁,竞争不到再进入队列
唤醒:无论公平锁还是非公平锁都会直接唤醒队列第一个获取锁
tryLock()可能加锁成功[返回真],也可能加锁不成功[返回假],非阻塞加锁
lock()阻塞性加锁,一直执行,直到加锁成功