`
zsxxsz
  • 浏览: 446106 次
  • 性别: Icon_minigender_1
  • 来自: 北京
社区版块
存档分类
最新评论

线程编程常见API简介(上)

阅读更多

 

一、概述

      本文主要讲述了 Posix 标准的常用线程 API 接口的使用,目前 Linux/Unix 均提供了遵循 Posix 标准的线程编程 API,微软提供了自己的一套接口,acl  线程模块库根据 Posix 标准,提供了跨平台(支持 LINUX/WIN32)的线程库,接口定义及参数含义均与 Posix 的相同。如果您对 Linux 下的线程 API 比较熟悉,则当需要移植您的程序至 WIN32 平台时,只要需要在所用线程 API 前加前缀 acl_,同时将 acl 的 lib_acl.a 及相应头文件集成到您的程序中,即可将 LINUX 下线程程序移植至 WIN32 平台。

 

二、常用API 介绍

1)创建线程 API:pthread_create,在 acl 库中的表现形式:acl_pthread_create

/**
 * 创建独立的线程,使处理任务在该线程中运行,线程运行完毕,该线程的创建者
 * 可以接收该线程的退出返回值
 * @param tid {pthread_t*} 当线程创建成功时,该变量所指内存区域存储线程
 *    的线程 ID 号
 * @param attr{pthread_attr_t*} 创建线程的属性,该属性里可以设定线程的
 *    堆栈大小、是否与创建线程分离等
 * @param start_routine {void *(*)(void*)} 线程成功创建后开始运行的函数指针,
 *    该函数指针是用户应用的功能函数入口,函数的参数也由用户指定
 * @param arg {void*} start 函数运行时传入的参数,该参数由用户设定
 * @return {int} 线程创建是否成功,返回 0 表示成功,否则表示失败
 *
 */
int pthread_create(pthread_t* tid, pthread_attr_t* attr, void *(*start)(void*), void *arg); 

      该 API 中有两个参数类型:pthread_t 和 pthread_attr_t,其中的创建线程属性的类型 pthread_attr_t 一般由下面 API 来初始化。

2)初始化/销毁线程属性 API:pthread_attr_init/pthread_attr_destroy,在 acl 库中的对应形式:acl_pthread_attr_init/acl_pthread_attr_destroy

/**
 * 初始化创建线程时的属性对象,该 API 会赋一些缺省值给属性对象,用户若想
 * 改变属性中的某个缺省值,可以通过 pthread_attr_setxxx 之类的 API 设定
 * @param attr {pthread_attr_t*} 线程属性对象的指针,该指针指向的空间
 *    必须由用户自己分配
 * @return {int} 成功则返回 0,否则返回非 0 值
 */
int pthread_attr_init(pthread_attr_t *attr);

/**
 * 销毁由 pthread_attr_init 创建的一些线程属性资源
 * @param attr {pthread_attr_t*} 线程属性对象指针
 * @return {int} 成功则返回 0,否则返回非 0 值
 */
int pthread_attr_destroy(pthread_attr_t *attr);

      在调用 pthread_attr_init 时,内部会对线程属性对象创建一些临时内存资源,所以当不需要线程属性时,需要调用 pthread_attr_destroy 来释放之。

      下面的两个 API 可以设定创建时的一些特殊属性:

3)设定创建线程为分离状态:int pthread_attr_setdetachstate(pthread_attr_t *attr, int detached),在 acl 库中的表现形式:int acl_pthread_attr_setdetachstate(acl_pthread_attr_t *attr, int detached);

/**
 * 设定所创建线程是否处于分离模式,当父线程创建一个子线程时指定了所创建
 * 子线程为可分离模式,则父线程不必接管子线程的退出状态,否则父线程必须
 * 调用 pthread_join 来接管子线程的退出状态以避免资源泄露
 * @param attr {pthread_attr_t*} 线程属性对象
 * @param detached {int} 非 0 表示采用线程分离模式
 * @return {int} 返回 0 表示成功,否则表示出错
 */
int pthread_attr_setdetachstate(pthread_attr_t *attr, int detached);

 4)设定线程创建时线程堆栈大小属性:int pthread_attr_setstacksize(pthread_attr_t *attr, size_t stacksize),在 acl 库中的表现形式:int acl_pthread_attr_setstacksize(acl_pthread_attr_t *attr, size_t stacksize)。

/**
 * 该函数设定所创建线程的堆栈大小
 * @param attr {pthread_attr_t*} 线程属性对象
 * @param stacksize {size_t} 新创建线程的堆栈大小(单位为字节,
 *    在LINUX 下默认堆栈一般是 2MB)
 * @return {int} 返回 0 表示成功
 */
int pthread_attr_setstacksize(pthread_attr_t *attr, size_t stacksize);

 5)当创建的子线程为非分离状态时父线程接管子线程退出状态:int pthread_join(pthread_t thread, void **thread_return) ,在 acl 库中的表现形式为:int acl_pthread_join(acl_pthread_t thread, void **thread_return)。

/**
 * 当所创建的子线程采用非分离方式创建时,则父线程应该调用本 API
 * 来接管子线程的退出状态,否则会造成资源泄露
 * @param thread {pthread_t} 子线程的线程号
 * @param thread_return {void**} 该指针地址指向子线程退出
 *   前返回的内存地址
 * @return {int} 返回 0 表示成功,否则表示失败
 */
int pthread_join(pthread_t thread, void **thread_return);

       在创建线程前通过 pthread_attr_setdetachstate API 给线程属性设定了将要创建的子线程为分离状态,还有另外一个 API 可以当子线程创建后再指定子线程为分离状态:

 6)子线程创建成功后设定子线程的分离状态:int pthread_detach(pthread_t thread),在 acl 库中的表现形式为:int acl_pthread_detach(acl_pthread_t thread)。

/**
 * 子线程创建成功后调用本函数设定子线程为分离模式,调用本函数后,
 * 父线程禁止再调用 pthread_join 接管子线程的退出状态
 * @param thread {pthread_t} 所创建的子线程的线程号
 * @return {int} 返回 0 表示成功,否则表示失败
 */
int pthread_detach(pthread_t thread);

 7)线程中获得自身的线程 ID 号:pthread_t pthread_self(void),在 acl 库中的表现形式为:unsinged long acl_pthread_self(void)。

/**
 * 返回当前线程的线程号
 * @return {pthread_t}
 */
pthread_t pthread_self(void);

 

      以上介绍了有关 Posix 标准线程的一些常用 API,下面举一个简单的例子来说明上面 API 的使用。  

三、例子

 

#include <pthread.h>
#include <stdlib.h>
#include <stdio.h>
#include <errno.h>
#include <string.h>

static void *mythread_main(void *arg)
{
	char *ptr = (char*) arg;

	printf("my thread id: %ld\r\n", pthread_self());
	printf("arg: %s\r\n", ptr);
	free(ptr);  /* 释放在父线程中分配的内存 */

	ptr = strdup("thread exit ok");
	return ptr;
}

int main(void)
{
	char *name = strdup("thread_test");
	pthread_t tid;
	pthread_attr_t attr;

	/* 初始化线程属性对象 */
	if (pthread_attr_init(&attr) != 0) {  /* 此处出错应该是内存资源不够所至 */
		printf("pthread_attr_init error: %s\r\n", strerror(errno));
		return 1;
	}

	/* 设定子线程的堆栈空间为 4MB */
	if (pthread_attr_setstacksize(&attr, 4096000) != 0) {
		printf("pthread_attr_setstacksize error: %s\r\n", strerror(errno));
		pthread_attr_destroy(&attr);  /* 必须释放线程属性资源 */
		return 1;
	}

	/* 创建子线程 */
	if (pthread_create(&tid, mythread_main, name) != 0) {
		printf("pthread_create error: %s\r\n", strerror(errno));
		pthread_attr_destroy(&attr);  /* 必须释放线程属性资源 */
		return 1;
	}
	printf("ok, create thread id: %ld\r\n", tid);

	/* 接管子线程的退出状态 */
	if (pthread_join(&tid, &ptr) != 0) {
		printf("pthread_join error: %s\r\n", strerror(errno));
		pthread_attr_destroy(&attr);  /* 必须释放线程属性资源 */
		return 1;
	}

	printf("child thread exit: %s\r\n", ptr);
	free(ptr);  /* 释放在子线程分配的内存 */

	pthread_attr_destroy(&attr);  /* 释放线程属性资源 */
	return 0;
}

      上述例子中,只需把 pthread_ 前添加前缀 acl_,同时包含头文件 #include "lib_acl.h",该例子便可以在 WIN32 平台下运行了。

      本节暂且说这一些有关线程编程时用到的 API,下一节继续。

本文地址

acl 库下载:https://sourceforge.net/projects/acl/

github: https://github.com/acl-dev/acl

个人微博:http://weibo.com/zsxxsz

2
0
分享到:
评论

相关推荐

    浅谈Linux下的多线程编程.pdf

    在Linux操作系统中,多线程编程是一种常见且重要的编程模型,它允许多个执行流(线程)在一个进程中同时运行,以提高程序的并发性和资源利用率。多线程在系统开发中扮演着关键角色,特别是在需要高性能计算、实时...

    linux下多线程编程

    在Linux系统中,多线程编程是一种常见的编程技术,它允许多个执行流在同一进程中并发运行,从而提高程序的响应速度、充分利用多核处理器资源,以及优化程序结构。本篇文章将详细探讨Linux环境下多线程编程的核心概念...

    浅谈.doclinux.doc多线程编程和.docwindows.doc多线程编程的异同.doc

    本文将对比Linux和Windows平台上的多线程编程,探讨它们的异同点。 首先,多线程编程的核心优势在于资源共享、通信效率和并行执行。在Linux和Windows系统中,多线程共享同一地址空间,减少了进程间通信(IPC)的...

    linux 多线程编程

    在Linux系统中,多线程编程是一种常见的并发执行方式,它允许多个任务在单个进程中同时运行。这使得程序能够充分利用多核处理器的计算能力,提高系统的效率和响应速度。以下是对多线程编程的一些关键知识点的详细...

    多线程编程指南PDF

    2 基本线程编程.............................................................................................................................................23 线程库.......................................

    1C#多线程编程实例[收集].pdf

    本文将深入探讨C#中的多线程编程,特别是如何利用Socket进行网络通信。C#语言是由微软公司推出的,旨在结合C++的强健性和VB的快速应用开发(RAD)特性,同时也为了应对Java的挑战。在网络编程方面,C#提供了丰富的...

    实用MFC多线程编程基础.pdf

    本文将探讨MFC(Microsoft Foundation Classes)库中的多线程编程基础,基于问题提出、多线程概述以及Win32 API对多线程的支持。 首先,问题的提出源于一个简单的单线程程序示例。当程序中有一个耗时的操作,如在...

    Windows多线程编程入门讲解.pdf

    在Windows操作系统中,多线程编程是一种常见的技术,允许在一个进程中同时执行多个代码段,从而提升应用程序的效率和响应性。本文将详细讲解Windows多线程编程的基本概念、API使用以及线程同步策略。 首先,线程是...

    VC中多线程编程的方法

    在软件开发中,多线程编程是一种常见的技术,特别是在需要并发执行任务或者优化程序响应能力时。在VC(Visual C++)环境中,我们可以利用API函数或MFC(Microsoft Foundation Classes)库来实现多线程。本文将详细...

    linux的多线程编程的高效开发经验.pdf

    Linux的多线程编程主要依赖于POSIX线程库(Pthread),该库提供了一套丰富的API来创建、管理和同步线程。以下是从给定文件中总结的五个关键知识点,旨在帮助开发者更高效地进行多线程编程并避免潜在的问题。 1. **...

    多线程编程指南(系统描述了线程标准 线程同步 多线程编程原则 等)

    2 基本线程编程23 线程库................................................................................................................................................. 23 创建缺省线程...................

    linux的多线程编程的高效开发经验借鉴.pdf

    竞态条件是多线程编程中常见的问题,当多个线程访问共享资源时,如果没有适当的同步,可能会导致不可预知的结果。使用互斥锁、条件变量或信号量来保护共享资源,防止竞态条件的发生。 5. **理解条件变量的使用**:...

    线程 JAVA java线程 java线程第3版 java线程第2版第3版合集

    用线程编程是技巧性很强的且不可移植。 而在Java中却完全不同。Java的线程工具易于使用,并且像Java中的其他东西一样可以在不同的平台之间移植。这是一件好事,因为如果没有线程,那么除了最简单的applet之外,几乎...

    linux的多线程编程的高效开发经验[归类].pdf

    Linux的多线程编程是开发高效并发应用的关键技术之一,特别是在服务器端软件和高性能计算领域。Pthread库作为Linux上最常用的多线程API,提供了丰富的接口来处理线程、互斥锁和条件变量等核心概念。以下是对Pthread...

    多线程API.zip

    常见的多线程API和用法 pthread_self函数 pthread_create函数 pthread_exit函数 pthread_join函数 pthread_detach函数 pthread_equal函数

    Java中的多线程是如何实现的以及常见问题汇总

    Java提供了一套丰富的API来支持多线程编程,使得开发者可以轻松地创建和管理线程。以下是关于Java多线程实现的详细介绍。多线程是指一个程序中可以同时运行多个线程(Thread),每个线程可以看作是程序执行的独立...

    java 多线程设计模式 进程详解

    第五章 Java线程编程的例子 数据结构和容器 简单的同步例子 一个网络服务器类 AsyncInputStream类 使用TCPServer和AsynclnputStream 总结 第六章 Java线程调度 线程调度概述 何时调度是重要的 调度和线程优先级 ...

    Unix编程常见问题解答

    - 多线程编程在Unix环境中也很常见,线程是共享同一地址空间的轻量级进程。线程库如POSIX threads(pthread)提供了创建、同步和管理线程的接口。 6. **权限和安全**: - Unix系统的权限模型包括用户ID、组ID以及...

    显卡的性能与api关系

    OpenGL是另一个重要的图形API,与DirectX并行发展,尤其在专业图形和跨平台应用中更为常见。OpenGL提供了一套开放的、标准化的接口,允许开发者编写能在多种操作系统和硬件上运行的3D图形程序。 总之,显卡的性能...

Global site tag (gtag.js) - Google Analytics