我正在为大学作业编写一个 bash 脚本,其中需要对某个目录执行多个操作(作为脚本的参数)。
- 显示具有特定权限的所有文件/目录(权限以八进制格式的参数给出)
- 显示目录树中最近 x 天内修改的文件(x 是一个参数)
- 显示最近 x 天内访问过的树的子目录(x 与上面使用的参数相同)
- 显示目录中所有管道/插座类型文件
- 显示目录中的所有空文件(不在任何子目录中)
在每次操作结束时,脚本还应显示找到的文件(或子目录)的数量。
我正在使用此命令来打印所需的输出(例如操作1):echo "$files_perms" | tee >(echo "Files found: $(wc -l)")
问题是,tee
在第一个和第二个之后的操作中,输出没有以正确的顺序显示。
第一次操作(输出正常):
第二次操作(输出仍然正常):
第三、第四和第五个操作(输出顺序混乱 - 箭头表示tee
每个操作的输出,op3-op5 是每个操作的实际输出):
以下是每个函数的代码:
#display files in the current directory tree with the specified permissions
sub1 () {
files_perms=$(ls $1 -l | grep $2 --color=never)
echo "$files_perms" | tee >(echo "Files found: $(wc -l)")
echo ""
}
#display files in the current directory tree that were modified within the last $2 days (without hidden files)
sub2 () {
files_modlastxdays=$(find $1 -not -path '*/.*' -type f -mtime -$2)
echo "$files_modlastxdays" | tee >(echo "Files found: $(wc -l)")
echo ""
}
#display subdirectories in the current directory tree that were accessed within the last $2 days (without hidden subdirs)
sub3 () {
subdirs_acclastxdays=$(find $1 -not -path '*/.*' -type d -atime -$2)
echo "$subdirs_acclastxdays" | tee >(echo "Subdirectories found: $(wc -l)")
echo ""
}
#display all files that are of pipe/socket type in the current directory tree
sub4 () {
ps_files=$(find $1 \( -type p -o -type s \))
echo "$ps_files" | tee >(echo "Files found: $(wc -l)")
echo ""
}
#display all empty files in current directory (NOT in subdirectories)
sub5 () {
empty_files=$(find $1 -maxdepth 1 -type f -empty)
echo "$empty_files" | tee >(echo "Files found: $(wc -l)")
echo ""
}
函数调用如下:
echo "Files with permission $1 ($rwx_converted):"
sub1 $3 $rwx_converted
echo "Files that were modified within the last $2 days:"
sub2 $3 $2
echo "Subdirectories that were accessed within the last $2 days:"
sub3 $3 $2
echo "Files that are of pipe/socket type:"
sub4 $3
echo "Empty files (NOT in subdirectories):"
sub5 $3
$1
是八进制格式的文件权限参数(rwx_converted
是将八进制格式转换为rwx格式),
$2
是操作 2 和 3 的 x 天参数,
是用于/命令$3
的目录参数。ls
find
脚本执行示例:bash labscript2.sh 755 8 /home/na-no
为什么的输出没有以正确的顺序显示(在每个/命令tee
的末尾和ls
find
不是在一堆行之后)?
答案1
您有多个并发进程同时运行。输出顺序将取决于哪个进程首先写入。
例如,您的第四个似乎tee
已开始写入输出,而第三个wc
仍在处理其输入。
考虑:
#!/bin/bash
echo 1 | tee >(sleep 8; echo 1b) >(sleep 4; echo 1c)
echo 2 | tee >(sleep 2; echo 2b) >(sleep 6; echo 2c)
echo 3 | tee >( echo 3b) >( echo 3c)
echo done
请注意,tee
一旦完成将输入复制到所有输出,就会退出。然而,由 bash 的进程替换启动的进程是异步运行的,并且在(甚至脚本本身)退出>(...)
后可能仍在运行。tee
另请注意,未定义tee
首先写入哪个输出。如果所有输出实际上都是同一个文件,则输出更有可能混合在一起。例如,在我的机器上,tee
上面的第三行输出:
3b
3c
3
ie 似乎是在其他输出之后stdout
写入tee
的,这意味着不能保证您会wc
按照您期望的顺序获得输出。