赞
踩
线程池中的执行流程:
(1)当线程数小于核心线程数的时候,使用核心线程数。
(2)如果核心线程数小于线程数,就将多余的线程放入任务队列(阻塞队列)中
(3)当任务队列(阻塞队列)满的时候,就启动最大线程数.
(4)当最大线程数也达到后,就将启动拒绝策略。
回答:有四种拒绝策略
1.ThreadPoolExecutor.AbortPolicy
线程池的默认拒绝策略为AbortPolicy,即丢弃任务并抛出RejectedExecutionException异常(即后面提交的请求不会放入队列也不会直接消费并抛出异常);
2.ThreadPoolExecutor.DiscardPolicy
丢弃任务,但是不抛出异常。如果线程队列已满,则后续提交的任务都会被丢弃,且是静默丢弃(也不会抛出任何异常,任务直接就丢弃了)。
3.ThreadPoolExecutor.DiscardOldestPolicy
丢弃队列最前面的任务,然后重新提交被拒绝的任务(丢弃掉了队列最前的任务,并不抛出异常,直接丢弃了)。
4.ThreadPoolExecutor.CallerRunsPolicy
由调用线程处理该任务(不会丢弃任务,最后所有的任务都执行了,并不会抛出异常)
相同点:
(1)都是可重入锁
(2)都保证了可见性和互斥性
(3)都可以用于控制多线程对共享对象的访问
不同点:
(1)ReentrantLock等待可中断
(2)synchronized中的锁是非公平的,ReentrantLock默认也是非公平的,但是可以通过修改参数来实现公平锁。
(3)ReentrantLock绑定多个条件
(4)synchronized是Java中的关键字是JVM级别的锁,而ReentrantLock是一个Lock接口下的实现类,是API层面的锁。
(5)synchronized隐式获取锁和释放锁,ReentrantLock显示获取和释放锁,在使用时避免程序异常无法释放锁,需要在finally控制块中进行解锁操作。
重载是发生在同一个类中,具有相同的方法名,但是有不同的参数,参数的个数不一样、参数的位置不一样,这就叫重载,常见的就比如构造方法,有有参构造和无参构造。
重写是发生在当子类继承父类时,对父类中的一些方法根据自己的需求进行重写操作。
Java中线程生命周期分为新建(New)、运行(Runnable)、阻塞(Blocked)、无限期等待(Waiting)、限期等待(Time Waiting)和结束(Terminated)这6种状态。
状态名称 | 说明 |
New | 初始状态,线程被构建,但是还没调用 start( )方法 |
Runnable | 运行状态,Java线程将操作系统中的就绪和运行两种状态笼统的称作“运行中” |
Blocked | 阻塞状态,表示线程阻塞于锁 |
Waiting | 等待状态,表示线程进入等待状态,进入该状态表示当前线程需要等待其他线程做出一些特定动作(通知或中断) |
Time Waiting | 超时等待状态,该状态不同于WAITING,它是可以在指定的时间自行返回的 |
Terminated | 终止状态,表示当前线程已执行完毕 |
(1)synchronize作用于成员变量和非静态方法时,锁住的是对象的实例,即this对象。
(2)synchronize作用于静态方法时,锁住的是Class实例
(3)synchronize作用于一个代码块时,锁住的是所有代码块中配置的对象。
作者:代码界的小白
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。