我怎么能产生0-60之间的sh(/ bin / sh,而不是bash)的随机数? 这是一个卫星箱,没有$RANDOM
variables,和其他货物[cksum,od(od -vAn -N4 -tu4 </ dev / urandom)]。
我想随机化一个crontab作业的时间。
如果你有tr,head和/ dev / urandom,你可以这样写:
tr -cd 0-9 </dev/urandom | head -c 3
那么你必须使用余数运算符来放置0-60的范围。
如何使用系统时间的纳秒?
date +%N
这不像你需要密码有用的数字在这里。
根据/bin/sh
版本,你可以做:
$(( date +%N
%60))
如果它不支持$(())
语法,但你有dc,你可以尝试:
dc -e `date +%N`' 60 % p'
在不知道哪个操作系统, /bin/sh
版本或者哪些工具可用的情况下,很难想出一个可以保证工作的解决方案。
你有awk吗? 你可以调用awk的rand()函数。 例如:
awk 'BEGIN { printf("%d\n",rand()*60) }' < /dev/null
我知道这个帖子是旧的,但建议的答案是不会产生统一的无偏倚随机数字。 接受的答案基本上是这样的:
% echo $(( $(tr -cd 0-9 </dev/urandom | head -c 3) % 60))
这个建议的问题是,通过从/dev/urandom
选择一个3位数字,范围是0-999,总共有1,000个数字。 但是,千分之六十不均匀。 因此,你会偏向产生0-959略超过960-999。
第二个答案,虽然创造性地使用你的时钟纳秒,但也有同样的偏见:
% echo $(( $(date +%N) % 60 ))
纳秒的范围是0-999,999,999,即10亿个数字。 所以,如果你把这个结果除以60,那么你将再次偏向产生0-999,999,959,略多于999,999,960-999,999,999。
所有其他的答案是相同的偏见不均匀的一代。
要生成0-59范围内的无偏差统一随机数(我假设他的意思是不是0-60,如果他试图随机化一个crontab(1)
条目),我们需要强制输出为60。
首先,我们将生成一个介于0和4294967295之间的随机32位数字:
% RNUM=$(od -An -N4 -tu2 /dev/urandom | awk '{print $1}')
现在我们将强制我们的范围在$ MIN和4294967295之间,是60的倍数:
% MIN=$((2**32 % 60)) # 16
意即:
4294967296 - 16 = 4294967280 4294967280 / 60 = 71582788.0
换句话说,我的范围[16,4294967295]恰好是60的倍数。所以,我在该范围内生成的每个数字,然后除以60,将与其他数字相同。 因此,我有一个没有偏见的数字0-59(或1-60,如果你加1)发电机。
唯一要做的就是确保我的号码在16到4294967295之间。如果我的号码小于16,那么我需要生成一个新号码:
% while [ $RNUM -lt $MIN ]; do RNUM=$(od -An -N1 -tu2 /dev/urandom); done % MINUTE=$(($RNUM % 60))
所有东西放在一起复制/粘贴goodnees:
#!/bin/bash RNUM=$(od -An -N4 -tu2 /dev/urandom | awk '{print $1}') MIN=$((2**32 % 60)) while [ $RNUM -lt $MIN ]; do RNUM=$(od -An -N1 -tu2 /dev/urandom); done MINUTE=$(($RNUM % 60))
value =`od -An -N2 -tu2 / dev / urandom` 分钟=`expr $ value%60`
种子将在0和65535之间,这不是60的偶数倍,所以0-15分钟的机会被选择的几率更大,但差异可能并不重要。
如果要实现完美,请使用“od -An -N1 -tu1”并循环,直到值小于240。
用busybox测试。
马可的答案将失败,只要生成的数字开始0,并有其他数字大于7,因为它被解释为八进制,我会建议:
tr -cd 0-9 </dev/urandom | head -c 4 | sed -e 's/^00*//
特别是如果你想进一步处理它,例如建立一个范围:
RANDOM=`tr -cd 0-9 </dev/urandom | head -c 4 | sed -e 's/^00*//'` RND50=$((($RANDOM%50)+1)) // random number between 1 and 50