58同城网站招聘怎么做,wordpress自定义链接后404,怎么做一个自己网站,找别人做的网站问什么域名解析后还是上线不介绍
多线程编程#xff0c;经常会遇到线程直接数据同步#xff0c;为了保证数据访问安全#xff0c;就必须考虑线程之间的同步问题。在C语言中#xff0c;多线程编程的线程同步主要依赖于POSIX线程#xff08;Pthreads#xff09;库提供的同步原语。以下是一些关键的线…介绍
多线程编程经常会遇到线程直接数据同步为了保证数据访问安全就必须考虑线程之间的同步问题。在C语言中多线程编程的线程同步主要依赖于POSIX线程Pthreads库提供的同步原语。以下是一些关键的线程同步机制 互斥锁 (Mutexes) pthread_mutex_t 是一种互斥对象用于保护共享资源确保同一时间只有一个线程可以访问。 pthread_mutex_t mutex;
pthread_mutex_init(mutex, NULL); // 初始化互斥锁
pthread_mutex_lock(mutex); // 上锁
// 访问共享资源的代码
pthread_mutex_unlock(mutex); // 解锁读写锁 (Read-Write Locks) pthread_rwlock_t 允许多个线程同时进行读取操作但在写入操作时会排斥所有其他读写线程。 pthread_rwlock_t rwlock;
pthread_rwlock_init(rwlock, NULL);
pthread_rwlock_rdlock(rwlock); // 读取锁定
// 读取共享资源的代码
pthread_rwlock_unlock(rwlock); // 释放锁定
pthread_rwlock_wrlock(rwlock); // 写入锁定
// 更新共享资源的代码
pthread_rwlock_unlock(rwlock); // 释放锁定条件变量 (Condition Variables) 条件变量 pthread_cond_t 与互斥锁结合使用允许线程阻塞等待特定条件变为真。 pthread_cond_t cond;
pthread_mutex_t mutex;
pthread_mutex_init(mutex, NULL);
pthread_cond_init(cond, NULL);pthread_mutex_lock(mutex);
while (!condition_is_true()) { // 检查条件pthread_cond_wait(cond, mutex); // 条件不满足则等待
}
// 当条件满足时执行相关操作
pthread_mutex_unlock(mutex);// 另一个线程改变条件后可以唤醒等待的线程
pthread_mutex_lock(mutex);
condition_make_true(); // 改变条件
pthread_cond_signal(cond); // 唤醒一个等待线程
// 或者唤醒所有等待线程
pthread_cond_broadcast(cond);
pthread_mutex_unlock(mutex);信号量 (Semaphores) POSIX信号量 sem_t 也可以用于同步线程它是一个计数器控制可以同时访问资源的线程数量。 sem_t semaphore;
sem_init(semaphore, 0, 1); // 初始化为1即一次只允许一个线程通过sem_wait(semaphore); // 阻塞直到信号量计数大于0并减一
// 执行临界区代码
sem_post(semaphore); // 信号量加一释放资源应用举例
以下是一个使用互斥锁Mutexes和条件变量Condition Variables实现的简单生产者-消费者问题的例子。生产者线程生成数据并放入缓冲区消费者线程从缓冲区取出数据处理。
#include pthread.h
#include stdio.h#define BUFFER_SIZE 10
int buffer[BUFFER_SIZE];
int buffer_count 0;
pthread_mutex_t mutex PTHREAD_MUTEX_INITIALIZER;
pthread_cond_t full PTHREAD_COND_INITIALIZER;
pthread_cond_t empty PTHREAD_COND_INITIALIZER;void* producer(void* arg) {int i;for (i 0; i 20; i) {pthread_mutex_lock(mutex);while (buffer_count BUFFER_SIZE) { // 如果缓冲区已满pthread_cond_wait(full, mutex); // 生产者等待}buffer[buffer_count] i; // 放入数据printf(Producer produced %d\n, i);pthread_cond_signal(empty); // 唤醒消费者pthread_mutex_unlock(mutex);}return NULL;
}void* consumer(void* arg) {int i;while (1) {pthread_mutex_lock(mutex);while (buffer_count 0) { // 如果缓冲区为空pthread_cond_wait(empty, mutex); // 消费者等待}int data buffer[--buffer_count]; // 取出数据printf(Consumer consumed %d\n, data);pthread_cond_signal(full); // 唤醒生产者pthread_mutex_unlock(mutex);// 在这里可以处理消费的数据这里为了简化直接输出}return NULL;
}int main() {pthread_t producer_thread, consumer_thread;pthread_create(producer_thread, NULL, producer, NULL);pthread_create(consumer_thread, NULL, consumer, NULL);pthread_join(producer_thread, NULL);pthread_join(consumer_thread, NULL);pthread_cond_destroy(full);pthread_cond_destroy(empty);pthread_mutex_destroy(mutex);return 0;
}示例说明
在这个例子中创建了两个线程一个生产者线程和一个消费者线程。生产者在缓冲区未满时产生数据并通过条件变量full通知消费者消费者在缓冲区非空时消费数据并通过条件变量empty通知生产者。通过互斥锁mutex保护对共享资源缓冲区和缓冲区计数器的访问确保了线程间的同步。
总结
在使用这些同步机制时重要的是要理解它们各自的适用场景和潜在的开销。不恰当的同步可能导致性能下降或死锁等问题。