简体   繁体   中英

Python - Is it possible to “stop” or “pause” a thread

I have two threads, and, I want one thread to run for 10 seconds, and then have this thread stop, whilst another thread executes and then the first thread starts up again; this process is repeated. So eg

from threading import Thread 
import sys  
import time

class Worker(Thread):

    Listened = False; 

    def __init__(self):

        while 1:
           if(self.Listened == False):
              time.sleep(0)
           else:
            time.sleep(20)

        for x in range(0, 10):
            print "I'm working"
            self.Listened = True

    class Processor(Thread):
        Listened = False;

        def __init__(self):
            # this is where I'm confused!!

Worker().start()
Processer().start()

(PS I have indented correctly, however, SO seems to have messed it up a bit)

Basically, what I want is:

The worker thread works for 10 seconds (or so) and then stops, the "processor" starts up and, once the processor has processed the data from the last run of the "Worker" thread, it then re-starts the "worker" thread up. I don't specifically have to re-start the "worker" thread from that current position, it can start from the beginning.

Does anyone have any ideas?

You can use a counting semaphore to block a thread, and then wake-it-up later.

A counting semaphore is an object that has a non-negative integer count. If a thread calls acquire() on the semaphore when the count is 0, the thead will block until the semaphore's count becomes greater than zero. To unblock the thread, another thread must increase the count of the semaphore by calling release() on the semaphore.

Create two semaphores, one to block the worker, and one to block the processor. Start the worker semaphore's count a 1 since we want it to run right away. Start the processor's semaphore's count to 0 since we want it to block until the worker is done.

Pass the semaphores to the worker and processor classes. After the worker has run for 10 seconds, it should wake-up the processor by calling processorSemaphore.release() , then it should sleep on its semaphore by calling workerSemaphore.acquire() . The processor does the same.

#!/usr/bin/env python
from threading import Thread, Semaphore
import sys  
import time

INTERVAL = 10

class Worker(Thread):

    def __init__(self, workerSemaphore, processorSemaphore):
        super(Worker, self).__init__()
        self.workerSemaphore    = workerSemaphore
        self.processorSemaphore = processorSemaphore

    def run(self):
        while True:
            # wait for the processor to finish
            self.workerSemaphore.acquire()
            start = time.time()
            while True:
                if time.time() - start > INTERVAL:
                    # wake-up the processor
                    self.processorSemaphore.release()
                    break

                # do work here
                print "I'm working"

class Processor(Thread):
    def __init__(self, workerSemaphore, processorSemaphore):
        super(Processor, self).__init__()
        print "init P"
        self.workerSemaphore    = workerSemaphore
        self.processorSemaphore = processorSemaphore

    def run(self):
        print "running P"
        while True:
            # wait for the worker to finish
            self.processorSemaphore.acquire()
            start = time.time()
            while True:
                if time.time() - start > INTERVAL:
                    # wake-up the worker
                    self.workerSemaphore.release()
                    break

                # do processing here
                print "I'm processing"

workerSemaphore    = Semaphore(1)
processorSemaphore = Semaphore(0)

worker    = Worker(workerSemaphore, processorSemaphore)
processor = Processor(workerSemaphore, processorSemaphore)

worker.start()
processor.start()

worker.join()
processor.join()

See Alvaro's answer. But if you must really use threads then you can do something like below. However you can call start() on a Thread object only once. So either your data should preserve state as to where the next Worker thread should start from and you create a new worker thread in Processor every time or try to use a critical section so that the Worker and Processor threads can take turns to access it.

#!/usr/bin/env python
from threading import Thread 
import time

class Worker(Thread):

    def __init__(self):
        Thread.__init__(self)
        pass

    def run(self):
        for x in range(0, 10):
            print "I'm working"
            time.sleep(1)

class Processor(Thread):

    def __init__(self, w):
        Thread.__init__(self)
        self.worker = w

    def run(self):
            # process data from worker thread, add your logic here
            self.worker.start()

w = Worker()    
p = Processor(w)
p.start()

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM