wait for terminal command to finish in python
use communicate:
cmd = subprocess.Popen(command)
cmd.communicate()
# Code to be run after execution finished
Is there a way to not wait for a system() command to finish? (in c)
system()
simply passes its argument to the shell (on Unix-like systems, usually /bin/sh
).
Try this:
int a = system("python -m plotter &");
Of course the value returned by system()
won't be the exit status of the python script, since it won't have finished yet.This is likely to work only on Unix-like systems (probably including MacOS); in particular, it probably won't work on MS Windows, unless you're running under Cygwin.
On Windows, system()
probably invokes cmd.exe
, which doesn't accept commands with the same syntax used on Unix-like systems. But the Windows start
command should do the job:
int a = system("start python -m plotter");
As long as you're writing Windows-specific code (start
won't work on Unix unless you happen to have a start
command in your $PATH
), you might consider using some lower-level Windows feature, perhaps by calling StartProcess
. That's more complicated, but it's likely to give you more control over how the process executes. On the other hand, if system()
meets your requirements, you might as well use it. how to wait for first command to finish?
Shell scripts, no matter how they are executed, execute one command after the other. So your code will execute results.sh
after the last command of st_new.sh
has finished.
Now there is a special command which messes this up: &
cmd &
means: "Start a new background process and execute cmd
in it. After starting the background process, immediately continue with the next command in the script."That means &
doesn't wait for cmd
to do it's work. My guess is that st_new.sh
contains such a command. If that is the case, then you need to modify the script:
cmd &
BACK_PID=$!
This puts the process ID (PID) of the new background process in the variable BACK_PID
. You can then wait for it to end:while kill -0 $BACK_PID ; do
echo "Process is still active..."
sleep 1
# You can add a timeout here if you want
done
or, if you don't want any special handling/output simplywait $BACK_PID
Note that some programs automatically start a background process when you run them, even if you omit the &
. Check the documentation, they often have an option to write their PID to a file or you can run them in the foreground with an option and then use the shell's &
command instead to get the PID. How to wait for system() completion before advancing into next cycle
I found out what the problem was.
I saw here: https://askubuntu.com/questions/420981/how-do-i-save-terminal-output-to-a-file
that in order to save the stderr to file I needed to do &>output.txt
.
So I was doing "./foo 1 2 3 &>output.txt"
but that &
causes the system process to go into background.
+1 to @Random832 for guessing it (even though I never said I was using &>
-sorry guys, my bad ).
Btw, if you want the stderr to be exported to a file you can use 2>output.txt
How to wait in bash for several subprocesses to finish, and return exit code !=0 when any subprocess ends with code !=0?
wait
also (optionally) takes the PID
of the process to wait for, and with $!
you get the PID
of the last command launched in the background.
Modify the loop to store the PID
of each spawned sub-process into an array, and then loop again waiting on each PID
.
# run processes and store pids in array
for i in $n_procs; do
./procs[${i}] &
pids[${i}]=$!
done
# wait for all pids
for pid in ${pids[*]}; do
wait $pid
done
wait one process to finish and execute another process
You can achieve a simple way of process synchronization in bash
using wait
which waits for one or more number of background jobs to complete before running the next.
You generally run jobs in the background by appending the &
operator to the end of a command. At that point the PID
(process ID) of the newly created background process is stored in a special bash variable: $!
and wait
command allows this process to be terminate before running the next instruction.
This can be demonstrated by a simple example
$ cat mywaitscript.sh
#!/bin/bash
sleep 3 &
wait $! # Can also be stored in a variable as pid=$!
# Waits until the process 'sleep 3' is completed. Here the wait on a single process is done by capturing its process id
echo "I am waking up"
sleep 4 &
sleep 5 &
wait # Without specifying the id, just 'wait' waits until all jobs started on the background is complete.
echo "I woke up again"
Command ouput$ time ./mywaitscript.sh
I am waking up
I woke up again
real 0m8.012s
user 0m0.004s
sys 0m0.006s
You can see the script has taken ~8s to run to completion. The breakdown on the time issleep 3
will take full 3s to complete its executionsleep 4
andsleep 5
are both started sequentially one after next and it has taken the max(4,5) which is approximately ~5s to run.
Related Topics
Why Can't The Mail Block See My Variable
Sql Like Operator in Ruby on Rails
Strong Parameters with Nested Hash
Alias_Method on Activerecord::Base Results in Nameerror
Rails + Mongoid - Don't Return Nil Values in JSON
How to Make Http Delete Request in My Ruby Code Using Net::Http
Why Does Including This Module Not Override a Dynamically-Generated Method
How to Get Content from a Website Using Ruby/Rails
How to Test Helpers Blocks in Sinatra, Using Rspec
Ruby: Is It Acceptable to Put More Than One Class in a File
How to Write (Large) Files with Ruby Eventmachine
Is The Assignment Operator Really "Just" an Operator
How to Show Longer Traces in Rails Testcases
How to Declare a Two-Dimensional Array in Ruby