如何可靠判断是否可创建线程以避免程序崩溃?
编辑:已找到解决方案(见本人回答),意识到下文问题表述存在误导性,引发诸多误解,但仍认为对有相同问题的人有帮助。
提问缘由
这已是我第三次提出该核心问题,前两次提问均偏离至非预期细节的讨论。
我坚信,解答此核心问题能为像我这样的多线程编程非专家提供宝贵帮助,因为目前网上相关内容不易获取,且这是一个切实存在的问题。
问题描述
假设有一个需通过线程并行执行的函数fct。线程能否在某一时刻创建取决于操作系统,受可用内存等因素影响。若无法创建却强行尝试,程序会崩溃。那么,如何可靠判断是否可创建线程,在不可创建时放弃,以避免程序失控崩溃?
(正如他人指出,通常可并发运行的线程数量"非常多"。但我有两台Windows设备:一台为48GB内存的Windows 10(VS 2019),另一台为64GB内存的Windows 11(VS 2022),在以下极简示例中,该数量均低于20;而在我实际优化的更复杂代码中,仅能运行5个线程。重点并非提升该数量或排查设备问题,而是让代码在任意操作系统上都能无崩溃运行。)
以下为最小可复现示例(MWE):
#include <iostream> #include <thread> #include <vector> #include <string> constexpr int NUM_JOBS{ 100 }; // Number of jobs to run. constexpr int NUM_THREADS{ 15 }; // Number of threads run at most in parallel. Setting this to 20 crashes on my machine. void fct(const std::string& str) // Some function to run in parallel. { std::cout << "Processing job: " + str + "\n"; } int main(int argc, char* argv[]) { std::vector<std::string> job_descriptions{}; // Different "configs" to call fct. std::vector<std::thread> threads{}; int numThreads{ 0 }; for (int i = 0; i < NUM_JOBS; i++) { // Create some "configs". job_descriptions.push_back("J" + std::to_string(i)); } for (const auto& job : job_descriptions) { // Run the jobs, in parallel if possible. bool spawned{ false }; while (!spawned) { if (numThreads < NUM_THREADS) { // Spawn new threads only if not more than NUM_THREADS are running simultaneously. threads.emplace_back(std::thread(fct, job)); spawned = true; numThreads++; } else if (!threads.empty()) { // Otherwise wait for the topmost thread to finish before spawning new ones. threads.front().join(); threads.erase(threads.begin()); numThreads--; } } } for (auto& t : threads) t.join(); // Join the remaining threads in the end. return 0; }
并行执行的函数fct非常简单,仅向cout输出一行内容。通过常量NUM_THREADS可控制最大并行任务数。将该值设得过高时,我的Windows设备会抛出以下异常:
Exception thrown at 0x768BA892 in ***.exe: Microsoft C++ exception: std::system_error at memory location 0x06DCFA68.
(在Linux上可将该值设得很高,但这并非重点。)
核心问题是:能否将条件numThreads < NUM_THREADS替换为类似"是否可创建线程"的判断逻辑?
内容的提问来源于stack exchange,提问作者Duke
相关产品推荐
相关产品推荐

