[thread foundation] realize multithreading

Method 1 inherits Thread class

public class Thread01 extends Thread{

    @Override
    public void run() {
        System.out.println(Thread.currentThread().getName()+" is running...");
    }

    public static void main(String[] args) {
        Thread01 thread01 = new Thread01();
        thread01.start();
    }
}

Method 2 implements the Runnable interface

public class Thread02 implements Runnable{
    @Override
    public void run() {
        System.out.println(Thread.currentThread().getName()+" is running...");
    }

    public static void main(String[] args) {
        Thread thread = new Thread(new Thread02());
        thread.start();
    }
}

Method 3: create a thread through Callable and FutureTask

public class Thread03 {
    public static void main(String[] args) throws ExecutionException, InterruptedException {
        Callable<String> callable = new Callback<String>();
        FutureTask<String> futureTask = new FutureTask<>(callable);
        Thread thread = new Thread(futureTask);
        thread.start();
        System.out.println(futureTask.get());
    }

    static class Callback<String> implements Callable<String>{
        @Override
        public String call() throws Exception {
            System.out.println("exec one times...");
            TimeUnit.SECONDS.sleep(2);
            System.out.println("sleep tow seconds");
            return (String) (Thread.currentThread().getName() + " is pass through callable accomplish");
        }
    }
}

Method 4: create a thread through the thread pool

public class Thread04 {

    static class RunnableTask implements Runnable{
        @Override
        public void run() {
            System.out.println(Thread.currentThread().getName()+" is running...");
        }
    }

    public static void main(String[] args) {
        ExecutorService executorService = Executors.newFixedThreadPool(1);
        executorService.execute(new RunnableTask());
        executorService.shutdown();
    }
}

Method 5 Timer

public class Thread05 extends TimerTask {
    @Override
    public void run() {
        System.out.println(LocalDateTime.now().format(DateTimeFormatter.ISO_LOCAL_DATE_TIME)+":"+Thread.currentThread().getName()+" is running...");
    }

    public static void main(String[] args) {
        Timer timer = new Timer();
        //Start after one second and then every two seconds.
        timer.schedule(new Thread05(), 1000,2000);
    }
}

Method 6 creates a thread using an anonymous inner class

public class Thread06 {

    public static void main(String[] args) {
        Thread thread = new Thread(()->{
            System.out.println(Thread.currentThread().getName()+" is running...");
        });
        thread.start();
    }
}

summary

Although threads can be created in the above six methods, each of them is implemented internally by implementing the Runnable interface

Please look at the following pictures
Thread

TimerTask

FutureTask

ExecutorService

It can be seen that no matter how many times a thread is created, its bottom layer can never escape the implementation of the Runnable interface, so in the final analysis, there is only one way to create a thread.

If you think about it carefully, why do Java create threads by implementing the Runnable interface? What are the advantages of implementing the Runnable interface compared with inheriting the Thread interface.

  • In fact, in Java, only single inheritance is allowed, but multiple interfaces can be implemented. This feature actually reflects the flexibility of threads to implement the Runnable interface.
  • In addition, in some cases, the performance can be improved by implementing Runnable. Using the method of inheriting Thread, you need to create an independent Thread without executing the task once. After executing the task, the Thread will be destroyed at the end of its life cycle. If you still want to execute the task, you must create another Thread inheriting Thread class. If you implement the Runnable interface, you can directly transfer the task to the Thread pool and use some fixed threads to complete the task without creating or destroying threads. This greatly reduces the performance overhead.

To sum up, if an interviewer asks us how many ways to create threads, tell him that there is only one way, that is, to create threads by implementing the Runnable interface.

Keywords: Java

Added by Chappers on Mon, 24 Jan 2022 04:20:18 +0200