第一种:将类声明为Thread的子类。该子类重写Thread类的run方法,之后就可以分配并且启动该子类的实例。
第二种:声明实现Runnable的接口类。在该类实现run()方法,然后分配该类实例,之后创建Thread时作为一个参数传递并启动即可。Runnable为非Thread子类的类提供了一种激活的方式。因为接口实现的Thread的接口类并不是线程,所以使用的时候要先创建该类然后创建线程并把该类对象传进创建的线程类。
class ThreadDemo extends Thread/implements Runnable
{
public void run()
{
for(int x=0;x<60;x++)
System.out.println(Thread.currentThread()+"子线程运行");
//System.out.println(Thread.currentThread().getName()+" : "+ x);
}
}
class ThreadTest
{
public static void main(String[] args)
{
//1,继承方式:extends
ThreadDemo threadDemo= new ThreadDemo();
threadDemo.start();
for(int x=0;x<60;x++){
System.out.println("主线程运行");
}
/**2,实现接口方式测试:implements
ThreadDemo threadDemo= new ThreadDemo();
Thread td1 = new Thread(threadDemo);
Thread td2 = new Thread(threadDemo);
Thread td3 = new Thread(threadDemo);
td1.start();
td2.start();
td3.start();
**/
}
}
采用继承Thread类方式:
(1)优点:编写简单,如果需要访问当前线程,无需使用Thread.currentThread()方法,直接使用this,即可获得当前线程。
(2)缺点:因为线程类已经继承了Thread类,所以不能再继承其他的父类。
采用实现Runnable接口方式:
(1)优点:线程类只是实现了Runable接口,还可以继承其他的类。在这种方式下,可以多个线程共享同一个目标对象,所以非常适合多个相同线程来处理同一份资源的情况,从而可以将CPU代码和数据分开,形成清晰的模型,较好地体现了面向对象的思想。
(2)缺点:编程稍微复杂,如果需要访问当前线程,必须使用Thread.currentThread()方法
一般使用Runnable方式
还有一种是由第二种变形而来的直接new Runnable(){},使用匿名内部类实现的
public class TestRunnable {
public static void main(String[] args) {
Runnable runnable = new Runnable() {
@Override
public void run() {
System.out.println("i am new Runnable()");
}
};
Thread thread = new Thread(runnable);
thread.start();
}
}
相当于:
public class TestRunnable {
class Anomymous implements Runnable {
@Override
public void run() {
System.out.println("i am new Runnable()");
}
public static void main(String[] args) {
Runnable runnable = new Anomymous();
Thread thread = new Thread(runnable);
thread.start();
}
}
j简化方式:
new Thread(new Runnable() {
@Override public void run()
{
System.out.println("i am new Runnable()"); }
}
).start();
匿名内部类仅限于只实例化一次的内部类,如果内部类需要多次实例化,通常用后者。
另外,匿名内部类要么继承一个父类,要么实现一个接口,不能两者兼有,实现接口时也不能实现多个接口
java8以后的:
//Java 8 lambda方式:
new Thread(() -> System.out.println("i am new Runnable()")).start();
其中() -> {}代码块替代了整个匿名类