当前位置: 首页 > news >正文

线程API

1. 创建线程

#include <pthread.h>int pthread_create(pthread_t *thread, const pthread_attr_t *attr,void *(*start_routine) (void *), void *arg);

参数

  • thread 属于结果参数,函数结束时,返回线程ID并存储到thread中
  • attr 设置线程的属性,一般为NULL,表示采用线程默认属性
  • start_routine 回调函数,线程要执行的函数
  • arg 回调函数 start_routine() 执行时的参数。

返回值

  • 成功 0
  • 失败 非0

2. 线程标识

#include <pthread.h>int pthread_equal(pthread_t t1, pthread_t t2);
pthread_t pthread_self(void);

函数

  • pthread_equal 判断线程ID是否相等
  • pthread_self 返回调用线程的线程ID

3. 线程退出

3.1 线程自行退出

#include <pthread.h>void pthread_exit(void * retval);

retval 记录线程的退出信息,记录方式:

  1. 不可以使用线程的局部变量。
  2. NULL 仅退出,不返回信息
  3. 使用全局变量
  4. 动态分配内存
  5. 字符串常量

3.2 其他线程取消

#include <pthread.h>int pthread_cancel(pthread_t thread);
int pthread_setcancelstate(int state, int *oldstate);

函数

  • pthread_cancel 取消thread的线程
  • pthread_setcancelstate : 设置线程取消属性
    • state:
      • PTHREAD_CANCEL_ENABLE : 线程可以被取消
      • PTHREAD_CANCEL_DISABLE : 线程不可以被取消
    • oldstate : 保持上一次取消属性的状态。

4. 连接(释放)线程

join其他线程的时候会调用 __nptl_free_tcb (pd); 释放退出线程的资源。

但是NPTL模型会缓存该线程的地址空间,并不会立即 munmap ,后创建的线程会复用这块内存地址,避免了频繁的 mmapmunmap ,所以

  • 使用 pthread_join 连接退出线程,后面启动的线程会复用前面 joined 栈内存空间
  • 如果不使用 pthread_join 连接线程,那么新的线程会分配新的栈空间,从而导致内存泄漏。
#include <pthread.h>int pthread_join(pthread_t thread, void **retval);

retval : 存放线程返回值的地址

5. 线程分离

pthread_detach 用来设置一个线程的属性为分离属性

#include <pthread.h>int pthread_detach(pthread_t thread);

6. 线程同步

6.1 互斥锁(mutex)

#include <pthread.h>/* 初始化线程互斥锁 */
int pthread_mutex_init(pthread_mutex_t *mutex,const pthread_mutex_attr_t *mutexattr);
/* 阻塞加锁 */
int pthread_mutex_lock(pthread_mutex *mutex);
/* 非阻塞加锁 */
int pthread_mutex_trylock( pthread_mutex_t *mutex);
/* 解锁 */
int pthread_mutex_unlock(pthread_mutex *mutex);
/* 销毁锁 */
int pthread_mutex_destroy(pthread_mutex *mutex);

6.2 条件变量(cond)

#include <pthread.h>
/* 初始化条件变量 */
int pthread_cond_init(pthread_cond_t *cond,pthread_condattr_t *cond_attr);
/* 无条件等待 */
int pthread_cond_wait(pthread_cond_t *cond,pthread_mutex_t *mutex);
/* 计时条件 */
int pthread_cond_timewait(pthread_cond_t *cond,pthread_mutex *mutex,const timespec *abstime);
/* 激活一个等待该条件的线程 */
int pthread_cond_signal(pthread_cond_t *cond);
/* 激活所有等待线程 */
int pthread_cond_broadcast(pthread_cond_t *cond);
/* 销毁条件变量 */
int pthread_cond_destroy(pthread_cond_t *cond);

6.3 读写锁

  • 如果一个线程用读锁锁定了临界区,那么其他线程也可以用读锁来进入临界区,这样就可以多个线程并行操作。但这个时候,如果再进行写锁加锁就会发生阻塞,写锁请求阻塞后,后面如果继续有读锁来请求,这些后来的读锁都会被阻塞!这样避免了读锁长期占用资源,防止写锁饥饿!
  • 如果一个线程用写锁锁住了临界区,那么其他线程不管是读锁还是写锁都会发生阻塞!
#include <pthread.h>
/* 初始读写锁 */
int pthread_rwlock_init(pthread_rwlock_t *restrict rwlock, const pthread_rwlockattr_t *restrict attr);int pthread_rwlock_rdlock(pthread_rwlock_t *rwlock);
int pthread_rwlock_wrlock(pthread_rwlock_t *rwlock);
int pthread_rwlock_unlock(pthread_rwlock_t *rwlock);int pthread_rwlock_tryrdlock(pthread_rwlock_t *rwlock);
int pthread_rwlock_trywrlock(pthread_rwlock_t *rwlock);int pthread_rwlock_timedrdlock(pthread_rwlock_t *restrict rwlock, const struct timespec *restrict abs_timeout);
int pthread_rwlock_timedwrlock(pthread_rwlock_t *restrict rwlock, const struct timespec *restrict abs_timeout);
/* 销毁锁 */
int pthread_rwlock_destroy(pthread_rwlock_t *rwlock);
http://www.vanclimg.com/news/1297.html

相关文章:

  • 1000子读后感
  • Teamcenter: 度量单位
  • .NET 9 的免费午餐:GZip 性能提升38.3%
  • 暑假本校集训
  • 20250729-33
  • FHQ Treap 学习笔记
  • C#/.NET/.NET Core技术前沿周刊 | 第 48 期(2025年7.21-7.27)
  • Metasploit Pro 4.22.8-2025071801 (Linux, Windows) - 专业渗透测试框架
  • test的启动方法
  • Lombok @Builder失效问题排查与解决方案
  • 亚马逊Q Developer:用自然语言构建机器学习模型
  • day07
  • 读心与芯:我们与机器人的无限未来08计算思维
  • 前馈电容技术解析!
  • 7/29
  • js高级第一天
  • Git 小白极速入门笔记
  • Git课程讲义
  • sakuraFrp页面503
  • 企业级AI Agent(智能体)报告
  • 2025倒闭半导体公司大盘点
  • 大算力芯片,向左(定制)还是向右(通用)?
  • Z Waves|北大毕业的前OpenAI高管,如今创办估值120亿美金的AI新势力,翁荔想要重写AI安全的规则
  • Hyperlane性能调优秘籍:从毫秒级响应到百万QPS的优化之路(5845)
  • 轻量级服务器架构的极致优化(9293)
  • 高性能路由系统的设计与实现(2739)
  • TCP连接优化的实战经验(6269)
  • 实时通信技术深度对比:WebSocket与SSE的最佳实践(9733)
  • 现代Web框架的性能基准测试(8409)
  • 现代Web服务器性能革命:我的Rust框架探索之旅(1820)