1.java线程中的守护线程和用户线程概述
只要当JVM实例中尚存任何一个非守护线程没有结束,守护线程就全部工作,只有当最后一个非守护线程结束时,守护线程随着JVM一同结束
user和Daemon两者几乎没有区别,唯一的不同之处就在于虚拟机的离开,如果User Thread已经全部退出,只剩下Daemon Thread存在,虚拟机也就退出了,以为没有了被守护者,也就没有继续运行的必要了,守护线程最典型的例子就是GC
2.什么是多线程上线文切换
多线程会共同使用一组计算机上的CPU,而线程数大于给程序分配的CPU数量时,为了让各个线程有有机会执行,就需要轮转是用CPU
在上下文切换过程中,CPU会停止处理当前运行的程序,并保存当前程序的具体位置以后继续运行
上下文切换是存储和恢复CPU状态的过程,它使得线程执行能够从中断点恢复执行,上下文切换是多任务操作系统和多线程环境的基本特
3.java中用到的线程调度算法是什么?
有两种调度模型:分时调度和抢占式调度模型
分时调度:让所有的线程轮流获得CPU使用权,并且平均分配占用CPU的时间片
抢占式调度模型:是指让运行池中优先级高的线程占用CPU,如果可运行池中的线程优先级相同,就随机选择一个线程,使其占用cpu
4.线程的生命周期?
线程一共有5中状态,分别如下:
1.新建:当创建一个Thread类的一个实例时,此线程会进入新建状态
2.可运行:线程对象创建后,其他线程调用了该对象的start方法,该状态的线程位于可运行线程池中,等待被线程调度选中,获取cpu使用权
3.运行:线程获得CPU资源,正在执行run()方法
4.死亡:当线程执行完毕或被其他线程杀死,线程就进入死亡状态,这是线程不可能进入就绪等待状态
正常终止:正常运行完run()方法
异常终止:调用stop()方法,让一个线程终止运行
5.阻塞:由于某种原因导致正在运行的线程让出cpu并暂停自己的执行,即进入阻塞状,阻塞的情况有三种:
1.睡眠:sleep(),可以使线程进入睡眠模式
2.等待:调用wait()方法,调用notify()回到就绪状态
3.被另外一个线程阻塞:调用suspend()方法

5.如何结束一个一直运行的线程
方式一:使用退出标志位,这个flag变量要多线程可见
方式二:线程经常会由于一些事件而发生阻塞,使线程进入不可运行状态,这里建议使用interrupt(),而不使用stop(),因为该方法虽然不会中断一个正在运行的线程,但是它可以是一个被阻塞的线程抛出异常,从而使线程提前结束阻塞状态,退出堵塞代码
在java中主要有3个相关方法,interrupt(),isInterrupted()和interrupted()
interrupt(),在一个线程中调用另一个线程的interrupt()方法,即会向那个线程发出信号——线程中断状态已被设置。至于那个线程何去何从,由具体的代码实现决定。
isInterrupted(),用来判断当前线程的中断状态(true or false)。
interrupted()是个Thread的static方法,用来恢复中断状态(!!!)
6.创建线程的方式及实现
方式一,继承 Thread 类创建线程类。
缺点:extends了Thread,重写run()方法,所以不能再继承别的类了
方式二,通过 Runnable 接口创建线程类。
implements了Runnable,并实现run()方法
方式三,通过 Callable 和 Future 创建线程。
implements了Callable,实现call()方法
7.如何使用wait+notify实现通知机制
Object 类的 wait 和 notify方法实现线程阻塞
1.首先,wait和notify方法是针对对象的,调用任意对象的wait和notify都将导致线程阻塞,阻塞的同时也将释放该对象的锁,相应的调用任意对象的notify方法将随机解除该对象阻塞的线程,但它需要重新获取该对象的锁,直到获取成功才往下执行
2.其次,wait和notify方法必须在synchtonized块或方法中调用,并且要保证同步块或方法的锁对象与调用wait和notify方法的对象是同一个,如此一来在调用wait之前当前线程就已经获取某对象的锁,执行wait阻塞后当前线程就将之前获取的对象锁释放
wait/notify用例
8.Semaphore 是什么?
Semaphore是一个计数信号,用来限流,它创建一个共享锁,可以让很多线程都拿到资源
semaphore.acquire()来进行获取资源,如果资源没有了则进行CLH同步队列的入队操作,这些都是基于AQS框架基础上的
9.CountDownLatch原理
CountDownLatch这个类能够使一个线程等待其他线程完成各自的工作后再执行,例如我们打游戏,加载游戏,必须所有玩家都加载成功,才能进入游戏.它首先创建一个计数器,每当一个线程完成任务就调用countDownLatch.countDown()方法,减少计数,最后调用countDownLatch.await()方法,等待所有线程都完成任务以后,才继续执行下面的任务
10. CyclicBarrier 原理
栅栏屏障,但所有线程都到达了这个屏障(也叫同步点)才继续执行下面的操作,和CountDownLatch类似,cyclicBarrier.await()方法对每个行程进行阻塞
11.CountDownLatch和CyclicBarrier的区别
CyclicBarrier 可以重复使用,而 CountdownLatch 不能重复使用。
CyclicBarrier必须等到所有线程都执行完才行,不然会一直堵塞

网友评论