线程与进程的区别
-----------------------------------------------------
1.节俭:在Linux系统下,启动新的进程,必须分配给它独立的地址空间,建立众多的数据表来维护它的代码段、堆栈段和数据段。运行于一个进程中的多个线程,它们彼此之间使用相同的地址空间,共享大部分数据,启动一个线程所花费的空间远远小于启动一个进程所花费的空间,而且,线程间彼此切换所需的时间也远远小于进程间切换所需要的时间。
2.通信方便:不同进程,它们具有独立的数据空间,要进行数据的传递只能通过通信的方式进行,这种方式不仅费时,而且很不方便。线程则不然,由于同一进程下的线程之间共享数据空间,所以一个线程的数据可以直接为其它线程所用,这不仅快捷,而且方便。
本身的优点
-----------------------------------------------------
1) 提高应用程序响应。这对图形界面的程序尤其有意义,当一个操作耗时很长时,整个系统都会等待这个操作,此时程序不会响应键盘、鼠标、菜单的操作,而使用多线程技术,将耗时长的操作(time consuming)置于一个新的线程,可以避免这种尴尬的情况。
2) 使多CPU系统更加有效。操作系统会保证当线程数不大于CPU数目时,不同的线程运行于不同的CPU上。
3) 改善程序结构。一个既长又复杂的进程可以考虑分为多个线程,成为几个独立或半独立的运行部分,这样的程序会利于理解和修改。
线程编程
----------------------------------------------------
Linux系统下的多线程遵循POSIX线程接口,称为pthread。编写Linux下的多线程程序,需要使用头文件pthread.h,连接时需要使用库libpthread.a。
#include <pthread.h>
#include <stdio.h>
void thread(void)
{
int i;
for(i=0;i<3;i++)
printf("This is a pthread./n");
}
int main(void)
{
pthread_t id;
int i,ret;
ret=pthread_create(&id,NULL,(void *) thread,NULL);
if(ret!=0){
printf ("Create pthread error!/n");
exit (1);
}
for(i=0;i<3;i++)
printf("This is the main process./n");
pthread_join(id,NULL);
return (0);
}
gcc -o thread -lpthread test //pthread库不是Linux系统默认的库,连接时需要使用库libpthread.a,
运行thread ,我们得到如下结果:
This is the main process.
This is a pthread.
This is the main process.
This is the main process.
This is a pthread.
This is a pthread.
再次运行thread ,我们可能得到如下结果:
This is a pthread.
This is the main process.
This is a pthread.
This is the main process.
This is a pthread.
This is the main process.
前后两次结果不一样,这是两个线程争夺CPU资源的结果。
线程函数介绍
----------------------------------------------------------------
int pthread_create( pthread_t *restrict tidp, const pthread_attr_t *restrict attr,
void *(*start_rtn)(void), void *restrict arg );
第一个参数为指向线程标识符的指针。
第二个参数用来设置线程属性。
第三个参数是线程运行函数的起始地址。
最后一个参数是运行函数的参数。
注:如果想传递参数给线程函数,可以通过其参数arg,其类型是void *。如果你需要传递多个参数的话,可以考虑将这些参数组成一个结构体来传递。另外,由于类型是void *,所以你的参数不可以被提前释放掉。
int pthread_join(pthread_t thread, void **value_ptr);
线程阻塞函数,将当前线程挂起,等待指定的线程结束,并回收资源。
void pthread_exit(void *rval_ptr)
单个线程退出方式有3种:从启动例程中返回,返回值是线程的退出码;被其它线程取消;线程调用pthread_exit。
rval_ptr 是一个无类型指针,相当于线程的退出码。它通过pthread_join()访问到
void * thr_fn1(void *arg)
{
printf("thread 1 returning/n");
return((void *)1);
}
void * thr_fn2(void *arg)
{
printf("thread 2 exiting/n");
pthread_exit((void *)2);
}
pthread_create(&tid1, NULL, thr_fn1, NULL);
pthread_create(&tid2, NULL, thr_fn2, NULL);
pthread_join(tid1, &tret);// tret = 1
pthread_join(tid2, &tret);// tret = 2