One , summary

    stay JAVA in , use Thread Class represents a thread , All thread objects , All have to be Thread Class or Thread An instance of a subclass of a class . The task of each thread is to execute a sequence of code
,JAVA Use the thread executable to hold the code . therefore , When we create a thread , Mainly according to the actual demand , Write the code to put into the thread execution body .

Two , Three creation methods

2.1   The first one , By inheritance Thread Class creates a thread class

  By inheritance Thread Class to create and start multithreading :

1, Define a class inheritance Thread class , And rewrite Thread Class run() method ,run() The method body of a method is the task to be completed by the thread , So the run() The execution body called a thread ;

2, Create an instance object of the class , The thread object is created ;

3, Calling the thread object's start() Method to start the thread ;

Code instance :
public class ExtendThread extends Thread { private int i; public static void
main(String[] args) { for(int j = 0;j < 50;j++) {
// call Thread Class currentThread() Method to get the current thread
System.out.println(Thread.currentThread().getName() + " " + j); if(j == 10) {
// Create and start the first thread new ExtendThread().start(); // Create and start a second thread new
ExtendThread().start(); } } } public void run() { for(;i < 100;i++) {
// By inheritance Thread Class to implement multithreading , It can be used directly this Gets the currently executing thread System.out.println(this.getName() +
" " + i); } } }
Code dependent :

1, Above getName() Method is to return the name of the current thread , It can also be done through setName() Method to set the name of the current thread ;

2, When JAVA After running the program , The program creates at least one main thread ( automatic ), The thread execution body of the main thread is not run() Method determined , Instead, it was created by main() Method determined ;

3, By default , The thread name of the main thread is main, The threads created by the user are Thread—1,Thread—2,....Thread—3;

code analysis :

This is a screenshot of the code running , As can be seen from the figure :

1, There are three threads :main,Thread-0 ,Thread-1

2,Thread-0 ,Thread-1 Member variables output by two threads i  The value of is discontinuous ( there i  It's an instance variable, not a local variable
). because : By inheritance Thread Class implements multithreading , Each thread is created with a different subclass object , cause Thread-0 ,Thread-1 Two threads cannot share member variables i ;

3, Thread execution is preemptive , It didn't say Thread-0  perhaps Thread-1 Always occupied CPU( This is also related to thread priority , here Thread-0
,Thread-1 Same thread priority , The knowledge about thread priority is not expanded here );

2.2  The second kind , By implementing Runnable Interface to create thread class

The steps to create and start multithreading in this way are as follows :

1, Define a class implementation Runnable Interface ;

2, Create an instance object of the class obj;

3, take obj Pass in as a constructor parameter Thread Class instance object , This object is the real thread object ;

4, Calling the thread object's start() Method to start the thread ;

Code instance :
public class ImpRunnable implements Runnable { private int i; @Override public
void run() { for(;i < 50;i++) {
// When the thread class is implemented Runnable Interface time , To get the current thread object, you must pass the Thread.currentThread() obtain
System.out.println(Thread.currentThread().getName() + " " + i); } } public
static void main(String[] args) { for(int j = 0;j < 30;j++) {
System.out.println(Thread.currentThread().getName() + " " + j); if(j == 10) {
ImpRunnable thread_target = new ImpRunnable(); // adopt new
Thread(target,name) To create a thread new Thread(thread_target," thread 1").start(); new
Thread(thread_target," thread 2").start(); } } } }
Code dependent :

1, realization Runnable The instance object of the class of the interface is only used as Thread Object's target,Runnable Implement the run() Methods are only used as thread executors , and
The actual thread object is still Thread example , there Thread Instance is responsible for executing its target Of run() method ;

2, By implementing Runnable Interface to implement multithreading , To get the current thread object, you can only use Thread.currentThread() method , And can't pass this Keyword acquisition ;

3, from JAVA8 start ,Runnable The interface uses the @FunctionlInterface modification , in other words Runnable Interface is a functional interface , Can make
use lambda Expression create object , use lambda Expressions can be created without creating an implementation like the above code Runnable The class of the interface , Then create an instance of the class .

code analysis :

This is a screenshot of the result of running the code , As can be seen from the figure :

1, thread 1 And threads 2 Output member variables i It's continuous , In other words, threads are created in this way , You can make multiple threads share instance variables of the thread class
, Because multiple threads here use the same one target Instance variable . however , When you run with my code above , You'll find out , In fact, some of the results are not continuous , This is because multiple threads access the same resource , If the resource is not locked , Then it will appear
Thread safety ( This is the knowledge of thread synchronization , It doesn't unfold here );

2.3  The third kind , adopt Callable and Future Interface creation thread

Create threads through these two interfaces , You need to know what these two interfaces do , Let's take a look at these two interfaces : By implementing Runnable Interface creates multithreading ,Thread The function of class is to run() Method is wrapped into the execution body of the thread , that , Is it possible to directly
How about wrapping any method as an executable of a thread ? from JAVA5 start ,JAVA Provided by Callable Interface , The interface is Runnable Enhanced version of the interface ,
Callable Interface provides a call() Methods can be used as thread executors , but call() Method comparison run() More powerful methods ,call() The powerful function of the method is embodied in :

1,call() Method can have a return value ;

2,call() Method can declare to throw an exception ;

You can see from this , It can provide one Callable Object as Thread Of target, The thread execution body of the thread is call() method . But the problem is :
Callable The interface is JAVA New interfaces , And it's not Runnable Sub interface of the interface , therefore Callable Object cannot be directly used as Thread Of target
. Another reason is that :call() Method has a return value ,call() Method is not called directly , It is called as the thread execution body , So it's about getting call() Method return value problem .

therefore ,JAVA5 Provided Future Interface Callable In the interface call() The return value of the method , And for Future Interface provides a FutureTask Implementation class , This class
Yes Future Interface , And realized Runnable Interface , therefore FutureTask Can be used as Thread Class target
, It's also solved Callable Object cannot be used as Thread Class target This problem .

stay Future The interface defines the following public methods to control the Callable task :

1,boolean cancel(boolean mayInterruptIfRunning): Attempt to cancel Future Related in Callable task ;

2,V get(): return Callable Mission call() The return value of the method , Calling this method causes the program to block , You must wait until the child thread finishes before you get the return value ;

3,V get(long timeout, TimeUnit
unit): return Callable Mission call() The return value of the method . This method makes the program block at most timeout and unit Specified time , If the specified time has passed ,Callable The task still has no return value , Will be thrown out TimeoutException abnormal ;

4,boolean isCancelled(): If Callable The task was cancelled before it was completed normally , Return to true;

5,boolean isDone(): If Callable The task has been completed ,  Return to true;

This is how to start the multithreading :

1, establish Callable Interface implementation class , And realize call() method , This method will be used as the thread execution body , And the method has a return value , Recreate Callable An instance of an implementation class ;

2, use FutureTask Class Callable object , The FutureTask Object encapsulates the Callable Object's call() The return value of the method ;

3, use FutureTask Object as Thread Object's target Create and start a new thread ;

4, call FutureTask Object's get() Method to get the return value after the execution of the child thread .

Code instance :
public class ThirdThreadImp { public static void main(String[] args) {
// here call() Method is rewritten using the lambda expression , There is no new one Callable The implementation class of the interface FutureTask<Integer> task = new
FutureTask<Integer>((Callable<Integer>)()->{ int i = 0; for(;i < 50;i++) {
System.out.println(Thread.currentThread().getName() + " The loop variable in the execution body of the thread i The value of is :" +
i); } //call() The return value of the method return i; }); for(int j = 0;j < 50;j++) {
System.out.println(Thread.currentThread().getName() + " Loop variables of Large Cycles j The value of is :" + j);
if(j == 20) { new Thread(task," Threads with return values ").start(); } } try {
System.out.println(" The return value of the child thread :" + task.get()); } catch (Exception e) {
e.printStackTrace(); } } }
Code dependent :

1, The above code does not use to create an implementation Callable The class of the interface , Then create an implementation class instance . because , from JAVA8 It can be used directly at first
Lambda Create an expression Callable object , So the code above uses Lambda expression ;

2,call() Method return value type and creation FutureTask Object time <> In the same type .

code analysis :

There is not much analysis here , Just look at the output of the last line : call FutureTask Object's get() method , You must wait until the child thread finishes , Will have a return value .

Three , Comparison of three creation methods

   
  That's all JAVA Three ways to create threads in , We can know by comparison ,JAVA The implementation of multithreading can be divided into two categories : One is inheritance Thread Class to implement multithreading ; The other is : By implementing Runnable Interface or Callable Interface implementation multithreading .

Let's analyze the advantages and disadvantages of these two kinds of multithreading methods :

By inheritance Thread Class to implement multithreading :

advantage :

1, It's easy to implement , And get the current thread , No call is required Thread.currentThread() method , Direct use this To get the current thread ;

shortcoming :

1, Thread class already inherited Thread Class , You can no longer inherit other classes ;

2, Multiple threads cannot share the same resource ( As in the previous analysis of member variables i );

By implementing Runnable Interface or Callable Interface implementation multithreading :

advantage :

1, The thread class only implements the interface , You can also inherit other classes ;

2, Multiple threads can use the same target object , It is suitable for multiple threads to process the same resource .

shortcoming :

1, In this way, multithreading is realized , Compared with the first type , Programming is complex ;

2, To access the current thread , Must be called Thread.currentThread() method .

All in all :

Generally, the second method is adopted to realize multithreading .

Technology