public class Run {
public static void main(String[] args){
CountOperate c = new CountOperate();
Thread t1 = new Thread(c);
System.out.println("main begin t1 isAlive = " + t1.isAlive());
t1.setName("A");
t1.start();
System.out.println("main end t1 isAlive = " + t1.isAlive());
System.out.println("main end c isAlive = " + c.isAlive());
}
}
class CountOperate extends Thread {
public CountOperate(){
System.out.println("CountOperate --- begin");
System.out.println("Thread.currentThread().getName() = " + Thread.currentThread().getName());
System.out.println("Thread.currentThread().isAlive() = " + Thread.currentThread().isAlive());
System.out.println("Thread.currentThread() == this : " + (Thread.currentThread() == this));
System.out.println("this.getName = " + this.getName());
System.out.println("this.isAlive() = " + this.isAlive());
System.out.println("CountOperate --- end ");
}
@Override
public void run() {
System.out.println("run --- begin");
System.out.println("Thread.currentThread().getName = " + Thread.currentThread().getName());
System.out.println("Thread.currentThread().isAlive() = " + Thread.currentThread().isAlive());
System.out.println("Thread.currentThread() == this : " + (Thread.currentThread() == this));
System.out.println("this.getName() = " + this.getName());
System.out.println("this.isAlive() = " + this.isAlive());
System.out.println("run --- end");
}
}
结果:
CountOperate --- begin
Thread.currentThread().getName() = main
Thread.currentThread().isAlive() = true
Thread.currentThread() == this : false
this.getName = Thread-0
this.isAlive() = false
CountOperate --- end
main begin t1 isAlive = false
main end t1 isAlive = true
main end c isAlive = false
run --- begin
Thread.currentThread().getName = A
Thread.currentThread().isAlive() = true
Thread.currentThread() == this : false
this.getName() = Thread-0
this.isAlive() = false
run --- end
根据打印的 Log 可以知道调用 CountOperate 构造函数的是 main 线程,因此打印出:
Thread.currentThread().getName() = main
Thread.currentThread().isAlive() = true
而此时还没有启动 CountOperate 子线程所以打印出:
this.getName = Thread-0
this.isAlive() = false
此时 this 代表的是 CountOperate 对象实例,所以
Thread.currentThread() == this : false
这里比较让人疑惑的是this.getName() = Thread-0
,这个 Thread-0 是什么东西
通过查看 Thread 源码发现,在 Thread 类的构造方法中,会自动给 name 赋值:
public Thread() {
init(null, null, "Thread-" + nextThreadNum(), 0);
}
然后执行到:
Thread t1 = new Thread(c);
System.out.println("main begin t1 isAlive = " + t1.isAlive());
t1.setName("A");
t1.start();
Log 打印:
Thread.currentThread().getName = A
Thread.currentThread().isAlive() = true
Thread.currentThread() == this : false
this.getName() = Thread-0
this.isAlive() = false
说明此时的 this 和 Thread.currentThread() 指向不是同一个线程实例
也就是说,this 指向的还是 new CountOperate() 创建的那个线程实例 c,而不是 new Thread(thread) 创建的那个实例即 t1。
查看源代码可以知道:
public Thread(Runnable target) {
init(null, target, "Thread-" + nextThreadNum(), 0);
}
实际上 new Thread(thread) 会将 thread 应用的对象绑定到一个 private 变量 target 上
在 t1 被执行的时候即 t1.run() 被调用的时候,它会调用 target.run() 方法
再确切的说,在 run 方法被执行的时候,this.getName() 实际上返回的是 target.getName(),而 Thread.currentThread().getName() 实际上是 t1.getName()
因为调用 start() 的线程是 t1,而不是 c,所以 this.isAlive() = false
如果修改 main 中的代码为:
public class Run {
public static void main(String[] args){
CountOperate c = new CountOperate();
c.start();
}
}
结果:
CountOperate --- begin
Thread.currentThread().getName() = main
Thread.currentThread().isAlive() = true
Thread.currentThread() == this : false
this.getName = Thread-0
this.isAlive() = false
CountOperate --- end
run --- begin
Thread.currentThread().getName = Thread-0
Thread.currentThread().isAlive() = true
Thread.currentThread() == this : true
this.getName() = Thread-0
this.isAlive() = true
run --- end
符合预期