𝐬𝐭𝐝::𝐭𝐡𝐫𝐞𝐚𝐝 vs 𝐬𝐭𝐝::𝐣𝐭𝐡𝐫𝐞𝐚𝐝 in C++20: What You Need to Know
🎯 In this post, I’d like to discuss about 𝐬𝐭𝐝::𝐭𝐡𝐫𝐞𝐚𝐝 vs 𝐬𝐭𝐝::𝐣𝐭𝐡𝐫𝐞𝐚𝐝.
⭕𝐓𝐡𝐫𝐞𝐚𝐝𝐬:
A 𝐩𝐫𝐨𝐜𝐞𝐬𝐬 is the operating system’s abstraction for a running program.
In modern systems a process can consist of multiple execution units, called 𝐭𝐡𝐫𝐞𝐚𝐝𝐬, each running in the context of the process and sharing the same code and global data. Threads allow multiple executions to take place in the same process environment (and address space), largely independent of one another.
⭕𝐬𝐭𝐝::𝐭𝐡𝐫𝐞𝐚𝐝
C++11 introduced the type std::thread.
std::thread objects in a C++ process act as handles to underlying 𝐬𝐨𝐟𝐭𝐰𝐚𝐫𝐞 𝐭𝐡𝐫𝐞𝐚𝐝𝐬 (also known as 𝘖𝘚 threads or 𝘴𝘺𝘴𝘵𝘦𝘮 threads).
However, the type has a significant design flaw: 𝐈𝐭 𝐢𝐬 𝐧𝐨𝐭 𝐚𝐧 𝐑𝐀𝐈𝐈 𝐭𝐲𝐩𝐞.
This means that std::thread does not automatically manage the lifecycle of the thread it represents. If a std::thread object is destroyed before the thread is 𝐣𝐨𝐢𝐧𝐞𝐝 or 𝐝𝐞𝐭𝐚𝐜𝐡𝐞𝐝, the program calls std::terminate(), which calls std::abort().
⭕𝐬𝐭𝐝::𝐣𝐭𝐡𝐫𝐞𝐚𝐝
𝐂++20 introduces a 𝘯𝘦𝘸 𝘵𝘺𝘱𝘦 for representing threads:
std::jthread. (the “j” stands for “joining”)
Get Samira’s stories in your inbox
Join Medium for free to get updates from this writer.
𝐊𝐞𝐲 𝐅𝐞𝐚𝐭𝐮𝐫𝐞𝐬 𝐨𝐟 𝐬𝐭𝐝::𝐣𝐭𝐡𝐫𝐞𝐚𝐝:
☑️ std::jthread is an RAII type that correctly cleans up the resources it uses. This means that the thread 𝘢𝘴𝘴𝘰𝘤𝘪𝘢𝘵𝘦𝘥 𝘸𝘪𝘵𝘩 a std::jthread object will automatically be joined in the following situation, provided the thread is still joinable and not detached.
➖ 𝐀𝐭 𝐭𝐡𝐞 𝐞𝐧𝐝 𝐨𝐟 𝒕𝒉𝒆 𝒃𝒍𝒐𝒄𝒌 that created the jthread, or
➖ 𝐖𝐡𝐞𝐧 𝒕𝒉𝒆 𝒃𝒍𝒐𝒄𝒌 𝐭𝐞𝐫𝐦𝐢𝐧𝐚𝐭𝐞𝐬 due to an exception.
☑️ std::jthread Supports 𝐂𝐨𝐨𝐩𝐞𝐫𝐚𝐭𝐢𝐯𝐞 𝐂𝐚𝐧𝐜𝐞𝐥𝐥𝐚𝐭𝐢𝐨𝐧/𝐈𝐧𝐭𝐞𝐫𝐫𝐮𝐩𝐭𝐢𝐨𝐧:
std::jthread provides a cooperative mechanism to signal that a thread should no longer run. It is 𝒄𝒐𝒐𝒑𝒆𝒓𝒂𝒕𝒊𝒗𝒆 because it does not forcibly kill the running thread (which could leave a program in a corrupt state and is therefore not supported by C++ threads). Instead, it uses mechanisms like std::stop_token to request cancellation.
⚠️ 𝐏𝐥𝐞𝐚𝐬𝐞 𝐍𝐨𝐭𝐞:
🔸If a block containing a std::jthread terminates due to an exception, the destructor automatically joins the thread if it is still joinable, preventing crashes from unjoined threads.
🔸However, if the thread’s executing function (whether using std::thread or std::jthread) throws an exception that is not caught within the executing thread, it cannot be caught in the originating context. So the program terminates abnormally with a call to std::terminate().
🔸So, all exceptions 𝐦𝐮𝐬𝐭 be handled within the executing thread, but they can be transferred across threads using a std::exception_ptr object.
🤔 Why std::jthread instead of fixing std::thread?
💠Backward Compatibility.
💠Binary Compatibility: new features would disrupt existing binaries.
➡️Resources:
-Modern Operating Systems, Fifth Edition by Andrew Tanenbaum and Herbert Bos.
-C++20 The Complete Guide by Nicolai Josuttis.
-Concurrency with Modern C++ by Rainer Grimm.
-C++20 for Programmers, 3rd Edition by Paul Deitel and Harvey Deitel.
-Professional C++, 6th Edition by Marc Gregoire.
-Effective Modern C++ by Scott Meyers.
-Modern C++ Programming Cookbook, Third Edition by Marius Bancila.
#cpp #multithreading #iLovecpp💗






