本文主要是介绍华清远见作业第二十二天——IO(第五天),希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!
思维导图:
将互斥机制代码重新实现一遍
代码:
#include<stdio.h>
#include<string.h>
#include<stdlib.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include<a.h>
char buf[128]; //全局数组,临界资源
//1、创建一个互斥锁
pthread_mutex_t mutex;
//定义分支线程
void *task(void *arg)
{while(1){//3、获取锁资源pthread_mutex_lock(&mutex);printf("分支线程中:buf=%s\n",buf);strcpy(buf,"I love China\n");//4释放锁资源pthread_mutex_unlock(&mutex);}
}
int main(int argc, const char *argv[])
{//定义线程号变量pthread_t tid;//2初始化互斥锁pthread_mutex_init(&mutex,NULL);//创建线程if(pthread_create(&tid,NULL,task,NULL)!=0){printf("tid create error\n");return -1;}//主线程while(1){//获取锁资源pthread_mutex_lock(&mutex);printf("主线程中buf=%s\n",buf); //访问临界资源strcpy(buf,"hello world\n");//释放锁资源pthread_mutex_unlock(&mutex);}pthread_join(tid,NULL); //阻塞回收线程资源//销毁锁资源pthread_mutex_destroy(&mutex);return 0;
}
运行效果:
将同步机制代码重新实现一遍
代码:
#include<stdio.h>
#include<string.h>
#include<stdlib.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <a.h>
//1创建一个无名信号量
sem_t sem;
//生产者线程
void *task1(void *arg)
{while(1){sleep(2);printf("我生产了一辆特斯拉\n");//4释放资源sem_post(&sem);}
}
//消费者线程
void *task2(void *arg)
{while(1){//3申请资源,如果没有资源sem_wait(&sem);printf("我消费了一辆特斯拉\n");}
}
int main(int argc, const char *argv[])
{//创建两个线程pthread_t tid1,tid2;//初始化无名信号量sem_init(&sem,0,0);//第一个0:表示线程之间的通信//第二个0:表示value初始值为0//创建生产者线程if(pthread_create(&tid1,NULL,task1,NULL)!=0){printf("tid1 create error\n");return -1;}//创建消费者线程if(pthread_create(&tid2,NULL,task2,NULL)!=0){printf("tid2 create error\n");return -1;}//主线程回收资源pthread_join(tid1,NULL);pthread_join(tid2,NULL);//销毁无名信号量sem_destroy(&sem);return 0;
}
运行效果:
使用三个线程完成两个文件的拷贝,线程1完成拷贝前一半,线程2完成拷贝后一半,主线程回收两个分支线程的资源。
代码:
#include<stdio.h>
#include<string.h>
#include<stdlib.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include<stdio.h>
#include<a.h>
//定义传参结构体
struct INFO
{const char *r; //读取的文件const char *w; //写入的文件int start; //开始位置int len; //长度
};
//定义求文档长度函数
int lenstr(const char *r)
{//以只读的形式打开源文件FILE *rfp=NULL;if((rfp=fopen(r,"r"))==NULL){perror("rfp error");return -1;}//使用fseek和ftell函数定位到文件的数量//fseek(文件指针,偏移量,开始的位置)//ftell(文件中指针),直接返回文件的位置,既把指针最后的位置,返回文件数量int len=0; //计数 fseek(rfp,0,SEEK_END); //光标偏移到文件最后的位置len=ftell(rfp); //返回值就是文件的数量fclose(rfp);return len;
}
//定义拷贝函数
int file_cpy(const char *r,const char *w,int start, int len)
{ char buf[128]=""; //数据搬运工//以只读的形式打开源文件FILE *rfp=NULL;if((rfp=fopen(r,"r"))==NULL){perror("rfp error");return -1;}//以追加写的形式打开被写的文件FILE *wfp=NULL;if((wfp=fopen(w,"a"))==NULL){perror("wfp error");return -1;}//bzero(清零的地址,空间字节数)//防止buf中有内容影响操作//bzero(buf,sizeof(buf)); //清零buf//由于读文件已经打开,故需要把光标定位到开头fseek(rfp,start,SEEK_SET); //光标定位到开始偏移的位置//由于需要限制位置,所以使用fread函数来进行读取int count=fread(buf,sizeof(buf[0]),len,rfp);//写入使用fwrite函数fwrite(buf,sizeof(buf[0]),count,wfp);//关闭文件fclose(rfp);fclose(wfp);return 0;
}
void *task1(void *arg)
{while(1){struct INFO * fap = (struct INFO *)arg;//调用文件拷贝函数进行拷贝file_cpy(fap->r,fap->w,fap->start,fap->len); printf("我是分支线程1\n");sleep(1);//将输入的拷贝函数的各个参数分解//将输入的拷贝函数的各参数结构体拆包到一个结构体变量中//获取当前线程的线程号printf("我是分支线程1:tid1=%#lx\n",pthread_self());//退出当前线程printf("分支线程1资源退出\n");pthread_exit(NULL);}
}
void *task2(void *arg)
{while(1){printf("我是分支线程2\n");sleep(1);//将输入的拷贝函数的各个参数分解struct INFO * fap = (struct INFO *)arg;//调用文件拷贝函数进行拷贝file_cpy(fap->r,fap->w,fap->start,fap->len); printf("我是分支线程1:tid1=%#lx\n",pthread_self());//退出当前线程printf("分支线程2资源退出\n");pthread_exit(NULL); }
}
int main(int argc, const char *argv[])
{if(argc!=3){printf("内容错误\n");return -1;}int len=lenstr(argv[1]);//定义结构体变量struct INFO t1={argv[1],argv[2],0,len/2};struct INFO t2={argv[1],argv[2],len/2,len-len/2};//定义一个线程号变量pthread_t tid1=0; //创建出一个分支线程if(pthread_create(&tid1,NULL,task1,&t1)!=0){printf("tid1 create error\n");return -1;}printf("tid1 create success tid=%#lx\n",tid1);//创建一个分支线程pthread_t tid2=0;if(pthread_create(&tid2,NULL,task2,&t2)!=0){printf("tid2 create error\n");return -1;}printf("tid2 create success tid2=%#lx\n",tid2);
// while(1){printf("我是主线程\n");sleep(1);}//主线程回收分支线程pthread_join(tid1,NULL);pthread_join(tid2,NULL);printf("主线程成功回收分支线程的资源\n");return 0;
}
运行效果:
使用三个线程完成线程1输出字符'A',线程2输出字符'B',线程3输出字符'C',要求输出结果为ABCABCABCABCABCABC...
代码:
#include<a.h>
//1创建一个无名信号量
sem_t sem1,sem2;
//A线程
void *task1(void *arg)
{while(1){sleep(2);printf("A");//释放资源sem_post(&sem1);}
}
//B线程资源
void *task2(void *arg)
{while(1){ //申请资源,如果没有资源则在该出堵塞sem_wait(&sem1);printf("B");//释放资源sem_post(&sem2);}
}
//B线程资源
void *task3(void *arg)
{while(1){ //申请资源,如果没有资源则在该出堵塞sem_wait(&sem2);printf("C");fflush(stdout); // 刷新 stdout 缓冲区}
}
int main(int argc, const char *argv[])
{//创建三个线程pthread_t tid1,tid2,tid3;//初始化无名信号量sem_init(&sem1,0,0);sem_init(&sem2,0,0);//第一个0:表示用于线程之间的通信//第二个0:表示value初始值为0//创建A线程if(pthread_create(&tid1,NULL,task1,NULL)!=0){printf("tid1 create error\n");return -1;}//创建B线程if(pthread_create(&tid2,NULL,task2,NULL)!=0){printf("tid2 create\n");return -1;}//创建C线程if(pthread_create(&tid3,NULL,task3,NULL)!=0){printf("tid3 create\n");return -1;}//主线程回收资源pthread_join(tid1,NULL);pthread_join(tid2,NULL);pthread_join(tid3,NULL);//销毁无名信号量sem_destroy(&sem1);sem_destroy(&sem2);return 0;
}
运行效果:
这篇关于华清远见作业第二十二天——IO(第五天)的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!