1.线程的生命周期
五个阶段
- 新建状态—- new关键字创建线程对象
- 就绪状态—- start()方法运行之前
- 运行状态—- run()方法的运行
- 堵塞状态— interrupt() sleep() join() yield() wait() 等方法
- 死亡状态— stop()方法(已过时) /或run()方法运行结束
2.实现多线程有哪些方式
继承Thread类创建线程
Thread类本质上是实现了Runnable接口的一个实例,代表一个线程的实例。启动线程的唯一方法就是通过Thread类的start()实例方法。start()方法是一个native方法,它将启动一个新线程,并执行run()方法。这种方式实现多线程很简单,通过自己的类直接extend Thread,并复写run()方法,就可以启动新线程并执行自己定义的run()方法。 实现Runnable接口创建线程实现Callable接口通过FutureTask包装器来创建Thread线程
使用ExecutorService、Callable、Future实现有返回结果的线程
3.sleep(),wait(),yield()和join()方法的区别
sleep()方法需要指定等待的时间,它可以让当前正在执行的线程在指定的时间内暂停执行,进入阻塞状态,但是sleep()方法不会释放“锁标志”。
wait()方法需要和notify()及notifyAll()这三个方法用于协调多个线程对共享数据的存取,所以必须在synchronized语句块内使用,它们都是Object类的方法。当调用某一对象的wait()方法后,会使当前线程暂停执行,并将当前线程放入对象等待池中,直到调用了notify()方法后,将从对象等待池中移出任意一个线程并放入锁标志等待池中,只有锁标志等待池中的线程可以获取锁标志,它们随时准备争夺锁的拥有权。wait()方法会释放对象的“锁标志”。
yield()方法和sleep()方法类似,也不会释放“锁标志”,区别在于,它没有参数,即yield()方法只是使当前线程重新回到可执行状态,所以执行yield()的线程有可能在进入到可执行状态后马上又被执行,另外yield()方法只能使同优先级或者高优先级的线程得到执行机会,这也和sleep()方法不同。
- join()方法会使当前线程等待调用join()方法的线程结束后才能继续执行。