线程的优先级无法保障线程的执行次序。只不过优先级高的线程获取 CPU 资源的概率大一点而已。

线程相关函数(1)-pthread_create(), pthread_join(), pthread_exit(), pthread_cancel() 创建取消线程

一. pthread_create()

#include <pthread.h>

int pthread_create(pthread_t *thread, const pthread_attr_t *attr, void *(*start_routine) (void *), void *arg);

pthread_t *thread:           传递一个pthread_t变量地址进来,用于保存新线程的tid(线程ID)
const pthread_attr_t *attr:      
线程属性设置,如使用默认属性,则传NULL
void *(*start_routine) (void *):      
函数指针,指向新线程应该加载执行的函数模块
void *arg:            
指定线程将要加载调用的那个函数的参数

返回值:成功返回0,失败返回错误号。以前学过的系统函数都是成功返回0,失败返回-1,而错误号保存在全局变量errno中,而pthread库的函数都是通过返回值返回错误号,虽然每个线程也都有一个errno,但这是为了兼容其它函数接口而提供的,pthread库本身并不使用它,通过返回值返回错误码更加清晰。

二.pthread_join()

#include <pthread.h>
int pthread_join(pthread_t thread, void **retval);

pthread_t thread:        回收线程的tid
void **retval:          接收退出线程传递出的返回值
返回值:成功返回0,失败返回错误号

注意:

调用该函数的线程将挂起等待,直到id为thread的线程终止。thread线程以不同的方法终止,通过pthread_join得到的终止状态是不同的,总结如下:

如果thread线程通过return返回,retval所指向的单元里存放的是thread线程函数的返回值。
如果thread线程被别的线程调用pthread_cancel异常终止掉,retval所指向的单元里存放的是常数PTHREAD_CANCELED。
如果thread线程是自己调用pthread_exit终止的,retval所指向的单元存放的是传给pthread_exit的参数。

如果对thread线程的终止状态不感兴趣,可以传NULL给retval参数。

三.pthread_exit()

#include <pthread.h>
void pthread_exit(void *retval);
void *retval:      线程退出时传递出的参数,可以是退出值或地址,如是地址时,不能是线程内部申请的局部地址。

注意和exit函数的区别,任何线程里exit导致进程退出,其他线程未工作结束,主线程退出时不能return或exit。需要注意,pthread_exit或者return返回的指针所指向的内存单元必须是全局的或者是用malloc分配的,不能在线程函数的栈上分配,因为当其它线程得到这个返回指针时线程函数已经退出了。

四.pthread_cancel()

#include <pthread.h>
int pthread_cancel(pthread_t thread);

定义在Linux的pthread库中常数PTHREAD_CANCELED的值是-1。可以在头文件pthread.h中找到它的定义:

#define PTHREAD_CANCELED ((void *) -1)

五.示例

#include <pthread.h>
#include <stdio.h>
#include <unistd.h>

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);
}

void *thr_fn3(void *arg)
{
    while(1) {
        printf("thread 3 writing\n");
        sleep(1);
    }
}

int main()
{
    pthread_t tid;
    void *retval;

    pthread_create(&tid, NULL, thr_fn1, NULL);
    pthread_join(tid, &retval);
    printf("thread 1 exit code %d\n", (int)retval);    

    pthread_create(&tid, NULL, thr_fn2, NULL);
    pthread_join(tid, &retval);
    printf("thread 2 exit code %d\n", (int)retval);

    pthread_create(&tid, NULL, thr_fn3, NULL);
    sleep(3);
    // 调用pthread_cancel函数取消第三个线程
    pthread_cancel(tid);
    // 如果线程是通过pthread_cancel异常终止掉,retval所指向的单元里存放的是常数PTHREAD_CANCELED
    pthread_join(tid, &retval);
    printf("thread 3 exit code %d\n", (int)retval);

    return 0;
}

运行结果:

thread 1 returning
thread 1 exit code 1
thread 2 exiting
thread 2 exit code 2
thread 3 writing
thread 3 writing
thread 3 writing
thread 3 exit code -1

linux线程(一)的更多相关文章

  1. [转载]Linux 线程实现机制分析

    本文转自http://www.ibm.com/developerworks/cn/linux/kernel/l-thread/ 支持原创.尊重原创,分享知识! 自从多线程编程的概念出现在 Linux ...

  2. linux线程的实现

    首先从OS设计原理上阐明三种线程:内核线程.轻量级进程.用户线程 内核线程 内核线程就是内核的分身,一个分身可以处理一件特定事情.这在处理异步事件如异步IO时特别有用.内核线程的使用是廉价的,唯一使用 ...

  3. linux线程的实现【转】

    转自:http://www.cnblogs.com/zhaoyl/p/3620204.html 首先从OS设计原理上阐明三种线程:内核线程.轻量级进程.用户线程 内核线程 内核线程就是内核的分身,一个 ...

  4. Linux线程-创建

    Linux的线程实现是在内核以外来实现的,内核本身并不提供线程创建.但是内核为提供线程[也就是轻量级进程]提供了两个系统调用__clone()和fork (),这两个系统调用都为准备一些参数,最终都用 ...

  5. Linux线程学习(一)

    一.Linux进程与线程概述 进程与线程 为什么对于大多数合作性任务,多线程比多个独立的进程更优越呢?这是因为,线程共享相同的内存空间.不同的线程可以存取内存中的同一个变量.所以,程序中的所有线程都可 ...

  6. Linux线程学习(二)

    线程基础 进程 系统中程序执行和资源分配的基本单位 每个进程有自己的数据段.代码段和堆栈段 在进行切换时需要有比较复杂的上下文切换   线程 减少处理机的空转时间,支持多处理器以及减少上下文切换开销, ...

  7. Linux 线程(进程)数限制分析

    1.问题来源公司线上环境出现MQ不能接受消息的异常,运维和开发人员临时切换另一台服务器的MQ后恢复.同时运维人员反馈在出现问题的服务器上很多基本的命令都不能运行,出现如下错误:2.   初步原因分析和 ...

  8. Linux 线程与进程,以及通信

    http://blog.chinaunix.net/uid-25324849-id-3110075.html 部分转自:http://blog.chinaunix.net/uid-20620288-i ...

  9. linux 线程的内核栈是独立的还是共享父进程的?

    需要考证 考证结果: 其内核栈是独立的 206 static struct task_struct *dup_task_struct(struct task_struct *orig) 207 { 2 ...

  10. Linux 线程模型的比较:LinuxThreads 和 NPTL

    Linux 线程模型的比较:LinuxThreads 和 NPTL GNU_LIBPTHREAD_VERSION 宏 大部分现代 Linux 发行版都预装了 LinuxThreads 和 NPTL,因 ...

随机推荐

  1. JHipster技术栈定制 - JHipster Registry配置信息加密

    本文说明了如何开启和使用JHipster-Registry的加解密功能. 1 整体规划 1.1 名词说明 名词 说明 备注 对称加密 最快速.最简单的一种加密方式,加密(encryption)与解密( ...

  2. 深入理解Mysql索引的底层数据结构 B+ Tree (2)

    sql查询 explain的详细用法 操作时间:寻道时间+旋转时间 引入索引:采用二叉树结构 把第二列做为索引生成二叉树结构,此时查询89 只做了两次io操作 但是mysql 为什么不用二叉树作为底层 ...

  3. AngularJS学习之旅—AngularJS 过滤器(七)

    1.AngularJS 过滤器 过滤器可以使用一个管道字符(|)添加到表达式和指令中. AngularJS 过滤器可用于转换数据: 过滤器 描述 currency 格式化数字为货币格式. filter ...

  4. Java文件下载:如何编码文件名称以及如何设置HttpServletResponse

    在下载文件时,经常遇到文件名乱码等问题. 本文说明如何编码文件名,以及如何设置HttpServletResponse对象. 1,如何编码文件名 String userAgent = request.g ...

  5. Thinkphp volist 多重循环原样输出数组key值的使用总结

    最近因为项目的缘故,要使用到volist.在这个过程中,遇到了一些小问题,主要就是volist在循环输出多重数据的时候,如何输出key.网上查阅了不少资料,很失望的是,大多资料就是粘贴复制Thinkp ...

  6. bootstrap,bootstrap-table,bootstrapValidator,animate,layer配合起来搞事情

    资源准备(just download) bootstrap: http://www.bootcss.com/ bootstrap-table: http://bootstrap-table.wenzh ...

  7. eclipse弃坑记第一篇之在idea上配置Tomcat环境并创建Javaweb项目的详细步骤原创

    IntelliJ IDEA是一款功能强大的开发工具,在代码自动提示.重构.J2EE支持.各类版本工具(如git.svn.github).maven等方面都有很好的应用. IntelliJ IDEA有免 ...

  8. 英语进阶系列-A05-英语升级练习三

    古诗背诵 要求:认真背诵和朗读,然后翻译成现代文,并绘制图像描述图中的意向,时间限制到10 minutes.另外,从中找出英文单词,并记录. 例如:慈母 = kind mother,手 = hand, ...

  9. C#深度学习のLINQ

    一.LINQ的由来 LINQ是Language Integrated Query的缩写,意思是语言扩展查询 查询是一种从数据源检索数据的表达式. 查询通常用专门的查询语言来表示. 随着时间的推移,人们 ...

  10. SpringBoot四大神器之auto-configuration

    SpringBoot 自动配置主要通过 @EnableAutoConfiguration, @Conditional, @EnableConfigurationProperties 或者 @Confi ...