1. Basic concepts of threads
Thread understanding: Thread is a different execution path in a program
Each branch is called a thread, and main() is called the main branch, also called the main thread.
A process is just a static concept, a .class file on the machine, a .exe file on the machine, this is called a process. The execution process of the program is like this: first, put the program's code into the code area of the memory. After the code is placed in the code area, it does not start executing immediately. However, this means that a process is ready to begin. The process has been generated, but has not started executing yet. This is the process, so the process is actually a static concept and cannot be moved by itself. The usual process execution refers to the main thread in the process that begins to execute, that is, the main() method begins to execute. Processes are a static concept, and actually threads run in our machines.
The Windows operating system supports multi-threading. It can execute many threads at the same time and also supports multiple processes. Therefore, the Windows operating system is an operating system that supports multi-threading and multi-processing. Linux and Uinux are also operating systems that support multi-threading and multi-processing. DOS does not support multi-threading and multi-processing. It only supports single processes. Only one process is executing at the same time point, which is called single-threading.
Is the CPU really powerful and able to execute so many programs at the same time? No, the execution of the CPU is as follows: the CPU is very fast, and it can be counted hundreds of millions of times in a second, so the CPU divides its time into small time slices. I execute this time slice for a while, the next time slice will execute it for a while, and the next time slice will execute others for a while. Although there are dozens of threads, they can be executed all of them in a very short time. But for us humans, the execution speed of the CPU is too fast, so it seems like it is executing at the same time, but in fact, at a point in time, there is only one thread running on the CPU.
First of all, you need to understand three concepts when learning threads :
1. Process: Process is a static concept
2. Thread: There is a main thread in a process called main() method, which is a program and a different execution path in a process.
3. At the same time, a CPU can only support one thread to execute. Because the CPU runs very fast, we look like we are multithreading.
What is true multithreading? If your machine has dual CPUs or dual cores, it is indeed multi-threaded.
2. Creation and startup of threads
In JAVA, JAVA threads are implemented through the java.lang.Thread class, and each Thread object represents a new thread. There are two ways to create a new thread: the first is to inherit from the Thread class, and the other is to implement the interface runnable. When the VM starts, there will be a thread defined by the main method (public static void main()), and this thread is called the main thread. New threads can be created by creating instances of Thread. You just need to new a Thread object, and a new thread will appear. Each thread completes its operation through the method run() corresponding to a specific Thread object. The method run() is called the thread body.
Example 1: Create and start a new thread using the implementation of the Runnable interface
Create a new thread to call the run method
package cn.galc.test;public class TestThread1{ public static void main(String args[]){ Runner1 r1 = new Runner1();// Here new object of the thread class comes out//r1.run();//This is called a method call. The execution of the method call is to wait until the run() method is executed before the main() method will continue to be executed. Thread t = new Thread(r1);//To start a new thread, you must new Thread object come out//Thread(Runnable target) is used here. The constructor t.start();//Start the newly opened thread, the new thread executes the run() method, and the new thread and the main thread will execute in parallel for(int i=0;i<10;i++){ System.out.println("maintheod:"+i); } }}/*Define a class to implement the Runnable interface. Implementing the Runnable interface means that this class is a thread class*/class Runner1 implements Runnable{ public void run(){ for(int i=0;i<10;i++){ System.out.println("Runner1:"+i); } }}The execution process of multi-threaded programs is as follows:
Call the run method directly without opening a new thread
The operation results are as follows:
Example 2: Inherit the Thread class and override its run() method to create and start a new thread
package cn.galc.test;/*The second method of thread creation and startup: define a subclass of Thread and implement the run() method*/public class TestThread2{ public static void main(String args[]){ Runner2 r2 = new Runner2(); r2.start();//Call the start() method to start the newly opened thread for(int i=0;i<=10;i++){ System.out.println("mainMethod:"+i); } }}/*Runner2 class inherits from Thread class By instantiating an object of Runner2 class, you can open a new thread. Call the start() method inherited from Thread class. You can start the newly opened thread*/class Runner2 extends Thread{ public void run(){//Rewrite the implementation of the run() method for(int i=0;i<=10;i++){ System.out.println("Runner2:"+i); } }}The choice of using two methods to create new threads, namely implementing the Runnable interface and inheriting the Thread class, should be given priority to opening a new thread. Because the implementation of an interface can implement multiple, the inheritance of a class can only be a single inheritance. Therefore, when you can use the Runnable interface when opening a new thread, try not to use inheritance from the Thread class to open new threads.
3. Thread state transition
3.1. Basic methods of thread control
3.2. Introduction to sleep/join/yield method
Example of application of sleep method:
package cn.galc.test;import java.util.*;public class TestThread3 { public static void main(String args[]){ MyThread thread = new MyThread(); thread.start();//Call the start() method to start the newly opened thread try { /*Thread.sleep(10000); sleep() method is a static method declared in the Thread class, so you can use the format of Thread.sleep() to call */ /*MyThread.sleep(10000); MyThread class inherits the Thread class and naturally also inherits the sleep() method, so you can also call it using the format of MyThread.sleep() */ /* The call of static methods can be directly called in the form of "class name.static method name" or "object reference.static method name" */ MyThread.sleep(10000); System.out.println("The main thread sleeps for 10 seconds and starts again"); // When calling another class's static method in the main() method, you need to use the "class.static method name where the static method is located" method to call /* So here is to let the main thread sleep for 10 seconds. Which thread calls the sleep() method, so now the main thread sleeps. */ } catch (InterruptedException e) { e.printStackTrace(); } //thread.interrupt();//Use interrupt() method to end the execution of a thread thread.flag=false;//Change the loop conditions and end the dead loop/** * When an InterruptedException occurs, directly set the loop condition to false to exit the dead loop, * Then end the execution of the child thread. This is a better way to end the child thread*/ /** * Calling interrupt() method to break the running thread is equivalent to pouring a pot of cold water on the main thread and breaking the executing sub-thread. After the executing sub-thread is interrupted, an InterruptedException will be thrown, which will execute the return statement and end the execution of the thread. So the sub-thread here ends the execution of the thread after 10 seconds of execution*/ }}class MyThread extends Thread { boolean flag = true;// Define a tag to control the conditions of the loop public void run() { /* * Note: Here, you cannot write throw Exception directly behind the run() method to throw exceptions, * Because now we need to rewrite the run() method inherited from the Thread class, the rewrite method cannot throw different exceptions than the rewritten method. * So here you can only write try...catch() to catch exceptions*/ while (flag) { System.out.println("============================================================================================================================================================================================================================================================================================================================================================================================================================================================================================= Of course, it is not wrong to call it using the format of "class name. method name"*/ // MyThread.sleep(1000);// Use the format of "class name. method name" to call the static method sleep(1000);// If it is interrupted during sleep, an InterruptedException will be thrown// Here is to let the newly opened thread sleep every second, and then start the thread again after sleeping for one second. Here, the thread is started every second in a dead loop, and the current system time is printed out each second} catch (InterruptedException e) { /* * When sleeping, a plate of cold water may interrupt sleep* Therefore, when the running thread is interrupted by some unexpected reasons, an exception that is interrupted (InterruptedException) may be thrown*/ return; // The thread returns after it is interrupted, which is equivalent to ending the thread} } }}Running results:
Example of join method:
package cn.galc.test;public class TestThread4 { public static void main(String args[]) { MyThread2 thread2 = new MyThread2("mythread"); // While creating a new thread object, name the thread object mythread thread2.start();// Start thread try { thread2.join();// Call the join() method to merge the thread, merge the child thread mythread into the main thread// After merging the thread, the execution process of the program is equivalent to the execution process of the method call} catch (InterruptedException e) { e.printStackTrace(); } for (int i = 0; i <= 5; i++) { System.out.println("I am main Thread"); } }}class MyThread2 extends Thread { MyThread2(String s) { super(s); /* * Use the super keyword to call the constructor of the parent class * One of the constructors of the parent class Thread: "public Thread(String name)" * Through such a constructor, the newly opened thread can be named, which facilitates the management of threads*/ } public void run() { for (int i = 1; i <= 5; i++) { System.out.println("I am a/t" + getName()); // Use //public final String getName() defined in the parent class Thread, Returns this thread's name. try { sleep(1000);// Make the child thread sleep for 1 second every time it is executed} catch (InterruptedException e) { return; } } }}Running results:
Example of use of yield method:
package cn.galc.test;public class TestThread5 { public static void main(String args[]) { MyThread3 t1 = new MyThread3("t1"); /* Two child threads t1 and t2 were opened at the same time. T1 and t2 both execute the run() method*/ /* There are a total of 3 threads in parallel during the execution of this program, namely child threads t1 and t2 and the main thread*/ MyThread3 t2 = new MyThread3("t2"); t1.start();// Starter child thread t1 t2.start();// Starter child thread t2 for (int i = 0; i <= 5; i++) { System.out.println("I am main Thread"); } }}class MyThread3 extends Thread { MyThread3(String s) { super(s); } public void run() { for (int i = 1; i <= 5; i++) { System.out.println(getName() + ":" + i); if (i % 2 == 0) { yield();// When the execution reaches i can be divided by 2, the current thread executing is given out and let another thread executing the run() method be executed first/* * You can see during the running of the program, * When thread t1 is executed (i%2==0) times, it will give out the thread and let the t2 thread execute first*, and when thread t2 is executed (i%2==0) times, it will give out the thread to the t1 thread to the priority execution */ } }}The operation results are as follows:
The above is all the content of this article. We hope it can help you.