这天学的是多线程编程

进程被看作是两个实体
资源分配单元 (进程或者是任务)
调度/处理机分派单元 (线程或轻量级进程)

线程是进程中一个处理机分派的单元

一个线程可以访问它的进程的内存和资源,而且这些资源为同一进程的所有线程共享

用线程的好处

更少的生成时间
更少的删除时间
进程间切换更快
不用恢复用户地址空间
通信更有效
共享地址空间
不需调用内核传递消息
进程的所有资源对线程都可用

进程同步的主要任务:协调多个相关进程的执行次序
并发执行的诸进程之间能有效地共享资源和相互合作
程序的执行具有可再现性
实现方式
使用互斥量
数据类型:pthread_mutex_t
程序员给某个数据加锁
同一时间只允许一个线程去访问数据

pthread_mutex_init: 初始化一个互斥量

pthread_mutex_lock: 给一个互斥量加锁

pthread_mutex_trylock:加琐,如果失败不阻塞

pthread_mutex_unlock:解锁

作业1:

请设计程序,程序有一个共享变量,创建两个线程,各自把counter增加5000次.要求:两个线程是并发执行.


#include <stdio.h>
#include <sys/types.h>
#include <stdlib.h>
#include <pthread.h>

#define NLOOP 10

pthread_mutex_t wm;
void *increase(void *vptr);
int print_count = 0;

int main(){
pthread_t a_thread;
pthread_t b_thread;

if(pthread_mutex_init(&wm,NULL)!=0){
perror("Mutex init failed");
exit(1);
}


pthread_create(&a_thread,NULL,&increase,NULL);
pthread_create(&b_thread,NULL,&increase,NULL);
pthread_join(a_thread,NULL);
pthread_join(b_thread,NULL);

return 0;

}


void *increase(void *vptr){
// if(pthread_mutex_lock(&wm)!=0){


int i,val;
for(i=0; i<NLOOP; i++){
pthread_mutex_lock(&wm);
val = print_count;
print_count = val + 1;
printf("%x count is %d \n",(unsigned int)pthread_self(),print_count,print_count);
pthread_mutex_unlock(&wm);
sleep(1);
}
}


互斥量的缺点

互斥量的缺点

互斥量需要时间来加锁和解锁
互斥量尽量少用,够用即可
每个互斥量保护的区域应尽量大
互斥量的本质是串行执行
如果很多线程需要频繁地加锁同一互斥量,则线程大部分时间都在等待-损害性能
互斥量保护的数据/代码包含彼此无关的片段-一个互斥量分解为几个小互斥量-任意时刻需要小互斥量的线程减少-减少线程的等待时间
互斥量应该足够多-有意义的地步
每个互斥量保护的区域应该尽量少

条件变量

条件变量是利用线程间共享的全局变量进行同步的一种机制
一个线程等待”条件变量的条件成立”而阻塞
另一线程改变了条件,它发信号给相关的条件变量,唤醒一个或多个等待它的线程
条件的检测在互斥锁的保护下进行
互斥锁用于短期等待
条件变量用于长期等待

使用条件变量之前要先进行初始化
进程间线程的通信
pthread_cond_t my_condition = PTHREAD_COND_INITIALIZER
调用系统函数
int pthread_cond_init(pthread_cond_t *cond,const pthread_condattr_t *attr)
释放为条件变量所分配的资源
int pthread_cond_destroy(pthread_cond_t *cond)

等待条件变量
int pthread_cond_wait(
pthread_cond_t *cond, pthread_mutex_t *mutex);
如果条件为假,调用线程自动阻塞,并释放等待状态改变的互斥锁.
如果另一个线程改变了条件,它发信号给关联的条件变量,唤醒一个或多个等待它的线程,重新获得互斥锁,重新评估条件.

一个生产者--消费者的例子

#include <pthread.h>
#include <stdio.h>
#include <stdlib.h>

#define MAX 5

pthread_mutex_t mutex = PTHREAD_MUTEX_INITIALIZER;
pthread_cond_t cond = PTHREAD_COND_INITIALIZER;

typedef struct
{
char buffer[MAX];
int how_many;
}BUFFER;

BUFFER share = {"",0};
char ch = 'A';

void *readFunc(void*);
void *writeFunc(void *);

int main(void)
{
pthread_t readThread;
pthread_t writeThread;

pthread_create(&readThread,NULL,readFunc,(void *)NULL);
pthread_create(&writeThread,NULL,writeFunc,(void *)NULL);

pthread_join(writeThread,(void **)NULL);
pthread_mutex_destroy(&mutex);
pthread_cond_destroy(&cond);
exit(0);
}

void *readFunc(void *junk)
{
int n = 0;
printf("Read Thread %2d:starting\n",pthread_self());

while(ch != 'Z')
{
pthread_mutex_lock(&mutex);
if(share.how_many != MAX)
{
share.buffer[share.how_many++] = ch++;
printf("Read Thread %2d: Got char[%c]\n",pthread_self(),ch-1);
if(share.how_many == MAX)
{
printf("Read Thread %2d: signaling full\n",pthread_self());
pthread_cond_signal(&cond);
}
}
pthread_mutex_unlock(&mutex);
}
sleep(1);
printf("Read Thread %2d: Exiting\n",pthread_self());
return NULL;
}

void *writeFunc(void *junk)
{
int i;
int n = 0;
printf("Write Thread %2d: starting\n",pthread_self());

while(ch != 'Z')
{
pthread_mutex_lock(&mutex);
printf("\nWrite Thread %2d: writing buffer\n",pthread_self());
while(share.how_many != MAX)
pthread_cond_wait(&cond,&mutex);
printf("Write Thread %2d: writing buffer\n",pthread_self());
for(i = 0; share.buffer[i]&&share.how_many;++i,share.how_many--)
putchar(share.buffer[i]);
pthread_mutex_unlock(&mutex);
}
printf("Write Thread %2d: exiting\n",pthread_self());
return NULL;
}



更多相关文章

  1. Linux多线程实践(一)线程基本概念和理论
  2. linux线程函数中代替sleep的方法
  3. linux 多线程基础
  4. linux进程和线程排查 · 记一次JVM CPU高负载的排查办法
  5. linux下main thread如何使用pthread_join等待子线程结束后再退出
  6. Linux进程通信[2]-互斥锁和条件变量
  7. 【Ubuntu手记】开发多线程程序时在eclipse中添加libpthread.a库
  8. Linux 多线程 ”一写多读” 模式下的无锁设计
  9. gdb捕获syscall条件和字符串比较

随机推荐

  1. 设计模式之门面模式
  2. java创建对象的过程(内存角度分析)
  3. java集合系列(2)collection
  4. jvm系列(3)类加载机制
  5. 数据结构与算法(3)链表
  6. java网络编程(2)socket通信案例
  7. java运行时数据区域
  8. java集合系列(6)Vector
  9. synchronized的实现原理和应用
  10. java集合系列(3)ArrayList