Linux系统编程-DAY06(线程)

一、线程概念
进程和线程共同点:并发

1.线程属于某一个进程,线程不共享栈区
优点:比多进程节省资源,可以共享变量。
      线程启动时,需要在栈区开一个8M的空间,进程拿到的资源,对于线程是共享的。

2.概念:线程是轻量级进程,一般是一个进程中的多个任务
    进程是系统中最小的资源分配单位
    线程是系统中最小的执行单位

3.区别:
    1)线程的并发度比进程多一些
    2)创建开销不同,thread 8M, proc 3G
    3)thread 共享进程中的资源,除了栈区。进程,独立(写时复制 cow)
    4)线程稳定性稍差。
    5)进程可以申请到硬件资源,线程用进程拿到的资源
    
4.三方库: pthread  clone   posix(posix便于移植的)
    4.1 编写代码头文件: pthread.h
    4.2 编译代码加载库: -lpthread   library 
libpthread.so  (lib开头so结尾,共享库)
gcc 1.c -lpthread 

5.线程的设计框架    
    1.创建多线程 --->线程空间操作  --->线程资源回收
    int pthread_create(
    pthread_t *thread, const pthread_attr_t *attr,
    void *(*start_routine) (void *), void *arg);
        eg: pthread_create(&tid, NULL, th, NULL);
    2.  arg  回调函数的参数,即参数3的指针函数参数。
返回值:成功 0
失败 错误码

6.pthrea_self(void)获取自己的tid号

7.线程的退出:
    1: 自行退出 --> 自杀 --> 子线程自己退出        void pthread_exit(void *retval);  exit  return p;
    2: 强制退出 --> 他杀 --> 主线程结束子线程    int pthread_cancel(pthread_t thread);

8.线程的回收
    不同与进程没有孤儿线程和僵尸线程。
      主线程结束任意生成的子线程都会结束。
      子线程的结束不会影响主线程的运行。
int pthread_join(pthread_t, thread, void **retva)
    join有阻塞的意思
      功能:通过该函数可以将指定的线程资源回收,该函数具有阻塞等待功能,如果指定的线程没有结束,则回收线程会阻塞。

9.地址有三种:
0、栈区变量  错误,子线程结束该地址失效。
1、全局变量  失去意义,本质可以直接访问。
正确形式:
2、静态变量 
3、堆区变量malloc

10.分离属性:
    int pthread_deatch(pthread_t thread);
        1)可以放在th里面调用,参数写自己的id号
        2)主线程调用:填入刚才创建的线程的线程号。

11.线程清理函数
    void pthread_cleanup_push(void (*routine)(void *), void *arg);
        功能:注册一个线程清理函数
        参数,routine,线程清理函数的入口
        arg,清理函数的参数。
        返回值,无
    void pthread_cleanup_pop(int execute);
        功能:调用清理函数
        execute,非0  执行清理函数
        0 ,不执行清理

12.线程起进程后,起完多线程就会变成单线程

二、练习及其代码
1.创造线程

#include 
#include 
#include 
#include 
#include 
#include 
void *th1(void *arg)
{
    while (1)
    {
        printf("打瓦\n");
        sleep(1);
    }
}

void *th2(void *arg)
{
    while (1)
    {
        printf("吃饭\n");
        sleep(1);
    }
}

int	main(int argc, char **argv)
{
    pthread_t tid1,tid2;
    pthread_create(&tid1, NULL, th1, NULL);
    pthread_create(&tid1, NULL, th2, NULL);
    while (1)
    {
        sleep(1);
    }
    return 0;
}

2.获得线程tid号

#include 
#include 
#include 
#include 
#include 
#include 
void *th1(void *arg)
{
    while (1)
    {
        printf("打瓦 th1, tid:%ld\n",pthread_self());
        sleep(1);
    }
}

void *th2(void *arg)
{
    while (1)
    {
        printf("吃饭 th2, tid:%ld\n",pthread_self());
        sleep(1);
    }
}

int	main(int argc, char **argv)
{
    pthread_t tid1,tid2;
    pthread_create(&tid1, NULL, th1, NULL);
    pthread_create(&tid1, NULL, th2, NULL);
    while (1)
    {
        printf("main th, tid:%ld\n",pthread_self());
        sleep(1);
    }
    return 0;
}

3.strerror


#include 
#include 
#include 
#include 
#include 


int	main(int argc, char **argv)
{
    int i = 0 ;
    for(i=0;i<400;i++)
    {
        printf("%d %s\n",i,strerror(i));
    }


    //system("pause");
    return 0;
}

4.线程的exit

#include 
#include 
#include 
#include 
#include 
#include 
#include 
void *th(void *arg)
{
    int i = 3;
    while(i--)
    {
        printf("th,tid:%ld\n",pthread_self());
        sleep(1);
    }
    pthread_exit(NULL);
}

int	main(int argc, char **argv)
{
    pthread_t tid;
    pthread_create(&tid, NULL, th, NULL);
    while (1)
    {
        sleep(1);
    }


    //system("pause");
    return 0;
}

5.线程的cancel

#include 
#include 
#include 
#include 
#include 
#include 
#include 
void *th(void *arg)
{
    int i = 3;
    while(i--)
    {
        printf("th,tid:%ld\n",pthread_self());
        sleep(1);
    }
    pthread_exit(NULL);
}

int	main(int argc, char **argv)
{
    pthread_t tid;
    pthread_create(&tid, NULL, th, NULL);
    int i = 0;
    while (1)
    {
        printf("main th, tid : %ld\n", pthread_self());
        sleep(1);
        ++i;
        if(3 == i)
        {
            pthread_cancel(tid);
        }
    }
    //system("pause");
    return 0;
}

6.线程的回收

#include 
#include 
#include 
#include 
#include 

void *th(void *arg)
{
    int i = 5;
    while(i--)
    {
        printf("th tid:%ld\n", pthread_self());
        sleep(1);
    }
    return NULL;
}

int	main(int argc, char **argv)
{
    pthread_t tid;
    pthread_create(&tid, NULL, th, NULL);
    pthread_join(tid, NULL);
    return 0;
}

7.线程join带返回值

#include 
#include 
#include 
#include 
#include 

void *th(void *arg)
{
    char *p = (char *)malloc(50);
    strcpy(p, "小凡是人机");
    sleep(3);
    return p;
}

int	main(int argc, char **argv)
{
    pthread_t tid;
    pthread_create(&tid, NULL, th, NULL);
    void *ret;
    pthread_join(tid, &ret);
    printf("ret %s\n",(char*)ret);
    free(ret);
    return 0;
}

8.线程的共享特性


#include 
#include 
#include 
#include 
#include 

int a = 0;
void *th(void *arg)
{
    sleep(1);
    a += 10;
    return NULL;
}

int	main(int argc, char **argv)
{
    pthread_t tid;
    printf("a is %d\n", a);
    pthread_create(&tid, NULL, th, NULL);
    pthread_join(tid, NULL);
    printf("a is %d\n", a);
    return 0;
}

9.

#include 
#include 
#include 
#include 
#include 
#include 

typedef struct
{
    char name[50];
    int age;
    char addr[50];
}PER;

void *th(void *arg)
{
    PER *per = (PER*)arg;
    printf("th: %s %d %s\n", per->name, per->age, per->addr);
    strcat(per->name, "Runa");
    return per;
}

int main(int argc, char **argv)
{
    PER per;
    bzero(&per, sizeof(per));

    printf("input name:");
    fgets(per.name, sizeof(per.name), stdin);
    per.name[strlen(per.name) - 1] = '\0';

    char buf[5] = {0};
    printf("input age:");
    fgets(buf, sizeof(buf), stdin);
    per.age = atoi(buf);

    printf("input addr:");
    fgets(per.addr, sizeof(per.addr), stdin);
    per.addr[strlen(per.addr) - 1] = '\0';

    pthread_t tid;
    pthread_create(&tid, NULL, th, &per);
    void *ret = NULL;
    pthread_join(tid, &ret);
    printf("join ret: %s %d %s\n",per.name
    , per.age, ((PER*)ret)->addr);
    return 0;
}

10.线程的栈区自动回收

#include 
#include 
#include 
#include 

void* th(void* arg)
{
  pthread_detach(pthread_self());  //栈区系统自动回收
  return NULL;
}

int main(int argc, char** argv)
{
  int i = 0;
  pthread_t tid;
  for (i = 0; i < 50000; i++)
    {
      int ret = pthread_create(&tid, NULL, th, NULL);
      if (ret != 0)
        {
          break;
        }
      printf("%d\n", i);
    }
  system("pause");
  return 0;
}

11.线程的清除

#include 
#include 
#include 
#include 
#include 
void clean(void *arg)
{
    printf("this clean %s\n", (char*)arg);
    free(arg);
}
void* th(void* arg)
{
    strcpy((char* )arg,"hello world\n");
    printf("th,strcpy over\n");
    return NULL;
}

int	main(int argc, char **argv)
{
    
    pthread_t tid;
    char* p = malloc(50);
    pthread_cleanup_push(clean,p);
    pthread_create(&tid,NULL,th,p);
    pthread_join(tid,NULL);

    printf("before pop\n");
    pthread_cleanup_pop(1);
    system("pause");
    return 0;
}

你可能感兴趣的:(linux,java,jvm)