一:线程概述
进程与线程区别:
- 在面向线程设计的系统中,进程本身不是基本运行单位,而是线程的容器。
- 进程有独立的地址空间,一个进程崩溃后,在保护模式下不会对其它进程产生影响,而线程只是一个进程中的不同执行路径。线程有自己的堆栈和局部变量,但线程没有单独的地址空间,一个线程死掉就等于整个进程死掉,所以多进程的程序要比多线程的程序健壮,但在进程切换时,耗费资源较大,效率要差一些。
线程的优点:
- 总的来说就是:进程有独立的地址空间,线程没有单独的地址空间(同一进程内的线程共享进程的地址空间)。
- 和进程相比,它是一种非常"节俭"的多任务操作方式。运行于一个进程中的多个线程,它们彼此之间使用相同的地址空间,共享大部分数据,启动一个线程所花费的空间远远小于启动一个进程所花费的空间,
- 线程间方便的通信机制。对不同进程来说,它们具有独立的数据空间,要进行数据的传递只能通过通信的方式进行,这种方式不仅费时,而且很不方便。线程则不然,由于同一进程下的线程之间共享数据空间,所以一个线程的数据可以直接为其它线程所用,这不仅快捷,而且方便。
二:线程
原型:
#include <pthread.h>
int pthread_create(pthread_t *restrict tidp, const pthread_attr_t *restrict attr, void *(*start_rtn)(void *), void *restrict arg); //创建进程int pthread_exit(void *rval_ptr); //进程退出
int pthread_join(pthread_t thread, void **rval_ptr); //添加进程
// 返回:若成功返回0,否则返回错误编号
#include <stdio.h>
#include <pthread.h>
//int pthread_create(pthread_t *restrict tidp, const pthread_attr_t *restrict attr, void *(*start_rtn)(void *), void *restrict arg);
void *func1(void *arg)
{
static int ret = 10; //参数需设置为static,否则被调用时数据错误
printf("t1:%ld,thread is created\n",(unsigned long)pthread_self());
printf("t1:param:%d\n",*((int *)arg));
pthread_exit((void *)&ret);
}
int main()
{
int ret;
pthread_t t1;
int param = 100;
int *pret = NULL;
ret = pthread_create(&t1,NULL,func1,(void *)¶m);
if(ret == 0){
printf("main:create the thread success\n");
}
printf("main:%ld\n",(unsigned long)pthread_self());
pthread_join(t1,(void **)&pret);
printf("main:quit:%d\n",*pret);
return 0;
}
为了防止main函数运行完就退出不执行线程,需要用到join和exit函数
三:验证线程对共享内存的操作
//共享内存代码验证demo4.c
#include <stdio.h>
#include <pthread.h>
//int pthread_create(pthread_t *restrict tidp, const pthread_attr_t *restrict attr, void *(*start_rtn)(void *), void *restrict arg);
int g_data = 0;