Search code examples
pythonmultiprocessing

How to call same process multiple times in a program


I am using python 2.7 multiprocessing module.I want to start a process and then terminate it and then start it again with new arguments.

p = Process(target=realwork, args=(up, down, middle, num))
def fun1():
    p.start()

def fun2():
    p.terminate()

And in the course of the program flow (through loops and events) I call the functions in this order:

fun1()
fun2()
fun1()
fun2()

If I try that i get an error saying I cannot call same process multiple times. Is there a workaround?


Solution

  • So - you probably had read somewhere that "using global variables is not a good practice" - and this is why. Your "p" variable only holds one "Process" instance, and it can only be started (and terminated) once.

    If you refactor your code so that "fun1" and "fun2" take the process upon which they act as a parameter, or maybe in an O.O. way, in which fun1 and fun2 are methods and the Process is an instance variable, you would not have any of these problems.

    In this case, O.O. is quick to see and straightforward to use:

    class MyClass(object):
        def __init__(self):
            self.p = Process(target=realwork,args=(up,down,middle,num))
        def fun1(self):
            self.p.start()
    
        def fun2(self):
            self.p.terminate()
    

    And then, wherever you need a pair of calls to "fun1" and "fun2", you do:

    action = Myclass()
    action.fun1()
    action.fun2() 
    

    instead. This would work even inside a for loop, or whatever.

    *edit - I just saw you are using this as answer to a button press in a Tkinter program, so, you have to record the Process instance somewhere between button clicks. Without having your code to refactor, and supposing you intend to persist on your global variable approach, you can simply create the Process instance inside "fun1" - this would work:

    def fun1():
        global p
        p = Process(target=realwork,args=(up,down,middle,num))
        p.start()
    
    def fun2():
        p.terminate()