我只是在寻找一种简单的方法来除法(或提供其他数学函数)。假设我有以下命令:
find . -name '*.mp4' | wc -l
如何将 wc -l 的结果除以 3?
我见过的例子不涉及重定向出/入。
使用
bc
:
$ bc -l <<< "scale=2;$(find . -name '*.mp4' | wc -l)/3"
2.33
相比之下,bash shell 只执行整数运算。
awk也很强大:
$ find . -name '*.mp4' | wc -l | awk '{print $1/3}'
2.33333
如果使用
wc
,你甚至不需要awk
:
$ find . -name '*.mp4' | awk 'END {print NR/3}'
2.33333
编辑2018-02-22:添加
shell connector
取决于所需的精度和要完成的计算数量!进一步查看
shell connector
!
bc
(二进制计算器)find . -type f -name '*.mp4' -printf \\n | wc -l | xargs printf "%d/3\n" | bc -l
6243.33333333333333333333
或
echo $(find . -name '*.mp4' -printf \\n | wc -l)/3|bc -l
6243.33333333333333333333
使用 bash,仅得出整数:
echo $(($(find . -name '*.mp4' -printf \\n| wc -l)/3))
6243
通过移位数字实现伪浮点(乘以 100 并在距末尾 2 位数字处放置一个基点):
res=000$((($(find . -type f -name '*.mp4' -printf "1+")0)*1000/3))
printf -v res "%.2f" ${res:0:${#res}-3}.${res:${#res}-3}
echo $res
6243.33
纯粹@glennjackman的想法使用globstar
,然后计算伪浮动可以通过以下方式完成:
shopt -s globstar
shopt -s nullglob
files=(**/*.mp4)
shopt -u globstar
res=000$(( ${#files[*]}000 / 3 ))
printf -v res "%.2f" ${res:0:${#res}-3}.${res:${#res}-3}
echo $res
6243.33
没有分叉,并且 $res
包含两位数四舍五入的浮动值。
注意:使用globstar
和**
时请注意符号链接
!介绍
shell connector
bash,你可以使用长时间运行bc
子进程:
mkfifo /tmp/mybcfifo
exec 5> >(exec bc -l >/tmp/mybcfifo)
exec 6</tmp/mybcfifo
rm /tmp/mybcfifo
然后现在:
echo >&5 '12/34'
read -u 6 result
echo $result
.35294117647058823529
此子流程保持打开和可用状态:
ps --sid $(ps ho sid $$) fw
PID TTY STAT TIME COMMAND
18027 pts/9 Ss 0:00 bash
18258 pts/9 S 0:00 \_ bc -l
18789 pts/9 R+ 0:00 \_ ps --sid 18027 fw
计算$PI
:
echo >&5 '4*a(1)'
read -u 6 PI
echo $PI
3.14159265358979323844
终止子进程:
exec 6<&-
exec 5>&-
小演示,关于 {1..157} / 42
(我会让你谷歌搜索
answer to the ultimate question of life, the universe, and everything
;)
...并按行打印 13 个结果以减少输出:
printf -v form "%s" "%5.3f "{,}{,}{,,};form+="%5.3f\n";
按常规方式
testBc(){
for ((i=1; i<157; i++)) ;do
echo $(bc -l <<<"$i/42");
done
}
通过使用长时间运行bc
子流程:
testLongBc(){
mkfifo /tmp/mybcfifo;
exec 5> >(exec bc -l >/tmp/mybcfifo);
exec 6< /tmp/mybcfifo;
rm /tmp/mybcfifo;
for ((i=1; i<157; i++)) ;do
echo "$i/42" 1>&5;
read -u 6 result;
echo $result;
done;
exec 6>&-;
exec 5>&-
}
让我们看看没有:
time printf "$form" $(testBc)
0.024 0.048 0.071 0.095 0.119 0.143 0.167 0.190 0.214 0.238 0.262 0.286 0.310
0.333 0.357 0.381 0.405 0.429 0.452 0.476 0.500 0.524 0.548 0.571 0.595 0.619
0.643 0.667 0.690 0.714 0.738 0.762 0.786 0.810 0.833 0.857 0.881 0.905 0.929
0.952 0.976 1.000 1.024 1.048 1.071 1.095 1.119 1.143 1.167 1.190 1.214 1.238
1.262 1.286 1.310 1.333 1.357 1.381 1.405 1.429 1.452 1.476 1.500 1.524 1.548
1.571 1.595 1.619 1.643 1.667 1.690 1.714 1.738 1.762 1.786 1.810 1.833 1.857
1.881 1.905 1.929 1.952 1.976 2.000 2.024 2.048 2.071 2.095 2.119 2.143 2.167
2.190 2.214 2.238 2.262 2.286 2.310 2.333 2.357 2.381 2.405 2.429 2.452 2.476
2.500 2.524 2.548 2.571 2.595 2.619 2.643 2.667 2.690 2.714 2.738 2.762 2.786
2.810 2.833 2.857 2.881 2.905 2.929 2.952 2.976 3.000 3.024 3.048 3.071 3.095
3.119 3.143 3.167 3.190 3.214 3.238 3.262 3.286 3.310 3.333 3.357 3.381 3.405
3.429 3.452 3.476 3.500 3.524 3.548 3.571 3.595 3.619 3.643 3.667 3.690 3.714
real 0m10.113s
user 0m0.900s
sys 0m1.290s
哇! 十秒在我的树莓派上!!
然后与:
time printf "$form" $(testLongBc)
0.024 0.048 0.071 0.095 0.119 0.143 0.167 0.190 0.214 0.238 0.262 0.286 0.310
0.333 0.357 0.381 0.405 0.429 0.452 0.476 0.500 0.524 0.548 0.571 0.595 0.619
0.643 0.667 0.690 0.714 0.738 0.762 0.786 0.810 0.833 0.857 0.881 0.905 0.929
0.952 0.976 1.000 1.024 1.048 1.071 1.095 1.119 1.143 1.167 1.190 1.214 1.238
1.262 1.286 1.310 1.333 1.357 1.381 1.405 1.429 1.452 1.476 1.500 1.524 1.548
1.571 1.595 1.619 1.643 1.667 1.690 1.714 1.738 1.762 1.786 1.810 1.833 1.857
1.881 1.905 1.929 1.952 1.976 2.000 2.024 2.048 2.071 2.095 2.119 2.143 2.167
2.190 2.214 2.238 2.262 2.286 2.310 2.333 2.357 2.381 2.405 2.429 2.452 2.476
2.500 2.524 2.548 2.571 2.595 2.619 2.643 2.667 2.690 2.714 2.738 2.762 2.786
2.810 2.833 2.857 2.881 2.905 2.929 2.952 2.976 3.000 3.024 3.048 3.071 3.095
3.119 3.143 3.167 3.190 3.214 3.238 3.262 3.286 3.310 3.333 3.357 3.381 3.405
3.429 3.452 3.476 3.500 3.524 3.548 3.571 3.595 3.619 3.643 3.667 3.690 3.714
real 0m0.670s
user 0m0.190s
sys 0m0.070s
不到一秒!!
希望结果是相同的,但执行时间却截然不同!我的
shell connector
Connector-bash 和 shell_connector.sh 在我自己的网站上。
source shell_connector.sh
newConnector /usr/bin/bc -l 0 0
myBc 1764/42 result
echo $result
42.00000000000000000000
find . -name '*.mp4' | wc -l | xargs -I{} expr {} / 2
xargs
。使用
{}
作为表达式术语的占位符。
shopt -s nullglob globstar
files=( **/*.mp4 )
dc -e "3 k ${#files[@]} 3 / p"
此方法将正确处理包含换行符的文件名的奇怪边缘情况。