我想w
周期性地启动命令,按照man watch
最小可能的时间间隔是0.1。
我试过:
watch -n1 w (works)
watch -n1.5 w (does not work)
watch -n0.1 w (does not work)
当我尝试watch
使用 n 选项作为非整数启动命令时,我收到错误消息:
watch: failed to parse argument: '0.1'
答案1
这是一个区域设置问题。watch
使用strtod(3)
与语言环境相关的 来将参数 转换-n
为double
。
要解决此问题,您需要-n
使用不同的分隔符指定参数:
watch -n 0,1 w
或者将您的区域设置更改为使用句点字符作为小数点的设置:
export LC_NUMERIC=en_US.UTF-8
watch -n 0.1 w
一些参考资料:
- Linux 联机帮助页的相关部分
strtod
:
十进制数由非空的十进制数字序列组成,可能包含基数字符(小数点,取决于区域设置,通常为“.”)
locale
您可以通过在终端中运行来查看当前设置:locale LANG=en_US.UTF-8 LC_CTYPE="en_US.UTF-8" LC_NUMERIC="en_US.UTF-8" LC_TIME="en_US.UTF-8" LC_COLLATE="en_US.UTF-8" LC_MONETARY="en_US.UTF-8" ...
有问题的源代码可以在 gitlab 上查看:
https://gitlab.com/procps-ng/procps/blob/85fff468fa263cdd2ff1c0144579527c32333695/watch.c#L625
https://gitlab.com/procps-ng/procps/blob/85fff468fa263cdd2ff1c0144579527c32333695/lib/strutils.c#L49
(编辑2017-09-07):更新了gitlab链接
答案2
只是一个补充扎克斯的好答案。
有两个问题:
LC_NUMERIC=en_US.UTF-8 watch -n 0.1 w
作为一种解决方法,因为您watch
希望数字按照用户约定格式化,而您希望它采用英语格式。
LC_ALL
如果设置了则不起作用。LC_ALL
覆盖所有其他区域设置,包括LC_NUMERIC
.解决方法是使用:LC_ALL=en_US.UTF-8 watch -n 0.1 w
但这样会使下面的第二点变得更糟
watch
由(在本例中w
)启动的命令继承了该命令LC_NUMERIC
。因此,它不会以用户期望的格式输出其数字,而是以美国英语格式输出。
理想情况下,我们希望告诉 watchw
每十分之一秒运行一次(无论用户的区域设置如何),而不影响命令的行为w
(它应该始终给出用户在其自己的区域设置中可以理解的输出)。
使用yash
shell,您可以执行以下操作:
watch -n "$((0.1))" w
yash
是 3 个支持浮点运算的类 Bourne shell 之一(其他的是zsh
和ksh93
)。但它是唯一能够正确进行国际化的一个。zsh
始终用作.
小数点,并ksh93
在其内部语法中遵循区域设置事件中的小数点。
对于yash
,.
是其算术语法的小数点,但它在输入/输出时遵循语言环境的小数点。
您可以在此处使用的另一个技巧是使用科学记数法来避免完全输入小数点:
watch -n 1e-1 w
或者您可以从语言环境中查询小数点:
m=$(locale decimal_point)
watch -n "0${m}1" w
答案3
除了第一个字母相同之外,命令watch
和w
彼此无关。您不能假设 的参数w
对于 同样有效watch
。该watch
命令采用整数秒作为 的值-n
。
顺便说一句,我也看过手册页w
我看不到任何对时间段的提及。我很想知道您从哪里获得此信息,以便我可以(希望)进一步解释。
更新
看来您实际上指的是计时器 for watch
,而不是 for w
。我将更新您的问题以匹配此新披露。终于发现了这一点,我看不出有什么问题watch -n 0.1 w
。