vesperW · 2024年11月26日

分享一个轻量级的嵌入式线程池库

在嵌入式开发中,多线程编程是提高系统性能和响应速度的重要手段。然而,频繁地创建和销毁线程会带来较大的开销,影响系统的整体性能。为了解决这个问题,我们可以使用线程池技术。

什么是线程池?

线程池(Thread Pool)是一种基于池化技术的多线程处理形式,用于管理线程的创建和生命周期,以及提供一个用于并行执行任务的线程队列。

线程池的主要目的:

  • 线程复用:线程池中的线程可以被重复利用,用于执行多个任务,避免了频繁创建和销毁线程的性能开销。提高响应速度。假如创建线程用的时间为 T1,执行任务用的时间为 T2,销毁线程用的时间为 T3,那么使用线程池就免去了 T1 和 T3 的时间。
  • 资源控制:线程池可以限制系统中线程的最大数量,防止因为线程数过多而消耗过多内存,或者导致过高的上下文切换开销。
  • 更方便的管理:通过线程池提供了可配置的参数,如核心线程数、最大线程数、空闲线程存活时间、任务队列的大小等,允许定制以适应不同的应用需求。

C-Thread-Pool

C-Thread-Pool 是一个轻量级、易用的线程池实现。

image.png

https://github.com/Pithikos/C...
MIT license

特点:

  • 符合 ANSI C 和 POSIX 标准
  • 支持暂停/恢复/等待操作
  • 简单易懂的 API
  • 经过充分测试

C-Thread-Pool 库未预编译,我们需要与项目一起编译。在 Linux 上用 gcc 编译时,需要添加标志 -pthread,如:

gcc example.c thpool.c -D THPOOL_DEBUG -pthread -o example  

基本用法:

1、在源文件中包含头文件:#include "thpool.h"
2、创建一个具有所需线程数的线程池:threadpool thpool = thpool_init(4);
3、向池中添加工作:thpool_add_work(thpool, (void*)function_p, (void*)arg_p);

C-Thread-Pool 应用 API 可查看 thpool.h 文件:

image.png

C-Thread-Pool 并发处理数据的例子:

#include <stdio.h>  
#include <stdlib.h>  
#include <pthread.h>  
#include "thpool.h"  
  
typedef struct   
{  
    int *data;  
    int index;   
    long result;   
} test_data_t;  
  
void task(void *arg)   
{  
    test_data_t *test_data = (test_data_t *)arg;  
    test_data->result = (long)test_data->data[test_data->index] * test_data->data[test_data->index];  
    printf("Thread #%u work, test_data->result = %ld\n", (int)pthread_self(), test_data->result);  
    free(test_data);   
}  
  
int main(int argc, char *argv[])   
{  
    int data[] = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10};  
    int num_elements = sizeof(data) / sizeof(data[0]);  
  
    // 创建一个线程池,包含4个线程  
    threadpool thpool = thpool_init(4);  
  
    // 添加num_elements个任务到线程池  
    for (int i = 0; i < num_elements; i++)   
    {  
        test_data_t *test_data = malloc(sizeof(test_data_t));  
        test_data->data = data;  
        test_data->index = i;  
        thpool_add_work(thpool, task, test_data);  
    }  
  
 thpool_wait(thpool);  
 puts("Killing threadpool");  
 thpool_destroy(thpool);  
  
    return 0;  
}  
`

`THPOOL_DEBUG: Created thread 0 in pool   
THPOOL_DEBUG: Created thread 1 in pool   
THPOOL_DEBUG: Created thread 2 in pool   
THPOOL_DEBUG: Created thread 3 in pool   
Thread #3894134336 work, test_data->result = 1  
Thread #3910919744 work, test_data->result = 9  
Thread #3902527040 work, test_data->result = 16  
Thread #3885741632 work, test_data->result = 4  
Thread #3910919744 work, test_data->result = 25  
Thread #3910919744 work, test_data->result = 64  
Thread #3910919744 work, test_data->result = 100  
Thread #3885741632 work, test_data->result = 81  
Thread #3902527040 work, test_data->result = 36  
Thread #3894134336 work, test_data->result = 49  
Killing threadpool  

在嵌入式系统中,线程池技术可以应用于多种场景,如数据处理、网络通信、传感器数据采集等。

网络服务器

  • 用途:在网络服务器中,使用线程池处理多个客户端的请求。每个客户端的请求可以被视为一个任务,线程池中的线程可以并发地处理这些任务。
  • 优势:使用线程池可以提高服务器的并发处理能力,减少因频繁创建和销毁线程而带来的开销,从而提高服务器的响应速度和整体性能。

数据处理

  • 用途:在数据处理场景中,使用线程池用于并行处理大量数据。例如,对大量数据进行排序、搜索或分析时,可以将数据分成多个小块,每个小块作为一个任务交给线程池处理。
  • 优势:通过并行处理,可以显著缩短数据处理时间,提高数据处理的效率。

数据采集

  • 用途:在实时系统中,使用线程池可以用于处理周期性或突发性的任务。例如,在嵌入式实时操作系统中,可以使用线程池来管理传感器数据的采集和处理任务。
  • 优势:线程池可以提供稳定的响应时间,确保任务在预定的时间内完成,从而满足实时系统的要求。

END

来源:strongerHuang

推荐阅读

欢迎大家点赞留言,更多 Arm 技术文章动态请关注极术社区嵌入式客栈专栏欢迎添加极术小姐姐微信(id:aijishu20)加入技术交流群,请备注研究方向。

推荐阅读
关注数
2896
内容数
304
分享一些在嵌入式应用开发方面的浅见,广交朋友
目录
极术微信服务号
关注极术微信号
实时接收点赞提醒和评论通知
安谋科技学堂公众号
关注安谋科技学堂
实时获取安谋科技及 Arm 教学资源
安谋科技招聘公众号
关注安谋科技招聘
实时获取安谋科技中国职位信息