bash 有没有办法在shell中找到最后执行的命令的运行时间?
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/2704635/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Is there a way to find the running time of the last executed command in the shell?
提问by Behrang Saeedzadeh
Is there a command like timethat can display the running time details of the last or past executed commands on the shell?
是否有这样的命令time可以在 shell 上显示上次或过去执行的命令的运行时间详细信息?
采纳答案by ZyX
I do not know, how it is in bash, but in zsh you can define preexecand precmdfunctions so that they save the current time to variables $STARTTIME(preexec) and $ENDTIME(precmd) so you will be able to find the approximate running time. Or you can define an accept-linefunction so that it will prepend timebefore each command.
我不知道它在 bash 中如何,但是在 zsh 中,您可以定义preexec和precmd函数,以便它们将当前时间保存到变量$STARTTIME(preexec) 和$ENDTIME(precmd) 中,这样您就可以找到大致的运行时间。或者您可以定义一个accept-line函数,以便time在每个命令之前添加它。
UPDATE:
This is the code, which will store elapsed times in the $_elapsedarray:
更新:这是代码,它将在$_elapsed数组中存储经过的时间:
preexec () {
(( $#_elapsed > 1000 )) && set -A _elapsed $_elapsed[-1000,-1]
typeset -ig _start=SECONDS
}
precmd() { set -A _elapsed $_elapsed $(( SECONDS-_start )) }
Then if you run sleep 10s:
然后如果你运行sleep 10s:
% set -A _elapsed # Clear the times
% sleep 10s
% sleep 2s ; echo $_elapsed[-1]
10
% echo $_elapsed
0 10 0
No need in four variables. No problems with names or additional delays. Just note that $_elapsedarray may grow very big, so you need to delete the first items (this is done with the following piece of code: (( $#_elapsed > 1000 )) && set -A _elapsed $_elapsed[-1000,-1]).
不需要在四个变量中。名称或额外延迟没有问题。请注意,$_elapsed数组可能会变得非常大,因此您需要删除第一项(这是通过以下代码完成的:)(( $#_elapsed > 1000 )) && set -A _elapsed $_elapsed[-1000,-1]。
UPDATE2:
Found the script to support zsh-style precmd and preexec in bash. Maybe you will need to remove typeset -ig(I used just to force $_startto be integer) and replace set -A var ...with var=( ... )in order to get this working. And I do not know how to slice arrays and get their length in bash.
UPDATE2:在 bash 中找到了支持 zsh 风格的 precmd 和 preexec 的脚本。也许您需要删除typeset -ig(我曾经只是强制$_start为整数)并替换set -A var ...为var=( ... )以使其正常工作。而且我不知道如何切片数组并在 bash 中获取它们的长度。
Script: http://www.twistedmatrix.com/users/glyph/preexec.bash.txt
脚本:http: //www.twistedmatrix.com/users/glyph/preexec.bash.txt
UPDATE3:
Found one problem: if you hit return with an empty line preexec does not run, while precmd does, so you will get meaningless values in $_elapsedarray. In order to fix this replace the precmdfunction with the following code:
UPDATE3:发现一个问题:如果你用空行点击返回,preexec 不会运行,而 precmd 会运行,所以你会在$_elapsed数组中得到无意义的值。为了解决此问题precmd,请使用以下代码替换该函数:
precmd () {
(( _start >= 0 )) && set -A _elapsed $_elapsed $(( SECONDS-_start ))
_start=-1
}
回答by Paused until further notice.
Edit 3:
编辑3:
The structure of this answer:
这个答案的结构:
- There is no ready-made way to time a command that has already been run
- There are ways that you can deduce a guesstimate of the duration of a command's run time.
- A proof of concept is shown (starting with the hypothesis that it can't be done and ending with the conclusion that the hypothesis was wrong).
- There are hacks you can put into place before-hand that will record the elapsed time of every command you run
- Conclusion
- 没有现成的方法可以为已经运行的命令计时
- 有多种方法可以推断命令运行时间的估计值。
- 显示了概念证明(从无法完成的假设开始,以假设错误的结论结束)。
- 您可以预先设置一些技巧来记录您运行的每个命令的经过时间
- 结论
The answer labeled by its parts according to the outline above:
根据上面的大纲由其部分标记的答案:
Part 1- the short answer is "no"
第 1 部分- 简短的回答是“不”
Original
原来的
Nope, sorry. You have to use time.
不,谢谢。你必须使用time.
Part 2- maybe you can deduce a result
第 2 部分- 也许你可以推断出一个结果
In some cases if a program writes output files or information in log files, you might be able to deduce running time, but that would be program-specific and only a guesstimate. If you have HISTTIMEFORMAT set in Bash, you can look at entries in the history file to get an idea of when a program started. But the ending time isn't logged, so you could only deduce a duration if another program was started immediately after the one you're interested in finished.
在某些情况下,如果程序在日志文件中写入输出文件或信息,您可能能够推断出运行时间,但这将是特定于程序的,并且只是一个猜测。如果您在 Bash 中设置了 HISTTIMEFORMAT,您可以查看历史文件中的条目以了解程序何时启动。但是不会记录结束时间,因此您只能在您感兴趣的程序完成后立即启动另一个程序的情况下推断持续时间。
Part 3- a hypothesis is falsified
第 3 部分- 假设被证伪
Hypothesis: Idle time will be counted in the elapsed time
假设:空闲时间将计入经过时间
Edit:
编辑:
Here is an example to illustrate my point. It's based on the suggestion by ZyX, but would be similar using other methods.
这里有一个例子来说明我的观点。它基于ZyX的建议,但使用其他方法也会类似。
In zsh:
在zsh:
% precmd() { prevstart=start; start=$SECONDS; }
% preexec() { prevend=$end; end=$SECONDS; }
% echo "T: $SECONDS ps: $prevstart pe: $prevend s: $start e: $end"
T: 1491 ps: 1456 pe: 1458 s: 1459 e: 1491
Now we wait... let's say for 15 seconds, then:
现在我们等待......让我们说 15 秒,然后:
% echo "T: $SECONDS"; sleep 10
T: 1506
Now we wait... let's say for 20 seconds, then:
现在我们等待......让我们说 20 秒,然后:
% echo "T: $SECONDS ps: $prevstart pe: $prevend s: $start e: $end"
T: 1536 ps: 1492 pe: 1506 s: 1516 e: 1536
As you can see, I was wrong. The start time (1516) minus the previousend time (1506) isthe duration of the command (sleep 10). Which also shows that the variables I used in the functions need better names.
如你所见,我错了。开始时间 (1516) 减去前一个结束时间 (1506)是命令 ( sleep 10)的持续时间。这也表明我在函数中使用的变量需要更好的名称。
Hypothesis falsified- it ispossible to get the correct elapsed time without including the idle time
假设伪造-这是可能得到正确经过时间不包括空闲时间
Part 4- a hack to record the elapsed time of everycommand
第 4 部分- 记录每个命令经过的时间的技巧
Edit 2:
编辑2:
Here are the Bash equivalents to the functions in ZyX'sanswer (they require the script linked to there):
以下是ZyX答案中函数的 Bash 等效项(它们需要链接到那里的脚本):
preexec () {
(( ${#_elapsed[@]} > 1000 )) && _elapsed=(${_elapsed[@]: -1000})
_start=$SECONDS
}
precmd () {
(( _start >= 0 )) && _elapsed+=($(( SECONDS-_start )))
_start=-1
}
After installing preexec.bash(from the linked script) and creating the two functions above, the example run would look like this:
安装preexec.bash(从链接脚本)并创建上面的两个函数后,示例运行将如下所示:
$ _elapsed=() # Clear the times
$ sleep 10s
$ sleep 2s ; echo ${_elapsed[@]: -1}
10
$ echo ${_elapsed[@]}
0 10 2
Part 5- conclusion
第 5 部分- 结论
Use time.
使用time.
回答by Att Righ
The world might have moved on a little since other people answered these questions.
自从其他人回答了这些问题后,世界可能会发生一些变化。
zshhas some built in features to time how long commands take.
zsh有一些内置功能来计算命令需要多长时间。
If you enable the inc_append_history_time option with
如果您启用 inc_append_history_time 选项
setopt inc_append_history_time
setopt inc_append_history_time
Then the time taken to run every command is saved in your history and then can be viewed with history -D.
然后运行每个命令所花费的时间会保存在您的历史记录中,然后可以使用history -D.
回答by Joseph Garvin
I take it you are running commands that take a long time and not realizing at the beginning that you would like to time how long they take to complete. In zsh if you set the environment variable REPORTTIME to a number, any command taking longer than that number of seconds will have the time it took printed as if you had run it with the time command in front of it. You can set it in your .zshrc so that long running commands will always have their time printed. Note that time spent sleeping (as opposed to user/system time) is not counted towards triggering the timer but is still tracked.
我认为您正在运行需要很长时间的命令,并且一开始没有意识到您想要计算它们需要多长时间才能完成。在 zsh 中,如果您将环境变量 REPORTTIME 设置为一个数字,则任何超过该秒数的命令都会打印它所花费的时间,就好像您在它前面运行了 time 命令一样。您可以在 .zshrc 中设置它,以便长时间运行的命令将始终打印其时间。请注意,睡眠时间(与用户/系统时间相反)不计入触发计时器,但仍会被跟踪。
回答by pau.estalella
I think you can only get timing statistics for commands you run using the command 'time'.
我认为您只能获取使用命令“time”运行的命令的计时统计信息。
From the man page:
从手册页:
time [options] command [arguments...]
DESCRIPTION The time command runs the specified program command with the given arguments. When command finishes, time writes a message to standard error giving timing statistics about this program run.
时间 [选项] 命令 [参数...]
描述 time 命令使用给定的参数运行指定的程序命令。命令完成后,time 会向标准错误写入一条消息,提供有关此程序运行的计时统计信息。
回答by spawn
I wrote a tool (discalimer!) which tracks the command-start- and stop-time, besides other command meta-data (e.g. cwd or modified files) by hiHymaning into a running shell-process (currently only bashis supported). In contrast to the other solutions posted here, it also correctly tracks the run-time of async commands, e.g. sleep 5 &.
Check it out here:
我编写了一个工具(discalimer!),它通过劫持到正在运行的 shell 进程(目前仅支持bash)来跟踪命令开始和停止时间,以及其他命令元数据(例如 cwd 或修改后的文件)。与此处发布的其他解决方案相比,它还可以正确跟踪异步命令的运行时间,例如sleep 5 &.
在这里查看:

