A closer look at the right and wrong ways to start threads in Java
Sep 28, 2020 pm 04:55 PMA closer look at the correct and incorrect ways to start threads in Java
Review of the previous article
- Detailed analysis of the methods of implementing multi-threading in Java are How many? (Based on the essence)
Comparison of start method and run method
Code demonstration:
/** * <p> * start() 和 run() 的比較 * </p> * * @author 踏雪彡尋梅 * @version 1.0 * @date 2020/9/20 - 16:15 * @since JDK1.8 */public class StartAndRunMethod { public static void main(String[] args) { // run 方法演示 // 輸出: name: main // 說明由主線程去執(zhí)行的, 不符合新建一個(gè)線程的本意 Runnable runnable = () -> { System.out.println("name: " + Thread.currentThread().getName()); }; runnable.run(); // start 方法演示 // 輸出: name: Thread-0 // 說明新建了一個(gè)線程, 符合本意 new Thread(runnable).start(); } }復(fù)制代碼
From the above example The following two points can be analyzed:
Directly using the
run
method will not start a new thread. (wrong way)start
method starts a new thread. (Correct way)
start method analysis
The meaning of the start method and precautions
start
method can start a new thread.- After the thread object calls the
start
method after initialization, the current thread (usually the main thread) will request the JVM virtual machine to start this if it is free. New thread. - In other words, the essence of starting a new thread is to request the JVM to run the thread.
- As for when this thread can run, it is not simply decided by us, but by the thread scheduler.
- If it is very busy, even if we run the
start
method, we may not be able to start the thread immediately. - So after the
srtart
method is called, it does not mean that this method has started running. It may not run until later, or it may not run for a long time, such as in case of starvation. - This also proves that in some cases, thread 1 first calls the
start
method, and then thread 2 calls thestart
method, only to find that thread 2 first The situation of execution after executing thread 1. - Summary: The order in which the
start
method is called does not determine the order in which the actual threads are executed. - Note
start
method will involve two threads.- The first one is the main thread, because we must have a main thread or other threads (even if it is not the main thread) to execute this
start
method, the second one is the new one the rout. - In many cases, the main thread that creates the thread for us will be ignored. Don't mistakenly think that calling
start
is already executed by the child thread. This statement is actually the main thread or the main thread. It is executed by the parent thread, and a new thread is created after it is executed.
- After the thread object calls the
start
Method to create a new thread preparations- First, it will make itself In ready state.
- The ready state means that other resources besides the CPU have been obtained, such as the context, stack, thread status and PC (PC is a register, PC points to the location where the program is running), etc. have been set.
- After completing these preparations, everything is ready and all you need is Dongfeng, which is the CPU resource.
- After completing the preparation work, the thread can be further scheduled by the JVM or operating system to the execution state to wait for CPU resources, and then it will actually enter the running state to execute the
run
method. code.
- First, it will make itself In ready state.
Note: The start method cannot be executed repeatedly
Code example
/** * <p> * 演示不能重復(fù)的執(zhí)行 start 方法(兩次及以上), 否則會(huì)報(bào)錯(cuò) * </p> * * @author 踏雪彡尋梅 * @version 1.0 * @date 2020/9/20 - 16:47 * @since JDK1.8 */public class CantStartTwice { public static void main(String[] args) { Runnable runnable = () -> { System.out.println("name: " + Thread.currentThread().getName()); }; Thread thread = new Thread(runnable); // 輸出: name: Thread-0 thread.start(); // 輸出: 拋出 java.lang.IllegalThreadStateException // 即非法線程狀態(tài)異常(線程狀態(tài)不符合規(guī)定) thread.start(); } }復(fù)制代碼
Cause of error
start
Once execution starts, the thread state will enter the subsequent state from the initial New state, such as Runnable, and then Once the thread completes execution, the thread will become a terminated state, and the terminated state can never be returned, so the above exception will be thrown, which means that it cannot return to the initial state. The description here is not clear enough. Let's take a look at the source code to understand more thoroughly.
start method source code analysis
Source code
public synchronized void start() { /** * This method is not invoked for the main method thread or "system" * group threads created/set up by the VM. Any new functionality added * to this method in the future may have to also be added to the VM. * * A zero status value corresponds to state "NEW". */ // 第一步, 檢查線程狀態(tài)是否為初始狀態(tài), 這里也就是上面拋出異常的原因 if (threadStatus != 0) throw new IllegalThreadStateException(); /* Notify the group that this thread is about to be started * so that it can be added to the group's list of threads * and the group's unstarted count can be decremented. */ // 第二步, 加入線程組 group.add(this); boolean started = false; try { // 第三步, 調(diào)用 start0 方法 start0(); started = true; } finally { try { if (!started) { group.threadStartFailed(this); } } catch (Throwable ignore) { /* do nothing. If start0 threw a Throwable then it will be passed up the call stack */ } } }復(fù)制代碼
Process in the source code
Step one: When starting a new thread, it will first check whether the thread state is the initial state, which is also the reason why the above exception is thrown. That is, the following code:
if (threadStatus != 0) throw new IllegalThreadStateException();復(fù)制代碼
Among them, threadStatus
The annotation of this variable is as follows, which means that the Java thread status is initially expressed as 0 (not yet started):
/* Java thread status for tools, * initialized to indicate thread 'not yet started' */private volatile int threadStatus = 0;復(fù)制代碼
Step 2:Add it to the thread group. That is, the following code:
group.add(this);復(fù)制代碼
The third step:Finally call start0()
This native method (native means that its code is not implemented by Java, but by C/C implementation, the specific implementation can be seen in the JDK, just understand it), that is, the following code:
boolean started = false;try { // 第三步, 調(diào)用 start0 方法 start0(); started = true; } finally { try { if (!started) { group.threadStartFailed(this); } } catch (Throwable ignore) { /* do nothing. If start0 threw a Throwable then it will be passed up the call stack */ } }復(fù)制代碼
run method analysis
run method source code analysis
@Overridepublic void run() { // 傳入了 target 對象(即 Runnable 接口的實(shí)現(xiàn)), 執(zhí)行傳入的 target 對象的 run 方法 if (target != null) { target.run(); } }復(fù)制代碼
Two situations for the run method
The first one: Overriding the
run
method of theThread
class,Thread
'srun
method will be invalid, and the overriddenrun
method will be executed.Second type: Pass in the
target
object (that is, the implementation of theRunnable
interface) and execute the original # ofThread
The ##runmethod then proceeds to execute the
runmethod of the
targetobject.
- Summary: The
- #run
method is an ordinary method. The
runmethod is directly executed above. It is equivalent to executing the ordinary method we wrote ourselves, so its execution thread is our main thread.
So if you want to actually start the thread, you cannot call the - run
method directly, but you must call the
startmethod, in which you can call
run## indirectly. # method.
- #run
Related learning recommendations:
The above is the detailed content of A closer look at the right and wrong ways to start threads in Java. For more information, please follow other related articles on the PHP Chinese website!

Hot AI Tools

Undress AI Tool
Undress images for free

Undresser.AI Undress
AI-powered app for creating realistic nude photos

AI Clothes Remover
Online AI tool for removing clothes from photos.

Clothoff.io
AI clothes remover

Video Face Swap
Swap faces in any video effortlessly with our completely free AI face swap tool!

Hot Article

Hot Tools

Notepad++7.3.1
Easy-to-use and free code editor

SublimeText3 Chinese version
Chinese version, very easy to use

Zend Studio 13.0.1
Powerful PHP integrated development environment

Dreamweaver CS6
Visual web development tools

SublimeText3 Mac version
God-level code editing software (SublimeText3)

The settings.json file is located in the user-level or workspace-level path and is used to customize VSCode settings. 1. User-level path: Windows is C:\Users\\AppData\Roaming\Code\User\settings.json, macOS is /Users//Library/ApplicationSupport/Code/User/settings.json, Linux is /home//.config/Code/User/settings.json; 2. Workspace-level path: .vscode/settings in the project root directory

To correctly handle JDBC transactions, you must first turn off the automatic commit mode, then perform multiple operations, and finally commit or rollback according to the results; 1. Call conn.setAutoCommit(false) to start the transaction; 2. Execute multiple SQL operations, such as INSERT and UPDATE; 3. Call conn.commit() if all operations are successful, and call conn.rollback() if an exception occurs to ensure data consistency; at the same time, try-with-resources should be used to manage resources, properly handle exceptions and close connections to avoid connection leakage; in addition, it is recommended to use connection pools and set save points to achieve partial rollback, and keep transactions as short as possible to improve performance.

DependencyInjection(DI)isadesignpatternwhereobjectsreceivedependenciesexternally,promotingloosecouplingandeasiertestingthroughconstructor,setter,orfieldinjection.2.SpringFrameworkusesannotationslike@Component,@Service,and@AutowiredwithJava-basedconfi

itertools.combinations is used to generate all non-repetitive combinations (order irrelevant) that selects a specified number of elements from the iterable object. Its usage includes: 1. Select 2 element combinations from the list, such as ('A','B'), ('A','C'), etc., to avoid repeated order; 2. Take 3 character combinations of strings, such as "abc" and "abd", which are suitable for subsequence generation; 3. Find the combinations where the sum of two numbers is equal to the target value, such as 1 5=6, simplify the double loop logic; the difference between combinations and arrangement lies in whether the order is important, combinations regard AB and BA as the same, while permutations are regarded as different;

fixture is a function used to provide preset environment or data for tests. 1. Use the @pytest.fixture decorator to define fixture; 2. Inject fixture in parameter form in the test function; 3. Execute setup before yield, and then teardown; 4. Control scope through scope parameters, such as function, module, etc.; 5. Place the shared fixture in conftest.py to achieve cross-file sharing, thereby improving the maintainability and reusability of tests.

TheJVMenablesJava’s"writeonce,runanywhere"capabilitybyexecutingbytecodethroughfourmaincomponents:1.TheClassLoaderSubsystemloads,links,andinitializes.classfilesusingbootstrap,extension,andapplicationclassloaders,ensuringsecureandlazyclassloa

Use classes in the java.time package to replace the old Date and Calendar classes; 2. Get the current date and time through LocalDate, LocalDateTime and LocalTime; 3. Create a specific date and time using the of() method; 4. Use the plus/minus method to immutably increase and decrease the time; 5. Use ZonedDateTime and ZoneId to process the time zone; 6. Format and parse date strings through DateTimeFormatter; 7. Use Instant to be compatible with the old date types when necessary; date processing in modern Java should give priority to using java.timeAPI, which provides clear, immutable and linear

ChromecanopenlocalfileslikeHTMLandPDFsbyusing"Openfile"ordraggingthemintothebrowser;ensuretheaddressstartswithfile:///;2.SecurityrestrictionsblockAJAX,localStorage,andcross-folderaccessonfile://;usealocalserverlikepython-mhttp.server8000tor
