1.线程的状态
- 创建, 调用完构造函数后,线程就为创建状态。
- 就绪, 调用start()方法后,所处的状态。
- 运行, 正常的运行。
- 阻塞, 资源等待的状态。
- 死亡, run()方法执行完毕后,该线程就死掉了。注意不能再次调用此线程的start()方法。
2.常用函数
java.lang.Thread.Thread(Runnable target, String name)
创建新线程,并指定线程的名字。
void java.lang.Thread.start()
让线程置于就绪状态,等待操作系统调度。
问:它与run()有什么区别呢?
答:start()是异步的,会新起一个线程,在新的线程中调用run()方法。直接调用run()就是在当前线程中执行同步的方法。
Thread java.lang.Thread.currentThread()
返回当前线程。
void java.lang.Thread.yield()
告诉操作系统此时可以进行线程切换。使用此方法有助于暴露线程不安全问题导致的异常现象。
java.lang.Thread.sleep(long millis, int nanos)
当前线程睡眠(millis 毫秒+nanos纳秒)。此方法会被TimeUnit这个枚举类型调用,可见:void java.util.concurrent.TimeUnit.sleep(long timeout)。
void java.lang.Thread.join(long millis)
此函数是同步的,当线程结束或等待达到超时时间后返回。
3.线程中断
Thread 的stop()与destory()方法被废弃,直接调用会有异常,见下:
@Deprecated
public void destroy() {
throw new NoSuchMethodError();
}
所以现在你不能暴力地中断一个线程,只能让线程自己来配合。
void java.lang.Thread.interrupt()
Thread类有一个布尔字段isInterrupted,用来标记自己是否被中断。调用此方法会置这个变量为true。如果此线程被join()、wait()、sleep()方法阻塞,那么调用interrupt()方法时会引起InterruptedException异常。
boolean java.lang.Thread.isInterrupted()
返回上面说的isInterrupted布尔变量。
3.1 例子
@Override
public void run() {
while(true){
//do something
}
}
//above and below is a contrast.
@Override
public void run() {
while(!Thread.currentThread().isInterrupted()){
//do something
}
}
4.线程相关接口
Runnable
//: concurrency/BasicThreads.java
// The most basic use of the Thread class.
class LiftOff implements Runnable {
protected int countDown = 10; // Default
private static int taskCount = 0;
private final int id = taskCount++;
public LiftOff() {}
public String status() {
return "#" + id + "(" +
(countDown > 0 ? countDown : "Liftoff!") + "), ";
}
public void run() {
while(--countDown >= 0) {
System.out.print(status());
}
}
}
//Thread
public class BasicThreads {
public static void main(String[] args) {
Thread t = new Thread(new LiftOff());
t.start(); //start()函数为异步调用,立即返回啦
System.out.println("Waiting for LiftOff");
}
} /* Output: (90% match)
Waiting for LiftOff
#0(9), #0(8), #0(7), #0(6), #0(5), #0(4), #0(3), #0(2), #0(1), #0(Liftoff!),
*/
//ExecutorService
public class CachedThreadPool {
public static void main(String[] args) {
ExecutorService exec = Executors.newCachedThreadPool();
for(int i = 0; i < 3; i++)
exec.execute(new LiftOff());
exec.shutdown();
} /* Output: (Sample)
#1(2), #2(2), #0(2), #2(1), #1(1), #2(Liftoff!), #0(1), #1(Liftoff!), #0(Liftoff!),
*/