tags:

views:

905

answers:

4

I want to run a process in bash and save in an env variable the number of seconds it took to run. How would I do such a thing?

+6  A: 

Are you wanting to put this code in your script, or do it from the process that starts the script?

For the latter, you can use the "time" reserved word and then parse what it returns to get how much time a script takes.

If you want to do this from within a script you can set the variable SECONDS to zero, and each time thereafter that you reference that variable it will be updated to be the number of elapsed seconds. So, you can put "SECONDS=0" at the very start of your script, and whenever you need the elapsed time it will be in the SECONDS variable.

You can also use the $SECONDS trick on the command line as well, for example:

$ SECONDS=0; sleep 5 ; echo "that took approximately $SECONDS seconds"

The time reserved word and the SECONDS variable are both documented in the bash man page.

Bryan Oakley
bash is a never ending source of trick and surprises
flybywire
+2  A: 

This works in Bash, and also Zsh:

# Set time format to seconds
TIMEFORMAT=%R
# Time a process
PROC_TIME=$(time (insert command here >/dev/null 2>&1) 2>&1)
echo $PROC_TIME
  • The first two redirections hide your process's output ">/dev/null 2>&1"
  • The last redirect is needed because "time" prints the time on stderr
Farzy
A: 

Use the time command. Note that the bash version of time is not the same as /usr/bin/time. So you would have something like:

TIME=`/usr/bin/time --format="%e" your_command_here >/dev/null`

The format just pulls the "real" time value out. You would need to convert that from a string if you wanted to do anything more than display it.

If you just want to export the string, use export.

Oli
The variable `$TIME` is actually used by `/usr/bin/time` so it would be better to choose a different variable name. One way to avoid such collisions is to not use names that are all upper case for your own variables.
Dennis Williamson
A: 

Using GNU time,

\time -p -o time.log $COMMAND

and then read time.log.

(Use either \time or command time, otherwise you'll be using Bash's time built-in, which doesn't support these options.)

This will work even when $COMMAND prints to stderr (which would confuse Oli's answer), and keeps stdout/stderr (which Farzy's answer doesn't).

-o ... tells time to send its output to a file rather than to stderr (as is the default), and -p generates the traditional

real 0.00
user 0.00
sys 0.00

rather than GNU time's default of

0.00user 0.00system 0:00.01elapsed 8%CPU (0avgtext+0avgdata 0maxresident)k
80inputs+0outputs (1major+188minor)pagefaults 0swaps
ephemient