Java实现多线程的三种方法

  1. 通过继承Thread类创建并启动多线程的步骤:
  • 定义Thread类的子类,并重写该类的run()方法,该run()方法的方法体就代表了线程需要完成的任务,因此把run()方法称为线程执行体
  • 创建Tread子类的实例,即创建了线程对象
  • 调用线程对象的start()方法来启动该多线程。

示例

public class ThreadClass extends Thread{
    private int i;

    public void run(){
        System.out.println("Overwride run function");
        for(;i<100;i++){
            System.out.println(getName()+" "+i);
        }
    }

    public static void main(String[] args){
        for(int i=0;i<100;i++){
            System.out.println(Thread.currentThread().getName()+" "+i);
            if(i == 20){
                new ThreadClass().start();
                new ThreadClass().start();
            }
        }
    }
}
  1. 实现Runnable接口创建并启动多线程的步骤:
  • 定义Runnable接口的实现类,并重写该接口的run()方法,该run()方法的方法体即该线程的线程执行体;
  • 创建Runnable实现类的实例,并以此实例作为Thread的Target来创建Target对象,该Thread对象才是真正的线程对象;
  • 调用线程对象的start()方法来启动该线程。

示例

public class ThreadClass implements Runnable{
    private int i;
    public void run(){
        for(;i<100;i++){
            System.out.println(Thread.currentThread().getName()+" "+i);
        }
    }
    public static void main(String[] args){
        for(int i=0;i<100;i++){
            System.out.println(Thread.currentThread().getName()+" "+i);
            if(i==20){
                ThreadClass th = new ThreadClass();
                new Thread(th,"new Thread1").start();
                new Thread(th,"new Thread2").start();
            }
        }
    }
}
  1. 创建并启动有返回值的线程的步骤:
  • 创建Callable接口的实现类,并实现Call()方法,该方法作为线程执行体,并且有返回值;
  • 创建Callable实现类的实例,使用FutureTask类来包装Callable对象,该FutureTask对象封装了该Callable对象的call()方法的返回值;
  • 使用FutureTask对象作为Target对象的target创建并启动新线程;
  • 使用FutureTask对象的get()方法来获得子线程执行结束后的返回值

示例

public class ThreadClass implements Callable<Integer>{
    public Integer call(){
        int i = 0;
        for(;i<100;i++){
            System.out.println(Thread.currentThread().getName()+"的循环变量i的值:"+i);
        }
        return i;
    }
    public static void main(String[] args){
        ThreadClass rt = new ThreadClass();
        FutureTask<Integer> task = new FutureTask<Integer>(rt);
        for(int i=0;i<100;i++){
            System.out.println(Thread.currentThread().getName()+"的循环变量i的值:"+i);
            if(i==20){
                new Thread(task,"有返回值的线程").start();
            }
        }
        try{
            System.out.println("子线程的返回值:"+task.get());
        }catch(Exception e){
            e.printStackTrace();
        }
    }
}
  1. 通过继承类的实现接口来实现多线程的区别
  • 通过继承类:
    - 优点:编写简单,访问当前线程无需使用Thread.currentThread()方法,直接使用this即可获得当前线程;
    - 缺点: 线程类已经继承了Thread类,不能再继承其他父类 。
  • 通过实现接口:
    - 优点:可以继承其他类;多个线程可以共享一个Target对象,适合多个相同线程来处理同一份资源的情况。
    - 缺点:编程稍复杂,如访问当前线程必须使用Thread.currentThread()方法。
  • 总结:推荐使用实现接口的方法。
原文地址:https://www.cnblogs.com/liesun/p/8550386.html