linux多线程--相关函数的用法

注意:多线程相关的代码,在编译时必须加-lpthread或者-pthread选项,例如:

gcc thread_test.c  -o test_exe  -pthread


一、创建线程:pthread_create

原型:

int pthread_create(pthread_t *tid,
                    const pthread_attr_t *attr,
                    (void*)(*start_rtn)(void*),
                    void *arg);

形参:tid输出所成功创建的新线程的线程ID,tid=thread id;

attr设定所创建的线程参数,传入NULL意味着使用默认参数;

start_rtn线程入口函数,函数格式形如: void *thread_entry(void *para);

arg创建新线程时,要传给入口函数的参数;

二、线程退出:pthread_exit

原型:void pthread_exit(void* retval);

功能:立即退出线程,如果退出时还想返回一些数据供父线程处理/使用,那么这些数据可以通过函数形参retval传出,传出的值可通过pthread_join函数获得。

注意:

1、我们传出的是数据的地址,而不是数据本身,因此数据本身必须是静态的、或者从内存堆动态分配的,而决不能是函数中的动态临时变量,因为一旦线程入口函数返回,那么栈中的数据值就消失/不可用了

2、在线程的入口函数中执行return p;和执行pthread_exit(p);作用是一毛一样的:退出线程,并传出返回值,而且返回值都可以被pthread_join捕获。

区别在于:return p只能在入口函数中退出线程,而pthread_exit(p)可以在入口函数的子函数中退出线程。

三、阻塞地等待某个线程退出pthread_join

原型:int pthread_join(pthread_t tid, void **retval);

功能:阻塞地等待某个线程退出,另外注意:父线程创建子线程之后,父线程会维护一些子线程的信息,只有显式地调用了该函数,父进程才会在子线程结束后清理所维护的子线程信息,换句话说,如果父线程不调用该函数,那么大量的子线程信息得不到释放,可能会造成堆溢出,除非:我们把创建的子线程与父线程分离开,这样子线程的信息在子线程结束后自动释放,分离线程所用的函数为:pthread_detach(pthread_t tid);

形参:tid 要等待的线程id;

retval为线程退出时,传出的值的指针的指针

//编译:gcc thread_basic.c -o test_exe -pthread
#include <limits.h>
#include <string.h>
#include <pthread.h>
#include <stdlib.h>
#include <stdio.h>
#include <error.h>
#include <errno.h>
#include <sys/types.h>
#include <unistd.h>

void *thread_entry(void* arg)
{
        int arg_val =  *(int*)arg;
        printf("child thread start with para: %d\n", arg_val);

        int *p_out = malloc(sizeof(int));//申请的空间用于传出线程的退出值
        //static int data_out = 0;
        //int *p_out = &data_out;//局部静态空间也可用来传出退出值
        *p_out = arg_val + 1;
        pthread_exit(p_out); //在入口函数中,本行代码等价于 return p_out;
        return p_out;//这一行实际上执行不到,线程已经被pthread_exit给退出了
}

int main()
{
        int status;//线程操作函数的返回值
        pthread_t  tid;//子线程ID
        int arg = 2;//传给子线程入口函数的实参
        int *p_recv_out;//pthread_join接收子线程的返回值

        //创建子线程
        status = pthread_create(&tid, NULL, thread_entry, &arg);
        if(0 == status)
        {
                printf("creat thread ok, tid = %ld\n", tid);
        }
        else
        {
                printf("creat thread failed, error info: %s\n", strerror(errno));
                return -1;
        }

        //等待子线程结束,并接收子线程的结束值
        status = pthread_join(tid, (void**)&p_recv_out);
         if(0 == status)
         {
                printf("child thread quit normally\n");
                printf("parent thread received exit data: %d\n", *p_recv_out);
                free(p_rec

运行结果:





猜你喜欢

转载自blog.csdn.net/qq_31073871/article/details/80772887