Pausing the Main Thread in Python - python

I currently have a main function being run in Python on the main thread. This main function creates an additional thread called ArtificialPlayerControllerSynthesis to run a background process. I would like to pause the main thread for a second or two to allow the background process to finish before continuing in the main thread. However, all solutions to this issue that I can find, such as from Pausing a thread using threading class, require passing an event object as an argument to the thread I want to pause. This is not possible in my case, or would at the very least require restructuring my code and moving my main function to a new thread. Is it possible to simply pause the main thread? I am new to Python and threading, thanks in advance for yall's help.

thread = threading.Thread(target=some_func)
thread.start()
do_some_stuff_now()
thread.join() # blocks until thread finishes
do_some_stuff_later()

Related

What happens if I don't join() a python thread?

I have a query. I have seen examples where developers write something like the code as follows:
import threading
def do_something():
return true
t = threading.Thread(target=do_something)
t.start()
t.join()
I know that join() signals the interpreter to wait till the thread is completely executed. But what if I do not write t.join()? Will the thread get closed automatically and will it be reused later?
Please let me know the answer. It's my first attempt at creating a multi-threaded application in Python 3.5.0.
A Python thread is just a regular OS thread. If you don't join it, it still keeps running concurrently with the current thread. It will eventually die, when the target function completes or raises an exception. No such thing as "thread reuse" exists, once it's dead it rests in peace.
Unless the thread is a "daemon thread" (via a constructor argument daemon or assigning the daemon property) it will be implicitly joined for before the program exits, otherwise, it is killed abruptly.
One thing to remember when writing multithreading programs in Python, is that they only have limited use due to infamous Global interpreter lock. In short, using threads won't make your CPU-intensive program any faster. They can be useful only when you perform something involving waiting (e.g. you wait for certain file system event to happen in a thread).
The join part means the main program will wait for the thread to end before continuing. Without join, the main program will end and the thread will continue.
Now if you set the daemon parameter to "True", it means the thread will depends on the main program, and it will ends if the main program ends before.
Here is an example to understand better :
import threading
import time
def do_something():
time.sleep(2)
print("do_something")
return True
t = threading.Thread(target=do_something)
t.daemon = True # without the daemon parameter, the function in parallel will continue even your main program ends
t.start()
t.join() # with this, the main program will wait until the thread ends
print("end of main program")
no daemon, no join:
end of main program
do_something
daemon only:
end of main program
join only:
do_something
end of main program
daemon and join:
do_something
end of main program
# Note : in this case the daemon parameter is useless
Without join(), non-daemon threads are running and are completed with the main thread concurrently.
Without join(), daemon threads are running with the main thread concurrently and when the main thread is completed, the daemon threads are exited without completed if the daemon threads are still running.
You can see my answer in this post explaining about it in detail.

Killing a script while a function is active

I have a main thread and another thread which starts after threading.Timer(1,success).start() calls it.
In the defined function success I need to kill the whole python script, I tried sys.exit() but that only ends the thread. I can't signal the main thread as the reason the timer went off was because the main thread took too long to respond, so there's no guarantee the signal would be read by the main thread.
I considered using os.exit() which works, but it's messy as the script is reloaded after a second by another program and memory fills up.
You can join the created thread with a timeout:
join(timeout=None)
Thus, it will not wait for completion.

Is it possible to make the main function wait from a thread in Python?

This is a workaround program where I need to a logic like this:
Trigger a job in a normal function
Check if a certain directory is created in another Thread
Whenever this directory is created, pause the main thread, do some work in this thread and continue execution of the main thread.
Is there a way I can pause the main thread from another thread in Python?

How to keep the daemon threads alive after main thread exits?

I'm working on a python application, in which the main thread creates an object, say x, of a particular class.
Then it starts one thread which starts the execution in one of the methods of this object x. The method has a while True: loop, so its infinite.
Then it starts another thread which starts the execution in another method of the same object x. This method also has a while True: infinite loop.
I have made both the threads as daemon by calling t1.setDaemon(True), but it seems both stop execution once the main thread exits.
How do I keep the children alive after the parent thread is finished?
Or should I change my design to use a cron job or process fork?
The documentation says
A thread can be flagged as a "daemon thread". The significance of this flag is that the entire Python program exits when only daemon threads are left. The initial value is inherited from the creating thread. The flag can be set through the daemon property.
If you want to keep your program running, you must have at least one non daemon thread.

Do a callback from subclassed thread in main thread

I have a class that inherits from threading.Thread.
After processing an item from a queue I want it to call a function that I handed over to the thread when starting it. Doing that callback from the run-Method will have it run in my worker thread. Is there a way to run that callback inside the MainThread?
Thanks & Greetings,
Sean
You didnt mention intially that you are using pyqt. Qt has signals and slots built in just for this purpose. If you are launching your thread using QThread then it has the 'finished' signal that your main thread can be connected to on a slot. If you need even more control of the resulting signal you can emit a custom one from the thread with any value you want. When you construct the thread just connect its signal to the slot that you want to act as the callback.
Otherwise you would be blocking your main event loop if you are specifically waiting on the thread.
Here is a link specifically about the new style signal/slots: http://www.riverbankcomputing.co.uk/static/Docs/PyQt4/html/new_style_signals_slots.html
It makes it extremely easy now to create a python signal with whatever signature you want and connect it in an object oriented fashion to a slot.
Also as a side note about PyQt... Some of the other answers here have suggested creating a loop on your main thread that waits to collect responses in a queue from its dispatched threads. That is essentially what PyQt does. When you start your app the main thread goes into an event loop. This event loop is processing events that stack up in its event queue. There are different types of signal/slot connections. If your two endpoints are in the same thread, then a direct connection will be made and the emitting signal will call the slot. If they are in different threads, then I believe it goes through the event loop so that it can be processed outside of the emitters thread.
Push the method onto a queue and have the main thread sit and wait on that queue, running each method as it pulls them off.
You can use condition variables and have your main thread wait on a message from the sub-thread. The sub-thread can signal the main thread to call that method.

Categories