#include <pthread.h>
int pthread_cond_destroy(pthread_cond_t *cond);
int pthread_cond_init(pthread_cond_t *restrict cond,const pthread_condattr_t *restrict attr);
pthread_cond_t cond = PTHREAD_COND_INITIALIZER
pthread_cond_init
函数初始化一个Condition Variable,attr
参数为NULL
则表示缺省属性。pthread_cond_destroy
函数销毁一个Condition Variable。PTHEAD_COND_INITIALIZER
初始化,相当于用pthread_cond_init
函数初始化并且attr
参数为NULL
。#include <pthread.h>
int pthread_cond_timedwait(pthread_cond_t *restrict cond,pthread_mutex_t *restrict mutex,const struct timespec *restrict abstime);
int pthread_cond_wait(pthread_cond_t *restrict cond,pthread_mutex_t *restrict mutex);
int pthread_cond_broadcast(pthread_cond_t *cond);
int pthread_cond_signal(pthread_cond_t *cond);
pthread_cond_wait
在一个Condition Variable上阻塞等待,这个函数做以下三步操作:
pthread_cond_timedwait
函数还有一个额外的参数可以设定等待超时,如果到达了abstime
所指定的时刻仍然没有别的线程来唤醒当前线程,就返回ETIMEDOUT
。pthread_cond_signal
唤醒在某个Condition Variable上等待的另一个线程。pthread_cond_broadcast
唤醒在这个Condition Variable上等待的所有线程。#pragma once
#include "Mutex.h"
#include <pthread.h>
namespace muduo
{
class Condition
{
public:
Condition(MutexLock& mutex) : mutex_(mutex)
{
MCHECK(pthread_cond_init(&pcond_,NULL));
}
~Condition()
{
MCHECK(pthread_cond_destroy(&pcond_));
}
void wait()
{
//@ pthread_cond_wait will release mutex
MutexLock::UnassignGuard ug(mutex_);
MCHECK(pthread_cond_wait(&pcond_, mutex_.get_mutex()));
}
//@ returns true if time out, false otherwise.
bool wait_for_seconds(double seconds);
void notify()
{
MCHECK(pthread_cond_signal(&pcond_));
}
void notify_all()
{
MCHECK(pthread_cond_broadcast(&pcond_));
}
private:
MutexLock& mutex_;
pthread_cond_t pcond_;
};
}
#include "Condition.h"
namespace muduo
{
//@ returns true if time out, false otherwise.
bool Condition::wait_for_seconds(double seconds)
{
struct timespec abs_time;
clock_gettime(CLOCK_REALTIME,&abs_time);
const int64_t kNanoSecondsPerSecond = 1000000000;
int64_t nano_seconds = static_cast<int64_t>(seconds * kNanoSecondsPerSecond);
abs_time.tv_sec += static_cast<time_t>((abs_time.tv_sec + nano_seconds) / kNanoSecondsPerSecond);
abs_time.tv_nsec += static_cast<long>((abs_time.tv_sec + nano_seconds) % kNanoSecondsPerSecond);
MutexLock::UnassignGuard ug(mutex_);
return ETIMEDOUT == pthread_cond_timedwait(&pcond_,mutex_.get_mutex(),&abs_time);
}
}
原文:https://www.cnblogs.com/xiaojianliu/p/14697506.html