shell腳本中的多線程
很多場景中會用到多線程,例如備份資料庫,有100個庫,正常備份效率極其低下。有了多線程原本可能需要10個小時備份,現在分10個線程同時去幹,隻要一個小時就解決了。今天就介紹下shell中如何使用多線程去完成一些操作,提高我們的效率。
首先我們需要了解以下一些知識點:
1、檔案描述符
[root@localhost ~]# touch file1 #先建立一個檔案
[root@localhost ~]# exec 6<> file1 #通過exec的方式向目前程序号中丢入一個檔案描述符6,關聯檔案為file1
[root@localhost ~]# ll /proc/$$/fd #檢視目前程序号的檔案描述符
total 0
lrwx------ 1 root root 64 Jun 19 13:38 0 -> /dev/pts/0
lrwx------ 1 root root 64 Jun 19 13:38 1 -> /dev/pts/0
lrwx------ 1 root root 64 Jun 19 13:38 2 -> /dev/pts/0
lrwx------ 1 root root 64 Jun 19 13:39 255 -> /dev/pts/0
lrwx------ 1 root root 64 Jun 19 13:38 6 -> /root/file1 #我們丢進來的檔案描述符,關聯着file1檔案
[root@localhost ~]# echo "this is test file" >/proc/$$/fd/6 #向目前程序号的檔案描述符6中寫入一段内容
[root@localhost ~]# cat file1 #檢視file1檔案,發現與我們剛寫入檔案描述符中的内容一緻
this is test file
===================================================================================
[root@localhost ~]# rm -rf file1 #删除檔案file1
[root@localhost ~]# ll /proc/$$/fd/6 #檢視目前程序号中檔案描述符6的狀态,不難看出對應file1檔案的狀态問deleted
lrwx------ 1 root root 64 Jun 19 13:38 /proc/14530/fd/6 -> /root/file1 (deleted)
[root@localhost ~]# cp /proc/$$/fd/6 file1 #拷貝檔案描述符6為file1
[root@localhost ~]# cat file1 #檢視file1檔案,内容與删除一樣,未變。有一點,這個複原的file1檔案不再是原來的了,因為檔案描述符狀态依舊為deleted
[root@localhost ~]# exec 6<&- #釋放檔案描述符
==================================================================================
2、命名管道
[root@localhost ~]# ls *.txt | grep test # | 為我們的匿名管道
test2.txt
test.txt
[root@localhost ~]# mkfifo file-fifo #建立一個命名管道檔案file-fifo
[root@localhost ~]# file file-fifo #檢視檔案類型為name pipe,指令管道檔案,它的特點是1、即拿即用,用完就消失 2、先進先出
file-fifo: fifo (named pipe)
==============================================================================
#起兩個終端測試一下
#終端一
[root@localhost ~]# grep "vd" file-fifo
#終端二
[root@localhost ~]# ls /dev/ > file-fifo
操作完終端二後你會發現終端一馬上就會有結果顯示,但是你再次grep "vd"的時候則沒有任何結果,這就是命名管道檔案的特點,即拿即用,用完消失。
看完上面兩個知識點,就進入到我們腳本的正題,如何實作多線程。
#!/bin/bash
##################
#多線程批量建立使用者
#dingxiang
##################
#定義20個線程,以及fifo檔案名稱
thread=20
file=$(pwd)/file_thread
#建立fifo檔案,丢個檔案描述符6進去,把fifo檔案删掉
mkfifo $file
exec 6<> $file
rm -rf $file
#向檔案描述符6中寫入20個空行
for i in `seq $thread`
do
echo >&6
done
#建立alice1-alice500個使用者
for j in `seq 500`
do
#read -u 讀檔案描述符6
read -u 6
#建立使用者,因為每次拿20個空行,是以建立完之後再還20個空行回去
{
useradd alice$j
echo "123123" | passwd --stdin alice$j &>/dev/null
echo "alice$j creat....."
echo >&6
}&
done
#等待上面所有的操作結束
wait
#釋放檔案描述符,echo;all is ok
exec 6>&-
echo "all is ok......."