C++多线程编程简介

[复制链接]
发表于 2025-10-7 05:20:47 | 显示全部楼层 |阅读模式

马上注册,结交更多好友,享用更多功能,让你轻松玩转社区。

您需要 登录 才可以下载或查看,没有账号?立即注册

×
C++多线程编程

概述

多线程编程允许在同一个步调中同时实验多个任务,从而进步步调的服从,特别是在处理处罚 I/O 麋集型或盘算麋集型任务时。C++11 引入了标准库中的多线程支持,使得 C++ 开辟者可以或许更加方便地举行多线程编程。
线程根本

线程是步调中实验的最小单位,每个线程有本身的步调计数器、堆栈和局部变量。C++ 的  库提供了对线程的支持,允许我们在步调中启动多个并行的线程。
线程的创建与管理

要创建一个线程,起首须要包罗  头文件。通过 std::thread 类可以创建线程。
创建线程
  1. #include <iostream>
  2. #include <thread>
  3. void print_hello() {
  4.     std::cout << "Hello from thread!" << std::endl;
  5. }
  6. int main() {
  7.     std::thread t(print_hello);  // 创建一个线程,调用 print_hello 函数
  8.     t.join();  // 等待线程执行完成
  9.     return 0;
  10. }
复制代码
表明:

  • std::thread 构造函数吸取一个函数作为参数,该函数将在新线程中实验。
  • t.join() 会壅闭主线程,直到 t 所表现的线程实验完成。
  • join 是线程同步的一种方式,确保主线程等候子线程完成后再继续实验。
多个线程

可以创建多个线程来实验差别的任务。每个线程都会实验一个独立的任务。
  1. #include <iostream>
  2. #include <thread>
  3. void print_hello() {
  4.     std::cout << "Hello from thread!" << std::endl;
  5. }
  6. void print_world() {
  7.     std::cout << "World from thread!" << std::endl;
  8. }
  9. int main() {
  10.     std::thread t1(print_hello);
  11.     std::thread t2(print_world);
  12.     t1.join();
  13.     t2.join();
  14.     return 0;
  15. }
复制代码

  • t1 和 t2 是两个差别的线程,它们分别实验 print_hello 和 print_world 函数。
  • join() 确保在步调竣事之前,全部线程都完成。
线程的分离

除了 join,尚有 detach 函数。利用 detach 后,线程将独立于主线程实验,它不会被等候完成,主线程可以继续实验。
  1. #include <iostream>
  2. #include <thread>
  3. void print_message() {
  4.     std::cout << "Message from detached thread!" << std::endl;
  5. }
  6. int main() {
  7.     std::thread t(print_message);
  8.     t.detach();  // 分离线程,主线程继续执行
  9.     std::cout << "Main thread continues!" << std::endl;
  10.     // 注意:如果主线程结束,分离线程可能未执行完成
  11.     return 0;
  12. }
复制代码
留意:

  • 利用 detach 后,线程在背景实验,主线程可以退出,不会等候它的完成。若主线程竣事时子线程仍在运行,则大概会出现未界说的举动,因此要鉴戒利用 detach。
线程同步

多线程编程常常面临多个线程共享资源的环境。假如多个线程同时访问和修改共享数据,就会引发数据竞争标题。这时,须要对共享资源举行同步。
互斥量(Mutex)

互斥量是掩护共享资源的一种机制,它确保同一时间只有一个线程能访问共享资源。
  1. #include <iostream>
  2. #include <thread>
  3. #include <mutex>
  4. std::mutex mtx;  // 互斥量
  5. void print_message(const std::string &message) {
  6.     mtx.lock();  // 上锁
  7.     std::cout << message << std::endl;
  8.     mtx.unlock();  // 解锁
  9. }
  10. int main() {
  11.     std::thread t1(print_message, "Hello from thread 1");
  12.     std::thread t2(print_message, "Hello from thread 2");
  13.     t1.join();
  14.     t2.join();
  15.     return 0;
  16. }
复制代码

  • std::mutex mtx 界说了一个互斥量,用来掩护共享资源(此处是 std::cout)。
  • mtx.lock() 获取锁,确保当火线程独占对 cout 的访问。
  • mtx.unlock() 开释锁,允许其他线程获取锁。
std::lock_guard 和 std::unique_lock

为了制止手动调用 lock() 和 unlock(),C++ 提供了 std::lock_guard 和 std::unique_lock,它们在作用域竣事时自动开释锁,制止忘记解锁。
  1. #include <iostream>
  2. #include <thread>
  3. #include <mutex>
  4. std::mutex mtx;  // 互斥量
  5. void print_message(const std::string &message) {
  6.     std::lock_guard<std::mutex> lock(mtx);  // 上锁
  7.     std::cout << message << std::endl;
  8.     // 自动解锁,当 lock_guard 对象超出作用域时
  9. }
  10. int main() {
  11.     std::thread t1(print_message, "Hello from thread 1");
  12.     std::thread t2(print_message, "Hello from thread 2");
  13.     t1.join();
  14.     t2.join();
  15.     return 0;
  16. }
复制代码

  • std::lock_guard 自动获取和开释锁,使代码更加轻便安全。
std::condition_variable

std::condition_variable 用于在多个线程之间同步,通常用于实现线程之间的等候与关照机制。
  1. #include <iostream>
  2. #include <thread>
  3. #include <mutex>
  4. #include <condition_variable>
  5. std::mutex mtx;
  6. std::condition_variable cv;
  7. bool ready = false;
  8. void print_id(int id) {
  9.     std::unique_lock<std::mutex> lck(mtx);
  10.     while (!ready) cv.wait(lck);  // 等待条件满足
  11.     std::cout << "Thread " << id << std::endl;
  12. }
  13. void go() {
  14.     std::unique_lock<std::mutex> lck(mtx);
  15.     ready = true;  // 改变条件
  16.     cv.notify_all();  // 通知所有线程
  17. }
  18. int main() {
  19.     std::thread threads[10];
  20.     for (int i = 0; i < 10; ++i)
  21.         threads[i] = std::thread(print_id, i);
  22.     std::cout << "Waiting for threads to be ready..." << std::endl;
  23.     go();  // 通知线程
  24.     for (auto& th : threads) th.join();
  25.     return 0;
  26. }
复制代码

  • cv.wait(lck) 会使当火线程等候直到 ready 为 true。
  • cv.notify_all() 会关照全部等候的线程继续实验。
原子利用

原子利用是不会被克制的利用,它对于多线程同步非常有用。在 C++11 中,std::atomic 提供了对根本数据范例的原子利用支持。
  1. #include <iostream>
  2. #include <thread>
  3. #include <atomic>
  4. std::atomic<int> counter(0);
  5. void increment() {
  6.     for (int i = 0; i < 1000; ++i)
  7.         ++counter;  // 原子增加
  8. }
  9. int main() {
  10.     std::thread t1(increment);
  11.     std::thread t2(increment);
  12.     t1.join();
  13.     t2.join();
  14.     std::cout << "Final counter value: " << counter.load() << std::endl;
  15.     return 0;
  16. }
复制代码

  • std::atomic 确保对 counter 的利用是原子的,不会被多个线程同时修改,制止了数据竞争。
回复

使用道具 举报

登录后关闭弹窗

登录参与点评抽奖  加入IT实名职场社区
去登录
快速回复 返回顶部 返回列表