敞开生长之旅!这是我参与「日新计划 12 月更文挑战」的第1天,点击检查活动概况

创立线程的几种办法

承继Thread类创立线程

多线程的创立,办法一:承继于Thread类

  1. 创立一个承继于Thread类的子类
  2. 重写Thread类的run() –> 将此线程履行的操作声明在run()中
  3. 创立Thread类的子类的目标
  4. 经过此目标调用start()
  • 例子:遍历100以内的所有的偶数
//1. 创立一个承继于Thread类的子类
class MyThread extends Thread {
    //2. 重写Thread类的run()
    @Override
    public void run() {
        for (int i = 0; i < 100; i++) {
            if(i % 2 == 0){
                System.out.println(Thread.currentThread().getName() + ":" + i);
            }
        }
    }
}
public class ThreadTest {
    public static void main(String[] args) {
        //3. 创立Thread类的子类的目标
        MyThread t1 = new MyThread();
        //4.经过此目标调用start():①发动当时线程 ② 调用当时线程的run()
        t1.start();
        //问题一:我们不能经过直接调用run()的办法发动线程。
//        t1.run();
        /*
        问题二:再发动一个线程,遍历100以内的偶数。不能够还让现已start()的线程去履行。
        会报IllegalThreadStateException
        */    
//        t1.start();
        //我们需要从头创立一个线程的目标
        MyThread t2 = new MyThread();
        t2.start();
        //如下操作仍然是在main线程中履行的。
        for (int i = 0; i < 100; i++) {
            if(i % 2 == 0){
                System.out.println(Thread.currentThread().getName() + ":" + i + "***********main()************");
            }
        }
    }
}

完成Runnable接口创立线程

1、创立多线程的办法二:完成Runnable接口

  1. 创立一个完成了Runnable接口的类
  2. 完成类去完成Runnable中的抽象办法:run()
  3. 创立完成类的目标
  4. 将此目标作为参数传递到Thread类的结构器中,创立Thread类的目标
  5. 经过Thread类的目标调用start()

2、 比较创立线程的两种办法。
开发中:优先选择:完成Runnable接口的办法
原因:完成的办法没有类的单承继性的局限性,完成的办法更适合来处理多个线程有同享数据的状况。

//1. 创立一个完成了Runnable接口的类
class MThread implements Runnable{
    //2. 完成类去完成Runnable中的抽象办法:run()
    @Override
    public void run() {
        for (int i = 0; i < 100; i++) {
            if(i % 2 == 0){
                System.out.println(Thread.currentThread().getName() + ":" + i);
            }
        }
    }
}
public class ThreadTest1 {
    public static void main(String[] args) {
        //3. 创立完成类的目标
        MThread mThread = new MThread();
        //4. 将此目标作为参数传递到Thread类的结构器中,创立Thread类的目标
        Thread t1 = new Thread(mThread);
        t1.setName("线程1");
        /*
        5. 经过Thread类的目标调用start():① 发动线程 ②调用当时线程的run()-->
        调用了Runnable类型的target的run()
        */
        t1.start();
        //再发动一个线程,遍历100以内的偶数
        Thread t2 = new Thread(mThread);
        t2.setName("线程2");
        t2.start();
    }
}

完成Callable接口创立线程

//Callable完成多线程
class MyThread implements Callable<String> {//线程的主体类
    @Override
    public String call() throws Exception {
        for (int x = 0; x < 10; x++) {
            System.out.println("*******线程履行,x=" + x + "********");
        }
        return "线程履行完毕";
    }
}
public class Demo1 {
    public static void main(String[] args) throws Exception {
        FutureTask<String> task = new FutureTask<>(new MyThread());
        new Thread(task).start();
        System.out.println("线程回来数据" + task.get());
    }
}

完成 Runnable 接口和 Callable 接口的区别

Runnable自 Java 1.0 以来一直存在,但Callable仅在 Java 1.5 中引进,意图就是为了来处理Runnable不支持的用例。
● Runnable 接口不会回来成果或抛出检查反常
● 但是Callable 接口能够回来成果或抛出检查反常。
● 东西类 Executors 能够完成 Runnable 目标和 Callable 目标之间的相互转化。(Executors.callable(Runnable task)或 Executors.callable(Runnable task,Object resule))。
所以,假如任务不需要回来成果或抛出反常推荐运用 Runnable 接口,这样代码看起来会愈加简练。

声明:本站所有文章,如无特殊说明或标注,均为本站原创发布。任何个人或组织,在未征得本站同意时,禁止复制、盗用、采集、发布本站内容到任何网站、书籍等各类媒体平台。如若本站内容侵犯了原著者的合法权益,可联系我们进行处理。