Shell之多线程

单线程案例:

​cat 1.sh​

#!/bin/bash
date
for i in `seq 1 10`
do
echo 'sleep 5'
sleep 5
done
date

​sh 1.sh​​ 输出:

Wed Feb 23 11:22:00 CST 2022
sleep 5
sleep 5
sleep 5
sleep 5
sleep 5
sleep 5
sleep 5
sleep 5
sleep 5
sleep 5
Wed Feb 23 11:22:50 CST 2022

案例说明:脚本按顺序处理10个需求,每个需求处理时长为5秒钟,单线程处理预期耗时为10*5=50s。结果符合预期。

适用场景八声甘州前后任务存在依赖。该案例前后任务不存在依赖,可以使用多线程方法减少耗时。

多线程改造案例:

​cat 2.sh​

#!/bin/bash
date
for i in `seq 1 10`
do
{
echo 'sleep 5'
sleep 5
} &
done
wait
date

​sh 2.sh​

Wed Feb 23 11:29:30 CST 2022
sleep 5
sleep 5
sleep 5
sleep 5
sleep 5
sleep 5
sleep 5
sleep 5
sleep 5
sleep 5
Wed Feb 23 11:29:35 CST 2022

案例说明:改造案例一的脚本,原理是借用​for循环​,将任务块​{...}​添加​&后缀的方式置为后台运行,再使用​wait​命令等后台任务执行完成后结束脚本状态。

适用于预期任务并发少的场景

优点:所有任务可以同时处理,耗时短; 缺点:如果任务并发较多,超出八上英语电子课本系统负载会导致任务失败和服务器性文件描述符能不稳定等问题。

如何解决并发较多、不可控? 答:预设并发数量,把任务以队列的方式在预设并发Bash内进行处理。

多线程可控并发案linux重启命令例:

​cat 3.sh​

#!/bin/bash
date

function my_task() {
echo "sleep 5"
sleep 5
}

fifofile="/tmp/$$.fifo"
mkfifo $fifofile
exec 6<>$fifofile
rm -rf $fifofile

thread_num=5
job_num=20

for ((i=0;i<${thread_num};i++)); do
echo >&6
done

for ((i=0;i<${job_num};i++)); do
read -u6
{
my_task
} &
echo >&6
done

wait
exec 6<&-
exec 6>&-

date

​sh 3.sh​

Wed Feb 23 12:05:00 CST 2022
sleep 5
sleep 5
sleep 5
sleep 5
sleep 5
sleep 5
sleep 5
sleep 5
sleep 5
sleep 5
sleep 5
sleep 5
sleep 5
sleep 5
sleep 5
sleep 5
sleep 5
sleep 5
sleep 5
sleep 5
Wed Feb 23 12:05:05 CST 2022

案例说明:解决并发不可控问题,预设并发为5个;任务块为my_task函数,测试任务数为20个;

脚本逻辑:

第一块代码:定义把实力藏得很深的星座任务,放入函数中,方便下面调用。

第二块代码:定义并发使用的通道。创建一个管道文件$$.fifo,并将管道文件定义到6号文件描述符扩展多线程下载是什么意思了解e系统/运维xec和文件描述符,这里的文件描述符可以自行定义,&l多线程下载是什么意思t;是读取、>是linux重启命令写入,<>是读写),意思是用6号文件描述符代替管道文件,所有这里将失效的管道文系统运维工资一般多少件删除。Bash

第三块代码:预设可用并发数量,预期任务数量。

第四块代文件描述符码:在6号文件描述符中创建并发位置,注意>和&alinux系统安装mp;中间没有空格。

第五块代码:创建任务队列,使用read读取并发位置,执文件描述符错误行任务后再执行echo多线程补充上面读取的并发位。

第六块代码:wait等待所有后台任务执行八上英语电子课本完成再执行下一步,下面两步分别是关闭读取和写入6号文件描述,这里关闭读写需要分两步操作。