
pthread_create的实现
pthread_create是基于clone实现的, 创建出来的其实是进程, 但这些进程与父进程共享很多东西, 共享的东西都不用复制给子进程, 从而节省很多开销, 因此,这些子进程也叫轻量级进程(light-weight process)
姓名:王央京 学号:18050100052 学院:电子工程学院
转自:https://blog.csdn.net/qq_22847457/article/details/89371217
【嵌牛导读】本文介绍了Linux线程的相关信息
【嵌牛鼻子】Linux线程
【嵌牛提问】在了解Linux系统后,能否具体介绍线程的概念?
【嵌牛正文】
类Unix系统中,早期是没有“线程”概念的,80年代才引入,借助进程机制实现出了线程的概念。因此在这类系统中,进程和线程关系密切。一个进程可以有多个线程,这个进程本身也叫做线程只不过是主线程。通常主线程分配任务给子线程做。程序设计时候就可以某一时刻不止做一件事情,每一个线程处理各自独立的任务。
多个线程可以访问相同的存储地址空间和文件描述符。同一进程内的线程共享以下数据:全局内存、进程指令、打开的文件、信号处理函数和信号处置、当前工作目录、用户ID和用户组ID、大多数数据。每个线程有各自的线程ID、寄存器集合(包括程序计数器和栈指针)、栈、errono、信号掩码、优先级。
线程的优点有提高程序并发性、开销小和数据通信、共享数据方便等。线程的缺点有库函数不稳定、调试编写困难、gdb不支持、对信号支持不好等。除此之外,多线程内如果其中一个线程出现了 除0、野指针 等问题会造成该线程崩溃,进而导致整个进程终止。同时,线程是进程的执行分支,线程出异常,就类似进程出异常,进而触发信号机制,终止进程,进程终止,该进程内的所有线程也就随即退出。
从上述分析来看,线程的优点相对突出,缺点均不是硬伤。Linux下由于实现方法导致进程、线程差别不是很大。
线程有一套完整的与其有关的函数库调用,它们中的绝大多数函数名都以pthread_开头。为了使用这些函数库调用,我们必须定义宏_REENTRANT,在程序中包含头文件pthread.h,并且在编译程序时需要用选项-lpthread来链接线程库。其中常用的函数库如下:
1. pthread_self函数获取线程ID,其作用对应进程中getpid()函数。
2. pthread_create函数创建一个新线程,其作用对应进程中fork()函数。
3. pthread_exit函数将单个线程退出,其作用对应进程中exit()函数
4. pthread_join函数阻塞等待线程退出,获取线程退出状态其作用,对应进程中waitpid()函数。
5. pthread_cancel函数杀死(取消)线程其作用,对应进程中kill()函数。
6. pthread_detach函数实现线程分离。
配置文件为 conf.txt测试代码如下,注意链接的时候加上 -lpthread 这个参数
#include <stdio.h>
#include <errno.h>//perror()
#include <pthread.h>
#include <unistd.h>//sleep()
#include <time.h>// time()
#include <stdlib.h>//rand()
#define FD "conf.txt"
typedef void *(*fun)(void *)
struct my_struct
{
unsigned time_to_wait
int n
}
void *test_thread(struct my_struct *)
int main (int argc, char const *argv[])
{
FILE *fp = fopen(FD, "r")
if (fp == NULL)
{
perror(FD)
return -1
}
srand((unsigned)time(NULL))//初始化随机种子
int thread_count
fscanf(fp, "%d", &thread_count)
fclose(fp)
if (thread_count <= 0)
{
printf("线程数<1,退出程序。\n")
return -1
}
pthread_t *ptid = (pthread_t *)malloc(sizeof(pthread_t) * thread_count) //保存线程ID
int i
for (i = 0i <thread_counti++)
{
int tw = rand() % thread_count + 1//随机等待时间
struct my_struct * p = (struct my_struct *)malloc(sizeof(struct my_struct))
if (p == NULL)
{
perror("内存分配错误")
goto ERROR
}
p->time_to_wait = tw
p->n = i + 1
int rval = pthread_create(ptid + i, NULL, (fun) test_thread, (void *)(p))//注意这里的强制转换(两个)
if (rval != 0)
{
perror("Thread creation failed")
goto ERROR
}
//sleep(1) //这句加也可以,不加也可以。最开始的时候加上这个是为了让两个线程启动的时候之间有一定的时间差
}
printf("主线程启动\n\n")
fflush(stdout)
for (i = 0i <thread_counti++)
{
pthread_join(*(ptid + i), NULL)//等待所有线程退出。
}
printf("\n主线程退出\n")
ERROR:
free(ptid)
return 0
}
void *test_thread(struct my_struct * p) //线程启动的时候运行的函数
{
printf("第%d个线程启动,预计运行%d秒\n", p->n, p->time_to_wait)
fflush(stdout)
sleep(p->time_to_wait) //让线程等待一段时间
printf("第%d个线程结束\n", p->n)
fflush(stdout)
free(p)
return NULL
}
你的第二个问题我在百度HI回你了~
欢迎分享,转载请注明来源:内存溢出
微信扫一扫
支付宝扫一扫
评论列表(0条)