函数列表
函数 | 说明 |
---|
pthread_create | 创建线程 |
pthread_attr_init | 初始化线程属性 |
pthread_attr_destroy | 销毁线程属性 |
pthread_join | 等待线程执行完成 |
pthread_cancel | 杀死线程 |
函数 | 说明 |
---|
pthread_mutexattr_init | 初始化线程锁属性 |
pthread_mutexattr_destroy | 销毁线程锁属性 |
pthread_mutex_init | 初始化线程锁 |
pthread_mutex_destroy | 销毁线程锁 |
pthread_mutex_lock | 使用线程锁 |
pthread_mutex_unlock | 释放线程锁 |
pthread_mutex_trylock | 试图使用线程锁,如果当前锁已被其它线程持有,则立即返回(非阻塞状态) |
函数 | 说明 |
---|
pthread_condattr_init | 初始化条件变量属性 |
pthread_condattr_destroy | 销毁条件变量属性 |
pthread_cond_init | 初始化条件变量 |
pthread_cond_destroy | 销毁条件变量 |
pthread_cond_wait | 释放锁,等待条件变量被唤醒 |
pthread_cond_timedwait | 释放锁,等待条件变量被唤醒,到了指定的最大时间,即使条件变量未唤醒也会解除阻塞 |
pthread_cond_signal | 唤醒阻塞在指定条件变量上的一个线程 |
pthread_cond_broadcast | 唤醒阻塞在指定条件变量上的所有线程 |
pthread_create
- 参数1:线程句柄,需要先定义一个 pthread_t 类型变量 thread,将该变量的地址 &thread 传递到该参数中去。这是一个传出参数,传递进去的 thread 会得到系统为我们创建好的线程句柄。
- 参数2:线程属性,如果要使用默认属性直接传递 NULL 即可
- 参数3:线程函数,函数指针类型
- 参数4:线程函数的参数
- 返回值:成功情况下返回 0,失败情况下返回错误码
int pthread_create(pthread_t* __pthread_ptr, pthread_attr_t const* __attr, void* (*__start_routine)(void*), void*);
pthread_join
- 参数1:线程标识符,即线程ID
- 参数2:定义的指针,用来存储被等待线程的返回值,如果不需要则传入NULL
- 返回值:0代表成功。 失败,返回的则是错误号。
int pthread_join(pthread_t __pthread, void** __return_value_ptr);
示例
线程安全
pthread_mutex_t mutex;
int num;
void *num_increment(void *params) {
for (int i = 0; i < 10000; ++i) {
usleep(100);
pthread_mutex_lock(&mutex);
num += 1;
pthread_mutex_unlock(&mutex);
}
return nullptr;
}
void main() {
pthread_mutexattr_t mutexattr;
pthread_mutexattr_init(&mutexattr);
pthread_mutex_init(&mutex, &mutexattr);
pthread_t thread1;
pthread_create(&thread1, nullptr, num_increment, nullptr);
pthread_t thread2;
pthread_create(&thread2, nullptr, num_increment, nullptr);
pthread_join(thread1, NULL);
pthread_join(thread2, NULL);
LOGD("num = %d", num);
pthread_mutexattr_destroy(&mutexattr);
pthread_mutex_destroy(&mutex);
}
生产者-消费者模型
pthread_mutex_t mutex = PTHREAD_MUTEX_INITIALIZER;
pthread_cond_t cond;
class Iphone {
private:
int phoneId;
public:
explicit Iphone(int id) : phoneId(id) {}
int getPhoneId() {
return phoneId;
}
};
int productId;
std::list<Iphone> iphoneList;
void *producer_runnable(void *params) {
while (true) {
sleep(random() % 10);
pthread_mutex_lock(&mutex);
Iphone iphone(productId++);
iphoneList.push_back(iphone);
pthread_cond_signal(&cond);
pthread_mutex_unlock(&mutex);
}
return nullptr;
}
void *consumer_runnable(void *params) {
while (true) {
pthread_mutex_lock(&mutex);
if (iphoneList.size() == 0) {
pthread_cond_wait(&cond, &mutex);
}
Iphone iphone = iphoneList.front();
iphoneList.pop_front();
pthread_mutex_unlock(&mutex);
}
return nullptr;
}
void main() {
pthread_condattr_t condattr;
pthread_condattr_init(&condattr);
pthread_cond_init(&cond, &condattr);
pthread_t product_thread;
pthread_create(&product_thread, nullptr, producer_runnable, nullptr);
pthread_t consume_thread;
pthread_create(&consume_thread, nullptr, consumer_runnable, nullptr);
}